Add closingIssuesReferences JSON field to pr view (#10544)
* [gh pr view] Support `closingIssuesReferences` JSON field * Support pagination * Support pagination * Fix typo * Add more fields
This commit is contained in:
parent
e1387821af
commit
9ed733fa5e
6 changed files with 172 additions and 0 deletions
|
|
@ -139,6 +139,25 @@ func (pr *PullRequest) ExportData(fields []string) map[string]interface{} {
|
|||
}
|
||||
}
|
||||
data[f] = &requests
|
||||
case "closingIssuesReferences":
|
||||
items := make([]map[string]interface{}, 0, len(pr.ClosingIssuesReferences.Nodes))
|
||||
for _, n := range pr.ClosingIssuesReferences.Nodes {
|
||||
items = append(items, map[string]interface{}{
|
||||
|
||||
"id": n.ID,
|
||||
"number": n.Number,
|
||||
"url": n.URL,
|
||||
"repository": map[string]interface{}{
|
||||
"id": n.Repository.ID,
|
||||
"name": n.Repository.Name,
|
||||
"owner": map[string]interface{}{
|
||||
"id": n.Repository.Owner.ID,
|
||||
"login": n.Repository.Owner.Login,
|
||||
},
|
||||
},
|
||||
})
|
||||
}
|
||||
data[f] = items
|
||||
default:
|
||||
sf := fieldByName(v, f)
|
||||
data[f] = sf.Interface()
|
||||
|
|
|
|||
|
|
@ -245,6 +245,70 @@ func TestPullRequest_ExportData(t *testing.T) {
|
|||
}
|
||||
`),
|
||||
},
|
||||
{
|
||||
name: "linked issues",
|
||||
fields: []string{"closingIssuesReferences"},
|
||||
inputJSON: heredoc.Doc(`
|
||||
{ "closingIssuesReferences": { "nodes": [
|
||||
{
|
||||
"id": "I_123",
|
||||
"number": 123,
|
||||
"url": "https://github.com/cli/cli/issues/123",
|
||||
"repository": {
|
||||
"id": "R_123",
|
||||
"name": "cli",
|
||||
"owner": {
|
||||
"id": "O_123",
|
||||
"login": "cli"
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"id": "I_456",
|
||||
"number": 456,
|
||||
"url": "https://github.com/cli/cli/issues/456",
|
||||
"repository": {
|
||||
"id": "R_456",
|
||||
"name": "cli",
|
||||
"owner": {
|
||||
"id": "O_456",
|
||||
"login": "cli"
|
||||
}
|
||||
}
|
||||
}
|
||||
] } }
|
||||
`),
|
||||
outputJSON: heredoc.Doc(`
|
||||
{ "closingIssuesReferences": [
|
||||
{
|
||||
"id": "I_123",
|
||||
"number": 123,
|
||||
"repository": {
|
||||
"id": "R_123",
|
||||
"name": "cli",
|
||||
"owner": {
|
||||
"id": "O_123",
|
||||
"login": "cli"
|
||||
}
|
||||
},
|
||||
"url": "https://github.com/cli/cli/issues/123"
|
||||
},
|
||||
{
|
||||
"id": "I_456",
|
||||
"number": 456,
|
||||
"repository": {
|
||||
"id": "R_456",
|
||||
"name": "cli",
|
||||
"owner": {
|
||||
"id": "O_456",
|
||||
"login": "cli"
|
||||
}
|
||||
},
|
||||
"url": "https://github.com/cli/cli/issues/456"
|
||||
}
|
||||
] }
|
||||
`),
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
|
|
|
|||
|
|
@ -93,6 +93,8 @@ type PullRequest struct {
|
|||
Reviews PullRequestReviews
|
||||
LatestReviews PullRequestReviews
|
||||
ReviewRequests ReviewRequests
|
||||
|
||||
ClosingIssuesReferences ClosingIssuesReferences
|
||||
}
|
||||
|
||||
type StatusCheckRollupNode struct {
|
||||
|
|
@ -107,6 +109,26 @@ type CommitStatusCheckRollup struct {
|
|||
Contexts CheckContexts
|
||||
}
|
||||
|
||||
type ClosingIssuesReferences struct {
|
||||
Nodes []struct {
|
||||
ID string
|
||||
Number int
|
||||
URL string
|
||||
Repository struct {
|
||||
ID string
|
||||
Name string
|
||||
Owner struct {
|
||||
ID string
|
||||
Login string
|
||||
}
|
||||
}
|
||||
}
|
||||
PageInfo struct {
|
||||
HasNextPage bool
|
||||
EndCursor string
|
||||
}
|
||||
}
|
||||
|
||||
// https://docs.github.com/en/graphql/reference/enums#checkrunstate
|
||||
type CheckRunState string
|
||||
|
||||
|
|
|
|||
|
|
@ -132,6 +132,25 @@ var prCommits = shortenQuery(`
|
|||
}
|
||||
`)
|
||||
|
||||
var prClosingIssuesReferences = shortenQuery(`
|
||||
closingIssuesReferences(first: 100) {
|
||||
nodes {
|
||||
id,
|
||||
number,
|
||||
url,
|
||||
repository {
|
||||
id,
|
||||
name,
|
||||
owner {
|
||||
id,
|
||||
login
|
||||
}
|
||||
}
|
||||
}
|
||||
pageInfo{hasNextPage,endCursor}
|
||||
}
|
||||
`)
|
||||
|
||||
var autoMergeRequest = shortenQuery(`
|
||||
autoMergeRequest {
|
||||
authorEmail,
|
||||
|
|
@ -287,6 +306,7 @@ var PullRequestFields = append(sharedIssuePRFields,
|
|||
"baseRefName",
|
||||
"baseRefOid",
|
||||
"changedFiles",
|
||||
"closingIssuesReferences",
|
||||
"commits",
|
||||
"deletions",
|
||||
"files",
|
||||
|
|
@ -366,6 +386,8 @@ func IssueGraphQL(fields []string) string {
|
|||
q = append(q, StatusCheckRollupGraphQLWithoutCountByState(""))
|
||||
case "statusCheckRollupWithCountByState": // pseudo-field
|
||||
q = append(q, StatusCheckRollupGraphQLWithCountByState())
|
||||
case "closingIssuesReferences":
|
||||
q = append(q, prClosingIssuesReferences)
|
||||
default:
|
||||
q = append(q, field)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -239,6 +239,11 @@ func (f *finder) Find(opts FindOptions) (*api.PullRequest, ghrepo.Interface, err
|
|||
return preloadPrComments(httpClient, f.baseRefRepo, pr)
|
||||
})
|
||||
}
|
||||
if fields.Contains("closingIssuesReferences") {
|
||||
g.Go(func() error {
|
||||
return preloadPrClosingIssuesReferences(httpClient, f.baseRefRepo, pr)
|
||||
})
|
||||
}
|
||||
if fields.Contains("statusCheckRollup") {
|
||||
g.Go(func() error {
|
||||
return preloadPrChecks(httpClient, f.baseRefRepo, pr)
|
||||
|
|
@ -452,6 +457,45 @@ func preloadPrComments(client *http.Client, repo ghrepo.Interface, pr *api.PullR
|
|||
return nil
|
||||
}
|
||||
|
||||
func preloadPrClosingIssuesReferences(client *http.Client, repo ghrepo.Interface, pr *api.PullRequest) error {
|
||||
if !pr.ClosingIssuesReferences.PageInfo.HasNextPage {
|
||||
return nil
|
||||
}
|
||||
|
||||
type response struct {
|
||||
Node struct {
|
||||
PullRequest struct {
|
||||
ClosingIssuesReferences api.ClosingIssuesReferences `graphql:"closingIssuesReferences(first: 100, after: $endCursor)"`
|
||||
} `graphql:"...on PullRequest"`
|
||||
} `graphql:"node(id: $id)"`
|
||||
}
|
||||
|
||||
variables := map[string]interface{}{
|
||||
"id": githubv4.ID(pr.ID),
|
||||
"endCursor": githubv4.String(pr.ClosingIssuesReferences.PageInfo.EndCursor),
|
||||
}
|
||||
|
||||
gql := api.NewClientFromHTTP(client)
|
||||
|
||||
for {
|
||||
var query response
|
||||
err := gql.Query(repo.RepoHost(), "closingIssuesReferences", &query, variables)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
pr.ClosingIssuesReferences.Nodes = append(pr.ClosingIssuesReferences.Nodes, query.Node.PullRequest.ClosingIssuesReferences.Nodes...)
|
||||
|
||||
if !query.Node.PullRequest.ClosingIssuesReferences.PageInfo.HasNextPage {
|
||||
break
|
||||
}
|
||||
variables["endCursor"] = githubv4.String(query.Node.PullRequest.ClosingIssuesReferences.PageInfo.EndCursor)
|
||||
}
|
||||
|
||||
pr.ClosingIssuesReferences.PageInfo.HasNextPage = false
|
||||
return nil
|
||||
}
|
||||
|
||||
func preloadPrChecks(client *http.Client, repo ghrepo.Interface, pr *api.PullRequest) error {
|
||||
if len(pr.StatusCheckRollup.Nodes) == 0 {
|
||||
return nil
|
||||
|
|
|
|||
|
|
@ -37,6 +37,7 @@ func TestJSONFields(t *testing.T) {
|
|||
"changedFiles",
|
||||
"closed",
|
||||
"closedAt",
|
||||
"closingIssuesReferences",
|
||||
"comments",
|
||||
"commits",
|
||||
"createdAt",
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue