1. "${PSScriptRoot}\logging.ps1"
2
3$GithubAPIBaseURI = "https://api.github.com/repos"
4
5function Get-GitHubApiHeaders ($token) {
6 $headers = @{
7 Authorization = "bearer $token"
8 }
9 return $headers
10}
11
12function SplitParameterArray($members) {
13 if ($null -ne $members) {
14 if ($members -is [array])
15 {
16 return $members
17 }
18 else {
19 return (@($members.Split(",") | % { $_.Trim() } | ? { return $_ }))
20 }
21 }
22}
23
24function Set-GitHubAPIParameters ($members, $parameterName, $parameters, $allowEmptyMembers = $false) {
25 if ($null -ne $members) {
26 [array]$memberAdditions = SplitParameterArray -members $members
27
28 if ($null -eq $memberAdditions -and $allowEmptyMembers){ $memberAdditions = @() }
29
30 if ($memberAdditions.Count -gt 0 -or $allowEmptyMembers) {
31 $parameters[$parameterName] = $memberAdditions
32 }
33 }
34
35 return $parameters
36}
37
38function Get-GitHubPullRequests {
39 param (
40 $RepoOwner,
41 $RepoName,
42 $RepoId = "$RepoOwner/$RepoName",
43 [ValidateSet("open","closed","all")]
44 $State = "open",
45 $Head,
46 $Base,
47 [ValidateSet("created","updated","popularity","long-running")]
48 $Sort,
49 [ValidateSet("asc","desc")]
50 $Direction,
51 [Parameter(Mandatory = $true)]
52 [ValidateNotNullOrEmpty()]
53 $AuthToken
54 )
55 $uri = "$GithubAPIBaseURI/$RepoId/pulls"
56 if ($State -or $Head -or $Base -or $Sort -or $Direction) { $uri += '?' }
57 if ($State) { $uri += "state=$State&" }
58 if ($Head) { $uri += "head=$Head&" }
59 if ($Base) { $uri += "base=$Base&" }
60 if ($Sort) { $uri += "sort=$Sort&" }
61 if ($Direction){ $uri += "direction=$Direction&" }
62
63 return Invoke-RestMethod `
64 -Method GET `
65 -Uri $uri `
66 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
67 -MaximumRetryCount 3
68}
69
70#
71<#
72.PARAMETER Ref
73Ref to search for
74Pass 'heads/<branchame> ,tags/<tag name>, or nothing
75#>
76function Get-GitHubSourceReferences {
77 param (
78 $RepoOwner,
79 $RepoName,
80 $RepoId = "$RepoOwner/$RepoName",
81 $Ref,
82 [ValidateNotNullOrEmpty()]
83 [Parameter(Mandatory = $true)]
84 $AuthToken
85 )
86 $uri = "$GithubAPIBaseURI/$RepoId/git/matching-refs/"
87 if ($Ref) { $uri += "$Ref" }
88
89 return Invoke-RestMethod `
90 -Method GET `
91 -Uri $uri `
92 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
93 -MaximumRetryCount 3
94}
95
96function Get-GitHubPullRequest {
97 param (
98 $RepoOwner,
99 $RepoName,
100 $RepoId = "$RepoOwner/$RepoName",
101 [Parameter(Mandatory = $true)]
102 $PullRequestNumber,
103 [ValidateNotNullOrEmpty()]
104 [Parameter(Mandatory = $true)]
105 $AuthToken
106 )
107
108 $uri = "$GithubAPIBaseURI/$RepoId/pulls/$PullRequestNumber"
109
110 return Invoke-RestMethod `
111 -Method GET `
112 -Uri $uri `
113 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
114 -MaximumRetryCount 3
115}
116
117function New-GitHubPullRequest {
118 param (
119 $RepoOwner,
120 [Parameter(Mandatory = $true)]
121 $RepoName,
122 [Parameter(Mandatory = $true)]
123 $Title,
124 [Parameter(Mandatory = $true)]
125 $Head,
126 [Parameter(Mandatory = $true)]
127 $Base,
128 $Body=$Title,
129 [Boolean]$Maintainer_Can_Modify=$false,
130 [Boolean]$Draft=$false,
131 [ValidateNotNullOrEmpty()]
132 [Parameter(Mandatory = $true)]
133 $AuthToken
134 )
135
136 $parameters = @{
137 title = $Title
138 head = $Head
139 base = $Base
140 body = $Body
141 maintainer_can_modify = $Maintainer_Can_Modify
142 draft = $Draft
143 }
144
145 $uri = "$GithubAPIBaseURI/$RepoOwner/$RepoName/pulls"
146 return Invoke-RestMethod `
147 -Method POST `
148 -Body ($parameters | ConvertTo-Json) `
149 -Uri $uri `
150 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
151 -MaximumRetryCount 3
152}
153
154function Close-GitHubPullRequest {
155 param (
156 [Parameter(Mandatory = $true)]
157 $apiurl,
158 [ValidateNotNullOrEmpty()]
159 [Parameter(Mandatory = $true)]
160 $AuthToken
161 )
162
163 $parameters = @{
164 state = "closed"
165 }
166
167 return Invoke-RestMethod `
168 -Method PATCH `
169 -Uri $apiurl `
170 -Body ($parameters | ConvertTo-Json) `
171 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
172 -MaximumRetryCount 3
173}
174
175function New-GitHubIssue {
176 param (
177 [Parameter(Mandatory = $true)]
178 $RepoOwner,
179 [Parameter(Mandatory = $true)]
180 $RepoName,
181 [Parameter(Mandatory = $true)]
182 $Title,
183 [Parameter(Mandatory = $true)]
184 $Description,
185 [ValidateNotNullOrEmpty()]
186 [Parameter(Mandatory = $true)]
187 $AuthToken
188 )
189
190 $uri = "$GithubAPIBaseURI/$RepoOwner/$RepoName/issues"
191
192 $parameters = @{
193 title = $Title
194 body = $Description
195 }
196
197 return Invoke-RestMethod `
198 -Method POST `
199 -Body ($parameters | ConvertTo-Json) `
200 -Uri $uri `
201 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
202 -MaximumRetryCount 3
203}
204
205function Get-GitHubIssues {
206 param (
207 [Parameter(Mandatory = $true)]
208 $RepoOwner,
209 [Parameter(Mandatory = $true)]
210 $RepoName,
211 $CreatedBy,
212 [Parameter(Mandatory = $true)]
213 $Labels,
214 [ValidateNotNullOrEmpty()]
215 [Parameter(Mandatory = $true)]
216 $AuthToken
217 )
218
219 $uri = "$GithubAPIBaseURI/$RepoOwner/$RepoName/issues?labels=$Labels&per_page=100"
220
221 if ($CreatedBy) {
222 $uri += "&creator=$CreatedBy"
223 }
224
225 return Invoke-RestMethod `
226 -Method GET `
227 -Uri $uri `
228 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
229 -MaximumRetryCount 3
230}
231
232function Add-GitHubIssueComment {
233 param (
234 [Parameter(Mandatory = $true)]
235 $RepoOwner,
236 [Parameter(Mandatory = $true)]
237 $RepoName,
238 [Parameter(Mandatory = $true)]
239 $IssueNumber,
240 [Parameter(Mandatory = $true)]
241 $Comment,
242 [ValidateNotNullOrEmpty()]
243 [Parameter(Mandatory = $true)]
244 $AuthToken
245
246 )
247 $uri = "$GithubAPIBaseURI/$RepoOwner/$RepoName/issues/$IssueNumber/comments"
248
249 $parameters = @{
250 body = $Comment
251 }
252
253 return Invoke-RestMethod `
254 -Method POST `
255 -Body ($parameters | ConvertTo-Json) `
256 -Uri $uri `
257 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
258 -MaximumRetryCount 3
259}
260
261# Will add labels to existing labels on the issue
262function Add-GitHubIssueLabels {
263 param (
264 [Parameter(Mandatory = $true)]
265 $RepoOwner,
266 [Parameter(Mandatory = $true)]
267 $RepoName,
268 [Parameter(Mandatory = $true)]
269 $IssueNumber,
270 [ValidateNotNullOrEmpty()]
271 [Parameter(Mandatory = $true)]
272 $Labels,
273 [ValidateNotNullOrEmpty()]
274 [Parameter(Mandatory = $true)]
275 $AuthToken
276 )
277
278 if ($Labels.Trim().Length -eq 0)
279 {
280 throw " The 'Labels' parameter should not not be whitespace.
281 Use the 'Update-Issue' function if you plan to reset the labels"
282 }
283
284 $uri = "$GithubAPIBaseURI/$RepoOwner/$RepoName/issues/$IssueNumber/labels"
285 $parameters = @{}
286 $parameters = Set-GitHubAPIParameters -members $Labels -parameterName "labels" `
287 -parameters $parameters
288
289 return Invoke-RestMethod `
290 -Method POST `
291 -Body ($parameters | ConvertTo-Json) `
292 -Uri $uri `
293 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
294 -MaximumRetryCount 3
295}
296
297# Will add assignees to existing assignees on the issue
298function Add-GitHubIssueAssignees {
299 param (
300 [Parameter(Mandatory = $true)]
301 $RepoOwner,
302 [Parameter(Mandatory = $true)]
303 $RepoName,
304 [Parameter(Mandatory = $true)]
305 $IssueNumber,
306 [ValidateNotNullOrEmpty()]
307 [Parameter(Mandatory = $true)]
308 $Assignees,
309 [ValidateNotNullOrEmpty()]
310 [Parameter(Mandatory = $true)]
311 $AuthToken
312 )
313
314 if ($Assignees.Trim().Length -eq 0)
315 {
316 throw "The 'Assignees' parameter should not be whitespace.
317 You can use the 'Update-Issue' function if you plan to reset the Assignees"
318 }
319
320 $uri = "$GithubAPIBaseURI/$RepoOwner/$RepoName/issues/$IssueNumber/assignees"
321 $parameters = @{}
322 $parameters = Set-GitHubAPIParameters -members $Assignees -parameterName "assignees" `
323 -parameters $parameters
324
325 return Invoke-RestMethod `
326 -Method POST `
327 -Body ($parameters | ConvertTo-Json) `
328 -Uri $uri `
329 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
330 -MaximumRetryCount 3
331}
332
333function Add-GitHubPullRequestReviewers {
334 param (
335 [Parameter(Mandatory = $true)]
336 $RepoOwner,
337 [Parameter(Mandatory = $true)]
338 $RepoName,
339 [Parameter(Mandatory = $true)]
340 $PrNumber,
341 $Users,
342 $Teams,
343 [ValidateNotNullOrEmpty()]
344 [Parameter(Mandatory = $true)]
345 $AuthToken
346 )
347
348 $uri = "$GithubAPIBaseURI/$RepoOwner/$RepoName/pulls/$PrNumber/requested_reviewers"
349 $parameters = @{}
350
351 $parameters = Set-GitHubAPIParameters -members $Users -parameterName "reviewers" `
352 -parameters $parameters
353
354 $parameters = Set-GitHubAPIParameters -members $Teams -parameterName "team_reviewers" `
355 -parameters $parameters
356
357 return Invoke-RestMethod `
358 -Method POST `
359 -Body ($parameters | ConvertTo-Json) `
360 -Uri $uri `
361 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
362 -MaximumRetryCount 3
363}
364
365# For labels and assignee pass comma delimited string, to replace existing labels or assignees.
366# Or pass white space " " to remove all labels or assignees
367function Update-GitHubIssue {
368 param (
369 [Parameter(Mandatory = $true)]
370 $RepoOwner,
371 [Parameter(Mandatory = $true)]
372 $RepoName,
373 [Parameter(Mandatory = $true)]
374 $IssueNumber,
375 [string]$Title,
376 [string]$Body,
377 [ValidateSet("open","closed")]
378 [string]$State,
379 [int]$Milestome,
380 $Labels,
381 $Assignees,
382 [ValidateNotNullOrEmpty()]
383 [Parameter(Mandatory = $true)]
384 $AuthToken
385 )
386
387 $uri = "$GithubAPIBaseURI/$RepoOwner/$RepoName/issues/$IssueNumber"
388 $parameters = @{}
389 if ($Title) { $parameters["title"] = $Title }
390 if ($Body) { $parameters["body"] = $Body }
391 if ($State) { $parameters["state"] = $State }
392 if ($Milestone) { $parameters["milestone"] = $Milestone }
393
394 $parameters = Set-GitHubAPIParameters -members $Labels -parameterName "labels" `
395 -parameters $parameters -allowEmptyMembers $true
396
397 $parameters = Set-GitHubAPIParameters -members $Assignees -parameterName "assignees" `
398 -parameters $parameters -allowEmptyMembers $true
399
400 return Invoke-RestMethod `
401 -Method PATCH `
402 -Body ($parameters | ConvertTo-Json) `
403 -Uri $uri `
404 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
405 -MaximumRetryCount 3
406}
407
408function Remove-GitHubSourceReferences {
409 param (
410 $RepoOwner,
411 $RepoName,
412 $RepoId = "$RepoOwner/$RepoName",
413 [ValidateNotNullOrEmpty()]
414 [Parameter(Mandatory = $true)]
415 $Ref, # Using the format of "refs/heads/<branch>" or "heads/<branch>" for branch, and "tags/<tag>" for tag
416 [ValidateNotNullOrEmpty()]
417 [Parameter(Mandatory = $true)]
418 $AuthToken
419 )
420 if ($Ref.Trim().Length -eq 0)
421 {
422 throw "You must supply a valid 'Ref' Parameter to 'Delete-GithubSourceReferences'."
423 }
424 # Github is using branch in format of "heads/{branch_name}". Trim the "refs/heads/..." to "heads/..."
425 $Ref = $Ref -replace "refs/"
426 $uri = "$GithubAPIBaseURI/$RepoId/git/refs/$Ref"
427
428 return Invoke-RestMethod `
429 -Method DELETE `
430 -Uri $uri `
431 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
432 -MaximumRetryCount 3
433}
434
435
436function Get-GithubReferenceCommitDate($commitUrl, $AuthToken) {
437 $commitResponse = ""
438 if ($AuthToken)
439 {
440 $commitResponse = Invoke-RestMethod $commitUrl `
441 -Headers (Get-GitHubApiHeaders -token $AuthToken) `
442 -MaximumRetryCount 3
443 }
444 else
445 {
446 $commitResponse = Invoke-RestMethod $commitUrl -MaximumRetryCount 3
447 }
448 if (!$commitResponse.committer -or !$commitResponse.committer.date) {
449 LogDebug "No date returned from the commit sha. "
450 return $null
451 }
452 return $commitResponse.committer.date
453}
View as plain text