-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathqueries_issue.go
253 lines (219 loc) · 5.2 KB
/
queries_issue.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
package api
import (
"fmt"
"time"
"github.com/cli/cli/v2/internal/ghrepo"
)
type IssuesPayload struct {
Assigned IssuesAndTotalCount
Mentioned IssuesAndTotalCount
Authored IssuesAndTotalCount
}
type IssuesAndTotalCount struct {
Issues []Issue
TotalCount int
SearchCapped bool
}
type Issue struct {
Typename string `json:"__typename"`
ID string
Number int
Title string
URL string
State string
StateReason string
Closed bool
Body string
CreatedAt time.Time
UpdatedAt time.Time
ClosedAt *time.Time
Comments Comments
Author Author
Assignees Assignees
Labels Labels
ProjectCards ProjectCards
Milestone *Milestone
ReactionGroups ReactionGroups
IsPinned bool
}
func (i Issue) IsPullRequest() bool {
return i.Typename == "PullRequest"
}
type Assignees struct {
Nodes []GitHubUser
TotalCount int
}
func (a Assignees) Logins() []string {
logins := make([]string, len(a.Nodes))
for i, a := range a.Nodes {
logins[i] = a.Login
}
return logins
}
type Labels struct {
Nodes []IssueLabel
TotalCount int
}
func (l Labels) Names() []string {
names := make([]string, len(l.Nodes))
for i, l := range l.Nodes {
names[i] = l.Name
}
return names
}
type ProjectCards struct {
Nodes []*ProjectInfo
TotalCount int
}
type ProjectInfo struct {
Project struct {
Name string `json:"name"`
} `json:"project"`
Column struct {
Name string `json:"name"`
} `json:"column"`
}
func (p ProjectCards) ProjectNames() []string {
names := make([]string, len(p.Nodes))
for i, c := range p.Nodes {
names[i] = c.Project.Name
}
return names
}
type Milestone struct {
Number int `json:"number"`
Title string `json:"title"`
Description string `json:"description"`
DueOn *time.Time `json:"dueOn"`
}
type IssuesDisabledError struct {
error
}
type Owner struct {
ID string `json:"id,omitempty"`
Name string `json:"name,omitempty"`
Login string `json:"login"`
}
type Author struct {
ID string `json:"id,omitempty"`
Name string `json:"name,omitempty"`
Login string `json:"login"`
}
func (author *Author) IsBot() bool {
return author.ID == ""
}
// IssueCreate creates an issue in a GitHub repository
func IssueCreate(client *Client, repo *Repository, params map[string]interface{}) (*Issue, error) {
query := `
mutation IssueCreate($input: CreateIssueInput!) {
createIssue(input: $input) {
issue {
url
}
}
}`
inputParams := map[string]interface{}{
"repositoryId": repo.ID,
}
for key, val := range params {
inputParams[key] = val
}
variables := map[string]interface{}{
"input": inputParams,
}
result := struct {
CreateIssue struct {
Issue Issue
}
}{}
err := client.GraphQL(repo.RepoHost(), query, variables, &result)
if err != nil {
return nil, err
}
return &result.CreateIssue.Issue, nil
}
type IssueStatusOptions struct {
Username string
Fields []string
}
func IssueStatus(client *Client, repo ghrepo.Interface, options IssueStatusOptions) (*IssuesPayload, error) {
type response struct {
Repository struct {
Assigned struct {
TotalCount int
Nodes []Issue
}
Mentioned struct {
TotalCount int
Nodes []Issue
}
Authored struct {
TotalCount int
Nodes []Issue
}
HasIssuesEnabled bool
}
}
fragments := fmt.Sprintf("fragment issue on Issue{%s}", IssueGraphQL(options.Fields))
query := fragments + `
query IssueStatus($owner: String!, $repo: String!, $viewer: String!, $per_page: Int = 10) {
repository(owner: $owner, name: $repo) {
hasIssuesEnabled
assigned: issues(filterBy: {assignee: $viewer, states: OPEN}, first: $per_page, orderBy: {field: UPDATED_AT, direction: DESC}) {
totalCount
nodes {
...issue
}
}
mentioned: issues(filterBy: {mentioned: $viewer, states: OPEN}, first: $per_page, orderBy: {field: UPDATED_AT, direction: DESC}) {
totalCount
nodes {
...issue
}
}
authored: issues(filterBy: {createdBy: $viewer, states: OPEN}, first: $per_page, orderBy: {field: UPDATED_AT, direction: DESC}) {
totalCount
nodes {
...issue
}
}
}
}`
variables := map[string]interface{}{
"owner": repo.RepoOwner(),
"repo": repo.RepoName(),
"viewer": options.Username,
}
var resp response
err := client.GraphQL(repo.RepoHost(), query, variables, &resp)
if err != nil {
return nil, err
}
if !resp.Repository.HasIssuesEnabled {
return nil, fmt.Errorf("the '%s' repository has disabled issues", ghrepo.FullName(repo))
}
payload := IssuesPayload{
Assigned: IssuesAndTotalCount{
Issues: resp.Repository.Assigned.Nodes,
TotalCount: resp.Repository.Assigned.TotalCount,
},
Mentioned: IssuesAndTotalCount{
Issues: resp.Repository.Mentioned.Nodes,
TotalCount: resp.Repository.Mentioned.TotalCount,
},
Authored: IssuesAndTotalCount{
Issues: resp.Repository.Authored.Nodes,
TotalCount: resp.Repository.Authored.TotalCount,
},
}
return &payload, nil
}
func (i Issue) Link() string {
return i.URL
}
func (i Issue) Identifier() string {
return i.ID
}
func (i Issue) CurrentUserComments() []Comment {
return i.Comments.CurrentUserComments()
}