Functions/Invoke-PaginatedGitHubApiRoute.ps1
Function Invoke-PaginatedGitHubApiRoute { Param( [string] $Path, [hashtable] $Query = [hashtable]::new(), [string] $Method = "GET", [string] $Body, [string] $Token = "$(gh auth token)", [int] $PageSize = 50, [string] $ArrayProperty, [scriptblock] $StopCondition ) $Global:CachedEtags = @{} $Global:CachedLastModified = @{} # if no page is specified, start at 1 if(-not $Page) { $Page = 1 } $Query["page"] = $Page $Query["per_page"] = $PageSize $items = @() do{ # Add page and page size to query $responseHeaders= [hashtable]::new() # Invoke the API $data = Invoke-GitHubApiRoute -Path $Path -Query $Query -Method $Method -Body $Body -Token $Token -ResponseHeaders ([ref]$responseHeaders) if($ArrayProperty){ $data = $data.$ArrayProperty } else{ $data = @($data) } # Add the data to the items array $items += $data # Return if no data if($data.Count -lt $PageSize) { return $items } # Increment the page $Page = $Page + 1 if($StopCondition){ if(&$StopCondition -Items $data -Result $data){ return $items } } # Link header $link = $responseHeaders."Link" # link: <https://api.github.com/repositories/1300192/issues?page=2>; rel="prev", <https://api.github.com/repositories/1300192/issues?page=4>; rel="next", <https://api.github.com/repositories/1300192/issues?page=515>; rel="last", <https://api.github.com/repositories/1300192/issues?page=1>; rel="first" # Pull out path, query for the next link $nextLink = @($link -split "," | Where-Object { $_ -match 'rel="next"' } | ForEach-Object { $_ -replace ".*<([^>]+)>.*", '$1' }) if(-not $nextLink){ return $items } $nextLink = $nextLink[0] # Pull out path, query for the last link $Path = $nextLink -replace "https://api.github.com/", '' $Path = $Path -replace "\?.*", '' $query_s = $nextLink -replace ".*\?(.*)$", '$1' $query_s -split "&" | ForEach-Object { $split = $_ -split "=" @{ key = $split[0] value = $split[1] } } | ForEach-Object { $Query[$_.key] = $_.value } Write-Host "Getting next page: $Path, Query: $($Query | ConvertTo-Json -Compress)" }while($true) } |