GitHub.psm1
#region - From private/common.ps1 $script:APIBaseURI = 'https://api.github.com' $script:Owner = '' $script:Repo = '' $script:Token = '' #endregion - From private/common.ps1 #region - From private/Initialize-SecretVault.ps1 #Requires -Version 7.0 #Requires -Modules Microsoft.PowerShell.SecretManagement, Microsoft.PowerShell.SecretStore function Initialize-SecretVault { [CmdletBinding()] param ( [Parameter()] [string] $Name = 'SecretStore', [Parameter()] [Alias('ModuleName')] [string] $Type = 'Microsoft.PowerShell.SecretStore' ) $secretVault = Get-SecretVault | Where-Object { $_.ModuleName -eq $Type } $secretVaultExists = $secretVault.count -ne 0 Write-Verbose "$Name exists: $secretVaultExists" if (-not $secretVaultExists) { Write-Verbose "Registering [$Name]" $vaultParameters = @{ Authentication = 'None' PasswordTimeout = -1 Interaction = 'None' Scope = 'CurrentUser' WarningAction = 'SilentlyContinue' Confirm = $false Force = $true } Reset-SecretStore @vaultParameters $secretVault = @{ Name = $Name ModuleName = $Type DefaultVault = $true Description = 'SecretStore' } Register-SecretVault @secretVault } Get-SecretStoreConfiguration } #endregion - From private/Initialize-SecretVault.ps1 #region - From public/Connect-GitHubAccount.ps1 <# .SYNOPSIS Short description .DESCRIPTION Long description .PARAMETER Owner Parameter description .PARAMETER Repo Parameter description .PARAMETER Token Parameter description .PARAMETER APIBaseURI Parameter description .EXAMPLE An example .NOTES https://docs.github.com/en/rest/overview/other-authentication-methods#authenticating-for-saml-sso #> function Connect-GitHubAccount { [CmdletBinding()] param ( [Parameter()] [String] $Owner, [Parameter()] [String] $Repo, [Parameter(Mandatory)] [String] $Token, [Parameter()] [String] $APIBaseURI = 'https://api.github.com' ) $script:APIBaseURI = $APIBaseURI $script:Owner = $Owner $script:Repo = $Repo $script:Token = $Token Get-GitHubContext } #endregion - From public/Connect-GitHubAccount.ps1 #region - From public/Disable-GitHubWorkflow.ps1 <# .SYNOPSIS Short description .DESCRIPTION Long description .PARAMETER Owner Parameter description .PARAMETER Repo Parameter description .PARAMETER Token Parameter description .PARAMETER ID Parameter description .EXAMPLE An example .NOTES https://docs.github.com/en/rest/reference/actions#disable-a-workflow #> Function Disable-GitHubWorkflow { [CmdletBinding()] param ( [Parameter()] [string] $Owner = $script:Owner, [Parameter()] [string] $Repo = $script:Repo, [Parameter()] [string] $Token = $script:Token, [Parameter( Mandatory, ValueFromPipelineByPropertyName )] [string[]] $ID ) begin {} process { $InputObject = @{ Owner = $Owner Repo = $Repo Token = $Token Method = 'PUT' APIEndpoint = "repos/$Owner/$Repo/actions/workflows/$ID/disable" } $Response = Invoke-GitHubAPI @InputObject } end { return $Response } } #endregion - From public/Disable-GitHubWorkflow.ps1 #region - From public/Enable-GitHubWorkflow.ps1 Function Enable-GitHubWorkflow { [CmdletBinding()] param ( [Parameter()] [string] $Owner = $script:Owner, [Parameter()] [string] $Repo = $script:Repo, [Parameter()] [string] $Token = $script:Token, [Parameter( Mandatory, ValueFromPipelineByPropertyName )] [string[]] $ID ) begin {} process { # API Reference # https://docs.github.com/en/rest/reference/actions#enable-a-workflow $APICall = @{ Uri = "$APIBaseURI/repos/$Owner/$Repo/actions/workflows/$ID/enable" Headers = @{ Authorization = "token $Token" 'Content-Type' = 'application/json' } Method = 'PUT' Body = @{} | ConvertTo-Json -Depth 100 } try { if ($PSBoundParameters.ContainsKey('Verbose')) { $APICall } $Response = Invoke-RestMethod @APICall } catch { throw $_ } return $Response } end {} } #endregion - From public/Enable-GitHubWorkflow.ps1 #region - From public/Get-GitHubContext.ps1 <# .SYNOPSIS Get the authenticated user .DESCRIPTION If the authenticated user is authenticated through basic authentication or OAuth with the user scope, then the response lists public and private profile information. If the authenticated user is authenticated through OAuth without the user scope, then the response lists only public profile information. .PARAMETER Token Parameter description .EXAMPLE An example .NOTES https://docs.github.com/en/rest/reference/users#get-the-authenticated-user #> function Get-GitHubContext { [CmdletBinding()] param ( [Parameter()] [string] $Token = $script:Token ) $InputObject = @{ Owner = $Owner Repo = $Repo Token = $Token Method = 'GET' APIEndpoint = 'user' } $Response = Invoke-GitHubAPI @InputObject return $Response } New-Alias -Name Get-GitHubUser -Value Get-GitHubContext -Force #endregion - From public/Get-GitHubContext.ps1 #region - From public/Get-GitHubEmojis.ps1 <# .SYNOPSIS Short description .DESCRIPTION Long description .PARAMETER Token Parameter description .EXAMPLE An example .NOTES https://docs.github.com/en/rest/reference/emojis#get-emojis #> function Get-GitHubEmojis { [CmdletBinding()] param ( $Destination ) $Response = Invoke-GitHubAPI -Method Get -APIEndpoint emojis if (Test-Path -Path $Destination) { $Response.PSobject.Properties | ForEach-Object -Parallel { Invoke-WebRequest -Uri $_.Value -OutFile "$using:Destination/$($_.Name).png" } } return $Response } #endregion - From public/Get-GitHubEmojis.ps1 #region - From public/Get-GitHubEnvironment.ps1 function Get-GitHubEnvironment { [CmdletBinding()] param ( $Owner = $script:Owner, $Repo = $script:Repo, $Token = $script:Token ) begin {} process { # API Reference # https://docs.github.com/en/rest/reference/repos#get-all-environments $APICall = @{ Uri = "$APIBaseURI/repos/$Owner/$Repo/environments" Headers = @{ Authorization = "token $Token" 'Content-Type' = 'application/json' } Method = 'GET' Body = @{} | ConvertTo-Json -Depth 100 } try { if ($PSBoundParameters.ContainsKey('Verbose')) { $APICall } $Response = Invoke-RestMethod @APICall } catch { throw $_ } return $Response.Environments } end {} } #endregion - From public/Get-GitHubEnvironment.ps1 #region - From public/Get-GitHubEnvironmentSecrets.ps1 function Get-GitHubEnvironmentSecrets { [CmdletBinding()] param ( $Owner = $script:Owner, $Repo = $script:Repo, $Token = $script:Token , [Alias('name')] [Parameter( Mandatory, ValueFromPipelineByPropertyName )] [string] $EnvironmentName ) begin {} process { $RepoID = (Get-GitHubRepo).id #/repositories/{repository_id}/environments/{environment_name}/secrets/{secret_name} #/repositories/{repository_id}/environments/{environment_name}/secrets # API Reference # https://docs.github.com/en/rest/reference/repos#get-all-environments $APICall = @{ Uri = "$APIBaseURI/repositories/$RepoID/environments/$EnvironmentName/secrets" Headers = @{ Authorization = "token $Token" 'Content-Type' = 'application/json' } Method = 'GET' Body = @{} | ConvertTo-Json -Depth 100 } try { if ($PSBoundParameters.ContainsKey('Verbose')) { $APICall } $Response = Invoke-RestMethod @APICall } catch { throw $_ } return $Response.secrets } end {} } #endregion - From public/Get-GitHubEnvironmentSecrets.ps1 #region - From public/Get-GitHubRepoBranch.ps1 function Get-GitHubRepoBranch { [CmdletBinding()] param ( [Parameter()] [string] $Owner = $script:Owner, [Parameter()] [string] $Repo = $script:Repo, [Parameter()] [string] $Token = $script:Token ) $InputObject = @{ Owner = $Owner Repo = $Repo Token = $Token Method = 'Get' APIEndpoint = "repos/$Owner/$Repo/branches" } $Response = Invoke-GitHubAPI @InputObject return $Response } #endregion - From public/Get-GitHubRepoBranch.ps1 #region - From public/Get-GitHubRepoTeams.ps1 <# .SYNOPSIS Short description .DESCRIPTION Long description .PARAMETER Owner Parameter description .PARAMETER Repo Parameter description .PARAMETER Token Parameter description .EXAMPLE An example .NOTES https://docs.github.com/en/rest/reference/repos#get-a-repository #> function Get-GitHubRepoTeams { [CmdletBinding()] param ( [Parameter()] [string] $Owner = $script:Owner, [Parameter()] [string] $Repo = $script:Repo, [Parameter()] [string] $Token = $script:Token ) $InputObject = @{ Owner = $Owner Repo = $Repo Token = $Token Method = 'Get' APIEndpoint = "repos/$Owner/$Repo/teams" } $Response = Invoke-GitHubAPI @InputObject return $Response } #endregion - From public/Get-GitHubRepoTeams.ps1 #region - From public/Get-GitHubRoot.ps1 <# .SYNOPSIS Short description .DESCRIPTION Long description .PARAMETER Token Parameter description .EXAMPLE An example .NOTES https://docs.github.com/en/rest/reference/meta#github-api-root #> function Get-GitHubRoot { [CmdletBinding()] param ( $Token = $script:Token ) Invoke-GitHubAPI -Token $Token return $Response } #endregion - From public/Get-GitHubRoot.ps1 #region - From public/Get-GitHubWorkflow.ps1 <# .SYNOPSIS Short description .DESCRIPTION Long description .PARAMETER Owner Parameter description .PARAMETER Repo Parameter description .PARAMETER Token Parameter description .PARAMETER Name Parameter description .PARAMETER ID Parameter description .PARAMETER PageSize Parameter description .EXAMPLE An example .NOTES https://docs.github.com/en/rest/reference/actions#list-repository-workflows #> Function Get-GitHubWorkflow { [CmdletBinding(DefaultParameterSetName = 'ByName')] param ( [Parameter()] [string] $Owner = $script:Owner, [Parameter()] [string] $Repo = $script:Repo, [Parameter()] [string] $Token = $script:Token, [Parameter(ParameterSetName = 'ByName')] [string] $Name, [Parameter(ParameterSetName = 'ByID')] [string] $ID, [Parameter()] [int] $PageSize = 30 ) $processedPages = 0 $workflows = @() do { $processedPages += 1 $Response = Invoke-GitHubAPI -Method GET -APIEndpoint "repos/$Owner/$Repo/actions/workflows?per_page=$PageSize&page=$processedPages" $workflows += $Response.workflows | Where-Object name -Match $name | Where-Object id -Match $id } while ($workflows.count -ne $Response.total_count) return $workflows } #endregion - From public/Get-GitHubWorkflow.ps1 #region - From public/Get-GitHubWorkflowRun.ps1 Function Get-GitHubWorkflowRun { [CmdletBinding()] param ( $Owner = $script:Owner, $Repo = $script:Repo, $Token = $script:Token , $Name, $ID ) $Results = @() $i = 0 # API Reference # https://docs.github.com/en/rest/reference/actions#list-workflow-runs-for-a-repository do { $i++ $APICall = @{ Uri = "$APIBaseURI/repos/$Owner/$Repo/actions/runs?per_page=100&page=$i" Headers = @{ Authorization = "token $Token" 'Content-Type' = 'application/json' } Method = 'GET' Body = @{} | ConvertTo-Json -Depth 100 } try { if ($PSBoundParameters.ContainsKey('Verbose')) { $APICall } $Response = Invoke-RestMethod @APICall } catch { throw $_ } $WorkflowRuns = $Response.workflow_runs $Results += $WorkflowRuns } while ($WorkflowRuns.count -eq 100) return $Results | Where-Object Name -Match $Name | Where-Object workflow_id -Match $ID } #endregion - From public/Get-GitHubWorkflowRun.ps1 #region - From public/Get-GitHubWorkflowUsage.ps1 Function Get-GitHubWorkflowUsage { [CmdletBinding( DefaultParameterSetName = 'ByName' )] param ( $Owner = $script:Owner, $Repo = $script:Repo, $Token = $script:Token , [Parameter( Mandatory, ValueFromPipelineByPropertyName )] [string[]] $ID ) begin {} process { # API Reference # https://docs.github.com/en/rest/reference/actions#get-workflow-usage $APICall = @{ Uri = "$APIBaseURI/repos/$Owner/$Repo/actions/workflows/$ID/timing" Headers = @{ Authorization = "token $Token" 'Content-Type' = 'application/json' } Method = 'GET' Body = @{} | ConvertTo-Json -Depth 100 } try { if ($PSBoundParameters.ContainsKey('Verbose')) { $APICall } $Response = Invoke-RestMethod @APICall } catch { throw $_ } return $Response.billable } end {} } #endregion - From public/Get-GitHubWorkflowUsage.ps1 #region - From public/Invoke-GitHubAPI.ps1 function Invoke-GitHubAPI { [CmdletBinding()] param ( [Parameter()] [ValidateSet('GET', 'POST', 'PATCH', 'DELETE')] [String] $Method = 'GET', [Parameter()] [string] $APIEndpoint, [Parameter()] [hashtable] $Body = @{}, [Parameter()] [string] $Owner = $script:Owner, [Parameter()] [string] $Repo = $script:Repo, [Parameter()] [string] $Token = $script:Token ) $APICall = @{ Uri = ("$script:APIBaseURI/$APIEndpoint").Replace('\', '/').Replace('//', '/') Headers = @{ Authorization = "token $Token" 'Content-Type' = 'application/vnd.github.v3+json' #'application/json' } Method = $Method Body = $Body | ConvertTo-Json -Depth 100 } try { $Response = Invoke-RestMethod @APICall } catch { throw $_ } return $Response } #endregion - From public/Invoke-GitHubAPI.ps1 #region - From public/Remove-GitHubWorkflowRun.ps1 function Remove-GitHubWorkflowRun { [CmdletBinding()] param ( [Parameter()] [string] $Owner = $script:Owner, [Parameter()] [string] $Repo = $script:Repo, [Parameter()] [string] $Token = $script:Token, [Parameter( Mandatory, ValueFromPipelineByPropertyName )] [string] $ID ) begin {} process { # API Reference # https://docs.github.com/en/rest/reference/actions#delete-a-workflow-run $APICall = @{ Uri = "$APIBaseURI/repos/$Owner/$Repo/actions/runs/$ID" Headers = @{ Authorization = "token $Token" 'Content-Type' = 'application/json' } Method = 'DELETE' Body = @{} | ConvertTo-Json -Depth 100 } try { if ($PSBoundParameters.ContainsKey('Verbose')) { $APICall } $Response = Invoke-RestMethod @APICall } catch { throw $_ } return $Response } end {} } #endregion - From public/Remove-GitHubWorkflowRun.ps1 #region - From public/Start-GitHubWorkflow.ps1 <# .SYNOPSIS # .DESCRIPTION Long description .PARAMETER Owner Parameter description .PARAMETER Repo Parameter description .PARAMETER Token Parameter description .PARAMETER ID Parameter description .PARAMETER Ref Parameter description .PARAMETER Inputs Parameter description .EXAMPLE Get-GitHubWorkflow | Where-Object name -NotLike '.*' | Start-GitHubWorkflow -Inputs @{ staticValidation = $true deploymentValidation = $false removeDeployment = $true prerelease = $false } .NOTES General notes #> function Start-GitHubWorkflow { [CmdletBinding()] param ( $Owner = $script:Owner, $Repo = $script:Repo, $Token = $script:Token , [Alias('workflow_id')] [Parameter( Mandatory, ValueFromPipelineByPropertyName )] [string] $ID, [Parameter( ValueFromPipelineByPropertyName )] [Alias('branch', 'tag')] [string] $Ref = 'main', [Parameter()] [hashtable] $Inputs = @{} ) begin {} process { # API Reference # https://docs.github.com/en/free-pro-team@latest/rest/actions/workflows?apiVersion=2022-11-28#create-a-workflow-dispatch-event $APICall = @{ Uri = "$APIBaseURI/repos/$Owner/$Repo/actions/workflows/$ID/dispatches" Headers = @{ Authorization = "token $Token" 'Content-Type' = 'application/json' } Method = 'POST' Body = @{ ref = $Ref inputs = $Inputs } | ConvertTo-Json -Depth 100 } try { if ($PSBoundParameters.ContainsKey('Verbose')) { $APICall } $Response = Invoke-RestMethod @APICall } catch { throw $_ } return $Response } end {} } #endregion - From public/Start-GitHubWorkflow.ps1 #region - From public/Start-GitHubWorkflowReRun.ps1 function Start-GitHubWorkflowReRun { [CmdletBinding()] param ( $Owner = $script:Owner, $Repo = $script:Repo, $Token = $script:Token , [Alias('workflow_id')] [Parameter( Mandatory, ValueFromPipelineByPropertyName )] [string] $ID ) begin {} process { # API Reference # https://docs.github.com/en/rest/reference/actions#re-run-a-workflow $APICall = @{ Uri = "$APIBaseURI/repos/$Owner/$Repo/actions/runs/$ID/rerun" Headers = @{ Authorization = "token $Token" 'Content-Type' = 'application/json' } Method = 'POST' Body = @{} | ConvertTo-Json -Depth 100 } try { if ($PSBoundParameters.ContainsKey('Verbose')) { $APICall } $Response = Invoke-RestMethod @APICall } catch { throw $_ } return $Response } end {} } #endregion - From public/Start-GitHubWorkflowReRun.ps1 #region - From public/Stop-GitHubWorkflowRun.ps1 function Stop-GitHubWorkflowRun { [CmdletBinding()] [alias('Cancel-GitHubWorkflowRun')] param ( $Owner = $script:Owner, $Repo = $script:Repo, $Token = $script:Token , [Alias('workflow_id')] [Parameter( Mandatory, ValueFromPipelineByPropertyName )] [string] $ID ) begin {} process { # API Reference # https://docs.github.com/en/rest/reference/actions#cancel-a-workflow-run $APICall = @{ Uri = "$APIBaseURI/repos/$Owner/$Repo/actions/runs/$ID/cancel" Headers = @{ Authorization = "token $Token" 'Content-Type' = 'application/json' } Method = 'POST' Body = @{} | ConvertTo-Json -Depth 100 } try { if ($PSBoundParameters.ContainsKey('Verbose')) { $APICall } $Response = Invoke-RestMethod @APICall } catch { throw $_ } return $Response } end {} } #endregion - From public/Stop-GitHubWorkflowRun.ps1 #region - From public/Update-GitHubEnvironment.ps1 function Update-GitHubEnvironment { [CmdletBinding()] param ( $Owner = $script:Owner, $Repo = $script:Repo, $Token = $script:Token , [Alias('environment_name')] [Parameter( Mandatory, ValueFromPipelineByPropertyName )] [string] $Name ) begin {} process { # API Reference # https://docs.github.com/en/rest/reference/repos#create-or-update-an-environment $APICall = @{ Uri = "$APIBaseURI/repos/$Owner/$Repo/environments/$Name" Headers = @{ Authorization = "token $Token" 'Content-Type' = 'application/json' } Method = 'PUT' Body = @{ owner = $Owner repo = $Repo environment_name = $Name } | ConvertTo-Json -Depth 100 } try { if ($PSBoundParameters.ContainsKey('Verbose')) { $APICall } $Response = Invoke-RestMethod @APICall } catch { throw $_ } $Response } end {} } #endregion - From public/Update-GitHubEnvironment.ps1 Export-ModuleMember -Function 'Connect-GitHubAccount','Disable-GitHubWorkflow','Enable-GitHubWorkflow','Get-GitHubContext','Get-GitHubEmojis','Get-GitHubEnvironment','Get-GitHubEnvironmentSecrets','Get-GitHubRepoBranch','Get-GitHubRepoTeams','Get-GitHubRoot','Get-GitHubWorkflow','Get-GitHubWorkflowRun','Get-GitHubWorkflowUsage','Invoke-GitHubAPI','Remove-GitHubWorkflowRun','Start-GitHubWorkflow','Start-GitHubWorkflowReRun','Stop-GitHubWorkflowRun','Update-GitHubEnvironment' -Cmdlet '*' -Variable '*' -Alias '*' |