diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index c5856f6..9515999 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -19,8 +19,6 @@ jobs: - run: npm run build - run: npm run format-check - run: npm run lint - - run: npm run pack - - run: npm run gendocs - run: npm test - name: Verify no unstaged changes run: __test__/verify-no-unstaged-changes.sh @@ -37,7 +35,7 @@ jobs: uses: actions/checkout@v2 # Basic checkout - - name: Basic checkout + - name: Checkout basic uses: ./ with: ref: test-data/v2/basic @@ -50,7 +48,7 @@ jobs: - name: Modify work tree shell: bash run: __test__/modify-work-tree.sh - - name: Clean checkout + - name: Checkout clean uses: ./ with: ref: test-data/v2/basic @@ -60,12 +58,12 @@ jobs: run: __test__/verify-clean.sh # Side by side - - name: Side by side checkout 1 + - name: Checkout side by side 1 uses: ./ with: ref: test-data/v2/side-by-side-1 path: side-by-side-1 - - name: Side by side checkout 2 + - name: Checkout side by side 2 uses: ./ with: ref: test-data/v2/side-by-side-2 @@ -75,7 +73,7 @@ jobs: run: __test__/verify-side-by-side.sh # LFS - - name: LFS checkout + - name: Checkout LFS uses: ./ with: repository: actions/checkout # hardcoded, otherwise doesn't work from a fork @@ -86,6 +84,35 @@ jobs: shell: bash run: __test__/verify-lfs.sh + # Submodules false + - name: Checkout submodules false + uses: ./ + with: + ref: test-data/v2/submodule-ssh-url + path: submodules-false + - name: Verify submodules false + run: __test__/verify-submodules-false.sh + + # Submodules one level + - name: Checkout submodules true + uses: ./ + with: + ref: test-data/v2/submodule-ssh-url + path: submodules-true + submodules: true + - name: Verify submodules true + run: __test__/verify-submodules-true.sh + + # Submodules recursive + - name: Checkout submodules recursive + uses: ./ + with: + ref: test-data/v2/submodule-ssh-url + path: submodules-recursive + submodules: recursive + - name: Verify submodules recursive + run: __test__/verify-submodules-recursive.sh + # Basic checkout using REST API - name: Remove basic if: runner.os != 'windows' @@ -100,7 +127,7 @@ jobs: - name: Override git version (Windows) if: runner.os == 'windows' run: __test__\\override-git-version.cmd - - name: Basic checkout using REST API + - name: Checkout basic using REST API uses: ./ with: ref: test-data/v2/basic @@ -126,7 +153,7 @@ jobs: uses: actions/checkout@v2 # Basic checkout using git - - name: Basic checkout + - name: Checkout basic uses: ./ with: ref: test-data/v2/basic @@ -158,7 +185,7 @@ jobs: uses: actions/checkout@v2 # Basic checkout using git - - name: Basic checkout + - name: Checkout basic uses: ./ with: ref: test-data/v2/basic @@ -171,7 +198,7 @@ jobs: # Basic checkout using REST API - name: Override git version run: __test__/override-git-version.sh - - name: Basic checkout using REST API + - name: Checkout basic using REST API uses: ./ with: ref: test-data/v2/basic diff --git a/.gitignore b/.gitignore index 46f1072..2f909c0 100644 --- a/.gitignore +++ b/.gitignore @@ -1,2 +1,3 @@ +__test__/_temp lib/ node_modules/ \ No newline at end of file diff --git a/CHANGELOG.md b/CHANGELOG.md index 7546e84..6f40def 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,40 @@ # Changelog +## v2.3.1 + +- [Fix default branch resolution for .wiki and when using SSH](https://github.com/actions/checkout/pull/284) + + +## v2.3.0 + +- [Fallback to the default branch](https://github.com/actions/checkout/pull/278) + +## v2.2.0 + +- [Fetch all history for all tags and branches when fetch-depth=0](https://github.com/actions/checkout/pull/258) + +## v2.1.1 + +- Changes to support GHES ([here](https://github.com/actions/checkout/pull/236) and [here](https://github.com/actions/checkout/pull/248)) + +## v2.1.0 + +- [Group output](https://github.com/actions/checkout/pull/191) +- [Changes to support GHES alpha release](https://github.com/actions/checkout/pull/199) +- [Persist core.sshCommand for submodules](https://github.com/actions/checkout/pull/184) +- [Add support ssh](https://github.com/actions/checkout/pull/163) +- [Convert submodule SSH URL to HTTPS, when not using SSH](https://github.com/actions/checkout/pull/179) +- [Add submodule support](https://github.com/actions/checkout/pull/157) +- [Follow proxy settings](https://github.com/actions/checkout/pull/144) +- [Fix ref for pr closed event when a pr is merged](https://github.com/actions/checkout/pull/141) +- [Fix issue checking detached when git less than 2.22](https://github.com/actions/checkout/pull/128) + +## v2.0.0 + +- [Do not pass cred on command line](https://github.com/actions/checkout/pull/108) +- [Add input persist-credentials](https://github.com/actions/checkout/pull/107) +- [Fallback to REST API to download repo](https://github.com/actions/checkout/pull/104) + ## v2 (beta) - Improved fetch performance diff --git a/README.md b/README.md index 120d351..ab6642a 100644 --- a/README.md +++ b/README.md @@ -6,7 +6,7 @@ This action checks-out your repository under `$GITHUB_WORKSPACE`, so your workflow can access it. -Only a single commit is fetched by default, for the ref/SHA that triggered the workflow. Set `fetch-depth` to fetch more history. Refer [here](https://help.github.com/en/articles/events-that-trigger-workflows) to learn which commit `$GITHUB_SHA` points to for different events. +Only a single commit is fetched by default, for the ref/SHA that triggered the workflow. Set `fetch-depth: 0` to fetch all history for all branches and tags. Refer [here](https://help.github.com/en/articles/events-that-trigger-workflows) to learn which commit `$GITHUB_SHA` points to for different events. The auth token is persisted in the local git config. This enables your scripts to run authenticated git commands. The token is removed during post-job cleanup. Set `persist-credentials: false` to opt-out. @@ -18,6 +18,7 @@ When Git 2.18 or higher is not in your PATH, falls back to the REST API to downl - Fetches only a single commit by default - Script authenticated git commands - Auth token persisted in the local git config +- Supports SSH - Creates a local branch - No longer detached HEAD when checking out a branch - Improved layout @@ -26,7 +27,6 @@ When Git 2.18 or higher is not in your PATH, falls back to the REST API to downl - Fallback to REST API download - When Git 2.18 or higher is not in the PATH, the REST API will be used to download the files - When using a job container, the container's PATH is used -- Removed input `submodules` Refer [here](https://github.com/actions/checkout/blob/v1/README.md) for previous versions. @@ -42,17 +42,43 @@ Refer [here](https://github.com/actions/checkout/blob/v1/README.md) for previous # The branch, tag or SHA to checkout. When checking out the repository that # triggered a workflow, this defaults to the reference or SHA for that event. - # Otherwise, defaults to `master`. + # Otherwise, uses the default branch. ref: '' - # Auth token used to fetch the repository. The token is stored in the local git - # config, which enables your scripts to run authenticated git commands. The - # post-job step removes the token from the git config. [Learn more about creating - # and using encrypted secrets](https://help.github.com/en/actions/automating-your-workflow-with-github-actions/creating-and-using-encrypted-secrets) + # Personal access token (PAT) used to fetch the repository. The PAT is configured + # with the local git config, which enables your scripts to run authenticated git + # commands. The post-job step removes the PAT. + # + # We recommend using a service account with the least permissions necessary. Also + # when generating a new PAT, select the least scopes necessary. + # + # [Learn more about creating and using encrypted secrets](https://help.github.com/en/actions/automating-your-workflow-with-github-actions/creating-and-using-encrypted-secrets) + # # Default: ${{ github.token }} token: '' - # Whether to persist the token in the git config + # SSH key used to fetch the repository. The SSH key is configured with the local + # git config, which enables your scripts to run authenticated git commands. The + # post-job step removes the SSH key. + # + # We recommend using a service account with the least permissions necessary. + # + # [Learn more about creating and using encrypted secrets](https://help.github.com/en/actions/automating-your-workflow-with-github-actions/creating-and-using-encrypted-secrets) + ssh-key: '' + + # Known hosts in addition to the user and global host key database. The public SSH + # keys for a host may be obtained using the utility `ssh-keyscan`. For example, + # `ssh-keyscan github.com`. The public key for github.com is always implicitly + # added. + ssh-known-hosts: '' + + # Whether to perform strict host key checking. When true, adds the options + # `StrictHostKeyChecking=yes` and `CheckHostIP=no` to the SSH command line. Use + # the input `ssh-known-hosts` to configure additional hosts. + # Default: true + ssh-strict: '' + + # Whether to configure the token or SSH key with the local git config # Default: true persist-credentials: '' @@ -63,18 +89,28 @@ Refer [here](https://github.com/actions/checkout/blob/v1/README.md) for previous # Default: true clean: '' - # Number of commits to fetch. 0 indicates all history. + # Number of commits to fetch. 0 indicates all history for all branches and tags. # Default: 1 fetch-depth: '' # Whether to download Git-LFS files # Default: false lfs: '' + + # Whether to checkout submodules: `true` to checkout submodules or `recursive` to + # recursively checkout submodules. + # + # When the `ssh-key` input is not provided, SSH URLs beginning with + # `git@github.com:` are converted to HTTPS. + # + # Default: false + submodules: '' ``` # Scenarios +- [Fetch all history for all tags and branches](#Fetch-all-history-for-all-tags-and-branches) - [Checkout a different branch](#Checkout-a-different-branch) - [Checkout HEAD^](#Checkout-HEAD) - [Checkout multiple repos (side by side)](#Checkout-multiple-repos-side-by-side) @@ -82,10 +118,14 @@ Refer [here](https://github.com/actions/checkout/blob/v1/README.md) for previous - [Checkout multiple repos (private)](#Checkout-multiple-repos-private) - [Checkout pull request HEAD commit instead of merge commit](#Checkout-pull-request-HEAD-commit-instead-of-merge-commit) - [Checkout pull request on closed event](#Checkout-pull-request-on-closed-event) -- [Checkout submodules](#Checkout-submodules) -- [Fetch all tags](#Fetch-all-tags) -- [Fetch all branches](#Fetch-all-branches) -- [Fetch all history for all tags and branches](#Fetch-all-history-for-all-tags-and-branches) + +## Fetch all history for all tags and branches + +```yaml +- uses: actions/checkout@v2 + with: + fetch-depth: 0 +``` ## Checkout a different branch diff --git a/__test__/git-auth-helper.test.ts b/__test__/git-auth-helper.test.ts new file mode 100644 index 0000000..e4e640c --- /dev/null +++ b/__test__/git-auth-helper.test.ts @@ -0,0 +1,802 @@ +import * as core from '@actions/core' +import * as fs from 'fs' +import * as gitAuthHelper from '../lib/git-auth-helper' +import * as io from '@actions/io' +import * as os from 'os' +import * as path from 'path' +import * as stateHelper from '../lib/state-helper' +import {IGitCommandManager} from '../lib/git-command-manager' +import {IGitSourceSettings} from '../lib/git-source-settings' + +const isWindows = process.platform === 'win32' +const testWorkspace = path.join(__dirname, '_temp', 'git-auth-helper') +const originalRunnerTemp = process.env['RUNNER_TEMP'] +const originalHome = process.env['HOME'] +let workspace: string +let localGitConfigPath: string +let globalGitConfigPath: string +let runnerTemp: string +let tempHomedir: string +let git: IGitCommandManager & {env: {[key: string]: string}} +let settings: IGitSourceSettings +let sshPath: string + +describe('git-auth-helper tests', () => { + beforeAll(async () => { + // SSH + sshPath = await io.which('ssh') + + // Clear test workspace + await io.rmRF(testWorkspace) + }) + + beforeEach(() => { + // Mock setSecret + jest.spyOn(core, 'setSecret').mockImplementation((secret: string) => {}) + + // Mock error/warning/info/debug + jest.spyOn(core, 'error').mockImplementation(jest.fn()) + jest.spyOn(core, 'warning').mockImplementation(jest.fn()) + jest.spyOn(core, 'info').mockImplementation(jest.fn()) + jest.spyOn(core, 'debug').mockImplementation(jest.fn()) + + // Mock state helper + jest.spyOn(stateHelper, 'setSshKeyPath').mockImplementation(jest.fn()) + jest + .spyOn(stateHelper, 'setSshKnownHostsPath') + .mockImplementation(jest.fn()) + }) + + afterEach(() => { + // Unregister mocks + jest.restoreAllMocks() + + // Restore HOME + if (originalHome) { + process.env['HOME'] = originalHome + } else { + delete process.env['HOME'] + } + }) + + afterAll(() => { + // Restore RUNNER_TEMP + delete process.env['RUNNER_TEMP'] + if (originalRunnerTemp) { + process.env['RUNNER_TEMP'] = originalRunnerTemp + } + }) + + const configureAuth_configuresAuthHeader = + 'configureAuth configures auth header' + it(configureAuth_configuresAuthHeader, async () => { + // Arrange + await setup(configureAuth_configuresAuthHeader) + expect(settings.authToken).toBeTruthy() // sanity check + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + + // Act + await authHelper.configureAuth() + + // Assert config + const configContent = ( + await fs.promises.readFile(localGitConfigPath) + ).toString() + const basicCredential = Buffer.from( + `x-access-token:${settings.authToken}`, + 'utf8' + ).toString('base64') + expect( + configContent.indexOf( + `http.https://github.com/.extraheader AUTHORIZATION: basic ${basicCredential}` + ) + ).toBeGreaterThanOrEqual(0) + }) + + const configureAuth_configuresAuthHeaderEvenWhenPersistCredentialsFalse = + 'configureAuth configures auth header even when persist credentials false' + it( + configureAuth_configuresAuthHeaderEvenWhenPersistCredentialsFalse, + async () => { + // Arrange + await setup( + configureAuth_configuresAuthHeaderEvenWhenPersistCredentialsFalse + ) + expect(settings.authToken).toBeTruthy() // sanity check + settings.persistCredentials = false + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + + // Act + await authHelper.configureAuth() + + // Assert config + const configContent = ( + await fs.promises.readFile(localGitConfigPath) + ).toString() + expect( + configContent.indexOf( + `http.https://github.com/.extraheader AUTHORIZATION` + ) + ).toBeGreaterThanOrEqual(0) + } + ) + + const configureAuth_copiesUserKnownHosts = + 'configureAuth copies user known hosts' + it(configureAuth_copiesUserKnownHosts, async () => { + if (!sshPath) { + process.stdout.write( + `Skipped test "${configureAuth_copiesUserKnownHosts}". Executable 'ssh' not found in the PATH.\n` + ) + return + } + + // Arange + await setup(configureAuth_copiesUserKnownHosts) + expect(settings.sshKey).toBeTruthy() // sanity check + + // Mock fs.promises.readFile + const realReadFile = fs.promises.readFile + jest.spyOn(fs.promises, 'readFile').mockImplementation( + async (file: any, options: any): Promise => { + const userKnownHostsPath = path.join( + os.homedir(), + '.ssh', + 'known_hosts' + ) + if (file === userKnownHostsPath) { + return Buffer.from('some-domain.com ssh-rsa ABCDEF') + } + + return await realReadFile(file, options) + } + ) + + // Act + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + await authHelper.configureAuth() + + // Assert known hosts + const actualSshKnownHostsPath = await getActualSshKnownHostsPath() + const actualSshKnownHostsContent = ( + await fs.promises.readFile(actualSshKnownHostsPath) + ).toString() + expect(actualSshKnownHostsContent).toMatch( + /some-domain\.com ssh-rsa ABCDEF/ + ) + expect(actualSshKnownHostsContent).toMatch(/github\.com ssh-rsa AAAAB3N/) + }) + + const configureAuth_registersBasicCredentialAsSecret = + 'configureAuth registers basic credential as secret' + it(configureAuth_registersBasicCredentialAsSecret, async () => { + // Arrange + await setup(configureAuth_registersBasicCredentialAsSecret) + expect(settings.authToken).toBeTruthy() // sanity check + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + + // Act + await authHelper.configureAuth() + + // Assert secret + const setSecretSpy = core.setSecret as jest.Mock + expect(setSecretSpy).toHaveBeenCalledTimes(1) + const expectedSecret = Buffer.from( + `x-access-token:${settings.authToken}`, + 'utf8' + ).toString('base64') + expect(setSecretSpy).toHaveBeenCalledWith(expectedSecret) + }) + + const setsSshCommandEnvVarWhenPersistCredentialsFalse = + 'sets SSH command env var when persist-credentials false' + it(setsSshCommandEnvVarWhenPersistCredentialsFalse, async () => { + if (!sshPath) { + process.stdout.write( + `Skipped test "${setsSshCommandEnvVarWhenPersistCredentialsFalse}". Executable 'ssh' not found in the PATH.\n` + ) + return + } + + // Arrange + await setup(setsSshCommandEnvVarWhenPersistCredentialsFalse) + settings.persistCredentials = false + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + + // Act + await authHelper.configureAuth() + + // Assert git env var + const actualKeyPath = await getActualSshKeyPath() + const actualKnownHostsPath = await getActualSshKnownHostsPath() + const expectedSshCommand = `"${sshPath}" -i "$RUNNER_TEMP/${path.basename( + actualKeyPath + )}" -o StrictHostKeyChecking=yes -o CheckHostIP=no -o "UserKnownHostsFile=$RUNNER_TEMP/${path.basename( + actualKnownHostsPath + )}"` + expect(git.setEnvironmentVariable).toHaveBeenCalledWith( + 'GIT_SSH_COMMAND', + expectedSshCommand + ) + + // Asserty git config + const gitConfigLines = (await fs.promises.readFile(localGitConfigPath)) + .toString() + .split('\n') + .filter(x => x) + expect(gitConfigLines).toHaveLength(1) + expect(gitConfigLines[0]).toMatch(/^http\./) + }) + + const configureAuth_setsSshCommandWhenPersistCredentialsTrue = + 'sets SSH command when persist-credentials true' + it(configureAuth_setsSshCommandWhenPersistCredentialsTrue, async () => { + if (!sshPath) { + process.stdout.write( + `Skipped test "${configureAuth_setsSshCommandWhenPersistCredentialsTrue}". Executable 'ssh' not found in the PATH.\n` + ) + return + } + + // Arrange + await setup(configureAuth_setsSshCommandWhenPersistCredentialsTrue) + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + + // Act + await authHelper.configureAuth() + + // Assert git env var + const actualKeyPath = await getActualSshKeyPath() + const actualKnownHostsPath = await getActualSshKnownHostsPath() + const expectedSshCommand = `"${sshPath}" -i "$RUNNER_TEMP/${path.basename( + actualKeyPath + )}" -o StrictHostKeyChecking=yes -o CheckHostIP=no -o "UserKnownHostsFile=$RUNNER_TEMP/${path.basename( + actualKnownHostsPath + )}"` + expect(git.setEnvironmentVariable).toHaveBeenCalledWith( + 'GIT_SSH_COMMAND', + expectedSshCommand + ) + + // Asserty git config + expect(git.config).toHaveBeenCalledWith( + 'core.sshCommand', + expectedSshCommand + ) + }) + + const configureAuth_writesExplicitKnownHosts = 'writes explicit known hosts' + it(configureAuth_writesExplicitKnownHosts, async () => { + if (!sshPath) { + process.stdout.write( + `Skipped test "${configureAuth_writesExplicitKnownHosts}". Executable 'ssh' not found in the PATH.\n` + ) + return + } + + // Arrange + await setup(configureAuth_writesExplicitKnownHosts) + expect(settings.sshKey).toBeTruthy() // sanity check + settings.sshKnownHosts = 'my-custom-host.com ssh-rsa ABC123' + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + + // Act + await authHelper.configureAuth() + + // Assert known hosts + const actualSshKnownHostsPath = await getActualSshKnownHostsPath() + const actualSshKnownHostsContent = ( + await fs.promises.readFile(actualSshKnownHostsPath) + ).toString() + expect(actualSshKnownHostsContent).toMatch( + /my-custom-host\.com ssh-rsa ABC123/ + ) + expect(actualSshKnownHostsContent).toMatch(/github\.com ssh-rsa AAAAB3N/) + }) + + const configureAuth_writesSshKeyAndImplicitKnownHosts = + 'writes SSH key and implicit known hosts' + it(configureAuth_writesSshKeyAndImplicitKnownHosts, async () => { + if (!sshPath) { + process.stdout.write( + `Skipped test "${configureAuth_writesSshKeyAndImplicitKnownHosts}". Executable 'ssh' not found in the PATH.\n` + ) + return + } + + // Arrange + await setup(configureAuth_writesSshKeyAndImplicitKnownHosts) + expect(settings.sshKey).toBeTruthy() // sanity check + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + + // Act + await authHelper.configureAuth() + + // Assert SSH key + const actualSshKeyPath = await getActualSshKeyPath() + expect(actualSshKeyPath).toBeTruthy() + const actualSshKeyContent = ( + await fs.promises.readFile(actualSshKeyPath) + ).toString() + expect(actualSshKeyContent).toBe(settings.sshKey + '\n') + if (!isWindows) { + // Assert read/write for user, not group or others. + // Otherwise SSH client will error. + expect((await fs.promises.stat(actualSshKeyPath)).mode & 0o777).toBe( + 0o600 + ) + } + + // Assert known hosts + const actualSshKnownHostsPath = await getActualSshKnownHostsPath() + const actualSshKnownHostsContent = ( + await fs.promises.readFile(actualSshKnownHostsPath) + ).toString() + expect(actualSshKnownHostsContent).toMatch(/github\.com ssh-rsa AAAAB3N/) + }) + + const configureGlobalAuth_configuresUrlInsteadOfWhenSshKeyNotSet = + 'configureGlobalAuth configures URL insteadOf when SSH key not set' + it(configureGlobalAuth_configuresUrlInsteadOfWhenSshKeyNotSet, async () => { + // Arrange + await setup(configureGlobalAuth_configuresUrlInsteadOfWhenSshKeyNotSet) + settings.sshKey = '' + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + + // Act + await authHelper.configureAuth() + await authHelper.configureGlobalAuth() + + // Assert temporary global config + expect(git.env['HOME']).toBeTruthy() + const configContent = ( + await fs.promises.readFile(path.join(git.env['HOME'], '.gitconfig')) + ).toString() + expect( + configContent.indexOf(`url.https://github.com/.insteadOf git@github.com`) + ).toBeGreaterThanOrEqual(0) + }) + + const configureGlobalAuth_copiesGlobalGitConfig = + 'configureGlobalAuth copies global git config' + it(configureGlobalAuth_copiesGlobalGitConfig, async () => { + // Arrange + await setup(configureGlobalAuth_copiesGlobalGitConfig) + await fs.promises.writeFile(globalGitConfigPath, 'value-from-global-config') + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + + // Act + await authHelper.configureAuth() + await authHelper.configureGlobalAuth() + + // Assert original global config not altered + let configContent = ( + await fs.promises.readFile(globalGitConfigPath) + ).toString() + expect(configContent).toBe('value-from-global-config') + + // Assert temporary global config + expect(git.env['HOME']).toBeTruthy() + const basicCredential = Buffer.from( + `x-access-token:${settings.authToken}`, + 'utf8' + ).toString('base64') + configContent = ( + await fs.promises.readFile(path.join(git.env['HOME'], '.gitconfig')) + ).toString() + expect( + configContent.indexOf('value-from-global-config') + ).toBeGreaterThanOrEqual(0) + expect( + configContent.indexOf( + `http.https://github.com/.extraheader AUTHORIZATION: basic ${basicCredential}` + ) + ).toBeGreaterThanOrEqual(0) + }) + + const configureGlobalAuth_createsNewGlobalGitConfigWhenGlobalDoesNotExist = + 'configureGlobalAuth creates new git config when global does not exist' + it( + configureGlobalAuth_createsNewGlobalGitConfigWhenGlobalDoesNotExist, + async () => { + // Arrange + await setup( + configureGlobalAuth_createsNewGlobalGitConfigWhenGlobalDoesNotExist + ) + await io.rmRF(globalGitConfigPath) + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + + // Act + await authHelper.configureAuth() + await authHelper.configureGlobalAuth() + + // Assert original global config not recreated + try { + await fs.promises.stat(globalGitConfigPath) + throw new Error( + `Did not expect file to exist: '${globalGitConfigPath}'` + ) + } catch (err) { + if (err.code !== 'ENOENT') { + throw err + } + } + + // Assert temporary global config + expect(git.env['HOME']).toBeTruthy() + const basicCredential = Buffer.from( + `x-access-token:${settings.authToken}`, + 'utf8' + ).toString('base64') + const configContent = ( + await fs.promises.readFile(path.join(git.env['HOME'], '.gitconfig')) + ).toString() + expect( + configContent.indexOf( + `http.https://github.com/.extraheader AUTHORIZATION: basic ${basicCredential}` + ) + ).toBeGreaterThanOrEqual(0) + } + ) + + const configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsFalseAndSshKeyNotSet = + 'configureSubmoduleAuth configures submodules when persist credentials false and SSH key not set' + it( + configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsFalseAndSshKeyNotSet, + async () => { + // Arrange + await setup( + configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsFalseAndSshKeyNotSet + ) + settings.persistCredentials = false + settings.sshKey = '' + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + await authHelper.configureAuth() + const mockSubmoduleForeach = git.submoduleForeach as jest.Mock + mockSubmoduleForeach.mockClear() // reset calls + + // Act + await authHelper.configureSubmoduleAuth() + + // Assert + expect(mockSubmoduleForeach).toBeCalledTimes(1) + expect(mockSubmoduleForeach.mock.calls[0][0] as string).toMatch( + /unset-all.*insteadOf/ + ) + } + ) + + const configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsFalseAndSshKeySet = + 'configureSubmoduleAuth configures submodules when persist credentials false and SSH key set' + it( + configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsFalseAndSshKeySet, + async () => { + if (!sshPath) { + process.stdout.write( + `Skipped test "${configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsFalseAndSshKeySet}". Executable 'ssh' not found in the PATH.\n` + ) + return + } + + // Arrange + await setup( + configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsFalseAndSshKeySet + ) + settings.persistCredentials = false + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + await authHelper.configureAuth() + const mockSubmoduleForeach = git.submoduleForeach as jest.Mock + mockSubmoduleForeach.mockClear() // reset calls + + // Act + await authHelper.configureSubmoduleAuth() + + // Assert + expect(mockSubmoduleForeach).toHaveBeenCalledTimes(1) + expect(mockSubmoduleForeach.mock.calls[0][0]).toMatch( + /unset-all.*insteadOf/ + ) + } + ) + + const configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsTrueAndSshKeyNotSet = + 'configureSubmoduleAuth configures submodules when persist credentials true and SSH key not set' + it( + configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsTrueAndSshKeyNotSet, + async () => { + // Arrange + await setup( + configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsTrueAndSshKeyNotSet + ) + settings.sshKey = '' + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + await authHelper.configureAuth() + const mockSubmoduleForeach = git.submoduleForeach as jest.Mock + mockSubmoduleForeach.mockClear() // reset calls + + // Act + await authHelper.configureSubmoduleAuth() + + // Assert + expect(mockSubmoduleForeach).toHaveBeenCalledTimes(3) + expect(mockSubmoduleForeach.mock.calls[0][0]).toMatch( + /unset-all.*insteadOf/ + ) + expect(mockSubmoduleForeach.mock.calls[1][0]).toMatch(/http.*extraheader/) + expect(mockSubmoduleForeach.mock.calls[2][0]).toMatch(/url.*insteadOf/) + } + ) + + const configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsTrueAndSshKeySet = + 'configureSubmoduleAuth configures submodules when persist credentials true and SSH key set' + it( + configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsTrueAndSshKeySet, + async () => { + if (!sshPath) { + process.stdout.write( + `Skipped test "${configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsTrueAndSshKeySet}". Executable 'ssh' not found in the PATH.\n` + ) + return + } + + // Arrange + await setup( + configureSubmoduleAuth_configuresSubmodulesWhenPersistCredentialsTrueAndSshKeySet + ) + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + await authHelper.configureAuth() + const mockSubmoduleForeach = git.submoduleForeach as jest.Mock + mockSubmoduleForeach.mockClear() // reset calls + + // Act + await authHelper.configureSubmoduleAuth() + + // Assert + expect(mockSubmoduleForeach).toHaveBeenCalledTimes(3) + expect(mockSubmoduleForeach.mock.calls[0][0]).toMatch( + /unset-all.*insteadOf/ + ) + expect(mockSubmoduleForeach.mock.calls[1][0]).toMatch(/http.*extraheader/) + expect(mockSubmoduleForeach.mock.calls[2][0]).toMatch(/core\.sshCommand/) + } + ) + + const removeAuth_removesSshCommand = 'removeAuth removes SSH command' + it(removeAuth_removesSshCommand, async () => { + if (!sshPath) { + process.stdout.write( + `Skipped test "${removeAuth_removesSshCommand}". Executable 'ssh' not found in the PATH.\n` + ) + return + } + + // Arrange + await setup(removeAuth_removesSshCommand) + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + await authHelper.configureAuth() + let gitConfigContent = ( + await fs.promises.readFile(localGitConfigPath) + ).toString() + expect(gitConfigContent.indexOf('core.sshCommand')).toBeGreaterThanOrEqual( + 0 + ) // sanity check + const actualKeyPath = await getActualSshKeyPath() + expect(actualKeyPath).toBeTruthy() + await fs.promises.stat(actualKeyPath) + const actualKnownHostsPath = await getActualSshKnownHostsPath() + expect(actualKnownHostsPath).toBeTruthy() + await fs.promises.stat(actualKnownHostsPath) + + // Act + await authHelper.removeAuth() + + // Assert git config + gitConfigContent = ( + await fs.promises.readFile(localGitConfigPath) + ).toString() + expect(gitConfigContent.indexOf('core.sshCommand')).toBeLessThan(0) + + // Assert SSH key file + try { + await fs.promises.stat(actualKeyPath) + throw new Error('SSH key should have been deleted') + } catch (err) { + if (err.code !== 'ENOENT') { + throw err + } + } + + // Assert known hosts file + try { + await fs.promises.stat(actualKnownHostsPath) + throw new Error('SSH known hosts should have been deleted') + } catch (err) { + if (err.code !== 'ENOENT') { + throw err + } + } + }) + + const removeAuth_removesToken = 'removeAuth removes token' + it(removeAuth_removesToken, async () => { + // Arrange + await setup(removeAuth_removesToken) + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + await authHelper.configureAuth() + let gitConfigContent = ( + await fs.promises.readFile(localGitConfigPath) + ).toString() + expect(gitConfigContent.indexOf('http.')).toBeGreaterThanOrEqual(0) // sanity check + + // Act + await authHelper.removeAuth() + + // Assert git config + gitConfigContent = ( + await fs.promises.readFile(localGitConfigPath) + ).toString() + expect(gitConfigContent.indexOf('http.')).toBeLessThan(0) + }) + + const removeGlobalAuth_removesOverride = 'removeGlobalAuth removes override' + it(removeGlobalAuth_removesOverride, async () => { + // Arrange + await setup(removeGlobalAuth_removesOverride) + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + await authHelper.configureAuth() + await authHelper.configureGlobalAuth() + const homeOverride = git.env['HOME'] // Sanity check + expect(homeOverride).toBeTruthy() + await fs.promises.stat(path.join(git.env['HOME'], '.gitconfig')) + + // Act + await authHelper.removeGlobalAuth() + + // Assert + expect(git.env['HOME']).toBeUndefined() + try { + await fs.promises.stat(homeOverride) + throw new Error(`Should have been deleted '${homeOverride}'`) + } catch (err) { + if (err.code !== 'ENOENT') { + throw err + } + } + }) +}) + +async function setup(testName: string): Promise { + testName = testName.replace(/[^a-zA-Z0-9_]+/g, '-') + + // Directories + workspace = path.join(testWorkspace, testName, 'workspace') + runnerTemp = path.join(testWorkspace, testName, 'runner-temp') + tempHomedir = path.join(testWorkspace, testName, 'home-dir') + await fs.promises.mkdir(workspace, {recursive: true}) + await fs.promises.mkdir(runnerTemp, {recursive: true}) + await fs.promises.mkdir(tempHomedir, {recursive: true}) + process.env['RUNNER_TEMP'] = runnerTemp + process.env['HOME'] = tempHomedir + + // Create git config + globalGitConfigPath = path.join(tempHomedir, '.gitconfig') + await fs.promises.writeFile(globalGitConfigPath, '') + localGitConfigPath = path.join(workspace, '.git', 'config') + await fs.promises.mkdir(path.dirname(localGitConfigPath), {recursive: true}) + await fs.promises.writeFile(localGitConfigPath, '') + + git = { + branchDelete: jest.fn(), + branchExists: jest.fn(), + branchList: jest.fn(), + checkout: jest.fn(), + checkoutDetach: jest.fn(), + config: jest.fn( + async (key: string, value: string, globalConfig?: boolean) => { + const configPath = globalConfig + ? path.join(git.env['HOME'] || tempHomedir, '.gitconfig') + : localGitConfigPath + await fs.promises.appendFile(configPath, `\n${key} ${value}`) + } + ), + configExists: jest.fn( + async (key: string, globalConfig?: boolean): Promise => { + const configPath = globalConfig + ? path.join(git.env['HOME'] || tempHomedir, '.gitconfig') + : localGitConfigPath + const content = await fs.promises.readFile(configPath) + const lines = content + .toString() + .split('\n') + .filter(x => x) + return lines.some(x => x.startsWith(key)) + } + ), + env: {}, + fetch: jest.fn(), + getDefaultBranch: jest.fn(), + getWorkingDirectory: jest.fn(() => workspace), + init: jest.fn(), + isDetached: jest.fn(), + lfsFetch: jest.fn(), + lfsInstall: jest.fn(), + log1: jest.fn(), + remoteAdd: jest.fn(), + removeEnvironmentVariable: jest.fn((name: string) => delete git.env[name]), + revParse: jest.fn(), + setEnvironmentVariable: jest.fn((name: string, value: string) => { + git.env[name] = value + }), + shaExists: jest.fn(), + submoduleForeach: jest.fn(async () => { + return '' + }), + submoduleSync: jest.fn(), + submoduleUpdate: jest.fn(), + tagExists: jest.fn(), + tryClean: jest.fn(), + tryConfigUnset: jest.fn( + async (key: string, globalConfig?: boolean): Promise => { + const configPath = globalConfig + ? path.join(git.env['HOME'] || tempHomedir, '.gitconfig') + : localGitConfigPath + let content = await fs.promises.readFile(configPath) + let lines = content + .toString() + .split('\n') + .filter(x => x) + .filter(x => !x.startsWith(key)) + await fs.promises.writeFile(configPath, lines.join('\n')) + return true + } + ), + tryDisableAutomaticGarbageCollection: jest.fn(), + tryGetFetchUrl: jest.fn(), + tryReset: jest.fn() + } + + settings = { + authToken: 'some auth token', + clean: true, + commit: '', + fetchDepth: 1, + lfs: false, + submodules: false, + nestedSubmodules: false, + persistCredentials: true, + ref: 'refs/heads/master', + repositoryName: 'my-repo', + repositoryOwner: 'my-org', + repositoryPath: '', + sshKey: sshPath ? 'some ssh private key' : '', + sshKnownHosts: '', + sshStrict: true + } +} + +async function getActualSshKeyPath(): Promise { + let actualTempFiles = (await fs.promises.readdir(runnerTemp)) + .sort() + .map(x => path.join(runnerTemp, x)) + if (actualTempFiles.length === 0) { + return '' + } + + expect(actualTempFiles).toHaveLength(2) + expect(actualTempFiles[0].endsWith('_known_hosts')).toBeFalsy() + return actualTempFiles[0] +} + +async function getActualSshKnownHostsPath(): Promise { + let actualTempFiles = (await fs.promises.readdir(runnerTemp)) + .sort() + .map(x => path.join(runnerTemp, x)) + if (actualTempFiles.length === 0) { + return '' + } + + expect(actualTempFiles).toHaveLength(2) + expect(actualTempFiles[1].endsWith('_known_hosts')).toBeTruthy() + expect(actualTempFiles[1].startsWith(actualTempFiles[0])).toBeTruthy() + return actualTempFiles[1] +} diff --git a/__test__/git-directory-helper.test.ts b/__test__/git-directory-helper.test.ts new file mode 100644 index 0000000..70849b5 --- /dev/null +++ b/__test__/git-directory-helper.test.ts @@ -0,0 +1,441 @@ +import * as core from '@actions/core' +import * as fs from 'fs' +import * as gitDirectoryHelper from '../lib/git-directory-helper' +import * as io from '@actions/io' +import * as path from 'path' +import {IGitCommandManager} from '../lib/git-command-manager' + +const testWorkspace = path.join(__dirname, '_temp', 'git-directory-helper') +let repositoryPath: string +let repositoryUrl: string +let clean: boolean +let ref: string +let git: IGitCommandManager + +describe('git-directory-helper tests', () => { + beforeAll(async () => { + // Clear test workspace + await io.rmRF(testWorkspace) + }) + + beforeEach(() => { + // Mock error/warning/info/debug + jest.spyOn(core, 'error').mockImplementation(jest.fn()) + jest.spyOn(core, 'warning').mockImplementation(jest.fn()) + jest.spyOn(core, 'info').mockImplementation(jest.fn()) + jest.spyOn(core, 'debug').mockImplementation(jest.fn()) + }) + + afterEach(() => { + // Unregister mocks + jest.restoreAllMocks() + }) + + const cleansWhenCleanTrue = 'cleans when clean true' + it(cleansWhenCleanTrue, async () => { + // Arrange + await setup(cleansWhenCleanTrue) + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + git, + repositoryPath, + repositoryUrl, + clean, + ref + ) + + // Assert + const files = await fs.promises.readdir(repositoryPath) + expect(files.sort()).toEqual(['.git', 'my-file']) + expect(git.tryClean).toHaveBeenCalled() + expect(git.tryReset).toHaveBeenCalled() + expect(core.warning).not.toHaveBeenCalled() + }) + + const checkoutDetachWhenNotDetached = 'checkout detach when not detached' + it(checkoutDetachWhenNotDetached, async () => { + // Arrange + await setup(checkoutDetachWhenNotDetached) + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + git, + repositoryPath, + repositoryUrl, + clean, + ref + ) + + // Assert + const files = await fs.promises.readdir(repositoryPath) + expect(files.sort()).toEqual(['.git', 'my-file']) + expect(git.checkoutDetach).toHaveBeenCalled() + }) + + const doesNotCheckoutDetachWhenNotAlreadyDetached = + 'does not checkout detach when already detached' + it(doesNotCheckoutDetachWhenNotAlreadyDetached, async () => { + // Arrange + await setup(doesNotCheckoutDetachWhenNotAlreadyDetached) + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + const mockIsDetached = git.isDetached as jest.Mock + mockIsDetached.mockImplementation(async () => { + return true + }) + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + git, + repositoryPath, + repositoryUrl, + clean, + ref + ) + + // Assert + const files = await fs.promises.readdir(repositoryPath) + expect(files.sort()).toEqual(['.git', 'my-file']) + expect(git.checkoutDetach).not.toHaveBeenCalled() + }) + + const doesNotCleanWhenCleanFalse = 'does not clean when clean false' + it(doesNotCleanWhenCleanFalse, async () => { + // Arrange + await setup(doesNotCleanWhenCleanFalse) + clean = false + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + git, + repositoryPath, + repositoryUrl, + clean, + ref + ) + + // Assert + const files = await fs.promises.readdir(repositoryPath) + expect(files.sort()).toEqual(['.git', 'my-file']) + expect(git.isDetached).toHaveBeenCalled() + expect(git.branchList).toHaveBeenCalled() + expect(core.warning).not.toHaveBeenCalled() + expect(git.tryClean).not.toHaveBeenCalled() + expect(git.tryReset).not.toHaveBeenCalled() + }) + + const removesContentsWhenCleanFails = 'removes contents when clean fails' + it(removesContentsWhenCleanFails, async () => { + // Arrange + await setup(removesContentsWhenCleanFails) + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + let mockTryClean = git.tryClean as jest.Mock + mockTryClean.mockImplementation(async () => { + return false + }) + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + git, + repositoryPath, + repositoryUrl, + clean, + ref + ) + + // Assert + const files = await fs.promises.readdir(repositoryPath) + expect(files).toHaveLength(0) + expect(git.tryClean).toHaveBeenCalled() + expect(core.warning).toHaveBeenCalled() + expect(git.tryReset).not.toHaveBeenCalled() + }) + + const removesContentsWhenDifferentRepositoryUrl = + 'removes contents when different repository url' + it(removesContentsWhenDifferentRepositoryUrl, async () => { + // Arrange + await setup(removesContentsWhenDifferentRepositoryUrl) + clean = false + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + const differentRepositoryUrl = + 'https://github.com/my-different-org/my-different-repo' + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + git, + repositoryPath, + differentRepositoryUrl, + clean, + ref + ) + + // Assert + const files = await fs.promises.readdir(repositoryPath) + expect(files).toHaveLength(0) + expect(core.warning).not.toHaveBeenCalled() + expect(git.isDetached).not.toHaveBeenCalled() + }) + + const removesContentsWhenNoGitDirectory = + 'removes contents when no git directory' + it(removesContentsWhenNoGitDirectory, async () => { + // Arrange + await setup(removesContentsWhenNoGitDirectory) + clean = false + await io.rmRF(path.join(repositoryPath, '.git')) + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + git, + repositoryPath, + repositoryUrl, + clean, + ref + ) + + // Assert + const files = await fs.promises.readdir(repositoryPath) + expect(files).toHaveLength(0) + expect(core.warning).not.toHaveBeenCalled() + expect(git.isDetached).not.toHaveBeenCalled() + }) + + const removesContentsWhenResetFails = 'removes contents when reset fails' + it(removesContentsWhenResetFails, async () => { + // Arrange + await setup(removesContentsWhenResetFails) + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + let mockTryReset = git.tryReset as jest.Mock + mockTryReset.mockImplementation(async () => { + return false + }) + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + git, + repositoryPath, + repositoryUrl, + clean, + ref + ) + + // Assert + const files = await fs.promises.readdir(repositoryPath) + expect(files).toHaveLength(0) + expect(git.tryClean).toHaveBeenCalled() + expect(git.tryReset).toHaveBeenCalled() + expect(core.warning).toHaveBeenCalled() + }) + + const removesContentsWhenUndefinedGitCommandManager = + 'removes contents when undefined git command manager' + it(removesContentsWhenUndefinedGitCommandManager, async () => { + // Arrange + await setup(removesContentsWhenUndefinedGitCommandManager) + clean = false + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + undefined, + repositoryPath, + repositoryUrl, + clean, + ref + ) + + // Assert + const files = await fs.promises.readdir(repositoryPath) + expect(files).toHaveLength(0) + expect(core.warning).not.toHaveBeenCalled() + }) + + const removesLocalBranches = 'removes local branches' + it(removesLocalBranches, async () => { + // Arrange + await setup(removesLocalBranches) + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + const mockBranchList = git.branchList as jest.Mock + mockBranchList.mockImplementation(async (remote: boolean) => { + return remote ? [] : ['local-branch-1', 'local-branch-2'] + }) + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + git, + repositoryPath, + repositoryUrl, + clean, + ref + ) + + // Assert + const files = await fs.promises.readdir(repositoryPath) + expect(files.sort()).toEqual(['.git', 'my-file']) + expect(git.branchDelete).toHaveBeenCalledWith(false, 'local-branch-1') + expect(git.branchDelete).toHaveBeenCalledWith(false, 'local-branch-2') + }) + + const removesLockFiles = 'removes lock files' + it(removesLockFiles, async () => { + // Arrange + await setup(removesLockFiles) + clean = false + await fs.promises.writeFile( + path.join(repositoryPath, '.git', 'index.lock'), + '' + ) + await fs.promises.writeFile( + path.join(repositoryPath, '.git', 'shallow.lock'), + '' + ) + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + git, + repositoryPath, + repositoryUrl, + clean, + ref + ) + + // Assert + let files = await fs.promises.readdir(path.join(repositoryPath, '.git')) + expect(files).toHaveLength(0) + files = await fs.promises.readdir(repositoryPath) + expect(files.sort()).toEqual(['.git', 'my-file']) + expect(git.isDetached).toHaveBeenCalled() + expect(git.branchList).toHaveBeenCalled() + expect(core.warning).not.toHaveBeenCalled() + expect(git.tryClean).not.toHaveBeenCalled() + expect(git.tryReset).not.toHaveBeenCalled() + }) + + const removesAncestorRemoteBranch = 'removes ancestor remote branch' + it(removesAncestorRemoteBranch, async () => { + // Arrange + await setup(removesAncestorRemoteBranch) + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + const mockBranchList = git.branchList as jest.Mock + mockBranchList.mockImplementation(async (remote: boolean) => { + return remote ? ['origin/remote-branch-1', 'origin/remote-branch-2'] : [] + }) + ref = 'remote-branch-1/conflict' + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + git, + repositoryPath, + repositoryUrl, + clean, + ref + ) + + // Assert + const files = await fs.promises.readdir(repositoryPath) + expect(files.sort()).toEqual(['.git', 'my-file']) + expect(git.branchDelete).toHaveBeenCalledTimes(1) + expect(git.branchDelete).toHaveBeenCalledWith( + true, + 'origin/remote-branch-1' + ) + }) + + const removesDescendantRemoteBranches = 'removes descendant remote branch' + it(removesDescendantRemoteBranches, async () => { + // Arrange + await setup(removesDescendantRemoteBranches) + await fs.promises.writeFile(path.join(repositoryPath, 'my-file'), '') + const mockBranchList = git.branchList as jest.Mock + mockBranchList.mockImplementation(async (remote: boolean) => { + return remote + ? ['origin/remote-branch-1/conflict', 'origin/remote-branch-2'] + : [] + }) + ref = 'remote-branch-1' + + // Act + await gitDirectoryHelper.prepareExistingDirectory( + git, + repositoryPath, + repositoryUrl, + clean, + ref + ) + + // Assert + const files = await fs.promises.readdir(repositoryPath) + expect(files.sort()).toEqual(['.git', 'my-file']) + expect(git.branchDelete).toHaveBeenCalledTimes(1) + expect(git.branchDelete).toHaveBeenCalledWith( + true, + 'origin/remote-branch-1/conflict' + ) + }) +}) + +async function setup(testName: string): Promise { + testName = testName.replace(/[^a-zA-Z0-9_]+/g, '-') + + // Repository directory + repositoryPath = path.join(testWorkspace, testName) + await fs.promises.mkdir(path.join(repositoryPath, '.git'), {recursive: true}) + + // Repository URL + repositoryUrl = 'https://github.com/my-org/my-repo' + + // Clean + clean = true + + // Ref + ref = '' + + // Git command manager + git = { + branchDelete: jest.fn(), + branchExists: jest.fn(), + branchList: jest.fn(async () => { + return [] + }), + checkout: jest.fn(), + checkoutDetach: jest.fn(), + config: jest.fn(), + configExists: jest.fn(), + fetch: jest.fn(), + getDefaultBranch: jest.fn(), + getWorkingDirectory: jest.fn(() => repositoryPath), + init: jest.fn(), + isDetached: jest.fn(), + lfsFetch: jest.fn(), + lfsInstall: jest.fn(), + log1: jest.fn(), + remoteAdd: jest.fn(), + removeEnvironmentVariable: jest.fn(), + revParse: jest.fn(), + setEnvironmentVariable: jest.fn(), + shaExists: jest.fn(), + submoduleForeach: jest.fn(), + submoduleSync: jest.fn(), + submoduleUpdate: jest.fn(), + tagExists: jest.fn(), + tryClean: jest.fn(async () => { + return true + }), + tryConfigUnset: jest.fn(), + tryDisableAutomaticGarbageCollection: jest.fn(), + tryGetFetchUrl: jest.fn(async () => { + // Sanity check - this function shouldn't be called when the .git directory doesn't exist + await fs.promises.stat(path.join(repositoryPath, '.git')) + return repositoryUrl + }), + tryReset: jest.fn(async () => { + return true + }) + } +} diff --git a/__test__/input-helper.test.ts b/__test__/input-helper.test.ts index be4b166..920bc8e 100644 --- a/__test__/input-helper.test.ts +++ b/__test__/input-helper.test.ts @@ -4,7 +4,7 @@ import * as fsHelper from '../lib/fs-helper' import * as github from '@actions/github' import * as inputHelper from '../lib/input-helper' import * as path from 'path' -import {ISourceSettings} from '../lib/git-source-provider' +import {IGitSourceSettings} from '../lib/git-source-settings' const originalGitHubWorkspace = process.env['GITHUB_WORKSPACE'] const gitHubWorkspace = path.resolve('/checkout-tests/workspace') @@ -17,12 +17,18 @@ let originalContext = {...github.context} describe('input-helper tests', () => { beforeAll(() => { - // Mock @actions/core getInput() + // Mock getInput jest.spyOn(core, 'getInput').mockImplementation((name: string) => { return inputs[name] }) - // Mock @actions/github context + // Mock error/warning/info/debug + jest.spyOn(core, 'error').mockImplementation(jest.fn()) + jest.spyOn(core, 'warning').mockImplementation(jest.fn()) + jest.spyOn(core, 'info').mockImplementation(jest.fn()) + jest.spyOn(core, 'debug').mockImplementation(jest.fn()) + + // Mock github context jest.spyOn(github.context, 'repo', 'get').mockImplementation(() => { return { owner: 'some-owner', @@ -62,7 +68,7 @@ describe('input-helper tests', () => { }) it('sets defaults', () => { - const settings: ISourceSettings = inputHelper.getInputs() + const settings: IGitSourceSettings = inputHelper.getInputs() expect(settings).toBeTruthy() expect(settings.authToken).toBeFalsy() expect(settings.clean).toBe(true) @@ -80,7 +86,7 @@ describe('input-helper tests', () => { let originalRef = github.context.ref try { github.context.ref = 'some-unqualified-ref' - const settings: ISourceSettings = inputHelper.getInputs() + const settings: IGitSourceSettings = inputHelper.getInputs() expect(settings).toBeTruthy() expect(settings.commit).toBe('1234567890123456789012345678901234567890') expect(settings.ref).toBe('refs/heads/some-unqualified-ref') @@ -98,37 +104,23 @@ describe('input-helper tests', () => { it('roots path', () => { inputs.path = 'some-directory/some-subdirectory' - const settings: ISourceSettings = inputHelper.getInputs() + const settings: IGitSourceSettings = inputHelper.getInputs() expect(settings.repositoryPath).toBe( path.join(gitHubWorkspace, 'some-directory', 'some-subdirectory') ) }) - it('sets correct default ref/sha for other repo', () => { - inputs.repository = 'some-owner/some-other-repo' - const settings: ISourceSettings = inputHelper.getInputs() - expect(settings.ref).toBe('refs/heads/master') - expect(settings.commit).toBeFalsy() - }) - it('sets ref to empty when explicit sha', () => { inputs.ref = '1111111111222222222233333333334444444444' - const settings: ISourceSettings = inputHelper.getInputs() + const settings: IGitSourceSettings = inputHelper.getInputs() expect(settings.ref).toBeFalsy() expect(settings.commit).toBe('1111111111222222222233333333334444444444') }) it('sets sha to empty when explicit ref', () => { inputs.ref = 'refs/heads/some-other-ref' - const settings: ISourceSettings = inputHelper.getInputs() + const settings: IGitSourceSettings = inputHelper.getInputs() expect(settings.ref).toBe('refs/heads/some-other-ref') expect(settings.commit).toBeFalsy() }) - - it('gives good error message for submodules input', () => { - inputs.submodules = 'true' - assert.throws(() => { - inputHelper.getInputs() - }, /The input 'submodules' is not supported/) - }) }) diff --git a/__test__/verify-no-unstaged-changes.sh b/__test__/verify-no-unstaged-changes.sh index 9fe6173..9b30471 100755 --- a/__test__/verify-no-unstaged-changes.sh +++ b/__test__/verify-no-unstaged-changes.sh @@ -12,6 +12,6 @@ if [[ "$(git status --porcelain)" != "" ]]; then echo ---------------------------------------- echo Troubleshooting echo ---------------------------------------- - echo "::error::Unstaged changes detected. Locally try running: git clean -ffdx && npm ci && npm run all" + echo "::error::Unstaged changes detected. Locally try running: git clean -ffdx && npm ci && npm run format && npm run build" exit 1 fi diff --git a/__test__/verify-submodules-false.sh b/__test__/verify-submodules-false.sh new file mode 100755 index 0000000..733e247 --- /dev/null +++ b/__test__/verify-submodules-false.sh @@ -0,0 +1,11 @@ +#!/bin/bash + +if [ ! -f "./submodules-false/regular-file.txt" ]; then + echo "Expected regular file does not exist" + exit 1 +fi + +if [ -f "./submodules-false/submodule-level-1/submodule-file.txt" ]; then + echo "Unexpected submodule file exists" + exit 1 +fi \ No newline at end of file diff --git a/__test__/verify-submodules-not-checked-out.sh b/__test__/verify-submodules-not-checked-out.sh deleted file mode 100755 index dcc0487..0000000 --- a/__test__/verify-submodules-not-checked-out.sh +++ /dev/null @@ -1,11 +0,0 @@ -#!/bin/bash - -if [ ! -f "./submodules-not-checked-out/regular-file.txt" ]; then - echo "Expected regular file does not exist" - exit 1 -fi - -if [ -f "./submodules-not-checked-out/submodule-level-1/submodule-file.txt" ]; then - echo "Unexpected submodule file exists" - exit 1 -fi diff --git a/__test__/verify-submodules-recursive.sh b/__test__/verify-submodules-recursive.sh new file mode 100755 index 0000000..1b68f9b --- /dev/null +++ b/__test__/verify-submodules-recursive.sh @@ -0,0 +1,26 @@ +#!/bin/bash + +if [ ! -f "./submodules-recursive/regular-file.txt" ]; then + echo "Expected regular file does not exist" + exit 1 +fi + +if [ ! -f "./submodules-recursive/submodule-level-1/submodule-file.txt" ]; then + echo "Expected submodule file does not exist" + exit 1 +fi + +if [ ! -f "./submodules-recursive/submodule-level-1/submodule-level-2/nested-submodule-file.txt" ]; then + echo "Expected nested submodule file does not exists" + exit 1 +fi + +echo "Testing persisted credential" +pushd ./submodules-recursive/submodule-level-1/submodule-level-2 +git config --local --name-only --get-regexp http.+extraheader && git fetch +if [ "$?" != "0" ]; then + echo "Failed to validate persisted credential" + popd + exit 1 +fi +popd diff --git a/__test__/verify-submodules-true.sh b/__test__/verify-submodules-true.sh new file mode 100755 index 0000000..43769fe --- /dev/null +++ b/__test__/verify-submodules-true.sh @@ -0,0 +1,26 @@ +#!/bin/bash + +if [ ! -f "./submodules-true/regular-file.txt" ]; then + echo "Expected regular file does not exist" + exit 1 +fi + +if [ ! -f "./submodules-true/submodule-level-1/submodule-file.txt" ]; then + echo "Expected submodule file does not exist" + exit 1 +fi + +if [ -f "./submodules-true/submodule-level-1/submodule-level-2/nested-submodule-file.txt" ]; then + echo "Unexpected nested submodule file exists" + exit 1 +fi + +echo "Testing persisted credential" +pushd ./submodules-true/submodule-level-1 +git config --local --name-only --get-regexp http.+extraheader && git fetch +if [ "$?" != "0" ]; then + echo "Failed to validate persisted credential" + popd + exit 1 +fi +popd diff --git a/action.yml b/action.yml index 9650409..91d3982 100644 --- a/action.yml +++ b/action.yml @@ -1,6 +1,6 @@ name: 'Checkout' description: 'Checkout a Git repository at a particular version' -inputs: +inputs: repository: description: 'Repository name with owner. For example, actions/checkout' default: ${{ github.repository }} @@ -8,16 +8,45 @@ inputs: description: > The branch, tag or SHA to checkout. When checking out the repository that triggered a workflow, this defaults to the reference or SHA for that - event. Otherwise, defaults to `master`. + event. Otherwise, uses the default branch. token: description: > - Auth token used to fetch the repository. The token is stored in the local - git config, which enables your scripts to run authenticated git commands. - The post-job step removes the token from the git config. [Learn more about - creating and using encrypted secrets](https://help.github.com/en/actions/automating-your-workflow-with-github-actions/creating-and-using-encrypted-secrets) + Personal access token (PAT) used to fetch the repository. The PAT is configured + with the local git config, which enables your scripts to run authenticated git + commands. The post-job step removes the PAT. + + + We recommend using a service account with the least permissions necessary. + Also when generating a new PAT, select the least scopes necessary. + + + [Learn more about creating and using encrypted secrets](https://help.github.com/en/actions/automating-your-workflow-with-github-actions/creating-and-using-encrypted-secrets) default: ${{ github.token }} + ssh-key: + description: > + SSH key used to fetch the repository. The SSH key is configured with the local + git config, which enables your scripts to run authenticated git commands. + The post-job step removes the SSH key. + + + We recommend using a service account with the least permissions necessary. + + + [Learn more about creating and using + encrypted secrets](https://help.github.com/en/actions/automating-your-workflow-with-github-actions/creating-and-using-encrypted-secrets) + ssh-known-hosts: + description: > + Known hosts in addition to the user and global host key database. The public + SSH keys for a host may be obtained using the utility `ssh-keyscan`. For example, + `ssh-keyscan github.com`. The public key for github.com is always implicitly added. + ssh-strict: + description: > + Whether to perform strict host key checking. When true, adds the options `StrictHostKeyChecking=yes` + and `CheckHostIP=no` to the SSH command line. Use the input `ssh-known-hosts` to + configure additional hosts. + default: true persist-credentials: - description: 'Whether to persist the token in the git config' + description: 'Whether to configure the token or SSH key with the local git config' default: true path: description: 'Relative path under $GITHUB_WORKSPACE to place the repository' @@ -25,11 +54,20 @@ inputs: description: 'Whether to execute `git clean -ffdx && git reset --hard HEAD` before fetching' default: true fetch-depth: - description: 'Number of commits to fetch. 0 indicates all history.' + description: 'Number of commits to fetch. 0 indicates all history for all branches and tags.' default: 1 lfs: description: 'Whether to download Git-LFS files' default: false + submodules: + description: > + Whether to checkout submodules: `true` to checkout submodules or `recursive` to + recursively checkout submodules. + + + When the `ssh-key` input is not provided, SSH URLs beginning with `git@github.com:` are + converted to HTTPS. + default: false runs: using: node12 main: dist/index.js diff --git a/adrs/0153-checkout-v2.md b/adrs/0153-checkout-v2.md index de531bd..f174b1a 100644 --- a/adrs/0153-checkout-v2.md +++ b/adrs/0153-checkout-v2.md @@ -29,14 +29,26 @@ We want to take this opportunity to make behavioral changes, from v1. This docum description: > Personal access token (PAT) used to fetch the repository. The PAT is configured with the local git config, which enables your scripts to run authenticated git - commands. The post-job step removes the PAT. [Learn more about creating and using - encrypted secrets](https://help.github.com/en/actions/automating-your-workflow-with-github-actions/creating-and-using-encrypted-secrets) + commands. The post-job step removes the PAT. + + + We recommend using a service account with the least permissions necessary. + Also when generating a new PAT, select the least scopes necessary. + + + [Learn more about creating and using encrypted secrets](https://help.github.com/en/actions/automating-your-workflow-with-github-actions/creating-and-using-encrypted-secrets) default: ${{ github.token }} ssh-key: description: > - SSH key used to fetch the repository. SSH key is configured with the local + SSH key used to fetch the repository. The SSH key is configured with the local git config, which enables your scripts to run authenticated git commands. - The post-job step removes the SSH key. [Learn more about creating and using + The post-job step removes the SSH key. + + + We recommend using a service account with the least permissions necessary. + + + [Learn more about creating and using encrypted secrets](https://help.github.com/en/actions/automating-your-workflow-with-github-actions/creating-and-using-encrypted-secrets) ssh-known-hosts: description: > @@ -44,7 +56,10 @@ We want to take this opportunity to make behavioral changes, from v1. This docum SSH keys for a host may be obtained using the utility `ssh-keyscan`. For example, `ssh-keyscan github.com`. The public key for github.com is always implicitly added. ssh-strict: - description: 'Whether to perform strict host key checking' + description: > + Whether to perform strict host key checking. When true, adds the options `StrictHostKeyChecking=yes` + and `CheckHostIP=no` to the SSH command line. Use the input `ssh-known-hosts` to + configure additional hosts. default: true persist-credentials: description: 'Whether to configure the token or SSH key with the local git config' @@ -55,18 +70,26 @@ We want to take this opportunity to make behavioral changes, from v1. This docum description: 'Whether to execute `git clean -ffdx && git reset --hard HEAD` before fetching' default: true fetch-depth: - description: 'Number of commits to fetch. 0 indicates all history.' + description: 'Number of commits to fetch. 0 indicates all history for all tags and branches.' default: 1 lfs: description: 'Whether to download Git-LFS files' default: false + submodules: + description: > + Whether to checkout submodules: `true` to checkout submodules or `recursive` to + recursively checkout submodules. + + + When the `ssh-key` input is not provided, SSH URLs beginning with `git@github.com:` are + converted to HTTPS. + default: false ``` Note: - SSH support is new - `persist-credentials` is new - `path` behavior is different (refer [below](#path) for details) -- `submodules` was removed (error if specified; add later if needed) ### Fallback to GitHub API @@ -74,7 +97,7 @@ When a sufficient version of git is not in the PATH, fallback to the [web API](h Note: - LFS files are not included in the archive. Therefore fail if LFS is set to true. -- Submodules are also not included in the archive. However submodules are not supported by checkout v2 anyway. +- Submodules are also not included in the archive. ### Persist credentials @@ -95,7 +118,6 @@ Note: - The auth header is scoped to all of github `http.https://github.com/.extraheader` - Additional public remotes also just work. - If users want to authenticate to an additional private remote, they should provide the `token` input. - - Lines up if we add submodule support in the future. Don't need to worry about calculating relative URLs. Just works, although needs to be persisted in each submodule git config. #### SSH key @@ -229,6 +251,17 @@ A better solution is: Given a source file path, walk up the directories until the first `.git/config` is found. Check if it matches the self repo (`url = https://github.com/OWNER/REPO`). If not, drop the source file path. +### Submodules + +With both PAT and SSH key support, we should be able to provide frictionless support for +submodules scenarios: recursive, non-recursive, relative submodule paths. + +When fetching submodules, follow the `fetch-depth` settings. + +Also when fetching submodules, if the `ssh-key` input is not provided then convert SSH URLs to HTTPS: `-c url."https://github.com/".insteadOf "git@github.com:"` + +Credentials will be persisted in the submodules local git config too. + ### Port to typescript The checkout action should be a typescript action on the GitHub graph, for the following reasons: diff --git a/dist/index.js b/dist/index.js index 36e9e00..e0d0238 100644 --- a/dist/index.js +++ b/dist/index.js @@ -46,21 +46,49 @@ module.exports = /***/ 0: /***/ (function(module, __unusedexports, __webpack_require__) { -const Octokit = __webpack_require__(529); +const { requestLog } = __webpack_require__(916); +const { + restEndpointMethods +} = __webpack_require__(842); + +const Core = __webpack_require__(529); const CORE_PLUGINS = [ __webpack_require__(190), __webpack_require__(19), // deprecated: remove in v17 - __webpack_require__(372), + requestLog, __webpack_require__(148), - __webpack_require__(248), - __webpack_require__(586), + restEndpointMethods, __webpack_require__(430), __webpack_require__(850) // deprecated: remove in v17 ]; -module.exports = Octokit.plugin(CORE_PLUGINS); +const OctokitRest = Core.plugin(CORE_PLUGINS); + +function DeprecatedOctokit(options) { + const warn = + options && options.log && options.log.warn + ? options.log.warn + : console.warn; + warn( + '[@octokit/rest] `const Octokit = require("@octokit/rest")` is deprecated. Use `const { Octokit } = require("@octokit/rest")` instead' + ); + return new OctokitRest(options); +} + +const Octokit = Object.assign(DeprecatedOctokit, { + Octokit: OctokitRest +}); + +Object.keys(OctokitRest).forEach(key => { + /* istanbul ignore else */ + if (OctokitRest.hasOwnProperty(key)) { + Octokit[key] = OctokitRest[key]; + } +}); + +module.exports = Octokit; /***/ }), @@ -416,43 +444,103 @@ module.exports = osName; /***/ }), -/***/ 8: +/***/ 3: /***/ (function(module, __unusedexports, __webpack_require__) { -module.exports = iterator; +var once = __webpack_require__(969); -const normalizePaginatedListResponse = __webpack_require__(301); +var noop = function() {}; -function iterator(octokit, options) { - const headers = options.headers; - let url = octokit.request.endpoint(options).url; +var isRequest = function(stream) { + return stream.setHeader && typeof stream.abort === 'function'; +}; - return { - [Symbol.asyncIterator]: () => ({ - next() { - if (!url) { - return Promise.resolve({ done: true }); - } +var isChildProcess = function(stream) { + return stream.stdio && Array.isArray(stream.stdio) && stream.stdio.length === 3 +}; - return octokit - .request({ url, headers }) +var eos = function(stream, opts, callback) { + if (typeof opts === 'function') return eos(stream, null, opts); + if (!opts) opts = {}; - .then(response => { - normalizePaginatedListResponse(octokit, url, response); + callback = once(callback || noop); - // `response.headers.link` format: - // '; rel="next", ; rel="last"' - // sets `url` to undefined if "next" URL is not present or `link` header is not set - url = ((response.headers.link || "").match( - /<([^>]+)>;\s*rel="next"/ - ) || [])[1]; + var ws = stream._writableState; + var rs = stream._readableState; + var readable = opts.readable || (opts.readable !== false && stream.readable); + var writable = opts.writable || (opts.writable !== false && stream.writable); + var cancelled = false; - return { value: response }; - }); - } - }) - }; -} + var onlegacyfinish = function() { + if (!stream.writable) onfinish(); + }; + + var onfinish = function() { + writable = false; + if (!readable) callback.call(stream); + }; + + var onend = function() { + readable = false; + if (!writable) callback.call(stream); + }; + + var onexit = function(exitCode) { + callback.call(stream, exitCode ? new Error('exited with error code: ' + exitCode) : null); + }; + + var onerror = function(err) { + callback.call(stream, err); + }; + + var onclose = function() { + process.nextTick(onclosenexttick); + }; + + var onclosenexttick = function() { + if (cancelled) return; + if (readable && !(rs && (rs.ended && !rs.destroyed))) return callback.call(stream, new Error('premature close')); + if (writable && !(ws && (ws.ended && !ws.destroyed))) return callback.call(stream, new Error('premature close')); + }; + + var onrequest = function() { + stream.req.on('finish', onfinish); + }; + + if (isRequest(stream)) { + stream.on('complete', onfinish); + stream.on('abort', onclose); + if (stream.req) onrequest(); + else stream.on('request', onrequest); + } else if (writable && !ws) { // legacy streams + stream.on('end', onlegacyfinish); + stream.on('close', onlegacyfinish); + } + + if (isChildProcess(stream)) stream.on('exit', onexit); + + stream.on('end', onend); + stream.on('finish', onfinish); + if (opts.error !== false) stream.on('error', onerror); + stream.on('close', onclose); + + return function() { + cancelled = true; + stream.removeListener('complete', onfinish); + stream.removeListener('abort', onclose); + stream.removeListener('request', onrequest); + if (stream.req) stream.req.removeListener('finish', onfinish); + stream.removeListener('end', onlegacyfinish); + stream.removeListener('close', onlegacyfinish); + stream.removeListener('finish', onfinish); + stream.removeListener('exit', onexit); + stream.removeListener('end', onend); + stream.removeListener('error', onerror); + stream.removeListener('close', onclose); + }; +}; + +module.exports = eos; /***/ }), @@ -1176,6 +1264,13 @@ module.exports._parse = parse; module.exports._enoent = enoent; +/***/ }), + +/***/ 34: +/***/ (function(module) { + +module.exports = require("https"); + /***/ }), /***/ 39: @@ -1248,13 +1343,21 @@ const windowsRelease = release => { const ver = (version || [])[0]; - // Server 2008, 2012 and 2016 versions are ambiguous with desktop versions and must be detected at runtime. + // Server 2008, 2012, 2016, and 2019 versions are ambiguous with desktop versions and must be detected at runtime. // If `release` is omitted or we're on a Windows system, and the version number is an ambiguous version // then use `wmic` to get the OS caption: https://msdn.microsoft.com/en-us/library/aa394531(v=vs.85).aspx - // If the resulting caption contains the year 2008, 2012 or 2016, it is a server version, so return a server OS name. + // If `wmic` is obsoloete (later versions of Windows 10), use PowerShell instead. + // If the resulting caption contains the year 2008, 2012, 2016 or 2019, it is a server version, so return a server OS name. if ((!release || release === os.release()) && ['6.1', '6.2', '6.3', '10.0'].includes(ver)) { - const stdout = execa.sync('wmic', ['os', 'get', 'Caption']).stdout || ''; - const year = (stdout.match(/2008|2012|2016/) || [])[0]; + let stdout; + try { + stdout = execa.sync('powershell', ['(Get-CimInstance -ClassName Win32_OperatingSystem).caption']).stdout || ''; + } catch (_) { + stdout = execa.sync('wmic', ['os', 'get', 'Caption']).stdout || ''; + } + + const year = (stdout.match(/2008|2012|2016|2019/) || [])[0]; + if (year) { return `Server ${year}`; } @@ -1266,6 +1369,45 @@ const windowsRelease = release => { module.exports = windowsRelease; +/***/ }), + +/***/ 81: +/***/ (function(__unusedmodule, exports, __webpack_require__) { + +"use strict"; + +var __importStar = (this && this.__importStar) || function (mod) { + if (mod && mod.__esModule) return mod; + var result = {}; + if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; + result["default"] = mod; + return result; +}; +Object.defineProperty(exports, "__esModule", { value: true }); +const assert = __importStar(__webpack_require__(357)); +const url_1 = __webpack_require__(835); +function getFetchUrl(settings) { + assert.ok(settings.repositoryOwner, 'settings.repositoryOwner must be defined'); + assert.ok(settings.repositoryName, 'settings.repositoryName must be defined'); + const serviceUrl = getServerUrl(); + const encodedOwner = encodeURIComponent(settings.repositoryOwner); + const encodedName = encodeURIComponent(settings.repositoryName); + if (settings.sshKey) { + return `git@${serviceUrl.hostname}:${encodedOwner}/${encodedName}.git`; + } + // "origin" is SCHEME://HOSTNAME[:PORT] + return `${serviceUrl.origin}/${encodedOwner}/${encodedName}`; +} +exports.getFetchUrl = getFetchUrl; +function getServerUrl() { + // todo: remove GITHUB_URL after support for GHES Alpha is no longer needed + return new url_1.URL(process.env['GITHUB_SERVER_URL'] || + process.env['GITHUB_URL'] || + 'https://github.com'); +} +exports.getServerUrl = getServerUrl; + + /***/ }), /***/ 87: @@ -2249,7 +2391,7 @@ module.exports = function nodeRNG() { var net = __webpack_require__(631); var tls = __webpack_require__(16); var http = __webpack_require__(605); -var https = __webpack_require__(211); +var https = __webpack_require__(34); var events = __webpack_require__(614); var assert = __webpack_require__(357); var util = __webpack_require__(669); @@ -2588,12 +2730,10 @@ module.exports.MaxBufferError = MaxBufferError; module.exports = paginatePlugin; -const iterator = __webpack_require__(8); -const paginate = __webpack_require__(807); +const { paginateRest } = __webpack_require__(299); function paginatePlugin(octokit) { - octokit.paginate = paginate.bind(null, octokit); - octokit.paginate.iterator = iterator.bind(null, octokit); + Object.assign(octokit, paginateRest(octokit)); } @@ -2621,6 +2761,14 @@ exports.IsPost = !!process.env['STATE_isPost']; * The repository path for the POST action. The value is empty during the MAIN action. */ exports.RepositoryPath = process.env['STATE_repositoryPath'] || ''; +/** + * The SSH key path for the POST action. The value is empty during the MAIN action. + */ +exports.SshKeyPath = process.env['STATE_sshKeyPath'] || ''; +/** + * The SSH known hosts path for the POST action. The value is empty during the MAIN action. + */ +exports.SshKnownHostsPath = process.env['STATE_sshKnownHostsPath'] || ''; /** * Save the repository path so the POST action can retrieve the value. */ @@ -2628,6 +2776,20 @@ function setRepositoryPath(repositoryPath) { coreCommand.issueCommand('save-state', { name: 'repositoryPath' }, repositoryPath); } exports.setRepositoryPath = setRepositoryPath; +/** + * Save the SSH key path so the POST action can retrieve the value. + */ +function setSshKeyPath(sshKeyPath) { + coreCommand.issueCommand('save-state', { name: 'sshKeyPath' }, sshKeyPath); +} +exports.setSshKeyPath = setSshKeyPath; +/** + * Save the SSH known hosts path so the POST action can retrieve the value. + */ +function setSshKnownHostsPath(sshKnownHostsPath) { + coreCommand.issueCommand('save-state', { name: 'sshKnownHostsPath' }, sshKnownHostsPath); +} +exports.setSshKnownHostsPath = setSshKnownHostsPath; // Publish a variable so that when the POST action runs, it can determine it should run the cleanup logic. // This is necessary since we don't have a separate entry point. if (!exports.IsPost) { @@ -2695,7 +2857,7 @@ module.exports = opts => { var net = __webpack_require__(631); var tls = __webpack_require__(16); var http = __webpack_require__(605); -var https = __webpack_require__(211); +var https = __webpack_require__(34); var events = __webpack_require__(614); var assert = __webpack_require__(357); var util = __webpack_require__(669); @@ -3160,21 +3322,44 @@ else { /***/ }), /***/ 211: -/***/ (function(module) { +/***/ (function(__unusedmodule, exports, __webpack_require__) { + +"use strict"; + + +Object.defineProperty(exports, '__esModule', { value: true }); + +function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'default' in ex) ? ex['default'] : ex; } + +var osName = _interopDefault(__webpack_require__(2)); + +function getUserAgent() { + try { + return `Node.js/${process.version.substr(1)} (${osName()}; ${process.arch})`; + } catch (error) { + if (/wmic os get Caption/.test(error.message)) { + return "Windows "; + } + + return ""; + } +} + +exports.getUserAgent = getUserAgent; +//# sourceMappingURL=index.js.map -module.exports = require("https"); /***/ }), /***/ 215: /***/ (function(module) { -module.exports = {"name":"@octokit/rest","version":"16.38.1","publishConfig":{"access":"public"},"description":"GitHub REST API client for Node.js","keywords":["octokit","github","rest","api-client"],"author":"Gregor Martynus (https://github.com/gr2m)","contributors":[{"name":"Mike de Boer","email":"info@mikedeboer.nl"},{"name":"Fabian Jakobs","email":"fabian@c9.io"},{"name":"Joe Gallo","email":"joe@brassafrax.com"},{"name":"Gregor Martynus","url":"https://github.com/gr2m"}],"repository":"https://github.com/octokit/rest.js","dependencies":{"@octokit/auth-token":"^2.4.0","@octokit/request":"^5.2.0","@octokit/request-error":"^1.0.2","atob-lite":"^2.0.0","before-after-hook":"^2.0.0","btoa-lite":"^1.0.0","deprecation":"^2.0.0","lodash.get":"^4.4.2","lodash.set":"^4.3.2","lodash.uniq":"^4.5.0","octokit-pagination-methods":"^1.1.0","once":"^1.4.0","universal-user-agent":"^4.0.0"},"devDependencies":{"@gimenete/type-writer":"^0.1.3","@octokit/auth":"^1.1.1","@octokit/fixtures-server":"^5.0.6","@octokit/graphql":"^4.2.0","@types/node":"^13.1.0","bundlesize":"^0.18.0","chai":"^4.1.2","compression-webpack-plugin":"^3.1.0","cypress":"^3.0.0","glob":"^7.1.2","http-proxy-agent":"^3.0.0","lodash.camelcase":"^4.3.0","lodash.merge":"^4.6.1","lodash.upperfirst":"^4.3.1","mkdirp":"^0.5.1","mocha":"^6.0.0","mustache":"^4.0.0","nock":"^11.3.3","npm-run-all":"^4.1.2","nyc":"^15.0.0","prettier":"^1.14.2","proxy":"^1.0.0","semantic-release":"^16.0.0","sinon":"^8.0.0","sinon-chai":"^3.0.0","sort-keys":"^4.0.0","string-to-arraybuffer":"^1.0.0","string-to-jsdoc-comment":"^1.0.0","typescript":"^3.3.1","webpack":"^4.0.0","webpack-bundle-analyzer":"^3.0.0","webpack-cli":"^3.0.0"},"types":"index.d.ts","scripts":{"coverage":"nyc report --reporter=html && open coverage/index.html","lint":"prettier --check '{lib,plugins,scripts,test}/**/*.{js,json,ts}' 'docs/*.{js,json}' 'docs/src/**/*' index.js README.md package.json","lint:fix":"prettier --write '{lib,plugins,scripts,test}/**/*.{js,json,ts}' 'docs/*.{js,json}' 'docs/src/**/*' index.js README.md package.json","pretest":"npm run -s lint","test":"nyc mocha test/mocha-node-setup.js \"test/*/**/*-test.js\"","test:browser":"cypress run --browser chrome","build":"npm-run-all build:*","build:ts":"npm run -s update-endpoints:typescript","prebuild:browser":"mkdirp dist/","build:browser":"npm-run-all build:browser:*","build:browser:development":"webpack --mode development --entry . --output-library=Octokit --output=./dist/octokit-rest.js --profile --json > dist/bundle-stats.json","build:browser:production":"webpack --mode production --entry . --plugin=compression-webpack-plugin --output-library=Octokit --output-path=./dist --output-filename=octokit-rest.min.js --devtool source-map","generate-bundle-report":"webpack-bundle-analyzer dist/bundle-stats.json --mode=static --no-open --report dist/bundle-report.html","update-endpoints":"npm-run-all update-endpoints:*","update-endpoints:fetch-json":"node scripts/update-endpoints/fetch-json","update-endpoints:code":"node scripts/update-endpoints/code","update-endpoints:typescript":"node scripts/update-endpoints/typescript","prevalidate:ts":"npm run -s build:ts","validate:ts":"tsc --target es6 --noImplicitAny index.d.ts","postvalidate:ts":"tsc --noEmit --target es6 test/typescript-validate.ts","start-fixtures-server":"octokit-fixtures-server"},"license":"MIT","files":["index.js","index.d.ts","lib","plugins"],"nyc":{"ignore":["test"]},"release":{"publish":["@semantic-release/npm",{"path":"@semantic-release/github","assets":["dist/*","!dist/*.map.gz"]}]},"bundlesize":[{"path":"./dist/octokit-rest.min.js.gz","maxSize":"33 kB"}],"_resolved":"https://registry.npmjs.org/@octokit/rest/-/rest-16.38.1.tgz","_integrity":"sha512-zyNFx+/Bd1EXt7LQjfrc6H4wryBQ/oDuZeZhGMBSFr1eMPFDmpEweFQR3R25zjKwBQpDY7L5GQO6A3XSaOfV1w==","_from":"@octokit/rest@16.38.1"}; +module.exports = {"name":"@octokit/rest","version":"16.43.1","publishConfig":{"access":"public"},"description":"GitHub REST API client for Node.js","keywords":["octokit","github","rest","api-client"],"author":"Gregor Martynus (https://github.com/gr2m)","contributors":[{"name":"Mike de Boer","email":"info@mikedeboer.nl"},{"name":"Fabian Jakobs","email":"fabian@c9.io"},{"name":"Joe Gallo","email":"joe@brassafrax.com"},{"name":"Gregor Martynus","url":"https://github.com/gr2m"}],"repository":"https://github.com/octokit/rest.js","dependencies":{"@octokit/auth-token":"^2.4.0","@octokit/plugin-paginate-rest":"^1.1.1","@octokit/plugin-request-log":"^1.0.0","@octokit/plugin-rest-endpoint-methods":"2.4.0","@octokit/request":"^5.2.0","@octokit/request-error":"^1.0.2","atob-lite":"^2.0.0","before-after-hook":"^2.0.0","btoa-lite":"^1.0.0","deprecation":"^2.0.0","lodash.get":"^4.4.2","lodash.set":"^4.3.2","lodash.uniq":"^4.5.0","octokit-pagination-methods":"^1.1.0","once":"^1.4.0","universal-user-agent":"^4.0.0"},"devDependencies":{"@gimenete/type-writer":"^0.1.3","@octokit/auth":"^1.1.1","@octokit/fixtures-server":"^5.0.6","@octokit/graphql":"^4.2.0","@types/node":"^13.1.0","bundlesize":"^0.18.0","chai":"^4.1.2","compression-webpack-plugin":"^3.1.0","cypress":"^3.0.0","glob":"^7.1.2","http-proxy-agent":"^4.0.0","lodash.camelcase":"^4.3.0","lodash.merge":"^4.6.1","lodash.upperfirst":"^4.3.1","lolex":"^5.1.2","mkdirp":"^1.0.0","mocha":"^7.0.1","mustache":"^4.0.0","nock":"^11.3.3","npm-run-all":"^4.1.2","nyc":"^15.0.0","prettier":"^1.14.2","proxy":"^1.0.0","semantic-release":"^17.0.0","sinon":"^8.0.0","sinon-chai":"^3.0.0","sort-keys":"^4.0.0","string-to-arraybuffer":"^1.0.0","string-to-jsdoc-comment":"^1.0.0","typescript":"^3.3.1","webpack":"^4.0.0","webpack-bundle-analyzer":"^3.0.0","webpack-cli":"^3.0.0"},"types":"index.d.ts","scripts":{"coverage":"nyc report --reporter=html && open coverage/index.html","lint":"prettier --check '{lib,plugins,scripts,test}/**/*.{js,json,ts}' 'docs/*.{js,json}' 'docs/src/**/*' index.js README.md package.json","lint:fix":"prettier --write '{lib,plugins,scripts,test}/**/*.{js,json,ts}' 'docs/*.{js,json}' 'docs/src/**/*' index.js README.md package.json","pretest":"npm run -s lint","test":"nyc mocha test/mocha-node-setup.js \"test/*/**/*-test.js\"","test:browser":"cypress run --browser chrome","build":"npm-run-all build:*","build:ts":"npm run -s update-endpoints:typescript","prebuild:browser":"mkdirp dist/","build:browser":"npm-run-all build:browser:*","build:browser:development":"webpack --mode development --entry . --output-library=Octokit --output=./dist/octokit-rest.js --profile --json > dist/bundle-stats.json","build:browser:production":"webpack --mode production --entry . --plugin=compression-webpack-plugin --output-library=Octokit --output-path=./dist --output-filename=octokit-rest.min.js --devtool source-map","generate-bundle-report":"webpack-bundle-analyzer dist/bundle-stats.json --mode=static --no-open --report dist/bundle-report.html","update-endpoints":"npm-run-all update-endpoints:*","update-endpoints:fetch-json":"node scripts/update-endpoints/fetch-json","update-endpoints:typescript":"node scripts/update-endpoints/typescript","prevalidate:ts":"npm run -s build:ts","validate:ts":"tsc --target es6 --noImplicitAny index.d.ts","postvalidate:ts":"tsc --noEmit --target es6 test/typescript-validate.ts","start-fixtures-server":"octokit-fixtures-server"},"license":"MIT","files":["index.js","index.d.ts","lib","plugins"],"nyc":{"ignore":["test"]},"release":{"publish":["@semantic-release/npm",{"path":"@semantic-release/github","assets":["dist/*","!dist/*.map.gz"]}]},"bundlesize":[{"path":"./dist/octokit-rest.min.js.gz","maxSize":"33 kB"}],"_resolved":"https://registry.npmjs.org/@octokit/rest/-/rest-16.43.1.tgz","_integrity":"sha512-gfFKwRT/wFxq5qlNjnW2dh+qh74XgTQ2B179UX5K1HYCluioWj8Ndbgqw2PVqa1NnVJkGHp2ovMpVn/DImlmkw==","_from":"@octokit/rest@16.43.1"}; /***/ }), /***/ 227: -/***/ (function(__unusedmodule, exports) { +/***/ (function(__unusedmodule, exports, __webpack_require__) { "use strict"; @@ -3187,7 +3372,18 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge step((generator = generator.apply(thisArg, _arguments || [])).next()); }); }; +var __importStar = (this && this.__importStar) || function (mod) { + if (mod && mod.__esModule) return mod; + var result = {}; + if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; + result["default"] = mod; + return result; +}; Object.defineProperty(exports, "__esModule", { value: true }); +const url_1 = __webpack_require__(835); +const core = __importStar(__webpack_require__(470)); +const github = __importStar(__webpack_require__(469)); +exports.tagsRefSpec = '+refs/tags/*:refs/tags/*'; function getCheckoutInfo(git, ref, commit) { return __awaiter(this, void 0, void 0, function* () { if (!git) { @@ -3234,6 +3430,15 @@ function getCheckoutInfo(git, ref, commit) { }); } exports.getCheckoutInfo = getCheckoutInfo; +function getRefSpecForAllHistory(ref, commit) { + const result = ['+refs/heads/*:refs/remotes/origin/*', exports.tagsRefSpec]; + if (ref && ref.toUpperCase().startsWith('REFS/PULL/')) { + const branch = ref.substring('refs/pull/'.length); + result.push(`+${commit || ref}:refs/remotes/pull/${branch}`); + } + return result; +} +exports.getRefSpecForAllHistory = getRefSpecForAllHistory; function getRefSpec(ref, commit) { if (!ref && !commit) { throw new Error('Args ref and commit cannot both be empty'); @@ -3283,19 +3488,128 @@ function getRefSpec(ref, commit) { } } exports.getRefSpec = getRefSpec; - - -/***/ }), - -/***/ 248: -/***/ (function(module, __unusedexports, __webpack_require__) { - -module.exports = octokitRegisterEndpoints; - -const registerEndpoints = __webpack_require__(899); - -function octokitRegisterEndpoints(octokit) { - octokit.registerEndpoints = registerEndpoints.bind(null, octokit); +/** + * Tests whether the initial fetch created the ref at the expected commit + */ +function testRef(git, ref, commit) { + return __awaiter(this, void 0, void 0, function* () { + if (!git) { + throw new Error('Arg git cannot be empty'); + } + if (!ref && !commit) { + throw new Error('Args ref and commit cannot both be empty'); + } + // No SHA? Nothing to test + if (!commit) { + return true; + } + // SHA only? + else if (!ref) { + return yield git.shaExists(commit); + } + const upperRef = ref.toUpperCase(); + // refs/heads/ + if (upperRef.startsWith('REFS/HEADS/')) { + const branch = ref.substring('refs/heads/'.length); + return ((yield git.branchExists(true, `origin/${branch}`)) && + commit === (yield git.revParse(`refs/remotes/origin/${branch}`))); + } + // refs/pull/ + else if (upperRef.startsWith('REFS/PULL/')) { + // Assume matches because fetched using the commit + return true; + } + // refs/tags/ + else if (upperRef.startsWith('REFS/TAGS/')) { + const tagName = ref.substring('refs/tags/'.length); + return ((yield git.tagExists(tagName)) && commit === (yield git.revParse(ref))); + } + // Unexpected + else { + core.debug(`Unexpected ref format '${ref}' when testing ref info`); + return true; + } + }); +} +exports.testRef = testRef; +function checkCommitInfo(token, commitInfo, repositoryOwner, repositoryName, ref, commit) { + return __awaiter(this, void 0, void 0, function* () { + try { + // GHES? + if (isGhes()) { + return; + } + // Auth token? + if (!token) { + return; + } + // Public PR synchronize, for workflow repo? + if (fromPayload('repository.private') !== false || + github.context.eventName !== 'pull_request' || + fromPayload('action') !== 'synchronize' || + repositoryOwner !== github.context.repo.owner || + repositoryName !== github.context.repo.repo || + ref !== github.context.ref || + !ref.startsWith('refs/pull/') || + commit !== github.context.sha) { + return; + } + // Head SHA + const expectedHeadSha = fromPayload('after'); + if (!expectedHeadSha) { + core.debug('Unable to determine head sha'); + return; + } + // Base SHA + const expectedBaseSha = fromPayload('pull_request.base.sha'); + if (!expectedBaseSha) { + core.debug('Unable to determine base sha'); + return; + } + // Expected message? + const expectedMessage = `Merge ${expectedHeadSha} into ${expectedBaseSha}`; + if (commitInfo.indexOf(expectedMessage) >= 0) { + return; + } + // Extract details from message + const match = commitInfo.match(/Merge ([0-9a-f]{40}) into ([0-9a-f]{40})/); + if (!match) { + core.debug('Unexpected message format'); + return; + } + // Post telemetry + const actualHeadSha = match[1]; + if (actualHeadSha !== expectedHeadSha) { + core.debug(`Expected head sha ${expectedHeadSha}; actual head sha ${actualHeadSha}`); + const octokit = new github.GitHub(token, { + userAgent: `actions-checkout-tracepoint/1.0 (code=STALE_MERGE;owner=${repositoryOwner};repo=${repositoryName};pr=${fromPayload('number')};run_id=${process.env['GITHUB_RUN_ID']};expected_head_sha=${expectedHeadSha};actual_head_sha=${actualHeadSha})` + }); + yield octokit.repos.get({ owner: repositoryOwner, repo: repositoryName }); + } + } + catch (err) { + core.debug(`Error when validating commit info: ${err.stack}`); + } + }); +} +exports.checkCommitInfo = checkCommitInfo; +function fromPayload(path) { + return select(github.context.payload, path); +} +function select(obj, path) { + if (!obj) { + return undefined; + } + const i = path.indexOf('.'); + if (i < 0) { + return obj[path]; + } + const key = path.substr(0, i); + return select(obj[key], path.substr(i + 1)); +} +function isGhes() { + const ghUrl = new url_1.URL(process.env['GITHUB_SERVER_URL'] || 'https://github.com'); + return ghUrl.hostname.toUpperCase() !== 'GITHUB.COM'; } @@ -5051,6 +5365,300 @@ function coerce (version) { } +/***/ }), + +/***/ 287: +/***/ (function(__unusedmodule, exports, __webpack_require__) { + +"use strict"; + +var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { + function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } + return new (P || (P = Promise))(function (resolve, reject) { + function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } + function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } + function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } + step((generator = generator.apply(thisArg, _arguments || [])).next()); + }); +}; +var __importStar = (this && this.__importStar) || function (mod) { + if (mod && mod.__esModule) return mod; + var result = {}; + if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; + result["default"] = mod; + return result; +}; +var __importDefault = (this && this.__importDefault) || function (mod) { + return (mod && mod.__esModule) ? mod : { "default": mod }; +}; +Object.defineProperty(exports, "__esModule", { value: true }); +const assert = __importStar(__webpack_require__(357)); +const core = __importStar(__webpack_require__(470)); +const exec = __importStar(__webpack_require__(986)); +const fs = __importStar(__webpack_require__(747)); +const io = __importStar(__webpack_require__(1)); +const os = __importStar(__webpack_require__(87)); +const path = __importStar(__webpack_require__(622)); +const regexpHelper = __importStar(__webpack_require__(528)); +const stateHelper = __importStar(__webpack_require__(153)); +const urlHelper = __importStar(__webpack_require__(81)); +const v4_1 = __importDefault(__webpack_require__(826)); +const IS_WINDOWS = process.platform === 'win32'; +const SSH_COMMAND_KEY = 'core.sshCommand'; +function createAuthHelper(git, settings) { + return new GitAuthHelper(git, settings); +} +exports.createAuthHelper = createAuthHelper; +class GitAuthHelper { + constructor(gitCommandManager, gitSourceSettings) { + this.sshCommand = ''; + this.sshKeyPath = ''; + this.sshKnownHostsPath = ''; + this.temporaryHomePath = ''; + this.git = gitCommandManager; + this.settings = gitSourceSettings || {}; + // Token auth header + const serverUrl = urlHelper.getServerUrl(); + this.tokenConfigKey = `http.${serverUrl.origin}/.extraheader`; // "origin" is SCHEME://HOSTNAME[:PORT] + const basicCredential = Buffer.from(`x-access-token:${this.settings.authToken}`, 'utf8').toString('base64'); + core.setSecret(basicCredential); + this.tokenPlaceholderConfigValue = `AUTHORIZATION: basic ***`; + this.tokenConfigValue = `AUTHORIZATION: basic ${basicCredential}`; + // Instead of SSH URL + this.insteadOfKey = `url.${serverUrl.origin}/.insteadOf`; // "origin" is SCHEME://HOSTNAME[:PORT] + this.insteadOfValue = `git@${serverUrl.hostname}:`; + } + configureAuth() { + return __awaiter(this, void 0, void 0, function* () { + // Remove possible previous values + yield this.removeAuth(); + // Configure new values + yield this.configureSsh(); + yield this.configureToken(); + }); + } + configureGlobalAuth() { + return __awaiter(this, void 0, void 0, function* () { + // Create a temp home directory + const runnerTemp = process.env['RUNNER_TEMP'] || ''; + assert.ok(runnerTemp, 'RUNNER_TEMP is not defined'); + const uniqueId = v4_1.default(); + this.temporaryHomePath = path.join(runnerTemp, uniqueId); + yield fs.promises.mkdir(this.temporaryHomePath, { recursive: true }); + // Copy the global git config + const gitConfigPath = path.join(process.env['HOME'] || os.homedir(), '.gitconfig'); + const newGitConfigPath = path.join(this.temporaryHomePath, '.gitconfig'); + let configExists = false; + try { + yield fs.promises.stat(gitConfigPath); + configExists = true; + } + catch (err) { + if (err.code !== 'ENOENT') { + throw err; + } + } + if (configExists) { + core.info(`Copying '${gitConfigPath}' to '${newGitConfigPath}'`); + yield io.cp(gitConfigPath, newGitConfigPath); + } + else { + yield fs.promises.writeFile(newGitConfigPath, ''); + } + try { + // Override HOME + core.info(`Temporarily overriding HOME='${this.temporaryHomePath}' before making global git config changes`); + this.git.setEnvironmentVariable('HOME', this.temporaryHomePath); + // Configure the token + yield this.configureToken(newGitConfigPath, true); + // Configure HTTPS instead of SSH + yield this.git.tryConfigUnset(this.insteadOfKey, true); + if (!this.settings.sshKey) { + yield this.git.config(this.insteadOfKey, this.insteadOfValue, true); + } + } + catch (err) { + // Unset in case somehow written to the real global config + core.info('Encountered an error when attempting to configure token. Attempting unconfigure.'); + yield this.git.tryConfigUnset(this.tokenConfigKey, true); + throw err; + } + }); + } + configureSubmoduleAuth() { + return __awaiter(this, void 0, void 0, function* () { + // Remove possible previous HTTPS instead of SSH + yield this.removeGitConfig(this.insteadOfKey, true); + if (this.settings.persistCredentials) { + // Configure a placeholder value. This approach avoids the credential being captured + // by process creation audit events, which are commonly logged. For more information, + // refer to https://docs.microsoft.com/en-us/windows-server/identity/ad-ds/manage/component-updates/command-line-process-auditing + const output = yield this.git.submoduleForeach(`git config --local '${this.tokenConfigKey}' '${this.tokenPlaceholderConfigValue}' && git config --local --show-origin --name-only --get-regexp remote.origin.url`, this.settings.nestedSubmodules); + // Replace the placeholder + const configPaths = output.match(/(?<=(^|\n)file:)[^\t]+(?=\tremote\.origin\.url)/g) || []; + for (const configPath of configPaths) { + core.debug(`Replacing token placeholder in '${configPath}'`); + this.replaceTokenPlaceholder(configPath); + } + if (this.settings.sshKey) { + // Configure core.sshCommand + yield this.git.submoduleForeach(`git config --local '${SSH_COMMAND_KEY}' '${this.sshCommand}'`, this.settings.nestedSubmodules); + } + else { + // Configure HTTPS instead of SSH + yield this.git.submoduleForeach(`git config --local '${this.insteadOfKey}' '${this.insteadOfValue}'`, this.settings.nestedSubmodules); + } + } + }); + } + removeAuth() { + return __awaiter(this, void 0, void 0, function* () { + yield this.removeSsh(); + yield this.removeToken(); + }); + } + removeGlobalAuth() { + return __awaiter(this, void 0, void 0, function* () { + core.debug(`Unsetting HOME override`); + this.git.removeEnvironmentVariable('HOME'); + yield io.rmRF(this.temporaryHomePath); + }); + } + configureSsh() { + return __awaiter(this, void 0, void 0, function* () { + if (!this.settings.sshKey) { + return; + } + // Write key + const runnerTemp = process.env['RUNNER_TEMP'] || ''; + assert.ok(runnerTemp, 'RUNNER_TEMP is not defined'); + const uniqueId = v4_1.default(); + this.sshKeyPath = path.join(runnerTemp, uniqueId); + stateHelper.setSshKeyPath(this.sshKeyPath); + yield fs.promises.mkdir(runnerTemp, { recursive: true }); + yield fs.promises.writeFile(this.sshKeyPath, this.settings.sshKey.trim() + '\n', { mode: 0o600 }); + // Remove inherited permissions on Windows + if (IS_WINDOWS) { + const icacls = yield io.which('icacls.exe'); + yield exec.exec(`"${icacls}" "${this.sshKeyPath}" /grant:r "${process.env['USERDOMAIN']}\\${process.env['USERNAME']}:F"`); + yield exec.exec(`"${icacls}" "${this.sshKeyPath}" /inheritance:r`); + } + // Write known hosts + const userKnownHostsPath = path.join(os.homedir(), '.ssh', 'known_hosts'); + let userKnownHosts = ''; + try { + userKnownHosts = (yield fs.promises.readFile(userKnownHostsPath)).toString(); + } + catch (err) { + if (err.code !== 'ENOENT') { + throw err; + } + } + let knownHosts = ''; + if (userKnownHosts) { + knownHosts += `# Begin from ${userKnownHostsPath}\n${userKnownHosts}\n# End from ${userKnownHostsPath}\n`; + } + if (this.settings.sshKnownHosts) { + knownHosts += `# Begin from input known hosts\n${this.settings.sshKnownHosts}\n# end from input known hosts\n`; + } + knownHosts += `# Begin implicitly added github.com\ngithub.com ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEAq2A7hRGmdnm9tUDbO9IDSwBK6TbQa+PXYPCPy6rbTrTtw7PHkccKrpp0yVhp5HdEIcKr6pLlVDBfOLX9QUsyCOV0wzfjIJNlGEYsdlLJizHhbn2mUjvSAHQqZETYP81eFzLQNnPHt4EVVUh7VfDESU84KezmD5QlWpXLmvU31/yMf+Se8xhHTvKSCZIFImWwoG6mbUoWf9nzpIoaSjB+weqqUUmpaaasXVal72J+UX2B+2RPW3RcT0eOzQgqlJL3RKrTJvdsjE3JEAvGq3lGHSZXy28G3skua2SmVi/w4yCE6gbODqnTWlg7+wC604ydGXA8VJiS5ap43JXiUFFAaQ==\n# End implicitly added github.com\n`; + this.sshKnownHostsPath = path.join(runnerTemp, `${uniqueId}_known_hosts`); + stateHelper.setSshKnownHostsPath(this.sshKnownHostsPath); + yield fs.promises.writeFile(this.sshKnownHostsPath, knownHosts); + // Configure GIT_SSH_COMMAND + const sshPath = yield io.which('ssh', true); + this.sshCommand = `"${sshPath}" -i "$RUNNER_TEMP/${path.basename(this.sshKeyPath)}"`; + if (this.settings.sshStrict) { + this.sshCommand += ' -o StrictHostKeyChecking=yes -o CheckHostIP=no'; + } + this.sshCommand += ` -o "UserKnownHostsFile=$RUNNER_TEMP/${path.basename(this.sshKnownHostsPath)}"`; + core.info(`Temporarily overriding GIT_SSH_COMMAND=${this.sshCommand}`); + this.git.setEnvironmentVariable('GIT_SSH_COMMAND', this.sshCommand); + // Configure core.sshCommand + if (this.settings.persistCredentials) { + yield this.git.config(SSH_COMMAND_KEY, this.sshCommand); + } + }); + } + configureToken(configPath, globalConfig) { + return __awaiter(this, void 0, void 0, function* () { + // Validate args + assert.ok((configPath && globalConfig) || (!configPath && !globalConfig), 'Unexpected configureToken parameter combinations'); + // Default config path + if (!configPath && !globalConfig) { + configPath = path.join(this.git.getWorkingDirectory(), '.git', 'config'); + } + // Configure a placeholder value. This approach avoids the credential being captured + // by process creation audit events, which are commonly logged. For more information, + // refer to https://docs.microsoft.com/en-us/windows-server/identity/ad-ds/manage/component-updates/command-line-process-auditing + yield this.git.config(this.tokenConfigKey, this.tokenPlaceholderConfigValue, globalConfig); + // Replace the placeholder + yield this.replaceTokenPlaceholder(configPath || ''); + }); + } + replaceTokenPlaceholder(configPath) { + return __awaiter(this, void 0, void 0, function* () { + assert.ok(configPath, 'configPath is not defined'); + let content = (yield fs.promises.readFile(configPath)).toString(); + const placeholderIndex = content.indexOf(this.tokenPlaceholderConfigValue); + if (placeholderIndex < 0 || + placeholderIndex != content.lastIndexOf(this.tokenPlaceholderConfigValue)) { + throw new Error(`Unable to replace auth placeholder in ${configPath}`); + } + assert.ok(this.tokenConfigValue, 'tokenConfigValue is not defined'); + content = content.replace(this.tokenPlaceholderConfigValue, this.tokenConfigValue); + yield fs.promises.writeFile(configPath, content); + }); + } + removeSsh() { + return __awaiter(this, void 0, void 0, function* () { + // SSH key + const keyPath = this.sshKeyPath || stateHelper.SshKeyPath; + if (keyPath) { + try { + yield io.rmRF(keyPath); + } + catch (err) { + core.debug(err.message); + core.warning(`Failed to remove SSH key '${keyPath}'`); + } + } + // SSH known hosts + const knownHostsPath = this.sshKnownHostsPath || stateHelper.SshKnownHostsPath; + if (knownHostsPath) { + try { + yield io.rmRF(knownHostsPath); + } + catch (_a) { + // Intentionally empty + } + } + // SSH command + yield this.removeGitConfig(SSH_COMMAND_KEY); + }); + } + removeToken() { + return __awaiter(this, void 0, void 0, function* () { + // HTTP extra header + yield this.removeGitConfig(this.tokenConfigKey); + }); + } + removeGitConfig(configKey, submoduleOnly = false) { + return __awaiter(this, void 0, void 0, function* () { + if (!submoduleOnly) { + if ((yield this.git.configExists(configKey)) && + !(yield this.git.tryConfigUnset(configKey))) { + // Load the config contents + core.warning(`Failed to remove '${configKey}' from the git config`); + } + } + const pattern = regexpHelper.escape(configKey); + yield this.git.submoduleForeach(`git config --local --name-only --get-regexp '${pattern}' && git config --local --unset-all '${configKey}' || :`, true); + }); + } +} + + /***/ }), /***/ 289: @@ -5080,17 +5688,19 @@ const exec = __importStar(__webpack_require__(986)); const fshelper = __importStar(__webpack_require__(618)); const io = __importStar(__webpack_require__(1)); const path = __importStar(__webpack_require__(622)); +const refHelper = __importStar(__webpack_require__(227)); +const regexpHelper = __importStar(__webpack_require__(528)); const retryHelper = __importStar(__webpack_require__(587)); const git_version_1 = __webpack_require__(559); // Auth header not supported before 2.9 // Wire protocol v2 not supported before 2.18 exports.MinimumGitVersion = new git_version_1.GitVersion('2.18'); -function CreateCommandManager(workingDirectory, lfs) { +function createCommandManager(workingDirectory, lfs) { return __awaiter(this, void 0, void 0, function* () { return yield GitCommandManager.createCommandManager(workingDirectory, lfs); }); } -exports.CreateCommandManager = CreateCommandManager; +exports.createCommandManager = createCommandManager; class GitCommandManager { // Private constructor; use createCommandManager() constructor() { @@ -5171,32 +5781,37 @@ class GitCommandManager { yield this.execGit(args); }); } - config(configKey, configValue) { + config(configKey, configValue, globalConfig) { return __awaiter(this, void 0, void 0, function* () { - yield this.execGit(['config', '--local', configKey, configValue]); + yield this.execGit([ + 'config', + globalConfig ? '--global' : '--local', + configKey, + configValue + ]); }); } - configExists(configKey) { + configExists(configKey, globalConfig) { return __awaiter(this, void 0, void 0, function* () { - const pattern = configKey.replace(/[^a-zA-Z0-9_]/g, x => { - return `\\${x}`; - }); - const output = yield this.execGit(['config', '--local', '--name-only', '--get-regexp', pattern], true); + const pattern = regexpHelper.escape(configKey); + const output = yield this.execGit([ + 'config', + globalConfig ? '--global' : '--local', + '--name-only', + '--get-regexp', + pattern + ], true); return output.exitCode === 0; }); } - fetch(fetchDepth, refSpec) { + fetch(refSpec, fetchDepth) { return __awaiter(this, void 0, void 0, function* () { - const args = [ - '-c', - 'protocol.version=2', - 'fetch', - '--no-tags', - '--prune', - '--progress', - '--no-recurse-submodules' - ]; - if (fetchDepth > 0) { + const args = ['-c', 'protocol.version=2', 'fetch']; + if (!refSpec.some(x => x === refHelper.tagsRefSpec)) { + args.push('--no-tags'); + } + args.push('--prune', '--progress', '--no-recurse-submodules'); + if (fetchDepth && fetchDepth > 0) { args.push(`--depth=${fetchDepth}`); } else if (fshelper.fileExistsSync(path.join(this.workingDirectory, '.git', 'shallow'))) { @@ -5212,6 +5827,33 @@ class GitCommandManager { })); }); } + getDefaultBranch(repositoryUrl) { + return __awaiter(this, void 0, void 0, function* () { + let output; + yield retryHelper.execute(() => __awaiter(this, void 0, void 0, function* () { + output = yield this.execGit([ + 'ls-remote', + '--quiet', + '--exit-code', + '--symref', + repositoryUrl, + 'HEAD' + ]); + })); + if (output) { + // Satisfy compiler, will always be set + for (let line of output.stdout.trim().split('\n')) { + line = line.trim(); + if (line.startsWith('ref:') || line.endsWith('HEAD')) { + return line + .substr('ref:'.length, line.length - 'ref:'.length - 'HEAD'.length) + .trim(); + } + } + } + throw new Error('Unexpected output when retrieving default branch'); + }); + } getWorkingDirectory() { return this.workingDirectory; } @@ -5243,7 +5885,8 @@ class GitCommandManager { } log1() { return __awaiter(this, void 0, void 0, function* () { - yield this.execGit(['log', '-1']); + const output = yield this.execGit(['log', '-1']); + return output.stdout; }); } remoteAdd(remoteName, remoteUrl) { @@ -5251,6 +5894,64 @@ class GitCommandManager { yield this.execGit(['remote', 'add', remoteName, remoteUrl]); }); } + removeEnvironmentVariable(name) { + delete this.gitEnv[name]; + } + /** + * Resolves a ref to a SHA. For a branch or lightweight tag, the commit SHA is returned. + * For an annotated tag, the tag SHA is returned. + * @param {string} ref For example: 'refs/heads/master' or '/refs/tags/v1' + * @returns {Promise} + */ + revParse(ref) { + return __awaiter(this, void 0, void 0, function* () { + const output = yield this.execGit(['rev-parse', ref]); + return output.stdout.trim(); + }); + } + setEnvironmentVariable(name, value) { + this.gitEnv[name] = value; + } + shaExists(sha) { + return __awaiter(this, void 0, void 0, function* () { + const args = ['rev-parse', '--verify', '--quiet', `${sha}^{object}`]; + const output = yield this.execGit(args, true); + return output.exitCode === 0; + }); + } + submoduleForeach(command, recursive) { + return __awaiter(this, void 0, void 0, function* () { + const args = ['submodule', 'foreach']; + if (recursive) { + args.push('--recursive'); + } + args.push(command); + const output = yield this.execGit(args); + return output.stdout; + }); + } + submoduleSync(recursive) { + return __awaiter(this, void 0, void 0, function* () { + const args = ['submodule', 'sync']; + if (recursive) { + args.push('--recursive'); + } + yield this.execGit(args); + }); + } + submoduleUpdate(fetchDepth, recursive) { + return __awaiter(this, void 0, void 0, function* () { + const args = ['-c', 'protocol.version=2']; + args.push('submodule', 'update', '--init', '--force'); + if (fetchDepth > 0) { + args.push(`--depth=${fetchDepth}`); + } + if (recursive) { + args.push('--recursive'); + } + yield this.execGit(args); + }); + } tagExists(pattern) { return __awaiter(this, void 0, void 0, function* () { const output = yield this.execGit(['tag', '--list', pattern]); @@ -5263,9 +5964,14 @@ class GitCommandManager { return output.exitCode === 0; }); } - tryConfigUnset(configKey) { + tryConfigUnset(configKey, globalConfig) { return __awaiter(this, void 0, void 0, function* () { - const output = yield this.execGit(['config', '--local', '--unset-all', configKey], true); + const output = yield this.execGit([ + 'config', + globalConfig ? '--global' : '--local', + '--unset-all', + configKey + ], true); return output.exitCode === 0; }); } @@ -5420,21 +6126,21 @@ var __importStar = (this && this.__importStar) || function (mod) { }; Object.defineProperty(exports, "__esModule", { value: true }); const core = __importStar(__webpack_require__(470)); -const fs = __importStar(__webpack_require__(747)); const fsHelper = __importStar(__webpack_require__(618)); +const gitAuthHelper = __importStar(__webpack_require__(287)); const gitCommandManager = __importStar(__webpack_require__(289)); +const gitDirectoryHelper = __importStar(__webpack_require__(438)); const githubApiHelper = __importStar(__webpack_require__(464)); const io = __importStar(__webpack_require__(1)); const path = __importStar(__webpack_require__(622)); const refHelper = __importStar(__webpack_require__(227)); const stateHelper = __importStar(__webpack_require__(153)); -const serverUrl = 'https://github.com/'; -const authConfigKey = `http.${serverUrl}.extraheader`; +const urlHelper = __importStar(__webpack_require__(81)); function getSource(settings) { return __awaiter(this, void 0, void 0, function* () { // Repository URL core.info(`Syncing repository: ${settings.repositoryOwner}/${settings.repositoryName}`); - const repositoryUrl = `https://github.com/${encodeURIComponent(settings.repositoryOwner)}/${encodeURIComponent(settings.repositoryName)}`; + const repositoryUrl = urlHelper.getFetchUrl(settings); // Remove conflicting file path if (fsHelper.fileExistsSync(settings.repositoryPath)) { yield io.rmRF(settings.repositoryPath); @@ -5446,58 +6152,132 @@ function getSource(settings) { yield io.mkdirP(settings.repositoryPath); } // Git command manager + core.startGroup('Getting Git version info'); const git = yield getGitCommandManager(settings); + core.endGroup(); // Prepare existing directory, otherwise recreate if (isExisting) { - yield prepareExistingDirectory(git, settings.repositoryPath, repositoryUrl, settings.clean); + yield gitDirectoryHelper.prepareExistingDirectory(git, settings.repositoryPath, repositoryUrl, settings.clean, settings.ref); } if (!git) { // Downloading using REST API core.info(`The repository will be downloaded using the GitHub REST API`); core.info(`To create a local Git repository instead, add Git ${gitCommandManager.MinimumGitVersion} or higher to the PATH`); + if (settings.submodules) { + throw new Error(`Input 'submodules' not supported when falling back to download using the GitHub REST API. To create a local Git repository instead, add Git ${gitCommandManager.MinimumGitVersion} or higher to the PATH.`); + } + else if (settings.sshKey) { + throw new Error(`Input 'ssh-key' not supported when falling back to download using the GitHub REST API. To create a local Git repository instead, add Git ${gitCommandManager.MinimumGitVersion} or higher to the PATH.`); + } yield githubApiHelper.downloadRepository(settings.authToken, settings.repositoryOwner, settings.repositoryName, settings.ref, settings.commit, settings.repositoryPath); + return; } - else { - // Save state for POST action - stateHelper.setRepositoryPath(settings.repositoryPath); - // Initialize the repository - if (!fsHelper.directoryExistsSync(path.join(settings.repositoryPath, '.git'))) { - yield git.init(); - yield git.remoteAdd('origin', repositoryUrl); - } - // Disable automatic garbage collection - if (!(yield git.tryDisableAutomaticGarbageCollection())) { - core.warning(`Unable to turn off git automatic garbage collection. The git fetch operation may trigger garbage collection and cause a delay.`); - } - // Remove possible previous extraheader - yield removeGitConfig(git, authConfigKey); - try { - // Config extraheader - yield configureAuthToken(git, settings.authToken); - // LFS install - if (settings.lfs) { - yield git.lfsInstall(); + // Save state for POST action + stateHelper.setRepositoryPath(settings.repositoryPath); + // Initialize the repository + if (!fsHelper.directoryExistsSync(path.join(settings.repositoryPath, '.git'))) { + core.startGroup('Initializing the repository'); + yield git.init(); + yield git.remoteAdd('origin', repositoryUrl); + core.endGroup(); + } + // Disable automatic garbage collection + core.startGroup('Disabling automatic garbage collection'); + if (!(yield git.tryDisableAutomaticGarbageCollection())) { + core.warning(`Unable to turn off git automatic garbage collection. The git fetch operation may trigger garbage collection and cause a delay.`); + } + core.endGroup(); + const authHelper = gitAuthHelper.createAuthHelper(git, settings); + try { + // Configure auth + core.startGroup('Setting up auth'); + yield authHelper.configureAuth(); + core.endGroup(); + // Determine the default branch + if (!settings.ref && !settings.commit) { + core.startGroup('Determining the default branch'); + if (settings.sshKey) { + settings.ref = yield git.getDefaultBranch(repositoryUrl); } - // Fetch + else { + settings.ref = yield githubApiHelper.getDefaultBranch(settings.authToken, settings.repositoryOwner, settings.repositoryName); + } + core.endGroup(); + } + // LFS install + if (settings.lfs) { + yield git.lfsInstall(); + } + // Fetch + core.startGroup('Fetching the repository'); + if (settings.fetchDepth <= 0) { + // Fetch all branches and tags + let refSpec = refHelper.getRefSpecForAllHistory(settings.ref, settings.commit); + yield git.fetch(refSpec); + // When all history is fetched, the ref we're interested in may have moved to a different + // commit (push or force push). If so, fetch again with a targeted refspec. + if (!(yield refHelper.testRef(git, settings.ref, settings.commit))) { + refSpec = refHelper.getRefSpec(settings.ref, settings.commit); + yield git.fetch(refSpec); + } + } + else { const refSpec = refHelper.getRefSpec(settings.ref, settings.commit); - yield git.fetch(settings.fetchDepth, refSpec); - // Checkout info - const checkoutInfo = yield refHelper.getCheckoutInfo(git, settings.ref, settings.commit); - // LFS fetch - // Explicit lfs-fetch to avoid slow checkout (fetches one lfs object at a time). - // Explicit lfs fetch will fetch lfs objects in parallel. - if (settings.lfs) { - yield git.lfsFetch(checkoutInfo.startPoint || checkoutInfo.ref); - } - // Checkout - yield git.checkout(checkoutInfo.ref, checkoutInfo.startPoint); - // Dump some info about the checked out commit - yield git.log1(); + yield git.fetch(refSpec, settings.fetchDepth); } - finally { - if (!settings.persistCredentials) { - yield removeGitConfig(git, authConfigKey); + core.endGroup(); + // Checkout info + core.startGroup('Determining the checkout info'); + const checkoutInfo = yield refHelper.getCheckoutInfo(git, settings.ref, settings.commit); + core.endGroup(); + // LFS fetch + // Explicit lfs-fetch to avoid slow checkout (fetches one lfs object at a time). + // Explicit lfs fetch will fetch lfs objects in parallel. + if (settings.lfs) { + core.startGroup('Fetching LFS objects'); + yield git.lfsFetch(checkoutInfo.startPoint || checkoutInfo.ref); + core.endGroup(); + } + // Checkout + core.startGroup('Checking out the ref'); + yield git.checkout(checkoutInfo.ref, checkoutInfo.startPoint); + core.endGroup(); + // Submodules + if (settings.submodules) { + try { + // Temporarily override global config + core.startGroup('Setting up auth for fetching submodules'); + yield authHelper.configureGlobalAuth(); + core.endGroup(); + // Checkout submodules + core.startGroup('Fetching submodules'); + yield git.submoduleSync(settings.nestedSubmodules); + yield git.submoduleUpdate(settings.fetchDepth, settings.nestedSubmodules); + yield git.submoduleForeach('git config --local gc.auto 0', settings.nestedSubmodules); + core.endGroup(); + // Persist credentials + if (settings.persistCredentials) { + core.startGroup('Persisting credentials for submodules'); + yield authHelper.configureSubmoduleAuth(); + core.endGroup(); + } } + finally { + // Remove temporary global config override + yield authHelper.removeGlobalAuth(); + } + } + // Dump some info about the checked out commit + const commitInfo = yield git.log1(); + // Check for incorrect pull request merge commit + yield refHelper.checkCommitInfo(settings.authToken, commitInfo, settings.repositoryOwner, settings.repositoryName, settings.ref, settings.commit); + } + finally { + // Remove auth + if (!settings.persistCredentials) { + core.startGroup('Removing auth'); + yield authHelper.removeAuth(); + core.endGroup(); } } }); @@ -5512,22 +6292,22 @@ function cleanup(repositoryPath) { } let git; try { - git = yield gitCommandManager.CreateCommandManager(repositoryPath, false); + git = yield gitCommandManager.createCommandManager(repositoryPath, false); } catch (_a) { return; } - // Remove extraheader - yield removeGitConfig(git, authConfigKey); + // Remove auth + const authHelper = gitAuthHelper.createAuthHelper(git); + yield authHelper.removeAuth(); }); } exports.cleanup = cleanup; function getGitCommandManager(settings) { return __awaiter(this, void 0, void 0, function* () { core.info(`Working directory is '${settings.repositoryPath}'`); - let git = null; try { - return yield gitCommandManager.CreateCommandManager(settings.repositoryPath, settings.lfs); + return yield gitCommandManager.createCommandManager(settings.repositoryPath, settings.lfs); } catch (err) { // Git is required for LFS @@ -5535,108 +6315,7 @@ function getGitCommandManager(settings) { throw err; } // Otherwise fallback to REST API - return null; - } - }); -} -function prepareExistingDirectory(git, repositoryPath, repositoryUrl, clean) { - return __awaiter(this, void 0, void 0, function* () { - let remove = false; - // Check whether using git or REST API - if (!git) { - remove = true; - } - // Fetch URL does not match - else if (!fsHelper.directoryExistsSync(path.join(repositoryPath, '.git')) || - repositoryUrl !== (yield git.tryGetFetchUrl())) { - remove = true; - } - else { - // Delete any index.lock and shallow.lock left by a previously canceled run or crashed git process - const lockPaths = [ - path.join(repositoryPath, '.git', 'index.lock'), - path.join(repositoryPath, '.git', 'shallow.lock') - ]; - for (const lockPath of lockPaths) { - try { - yield io.rmRF(lockPath); - } - catch (error) { - core.debug(`Unable to delete '${lockPath}'. ${error.message}`); - } - } - try { - // Checkout detached HEAD - if (!(yield git.isDetached())) { - yield git.checkoutDetach(); - } - // Remove all refs/heads/* - let branches = yield git.branchList(false); - for (const branch of branches) { - yield git.branchDelete(false, branch); - } - // Remove all refs/remotes/origin/* to avoid conflicts - branches = yield git.branchList(true); - for (const branch of branches) { - yield git.branchDelete(true, branch); - } - // Clean - if (clean) { - if (!(yield git.tryClean())) { - core.debug(`The clean command failed. This might be caused by: 1) path too long, 2) permission issue, or 3) file in use. For futher investigation, manually run 'git clean -ffdx' on the directory '${repositoryPath}'.`); - remove = true; - } - else if (!(yield git.tryReset())) { - remove = true; - } - if (remove) { - core.warning(`Unable to clean or reset the repository. The repository will be recreated instead.`); - } - } - } - catch (error) { - core.warning(`Unable to prepare the existing repository. The repository will be recreated instead.`); - remove = true; - } - } - if (remove) { - // Delete the contents of the directory. Don't delete the directory itself - // since it might be the current working directory. - core.info(`Deleting the contents of '${repositoryPath}'`); - for (const file of yield fs.promises.readdir(repositoryPath)) { - yield io.rmRF(path.join(repositoryPath, file)); - } - } - }); -} -function configureAuthToken(git, authToken) { - return __awaiter(this, void 0, void 0, function* () { - // Configure a placeholder value. This approach avoids the credential being captured - // by process creation audit events, which are commonly logged. For more information, - // refer to https://docs.microsoft.com/en-us/windows-server/identity/ad-ds/manage/component-updates/command-line-process-auditing - const placeholder = `AUTHORIZATION: basic ***`; - yield git.config(authConfigKey, placeholder); - // Determine the basic credential value - const basicCredential = Buffer.from(`x-access-token:${authToken}`, 'utf8').toString('base64'); - core.setSecret(basicCredential); - // Replace the value in the config file - const configPath = path.join(git.getWorkingDirectory(), '.git', 'config'); - let content = (yield fs.promises.readFile(configPath)).toString(); - const placeholderIndex = content.indexOf(placeholder); - if (placeholderIndex < 0 || - placeholderIndex != content.lastIndexOf(placeholder)) { - throw new Error('Unable to replace auth placeholder in .git/config'); - } - content = content.replace(placeholder, `AUTHORIZATION: basic ${basicCredential}`); - yield fs.promises.writeFile(configPath, content); - }); -} -function removeGitConfig(git, configKey) { - return __awaiter(this, void 0, void 0, function* () { - if ((yield git.configExists(configKey)) && - !(yield git.tryConfigUnset(configKey))) { - // Load the config contents - core.warning(`Failed to remove '${configKey}' from the git config`); + return undefined; } }); } @@ -5762,8 +6441,15 @@ module.exports = class HttpError extends Error { /***/ }), -/***/ 301: -/***/ (function(module, __unusedexports, __webpack_require__) { +/***/ 299: +/***/ (function(__unusedmodule, exports) { + +"use strict"; + + +Object.defineProperty(exports, '__esModule', { value: true }); + +const VERSION = "1.1.2"; /** * Some “list” response that can be paginated have a different response structure @@ -5777,7 +6463,6 @@ module.exports = class HttpError extends Error { * - https://developer.github.com/v3/checks/suites/#response-1 (key: `check_suites`) * - https://developer.github.com/v3/apps/installations/#list-repositories (key: `repositories`) * - https://developer.github.com/v3/apps/installations/#list-installations-for-a-user (key `installations`) - * - https://developer.github.com/v3/orgs/#list-installations-for-an-organization (key `installations`) * * Octokit normalizes these responses so that paginated results are always returned following * the same structure. One challenge is that if the list response has only one page, no Link @@ -5786,102 +6471,123 @@ module.exports = class HttpError extends Error { * paths has to be added in order to normalize the response. We cannot check for the total_count * property because it also exists in the response of Get the combined status for a specific ref. */ - -module.exports = normalizePaginatedListResponse; - -const { Deprecation } = __webpack_require__(692); -const once = __webpack_require__(969); - -const deprecateIncompleteResults = once((log, deprecation) => - log.warn(deprecation) -); -const deprecateTotalCount = once((log, deprecation) => log.warn(deprecation)); -const deprecateNamespace = once((log, deprecation) => log.warn(deprecation)); - -const REGEX_IS_SEARCH_PATH = /^\/search\//; -const REGEX_IS_CHECKS_PATH = /^\/repos\/[^/]+\/[^/]+\/commits\/[^/]+\/(check-runs|check-suites)/; -const REGEX_IS_INSTALLATION_REPOSITORIES_PATH = /^\/installation\/repositories/; -const REGEX_IS_USER_INSTALLATIONS_PATH = /^\/user\/installations/; -const REGEX_IS_ORG_INSTALLATIONS_PATH = /^\/orgs\/[^/]+\/installations/; - +const REGEX = [/^\/search\//, /^\/repos\/[^/]+\/[^/]+\/commits\/[^/]+\/(check-runs|check-suites)([^/]|$)/, /^\/installation\/repositories([^/]|$)/, /^\/user\/installations([^/]|$)/, /^\/repos\/[^/]+\/[^/]+\/actions\/secrets([^/]|$)/, /^\/repos\/[^/]+\/[^/]+\/actions\/workflows(\/[^/]+\/runs)?([^/]|$)/, /^\/repos\/[^/]+\/[^/]+\/actions\/runs(\/[^/]+\/(artifacts|jobs))?([^/]|$)/]; function normalizePaginatedListResponse(octokit, url, response) { const path = url.replace(octokit.request.endpoint.DEFAULTS.baseUrl, ""); - if ( - !REGEX_IS_SEARCH_PATH.test(path) && - !REGEX_IS_CHECKS_PATH.test(path) && - !REGEX_IS_INSTALLATION_REPOSITORIES_PATH.test(path) && - !REGEX_IS_USER_INSTALLATIONS_PATH.test(path) && - !REGEX_IS_ORG_INSTALLATIONS_PATH.test(path) - ) { - return; - } + const responseNeedsNormalization = REGEX.find(regex => regex.test(path)); + if (!responseNeedsNormalization) return; // keep the additional properties intact as there is currently no other way + // to retrieve the same information. - // keep the additional properties intact to avoid a breaking change, - // but log a deprecation warning when accessed const incompleteResults = response.data.incomplete_results; const repositorySelection = response.data.repository_selection; const totalCount = response.data.total_count; delete response.data.incomplete_results; delete response.data.repository_selection; delete response.data.total_count; - const namespaceKey = Object.keys(response.data)[0]; - - response.data = response.data[namespaceKey]; - - Object.defineProperty(response.data, namespaceKey, { - get() { - deprecateNamespace( - octokit.log, - new Deprecation( - `[@octokit/rest] "result.data.${namespaceKey}" is deprecated. Use "result.data" instead` - ) - ); - return response.data; - } - }); + const data = response.data[namespaceKey]; + response.data = data; if (typeof incompleteResults !== "undefined") { - Object.defineProperty(response.data, "incomplete_results", { - get() { - deprecateIncompleteResults( - octokit.log, - new Deprecation( - '[@octokit/rest] "result.data.incomplete_results" is deprecated.' - ) - ); - return incompleteResults; - } - }); + response.data.incomplete_results = incompleteResults; } if (typeof repositorySelection !== "undefined") { - Object.defineProperty(response.data, "repository_selection", { - get() { - deprecateTotalCount( - octokit.log, - new Deprecation( - '[@octokit/rest] "result.data.repository_selection" is deprecated.' - ) - ); - return repositorySelection; - } - }); + response.data.repository_selection = repositorySelection; } - Object.defineProperty(response.data, "total_count", { + response.data.total_count = totalCount; + Object.defineProperty(response.data, namespaceKey, { get() { - deprecateTotalCount( - octokit.log, - new Deprecation( - '[@octokit/rest] "result.data.total_count" is deprecated.' - ) - ); - return totalCount; + octokit.log.warn(`[@octokit/paginate-rest] "response.data.${namespaceKey}" is deprecated for "GET ${path}". Get the results directly from "response.data"`); + return Array.from(data); } + }); } +function iterator(octokit, route, parameters) { + const options = octokit.request.endpoint(route, parameters); + const method = options.method; + const headers = options.headers; + let url = options.url; + return { + [Symbol.asyncIterator]: () => ({ + next() { + if (!url) { + return Promise.resolve({ + done: true + }); + } + + return octokit.request({ + method, + url, + headers + }).then(response => { + normalizePaginatedListResponse(octokit, url, response); // `response.headers.link` format: + // '; rel="next", ; rel="last"' + // sets `url` to undefined if "next" URL is not present or `link` header is not set + + url = ((response.headers.link || "").match(/<([^>]+)>;\s*rel="next"/) || [])[1]; + return { + value: response + }; + }); + } + + }) + }; +} + +function paginate(octokit, route, parameters, mapFn) { + if (typeof parameters === "function") { + mapFn = parameters; + parameters = undefined; + } + + return gather(octokit, [], iterator(octokit, route, parameters)[Symbol.asyncIterator](), mapFn); +} + +function gather(octokit, results, iterator, mapFn) { + return iterator.next().then(result => { + if (result.done) { + return results; + } + + let earlyExit = false; + + function done() { + earlyExit = true; + } + + results = results.concat(mapFn ? mapFn(result.value, done) : result.value.data); + + if (earlyExit) { + return results; + } + + return gather(octokit, results, iterator, mapFn); + }); +} + +/** + * @param octokit Octokit instance + * @param options Options passed to Octokit constructor + */ + +function paginateRest(octokit) { + return { + paginate: Object.assign(paginate.bind(null, octokit), { + iterator: iterator.bind(null, octokit) + }) + }; +} +paginateRest.VERSION = VERSION; + +exports.paginateRest = paginateRest; +//# sourceMappingURL=index.js.map + /***/ }), @@ -5946,7 +6652,7 @@ function hasLastPage (link) { module.exports = validate; -const { RequestError } = __webpack_require__(463); +const { RequestError } = __webpack_require__(497); const get = __webpack_require__(854); const set = __webpack_require__(883); @@ -6102,7 +6808,7 @@ function validate(octokit, options) { module.exports = authenticationRequestError; -const { RequestError } = __webpack_require__(463); +const { RequestError } = __webpack_require__(497); function authenticationRequestError(state, error, options) { /* istanbul ignore next */ @@ -6228,41 +6934,6 @@ function deprecate (message) { } -/***/ }), - -/***/ 372: -/***/ (function(module) { - -module.exports = octokitDebug; - -function octokitDebug(octokit) { - octokit.hook.wrap("request", (request, options) => { - octokit.log.debug("request", options); - const start = Date.now(); - const requestOptions = octokit.request.endpoint.parse(options); - const path = requestOptions.url.replace(options.baseUrl, ""); - - return request(options) - .then(response => { - octokit.log.info( - `${requestOptions.method} ${path} - ${ - response.status - } in ${Date.now() - start}ms` - ); - return response; - }) - - .catch(error => { - octokit.log.info( - `${requestOptions.method} ${path} - ${error.status} in ${Date.now() - - start}ms` - ); - throw error; - }); - }); -} - - /***/ }), /***/ 385: @@ -6276,7 +6947,7 @@ Object.defineProperty(exports, '__esModule', { value: true }); function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'default' in ex) ? ex['default'] : ex; } var isPlainObject = _interopDefault(__webpack_require__(696)); -var universalUserAgent = __webpack_require__(796); +var universalUserAgent = __webpack_require__(562); function lowercaseKeys(object) { if (!object) { @@ -6626,7 +7297,7 @@ function withDefaults(oldDefaults, newDefaults) { }); } -const VERSION = "5.5.1"; +const VERSION = "6.0.1"; const userAgent = `octokit-endpoint.js/${VERSION} ${universalUserAgent.getUserAgent()}`; // DEFAULTS has all properties set that EndpointOptions has, except url. // So we use RequestParameters and add method as additional required property. @@ -6874,13 +7545,137 @@ function escape(s) { } //# sourceMappingURL=command.js.map +/***/ }), + +/***/ 438: +/***/ (function(__unusedmodule, exports, __webpack_require__) { + +"use strict"; + +var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { + function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } + return new (P || (P = Promise))(function (resolve, reject) { + function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } + function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } + function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } + step((generator = generator.apply(thisArg, _arguments || [])).next()); + }); +}; +var __importStar = (this && this.__importStar) || function (mod) { + if (mod && mod.__esModule) return mod; + var result = {}; + if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k]; + result["default"] = mod; + return result; +}; +Object.defineProperty(exports, "__esModule", { value: true }); +const assert = __importStar(__webpack_require__(357)); +const core = __importStar(__webpack_require__(470)); +const fs = __importStar(__webpack_require__(747)); +const fsHelper = __importStar(__webpack_require__(618)); +const io = __importStar(__webpack_require__(1)); +const path = __importStar(__webpack_require__(622)); +function prepareExistingDirectory(git, repositoryPath, repositoryUrl, clean, ref) { + return __awaiter(this, void 0, void 0, function* () { + assert.ok(repositoryPath, 'Expected repositoryPath to be defined'); + assert.ok(repositoryUrl, 'Expected repositoryUrl to be defined'); + // Indicates whether to delete the directory contents + let remove = false; + // Check whether using git or REST API + if (!git) { + remove = true; + } + // Fetch URL does not match + else if (!fsHelper.directoryExistsSync(path.join(repositoryPath, '.git')) || + repositoryUrl !== (yield git.tryGetFetchUrl())) { + remove = true; + } + else { + // Delete any index.lock and shallow.lock left by a previously canceled run or crashed git process + const lockPaths = [ + path.join(repositoryPath, '.git', 'index.lock'), + path.join(repositoryPath, '.git', 'shallow.lock') + ]; + for (const lockPath of lockPaths) { + try { + yield io.rmRF(lockPath); + } + catch (error) { + core.debug(`Unable to delete '${lockPath}'. ${error.message}`); + } + } + try { + core.startGroup('Removing previously created refs, to avoid conflicts'); + // Checkout detached HEAD + if (!(yield git.isDetached())) { + yield git.checkoutDetach(); + } + // Remove all refs/heads/* + let branches = yield git.branchList(false); + for (const branch of branches) { + yield git.branchDelete(false, branch); + } + // Remove any conflicting refs/remotes/origin/* + // Example 1: Consider ref is refs/heads/foo and previously fetched refs/remotes/origin/foo/bar + // Example 2: Consider ref is refs/heads/foo/bar and previously fetched refs/remotes/origin/foo + if (ref) { + ref = ref.startsWith('refs/') ? ref : `refs/heads/${ref}`; + if (ref.startsWith('refs/heads/')) { + const upperName1 = ref.toUpperCase().substr('REFS/HEADS/'.length); + const upperName1Slash = `${upperName1}/`; + branches = yield git.branchList(true); + for (const branch of branches) { + const upperName2 = branch.substr('origin/'.length).toUpperCase(); + const upperName2Slash = `${upperName2}/`; + if (upperName1.startsWith(upperName2Slash) || + upperName2.startsWith(upperName1Slash)) { + yield git.branchDelete(true, branch); + } + } + } + } + core.endGroup(); + // Clean + if (clean) { + core.startGroup('Cleaning the repository'); + if (!(yield git.tryClean())) { + core.debug(`The clean command failed. This might be caused by: 1) path too long, 2) permission issue, or 3) file in use. For futher investigation, manually run 'git clean -ffdx' on the directory '${repositoryPath}'.`); + remove = true; + } + else if (!(yield git.tryReset())) { + remove = true; + } + core.endGroup(); + if (remove) { + core.warning(`Unable to clean or reset the repository. The repository will be recreated instead.`); + } + } + } + catch (error) { + core.warning(`Unable to prepare the existing repository. The repository will be recreated instead.`); + remove = true; + } + } + if (remove) { + // Delete the contents of the directory. Don't delete the directory itself + // since it might be the current working directory. + core.info(`Deleting the contents of '${repositoryPath}'`); + for (const file of yield fs.promises.readdir(repositoryPath)) { + yield io.rmRF(path.join(repositoryPath, file)); + } + } + }); +} +exports.prepareExistingDirectory = prepareExistingDirectory; + + /***/ }), /***/ 453: /***/ (function(module, __unusedexports, __webpack_require__) { var once = __webpack_require__(969) -var eos = __webpack_require__(562) +var eos = __webpack_require__(3) var fs = __webpack_require__(747) // we only need fs to get the ReadStream and WriteStream prototypes var noop = function () {} @@ -6978,7 +7773,7 @@ function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'defau var Stream = _interopDefault(__webpack_require__(413)); var http = _interopDefault(__webpack_require__(605)); var Url = _interopDefault(__webpack_require__(835)); -var https = _interopDefault(__webpack_require__(211)); +var https = _interopDefault(__webpack_require__(34)); var zlib = _interopDefault(__webpack_require__(761)); // Based on https://github.com/tmpvar/jsdom/blob/aa85b2abf07766ff7bf5c1f6daafb3726f2f2db5/lib/jsdom/living/blob.js @@ -8768,6 +9563,11 @@ const v4_1 = __importDefault(__webpack_require__(826)); const IS_WINDOWS = process.platform === 'win32'; function downloadRepository(authToken, owner, repo, ref, commit, repositoryPath) { return __awaiter(this, void 0, void 0, function* () { + // Determine the default branch + if (!ref && !commit) { + core.info('Determining the default branch'); + ref = yield getDefaultBranch(authToken, owner, repo); + } // Download the archive let archiveData = yield retryHelper.execute(() => __awaiter(this, void 0, void 0, function* () { core.info('Downloading the archive'); @@ -8812,6 +9612,42 @@ function downloadRepository(authToken, owner, repo, ref, commit, repositoryPath) }); } exports.downloadRepository = downloadRepository; +/** + * Looks up the default branch name + */ +function getDefaultBranch(authToken, owner, repo) { + return __awaiter(this, void 0, void 0, function* () { + return yield retryHelper.execute(() => __awaiter(this, void 0, void 0, function* () { + core.info('Retrieving the default branch name'); + const octokit = new github.GitHub(authToken); + let result; + try { + // Get the default branch from the repo info + const response = yield octokit.repos.get({ owner, repo }); + result = response.data.default_branch; + assert.ok(result, 'default_branch cannot be empty'); + } + catch (err) { + // Handle .wiki repo + if (err['status'] === 404 && repo.toUpperCase().endsWith('.WIKI')) { + result = 'master'; + } + // Otherwise error + else { + throw err; + } + } + // Print the default branch + core.info(`Default branch '${result}'`); + // Prefix with 'refs/heads' + if (!result.startsWith('refs/')) { + result = `refs/heads/${result}`; + } + return result; + })); + }); +} +exports.getDefaultBranch = getDefaultBranch; function downloadArchive(authToken, owner, repo, ref, commit) { return __awaiter(this, void 0, void 0, function* () { const octokit = new github.GitHub(authToken); @@ -8837,9 +9673,6 @@ function downloadArchive(authToken, owner, repo, ref, commit) { "use strict"; -var __importDefault = (this && this.__importDefault) || function (mod) { - return (mod && mod.__esModule) ? mod : { "default": mod }; -}; var __importStar = (this && this.__importStar) || function (mod) { if (mod && mod.__esModule) return mod; var result = {}; @@ -8850,13 +9683,13 @@ var __importStar = (this && this.__importStar) || function (mod) { Object.defineProperty(exports, "__esModule", { value: true }); // Originally pulled from https://github.com/JasonEtco/actions-toolkit/blob/master/src/github.ts const graphql_1 = __webpack_require__(898); -const rest_1 = __importDefault(__webpack_require__(0)); +const rest_1 = __webpack_require__(0); const Context = __importStar(__webpack_require__(262)); const httpClient = __importStar(__webpack_require__(539)); // We need this in order to extend Octokit -rest_1.default.prototype = new rest_1.default(); +rest_1.Octokit.prototype = new rest_1.Octokit(); exports.context = new Context.Context(); -class GitHub extends rest_1.default { +class GitHub extends rest_1.Octokit { constructor(token, opts) { super(GitHub.getOctokitOptions(GitHub.disambiguate(token, opts))); this.graphql = GitHub.getGraphQL(GitHub.disambiguate(token, opts)); @@ -8873,13 +9706,15 @@ class GitHub extends rest_1.default { static getOctokitOptions(args) { const token = args[0]; const options = Object.assign({}, args[1]); // Shallow clone - don't mutate the object provided by the caller + // Base URL - GHES or Dotcom + options.baseUrl = options.baseUrl || this.getApiBaseUrl(); // Auth const auth = GitHub.getAuthString(token, options); if (auth) { options.auth = auth; } // Proxy - const agent = GitHub.getProxyAgent(options); + const agent = GitHub.getProxyAgent(options.baseUrl, options); if (agent) { // Shallow clone - don't mutate the object provided by the caller options.request = options.request ? Object.assign({}, options.request) : {}; @@ -8890,6 +9725,7 @@ class GitHub extends rest_1.default { } static getGraphQL(args) { const defaults = {}; + defaults.baseUrl = this.getGraphQLBaseUrl(); const token = args[0]; const options = args[1]; // Authorization @@ -8900,7 +9736,7 @@ class GitHub extends rest_1.default { }; } // Proxy - const agent = GitHub.getProxyAgent(options); + const agent = GitHub.getProxyAgent(defaults.baseUrl, options); if (agent) { defaults.request = { agent }; } @@ -8916,17 +9752,31 @@ class GitHub extends rest_1.default { } return typeof options.auth === 'string' ? options.auth : `token ${token}`; } - static getProxyAgent(options) { + static getProxyAgent(destinationUrl, options) { var _a; if (!((_a = options.request) === null || _a === void 0 ? void 0 : _a.agent)) { - const serverUrl = 'https://api.github.com'; - if (httpClient.getProxyUrl(serverUrl)) { + if (httpClient.getProxyUrl(destinationUrl)) { const hc = new httpClient.HttpClient(); - return hc.getAgent(serverUrl); + return hc.getAgent(destinationUrl); } } return undefined; } + static getApiBaseUrl() { + return process.env['GITHUB_API_URL'] || 'https://api.github.com'; + } + static getGraphQLBaseUrl() { + let url = process.env['GITHUB_GRAPHQL_URL'] || 'https://api.github.com/graphql'; + // Shouldn't be a trailing slash, but remove if so + if (url.endsWith('/')) { + url = url.substr(0, url.length - 1); + } + // Remove trailing "/graphql" + if (url.toUpperCase().endsWith('/GRAPHQL')) { + url = url.substr(0, url.length - '/graphql'.length); + } + return url; + } } exports.GitHub = GitHub; //# sourceMappingURL=github.js.map @@ -9215,6 +10065,69 @@ function resolveCommand(parsed) { module.exports = resolveCommand; +/***/ }), + +/***/ 497: +/***/ (function(__unusedmodule, exports, __webpack_require__) { + +"use strict"; + + +Object.defineProperty(exports, '__esModule', { value: true }); + +function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'default' in ex) ? ex['default'] : ex; } + +var deprecation = __webpack_require__(692); +var once = _interopDefault(__webpack_require__(969)); + +const logOnce = once(deprecation => console.warn(deprecation)); +/** + * Error with extra properties to help with debugging + */ + +class RequestError extends Error { + constructor(message, statusCode, options) { + super(message); // Maintains proper stack trace (only available on V8) + + /* istanbul ignore next */ + + if (Error.captureStackTrace) { + Error.captureStackTrace(this, this.constructor); + } + + this.name = "HttpError"; + this.status = statusCode; + Object.defineProperty(this, "code", { + get() { + logOnce(new deprecation.Deprecation("[@octokit/request-error] `error.code` is deprecated, use `error.status`.")); + return statusCode; + } + + }); + this.headers = options.headers || {}; // redact request credentials without mutating original request options + + const requestCopy = Object.assign({}, options.request); + + if (options.request.headers.authorization) { + requestCopy.headers = Object.assign({}, options.request.headers, { + authorization: options.request.headers.authorization.replace(/ .*$/, " [REDACTED]") + }); + } + + requestCopy.url = requestCopy.url // client_id & client_secret can be passed as URL query parameters to increase rate limit + // see https://developer.github.com/v3/#increasing-the-unauthenticated-rate-limit-for-oauth-applications + .replace(/\bclient_secret=\w+/g, "client_secret=[REDACTED]") // OAuth tokens can be passed as URL query parameters, although it is not recommended + // see https://developer.github.com/v3/#oauth2-token-sent-in-a-header + .replace(/\baccess_token=\w+/g, "access_token=[REDACTED]"); + this.request = requestCopy; + } + +} + +exports.RequestError = RequestError; +//# sourceMappingURL=index.js.map + + /***/ }), /***/ 510: @@ -9332,6 +10245,22 @@ module.exports.Singular = Hook.Singular module.exports.Collection = Hook.Collection +/***/ }), + +/***/ 528: +/***/ (function(__unusedmodule, exports) { + +"use strict"; + +Object.defineProperty(exports, "__esModule", { value: true }); +function escape(value) { + return value.replace(/[^a-zA-Z0-9_]/g, x => { + return `\\${x}`; + }); +} +exports.escape = escape; + + /***/ }), /***/ 529: @@ -9813,7 +10742,7 @@ function hasFirstPage (link) { Object.defineProperty(exports, "__esModule", { value: true }); const url = __webpack_require__(835); const http = __webpack_require__(605); -const https = __webpack_require__(211); +const https = __webpack_require__(34); const pm = __webpack_require__(950); let tunnel; var HttpCodes; @@ -9839,12 +10768,22 @@ var HttpCodes; HttpCodes[HttpCodes["RequestTimeout"] = 408] = "RequestTimeout"; HttpCodes[HttpCodes["Conflict"] = 409] = "Conflict"; HttpCodes[HttpCodes["Gone"] = 410] = "Gone"; + HttpCodes[HttpCodes["TooManyRequests"] = 429] = "TooManyRequests"; HttpCodes[HttpCodes["InternalServerError"] = 500] = "InternalServerError"; HttpCodes[HttpCodes["NotImplemented"] = 501] = "NotImplemented"; HttpCodes[HttpCodes["BadGateway"] = 502] = "BadGateway"; HttpCodes[HttpCodes["ServiceUnavailable"] = 503] = "ServiceUnavailable"; HttpCodes[HttpCodes["GatewayTimeout"] = 504] = "GatewayTimeout"; })(HttpCodes = exports.HttpCodes || (exports.HttpCodes = {})); +var Headers; +(function (Headers) { + Headers["Accept"] = "accept"; + Headers["ContentType"] = "content-type"; +})(Headers = exports.Headers || (exports.Headers = {})); +var MediaTypes; +(function (MediaTypes) { + MediaTypes["ApplicationJson"] = "application/json"; +})(MediaTypes = exports.MediaTypes || (exports.MediaTypes = {})); /** * Returns the proxy URL, depending upon the supplied url and proxy environment variables. * @param serverUrl The server URL where the request will be sent. For example, https://api.github.com @@ -9854,8 +10793,18 @@ function getProxyUrl(serverUrl) { return proxyUrl ? proxyUrl.href : ''; } exports.getProxyUrl = getProxyUrl; -const HttpRedirectCodes = [HttpCodes.MovedPermanently, HttpCodes.ResourceMoved, HttpCodes.SeeOther, HttpCodes.TemporaryRedirect, HttpCodes.PermanentRedirect]; -const HttpResponseRetryCodes = [HttpCodes.BadGateway, HttpCodes.ServiceUnavailable, HttpCodes.GatewayTimeout]; +const HttpRedirectCodes = [ + HttpCodes.MovedPermanently, + HttpCodes.ResourceMoved, + HttpCodes.SeeOther, + HttpCodes.TemporaryRedirect, + HttpCodes.PermanentRedirect +]; +const HttpResponseRetryCodes = [ + HttpCodes.BadGateway, + HttpCodes.ServiceUnavailable, + HttpCodes.GatewayTimeout +]; const RetryableHttpVerbs = ['OPTIONS', 'GET', 'DELETE', 'HEAD']; const ExponentialBackoffCeiling = 10; const ExponentialBackoffTimeSlice = 5; @@ -9943,6 +10892,36 @@ class HttpClient { sendStream(verb, requestUrl, stream, additionalHeaders) { return this.request(verb, requestUrl, stream, additionalHeaders); } + /** + * Gets a typed object from an endpoint + * Be aware that not found returns a null. Other errors (4xx, 5xx) reject the promise + */ + async getJson(requestUrl, additionalHeaders = {}) { + additionalHeaders[Headers.Accept] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.Accept, MediaTypes.ApplicationJson); + let res = await this.get(requestUrl, additionalHeaders); + return this._processResponse(res, this.requestOptions); + } + async postJson(requestUrl, obj, additionalHeaders = {}) { + let data = JSON.stringify(obj, null, 2); + additionalHeaders[Headers.Accept] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.Accept, MediaTypes.ApplicationJson); + additionalHeaders[Headers.ContentType] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.ContentType, MediaTypes.ApplicationJson); + let res = await this.post(requestUrl, data, additionalHeaders); + return this._processResponse(res, this.requestOptions); + } + async putJson(requestUrl, obj, additionalHeaders = {}) { + let data = JSON.stringify(obj, null, 2); + additionalHeaders[Headers.Accept] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.Accept, MediaTypes.ApplicationJson); + additionalHeaders[Headers.ContentType] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.ContentType, MediaTypes.ApplicationJson); + let res = await this.put(requestUrl, data, additionalHeaders); + return this._processResponse(res, this.requestOptions); + } + async patchJson(requestUrl, obj, additionalHeaders = {}) { + let data = JSON.stringify(obj, null, 2); + additionalHeaders[Headers.Accept] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.Accept, MediaTypes.ApplicationJson); + additionalHeaders[Headers.ContentType] = this._getExistingOrDefaultHeader(additionalHeaders, Headers.ContentType, MediaTypes.ApplicationJson); + let res = await this.patch(requestUrl, data, additionalHeaders); + return this._processResponse(res, this.requestOptions); + } /** * Makes a raw http request. * All other methods such as get, post, patch, and request ultimately call this. @@ -9950,18 +10929,22 @@ class HttpClient { */ async request(verb, requestUrl, data, headers) { if (this._disposed) { - throw new Error("Client has already been disposed."); + throw new Error('Client has already been disposed.'); } let parsedUrl = url.parse(requestUrl); let info = this._prepareRequest(verb, parsedUrl, headers); // Only perform retries on reads since writes may not be idempotent. - let maxTries = (this._allowRetries && RetryableHttpVerbs.indexOf(verb) != -1) ? this._maxRetries + 1 : 1; + let maxTries = this._allowRetries && RetryableHttpVerbs.indexOf(verb) != -1 + ? this._maxRetries + 1 + : 1; let numTries = 0; let response; while (numTries < maxTries) { response = await this.requestRaw(info, data); // Check if it's an authentication challenge - if (response && response.message && response.message.statusCode === HttpCodes.Unauthorized) { + if (response && + response.message && + response.message.statusCode === HttpCodes.Unauthorized) { let authenticationHandler; for (let i = 0; i < this.handlers.length; i++) { if (this.handlers[i].canHandleAuthentication(response)) { @@ -9979,21 +10962,32 @@ class HttpClient { } } let redirectsRemaining = this._maxRedirects; - while (HttpRedirectCodes.indexOf(response.message.statusCode) != -1 - && this._allowRedirects - && redirectsRemaining > 0) { - const redirectUrl = response.message.headers["location"]; + while (HttpRedirectCodes.indexOf(response.message.statusCode) != -1 && + this._allowRedirects && + redirectsRemaining > 0) { + const redirectUrl = response.message.headers['location']; if (!redirectUrl) { // if there's no location to redirect to, we won't break; } let parsedRedirectUrl = url.parse(redirectUrl); - if (parsedUrl.protocol == 'https:' && parsedUrl.protocol != parsedRedirectUrl.protocol && !this._allowRedirectDowngrade) { - throw new Error("Redirect from HTTPS to HTTP protocol. This downgrade is not allowed for security reasons. If you want to allow this behavior, set the allowRedirectDowngrade option to true."); + if (parsedUrl.protocol == 'https:' && + parsedUrl.protocol != parsedRedirectUrl.protocol && + !this._allowRedirectDowngrade) { + throw new Error('Redirect from HTTPS to HTTP protocol. This downgrade is not allowed for security reasons. If you want to allow this behavior, set the allowRedirectDowngrade option to true.'); } // we need to finish reading the response before reassigning response // which will leak the open socket. await response.readBody(); + // strip authorization header if redirected to a different hostname + if (parsedRedirectUrl.hostname !== parsedUrl.hostname) { + for (let header in headers) { + // header names are case insensitive + if (header.toLowerCase() === 'authorization') { + delete headers[header]; + } + } + } // let's make the request with the new redirectUrl info = this._prepareRequest(verb, parsedRedirectUrl, headers); response = await this.requestRaw(info, data); @@ -10044,8 +11038,8 @@ class HttpClient { */ requestRawWithCallback(info, data, onResult) { let socket; - if (typeof (data) === 'string') { - info.options.headers["Content-Length"] = Buffer.byteLength(data, 'utf8'); + if (typeof data === 'string') { + info.options.headers['Content-Length'] = Buffer.byteLength(data, 'utf8'); } let callbackCalled = false; let handleResult = (err, res) => { @@ -10058,7 +11052,7 @@ class HttpClient { let res = new HttpClientResponse(msg); handleResult(null, res); }); - req.on('socket', (sock) => { + req.on('socket', sock => { socket = sock; }); // If we ever get disconnected, we want the socket to timeout eventually @@ -10073,10 +11067,10 @@ class HttpClient { // res should have headers handleResult(err, null); }); - if (data && typeof (data) === 'string') { + if (data && typeof data === 'string') { req.write(data, 'utf8'); } - if (data && typeof (data) !== 'string') { + if (data && typeof data !== 'string') { data.on('close', function () { req.end(); }); @@ -10103,29 +11097,40 @@ class HttpClient { const defaultPort = usingSsl ? 443 : 80; info.options = {}; info.options.host = info.parsedUrl.hostname; - info.options.port = info.parsedUrl.port ? parseInt(info.parsedUrl.port) : defaultPort; - info.options.path = (info.parsedUrl.pathname || '') + (info.parsedUrl.search || ''); + info.options.port = info.parsedUrl.port + ? parseInt(info.parsedUrl.port) + : defaultPort; + info.options.path = + (info.parsedUrl.pathname || '') + (info.parsedUrl.search || ''); info.options.method = method; info.options.headers = this._mergeHeaders(headers); if (this.userAgent != null) { - info.options.headers["user-agent"] = this.userAgent; + info.options.headers['user-agent'] = this.userAgent; } info.options.agent = this._getAgent(info.parsedUrl); // gives handlers an opportunity to participate if (this.handlers) { - this.handlers.forEach((handler) => { + this.handlers.forEach(handler => { handler.prepareRequest(info.options); }); } return info; } _mergeHeaders(headers) { - const lowercaseKeys = obj => Object.keys(obj).reduce((c, k) => (c[k.toLowerCase()] = obj[k], c), {}); + const lowercaseKeys = obj => Object.keys(obj).reduce((c, k) => ((c[k.toLowerCase()] = obj[k]), c), {}); if (this.requestOptions && this.requestOptions.headers) { return Object.assign({}, lowercaseKeys(this.requestOptions.headers), lowercaseKeys(headers)); } return lowercaseKeys(headers || {}); } + _getExistingOrDefaultHeader(additionalHeaders, header, _default) { + const lowercaseKeys = obj => Object.keys(obj).reduce((c, k) => ((c[k.toLowerCase()] = obj[k]), c), {}); + let clientHeader; + if (this.requestOptions && this.requestOptions.headers) { + clientHeader = lowercaseKeys(this.requestOptions.headers)[header]; + } + return additionalHeaders[header] || clientHeader || _default; + } _getAgent(parsedUrl) { let agent; let proxyUrl = pm.getProxyUrl(parsedUrl); @@ -10157,7 +11162,7 @@ class HttpClient { proxyAuth: proxyUrl.auth, host: proxyUrl.hostname, port: proxyUrl.port - }, + } }; let tunnelAgent; const overHttps = proxyUrl.protocol === 'https:'; @@ -10184,7 +11189,9 @@ class HttpClient { // we don't want to set NODE_TLS_REJECT_UNAUTHORIZED=0 since that will affect request for entire process // http.RequestOptions doesn't expose a way to modify RequestOptions.agent.options // we have to cast it to any and change it directly - agent.options = Object.assign(agent.options || {}, { rejectUnauthorized: false }); + agent.options = Object.assign(agent.options || {}, { + rejectUnauthorized: false + }); } return agent; } @@ -10193,6 +11200,73 @@ class HttpClient { const ms = ExponentialBackoffTimeSlice * Math.pow(2, retryNumber); return new Promise(resolve => setTimeout(() => resolve(), ms)); } + static dateTimeDeserializer(key, value) { + if (typeof value === 'string') { + let a = new Date(value); + if (!isNaN(a.valueOf())) { + return a; + } + } + return value; + } + async _processResponse(res, options) { + return new Promise(async (resolve, reject) => { + const statusCode = res.message.statusCode; + const response = { + statusCode: statusCode, + result: null, + headers: {} + }; + // not found leads to null obj returned + if (statusCode == HttpCodes.NotFound) { + resolve(response); + } + let obj; + let contents; + // get the result from the body + try { + contents = await res.readBody(); + if (contents && contents.length > 0) { + if (options && options.deserializeDates) { + obj = JSON.parse(contents, HttpClient.dateTimeDeserializer); + } + else { + obj = JSON.parse(contents); + } + response.result = obj; + } + response.headers = res.message.headers; + } + catch (err) { + // Invalid resource (contents not json); leaving result obj null + } + // note that 3xx redirects are handled by the http layer. + if (statusCode > 299) { + let msg; + // if exception/error in body, attempt to get better error + if (obj && obj.message) { + msg = obj.message; + } + else if (contents && contents.length > 0) { + // it may be the case that the exception is in the body message as string + msg = contents; + } + else { + msg = 'Failed request: (' + statusCode + ')'; + } + let err = new Error(msg); + // attach statusCode and body obj (if available) to the error object + err['statusCode'] = statusCode; + if (response.result) { + err['result'] = response.result; + } + reject(err); + } + else { + resolve(response); + } + }); + } } exports.HttpClient = HttpClient; @@ -10309,102 +11383,31 @@ exports.GitVersion = GitVersion; /***/ }), /***/ 562: -/***/ (function(module, __unusedexports, __webpack_require__) { +/***/ (function(__unusedmodule, exports, __webpack_require__) { -var once = __webpack_require__(969); +"use strict"; -var noop = function() {}; -var isRequest = function(stream) { - return stream.setHeader && typeof stream.abort === 'function'; -}; +Object.defineProperty(exports, '__esModule', { value: true }); -var isChildProcess = function(stream) { - return stream.stdio && Array.isArray(stream.stdio) && stream.stdio.length === 3 -}; +function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'default' in ex) ? ex['default'] : ex; } -var eos = function(stream, opts, callback) { - if (typeof opts === 'function') return eos(stream, null, opts); - if (!opts) opts = {}; +var osName = _interopDefault(__webpack_require__(2)); - callback = once(callback || noop); +function getUserAgent() { + try { + return `Node.js/${process.version.substr(1)} (${osName()}; ${process.arch})`; + } catch (error) { + if (/wmic os get Caption/.test(error.message)) { + return "Windows "; + } - var ws = stream._writableState; - var rs = stream._readableState; - var readable = opts.readable || (opts.readable !== false && stream.readable); - var writable = opts.writable || (opts.writable !== false && stream.writable); - var cancelled = false; + return ""; + } +} - var onlegacyfinish = function() { - if (!stream.writable) onfinish(); - }; - - var onfinish = function() { - writable = false; - if (!readable) callback.call(stream); - }; - - var onend = function() { - readable = false; - if (!writable) callback.call(stream); - }; - - var onexit = function(exitCode) { - callback.call(stream, exitCode ? new Error('exited with error code: ' + exitCode) : null); - }; - - var onerror = function(err) { - callback.call(stream, err); - }; - - var onclose = function() { - process.nextTick(onclosenexttick); - }; - - var onclosenexttick = function() { - if (cancelled) return; - if (readable && !(rs && (rs.ended && !rs.destroyed))) return callback.call(stream, new Error('premature close')); - if (writable && !(ws && (ws.ended && !ws.destroyed))) return callback.call(stream, new Error('premature close')); - }; - - var onrequest = function() { - stream.req.on('finish', onfinish); - }; - - if (isRequest(stream)) { - stream.on('complete', onfinish); - stream.on('abort', onclose); - if (stream.req) onrequest(); - else stream.on('request', onrequest); - } else if (writable && !ws) { // legacy streams - stream.on('end', onlegacyfinish); - stream.on('close', onlegacyfinish); - } - - if (isChildProcess(stream)) stream.on('exit', onexit); - - stream.on('end', onend); - stream.on('finish', onfinish); - if (opts.error !== false) stream.on('error', onerror); - stream.on('close', onclose); - - return function() { - cancelled = true; - stream.removeListener('complete', onfinish); - stream.removeListener('abort', onclose); - stream.removeListener('request', onrequest); - if (stream.req) stream.req.removeListener('finish', onfinish); - stream.removeListener('end', onlegacyfinish); - stream.removeListener('close', onlegacyfinish); - stream.removeListener('finish', onfinish); - stream.removeListener('exit', onexit); - stream.removeListener('end', onend); - stream.removeListener('error', onerror); - stream.removeListener('close', onclose); - }; -}; - -module.exports = eos; +exports.getUserAgent = getUserAgent; +//# sourceMappingURL=index.js.map /***/ }), @@ -10576,26 +11579,6 @@ function getPageLinks (link) { } -/***/ }), - -/***/ 586: -/***/ (function(module, __unusedexports, __webpack_require__) { - -module.exports = octokitRestApiEndpoints; - -const ROUTES = __webpack_require__(705); - -function octokitRestApiEndpoints(octokit) { - // Aliasing scopes for backward compatibility - // See https://github.com/octokit/rest.js/pull/1134 - ROUTES.gitdata = ROUTES.git; - ROUTES.authorization = ROUTES.oauthAuthorizations; - ROUTES.pullRequests = ROUTES.pulls; - - octokit.registerEndpoints(ROUTES); -} - - /***/ }), /***/ 587: @@ -12891,13 +13874,6 @@ module.exports = (promise, onFinally) => { }; -/***/ }), - -/***/ 705: -/***/ (function(module) { - -module.exports = {"activity":{"checkStarringRepo":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/user/starred/:owner/:repo"},"deleteRepoSubscription":{"method":"DELETE","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/subscription"},"deleteThreadSubscription":{"method":"DELETE","params":{"thread_id":{"required":true,"type":"integer"}},"url":"/notifications/threads/:thread_id/subscription"},"getRepoSubscription":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/subscription"},"getThread":{"method":"GET","params":{"thread_id":{"required":true,"type":"integer"}},"url":"/notifications/threads/:thread_id"},"getThreadSubscription":{"method":"GET","params":{"thread_id":{"required":true,"type":"integer"}},"url":"/notifications/threads/:thread_id/subscription"},"listEventsForOrg":{"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/users/:username/events/orgs/:org"},"listEventsForUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/users/:username/events"},"listFeeds":{"method":"GET","params":{},"url":"/feeds"},"listNotifications":{"method":"GET","params":{"all":{"type":"boolean"},"before":{"type":"string"},"page":{"type":"integer"},"participating":{"type":"boolean"},"per_page":{"type":"integer"},"since":{"type":"string"}},"url":"/notifications"},"listNotificationsForRepo":{"method":"GET","params":{"all":{"type":"boolean"},"before":{"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"participating":{"type":"boolean"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"},"since":{"type":"string"}},"url":"/repos/:owner/:repo/notifications"},"listPublicEvents":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/events"},"listPublicEventsForOrg":{"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/orgs/:org/events"},"listPublicEventsForRepoNetwork":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/networks/:owner/:repo/events"},"listPublicEventsForUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/users/:username/events/public"},"listReceivedEventsForUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/users/:username/received_events"},"listReceivedPublicEventsForUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/users/:username/received_events/public"},"listRepoEvents":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/events"},"listReposStarredByAuthenticatedUser":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"sort":{"enum":["created","updated"],"type":"string"}},"url":"/user/starred"},"listReposStarredByUser":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"sort":{"enum":["created","updated"],"type":"string"},"username":{"required":true,"type":"string"}},"url":"/users/:username/starred"},"listReposWatchedByUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/users/:username/subscriptions"},"listStargazersForRepo":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/stargazers"},"listWatchedReposForAuthenticatedUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/subscriptions"},"listWatchersForRepo":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/subscribers"},"markAsRead":{"method":"PUT","params":{"last_read_at":{"type":"string"}},"url":"/notifications"},"markNotificationsAsReadForRepo":{"method":"PUT","params":{"last_read_at":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/notifications"},"markThreadAsRead":{"method":"PATCH","params":{"thread_id":{"required":true,"type":"integer"}},"url":"/notifications/threads/:thread_id"},"setRepoSubscription":{"method":"PUT","params":{"ignored":{"type":"boolean"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"subscribed":{"type":"boolean"}},"url":"/repos/:owner/:repo/subscription"},"setThreadSubscription":{"method":"PUT","params":{"ignored":{"type":"boolean"},"thread_id":{"required":true,"type":"integer"}},"url":"/notifications/threads/:thread_id/subscription"},"starRepo":{"method":"PUT","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/user/starred/:owner/:repo"},"unstarRepo":{"method":"DELETE","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/user/starred/:owner/:repo"}},"apps":{"addRepoToInstallation":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"PUT","params":{"installation_id":{"required":true,"type":"integer"},"repository_id":{"required":true,"type":"integer"}},"url":"/user/installations/:installation_id/repositories/:repository_id"},"checkAccountIsAssociatedWithAny":{"method":"GET","params":{"account_id":{"required":true,"type":"integer"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/marketplace_listing/accounts/:account_id"},"checkAccountIsAssociatedWithAnyStubbed":{"method":"GET","params":{"account_id":{"required":true,"type":"integer"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/marketplace_listing/stubbed/accounts/:account_id"},"checkAuthorization":{"deprecated":"octokit.oauthAuthorizations.checkAuthorization() has been renamed to octokit.apps.checkAuthorization() (2019-11-05)","method":"GET","params":{"access_token":{"required":true,"type":"string"},"client_id":{"required":true,"type":"string"}},"url":"/applications/:client_id/tokens/:access_token"},"checkToken":{"headers":{"accept":"application/vnd.github.doctor-strange-preview+json"},"method":"POST","params":{"access_token":{"type":"string"},"client_id":{"required":true,"type":"string"}},"url":"/applications/:client_id/token"},"createContentAttachment":{"headers":{"accept":"application/vnd.github.corsair-preview+json"},"method":"POST","params":{"body":{"required":true,"type":"string"},"content_reference_id":{"required":true,"type":"integer"},"title":{"required":true,"type":"string"}},"url":"/content_references/:content_reference_id/attachments"},"createFromManifest":{"headers":{"accept":"application/vnd.github.fury-preview+json"},"method":"POST","params":{"code":{"required":true,"type":"string"}},"url":"/app-manifests/:code/conversions"},"createInstallationToken":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"POST","params":{"installation_id":{"required":true,"type":"integer"},"permissions":{"type":"object"},"repository_ids":{"type":"integer[]"}},"url":"/app/installations/:installation_id/access_tokens"},"deleteAuthorization":{"headers":{"accept":"application/vnd.github.doctor-strange-preview+json"},"method":"DELETE","params":{"access_token":{"type":"string"},"client_id":{"required":true,"type":"string"}},"url":"/applications/:client_id/grant"},"deleteInstallation":{"headers":{"accept":"application/vnd.github.gambit-preview+json,application/vnd.github.machine-man-preview+json"},"method":"DELETE","params":{"installation_id":{"required":true,"type":"integer"}},"url":"/app/installations/:installation_id"},"deleteToken":{"headers":{"accept":"application/vnd.github.doctor-strange-preview+json"},"method":"DELETE","params":{"access_token":{"type":"string"},"client_id":{"required":true,"type":"string"}},"url":"/applications/:client_id/token"},"findOrgInstallation":{"deprecated":"octokit.apps.findOrgInstallation() has been renamed to octokit.apps.getOrgInstallation() (2019-04-10)","headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"org":{"required":true,"type":"string"}},"url":"/orgs/:org/installation"},"findRepoInstallation":{"deprecated":"octokit.apps.findRepoInstallation() has been renamed to octokit.apps.getRepoInstallation() (2019-04-10)","headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/installation"},"findUserInstallation":{"deprecated":"octokit.apps.findUserInstallation() has been renamed to octokit.apps.getUserInstallation() (2019-04-10)","headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"username":{"required":true,"type":"string"}},"url":"/users/:username/installation"},"getAuthenticated":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{},"url":"/app"},"getBySlug":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"app_slug":{"required":true,"type":"string"}},"url":"/apps/:app_slug"},"getInstallation":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"installation_id":{"required":true,"type":"integer"}},"url":"/app/installations/:installation_id"},"getOrgInstallation":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"org":{"required":true,"type":"string"}},"url":"/orgs/:org/installation"},"getRepoInstallation":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/installation"},"getUserInstallation":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"username":{"required":true,"type":"string"}},"url":"/users/:username/installation"},"listAccountsUserOrOrgOnPlan":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"plan_id":{"required":true,"type":"integer"},"sort":{"enum":["created","updated"],"type":"string"}},"url":"/marketplace_listing/plans/:plan_id/accounts"},"listAccountsUserOrOrgOnPlanStubbed":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"plan_id":{"required":true,"type":"integer"},"sort":{"enum":["created","updated"],"type":"string"}},"url":"/marketplace_listing/stubbed/plans/:plan_id/accounts"},"listInstallationReposForAuthenticatedUser":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"installation_id":{"required":true,"type":"integer"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/installations/:installation_id/repositories"},"listInstallations":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/app/installations"},"listInstallationsForAuthenticatedUser":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/installations"},"listMarketplacePurchasesForAuthenticatedUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/marketplace_purchases"},"listMarketplacePurchasesForAuthenticatedUserStubbed":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/marketplace_purchases/stubbed"},"listPlans":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/marketplace_listing/plans"},"listPlansStubbed":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/marketplace_listing/stubbed/plans"},"listRepos":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/installation/repositories"},"removeRepoFromInstallation":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"DELETE","params":{"installation_id":{"required":true,"type":"integer"},"repository_id":{"required":true,"type":"integer"}},"url":"/user/installations/:installation_id/repositories/:repository_id"},"resetAuthorization":{"deprecated":"octokit.oauthAuthorizations.resetAuthorization() has been renamed to octokit.apps.resetAuthorization() (2019-11-05)","method":"POST","params":{"access_token":{"required":true,"type":"string"},"client_id":{"required":true,"type":"string"}},"url":"/applications/:client_id/tokens/:access_token"},"resetToken":{"headers":{"accept":"application/vnd.github.doctor-strange-preview+json"},"method":"PATCH","params":{"access_token":{"type":"string"},"client_id":{"required":true,"type":"string"}},"url":"/applications/:client_id/token"},"revokeAuthorizationForApplication":{"deprecated":"octokit.oauthAuthorizations.revokeAuthorizationForApplication() has been renamed to octokit.apps.revokeAuthorizationForApplication() (2019-11-05)","method":"DELETE","params":{"access_token":{"required":true,"type":"string"},"client_id":{"required":true,"type":"string"}},"url":"/applications/:client_id/tokens/:access_token"},"revokeGrantForApplication":{"deprecated":"octokit.oauthAuthorizations.revokeGrantForApplication() has been renamed to octokit.apps.revokeGrantForApplication() (2019-11-05)","method":"DELETE","params":{"access_token":{"required":true,"type":"string"},"client_id":{"required":true,"type":"string"}},"url":"/applications/:client_id/grants/:access_token"},"revokeInstallationToken":{"headers":{"accept":"application/vnd.github.gambit-preview+json"},"method":"DELETE","params":{},"url":"/installation/token"}},"checks":{"create":{"headers":{"accept":"application/vnd.github.antiope-preview+json"},"method":"POST","params":{"actions":{"type":"object[]"},"actions[].description":{"required":true,"type":"string"},"actions[].identifier":{"required":true,"type":"string"},"actions[].label":{"required":true,"type":"string"},"completed_at":{"type":"string"},"conclusion":{"enum":["success","failure","neutral","cancelled","timed_out","action_required"],"type":"string"},"details_url":{"type":"string"},"external_id":{"type":"string"},"head_sha":{"required":true,"type":"string"},"name":{"required":true,"type":"string"},"output":{"type":"object"},"output.annotations":{"type":"object[]"},"output.annotations[].annotation_level":{"enum":["notice","warning","failure"],"required":true,"type":"string"},"output.annotations[].end_column":{"type":"integer"},"output.annotations[].end_line":{"required":true,"type":"integer"},"output.annotations[].message":{"required":true,"type":"string"},"output.annotations[].path":{"required":true,"type":"string"},"output.annotations[].raw_details":{"type":"string"},"output.annotations[].start_column":{"type":"integer"},"output.annotations[].start_line":{"required":true,"type":"integer"},"output.annotations[].title":{"type":"string"},"output.images":{"type":"object[]"},"output.images[].alt":{"required":true,"type":"string"},"output.images[].caption":{"type":"string"},"output.images[].image_url":{"required":true,"type":"string"},"output.summary":{"required":true,"type":"string"},"output.text":{"type":"string"},"output.title":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"started_at":{"type":"string"},"status":{"enum":["queued","in_progress","completed"],"type":"string"}},"url":"/repos/:owner/:repo/check-runs"},"createSuite":{"headers":{"accept":"application/vnd.github.antiope-preview+json"},"method":"POST","params":{"head_sha":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/check-suites"},"get":{"headers":{"accept":"application/vnd.github.antiope-preview+json"},"method":"GET","params":{"check_run_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/check-runs/:check_run_id"},"getSuite":{"headers":{"accept":"application/vnd.github.antiope-preview+json"},"method":"GET","params":{"check_suite_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/check-suites/:check_suite_id"},"listAnnotations":{"headers":{"accept":"application/vnd.github.antiope-preview+json"},"method":"GET","params":{"check_run_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/check-runs/:check_run_id/annotations"},"listForRef":{"headers":{"accept":"application/vnd.github.antiope-preview+json"},"method":"GET","params":{"check_name":{"type":"string"},"filter":{"enum":["latest","all"],"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"status":{"enum":["queued","in_progress","completed"],"type":"string"}},"url":"/repos/:owner/:repo/commits/:ref/check-runs"},"listForSuite":{"headers":{"accept":"application/vnd.github.antiope-preview+json"},"method":"GET","params":{"check_name":{"type":"string"},"check_suite_id":{"required":true,"type":"integer"},"filter":{"enum":["latest","all"],"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"},"status":{"enum":["queued","in_progress","completed"],"type":"string"}},"url":"/repos/:owner/:repo/check-suites/:check_suite_id/check-runs"},"listSuitesForRef":{"headers":{"accept":"application/vnd.github.antiope-preview+json"},"method":"GET","params":{"app_id":{"type":"integer"},"check_name":{"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/commits/:ref/check-suites"},"rerequestSuite":{"headers":{"accept":"application/vnd.github.antiope-preview+json"},"method":"POST","params":{"check_suite_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/check-suites/:check_suite_id/rerequest"},"setSuitesPreferences":{"headers":{"accept":"application/vnd.github.antiope-preview+json"},"method":"PATCH","params":{"auto_trigger_checks":{"type":"object[]"},"auto_trigger_checks[].app_id":{"required":true,"type":"integer"},"auto_trigger_checks[].setting":{"required":true,"type":"boolean"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/check-suites/preferences"},"update":{"headers":{"accept":"application/vnd.github.antiope-preview+json"},"method":"PATCH","params":{"actions":{"type":"object[]"},"actions[].description":{"required":true,"type":"string"},"actions[].identifier":{"required":true,"type":"string"},"actions[].label":{"required":true,"type":"string"},"check_run_id":{"required":true,"type":"integer"},"completed_at":{"type":"string"},"conclusion":{"enum":["success","failure","neutral","cancelled","timed_out","action_required"],"type":"string"},"details_url":{"type":"string"},"external_id":{"type":"string"},"name":{"type":"string"},"output":{"type":"object"},"output.annotations":{"type":"object[]"},"output.annotations[].annotation_level":{"enum":["notice","warning","failure"],"required":true,"type":"string"},"output.annotations[].end_column":{"type":"integer"},"output.annotations[].end_line":{"required":true,"type":"integer"},"output.annotations[].message":{"required":true,"type":"string"},"output.annotations[].path":{"required":true,"type":"string"},"output.annotations[].raw_details":{"type":"string"},"output.annotations[].start_column":{"type":"integer"},"output.annotations[].start_line":{"required":true,"type":"integer"},"output.annotations[].title":{"type":"string"},"output.images":{"type":"object[]"},"output.images[].alt":{"required":true,"type":"string"},"output.images[].caption":{"type":"string"},"output.images[].image_url":{"required":true,"type":"string"},"output.summary":{"required":true,"type":"string"},"output.text":{"type":"string"},"output.title":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"started_at":{"type":"string"},"status":{"enum":["queued","in_progress","completed"],"type":"string"}},"url":"/repos/:owner/:repo/check-runs/:check_run_id"}},"codesOfConduct":{"getConductCode":{"headers":{"accept":"application/vnd.github.scarlet-witch-preview+json"},"method":"GET","params":{"key":{"required":true,"type":"string"}},"url":"/codes_of_conduct/:key"},"getForRepo":{"headers":{"accept":"application/vnd.github.scarlet-witch-preview+json"},"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/community/code_of_conduct"},"listConductCodes":{"headers":{"accept":"application/vnd.github.scarlet-witch-preview+json"},"method":"GET","params":{},"url":"/codes_of_conduct"}},"emojis":{"get":{"method":"GET","params":{},"url":"/emojis"}},"gists":{"checkIsStarred":{"method":"GET","params":{"gist_id":{"required":true,"type":"string"}},"url":"/gists/:gist_id/star"},"create":{"method":"POST","params":{"description":{"type":"string"},"files":{"required":true,"type":"object"},"files.content":{"type":"string"},"public":{"type":"boolean"}},"url":"/gists"},"createComment":{"method":"POST","params":{"body":{"required":true,"type":"string"},"gist_id":{"required":true,"type":"string"}},"url":"/gists/:gist_id/comments"},"delete":{"method":"DELETE","params":{"gist_id":{"required":true,"type":"string"}},"url":"/gists/:gist_id"},"deleteComment":{"method":"DELETE","params":{"comment_id":{"required":true,"type":"integer"},"gist_id":{"required":true,"type":"string"}},"url":"/gists/:gist_id/comments/:comment_id"},"fork":{"method":"POST","params":{"gist_id":{"required":true,"type":"string"}},"url":"/gists/:gist_id/forks"},"get":{"method":"GET","params":{"gist_id":{"required":true,"type":"string"}},"url":"/gists/:gist_id"},"getComment":{"method":"GET","params":{"comment_id":{"required":true,"type":"integer"},"gist_id":{"required":true,"type":"string"}},"url":"/gists/:gist_id/comments/:comment_id"},"getRevision":{"method":"GET","params":{"gist_id":{"required":true,"type":"string"},"sha":{"required":true,"type":"string"}},"url":"/gists/:gist_id/:sha"},"list":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"since":{"type":"string"}},"url":"/gists"},"listComments":{"method":"GET","params":{"gist_id":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/gists/:gist_id/comments"},"listCommits":{"method":"GET","params":{"gist_id":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/gists/:gist_id/commits"},"listForks":{"method":"GET","params":{"gist_id":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/gists/:gist_id/forks"},"listPublic":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"since":{"type":"string"}},"url":"/gists/public"},"listPublicForUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"since":{"type":"string"},"username":{"required":true,"type":"string"}},"url":"/users/:username/gists"},"listStarred":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"since":{"type":"string"}},"url":"/gists/starred"},"star":{"method":"PUT","params":{"gist_id":{"required":true,"type":"string"}},"url":"/gists/:gist_id/star"},"unstar":{"method":"DELETE","params":{"gist_id":{"required":true,"type":"string"}},"url":"/gists/:gist_id/star"},"update":{"method":"PATCH","params":{"description":{"type":"string"},"files":{"type":"object"},"files.content":{"type":"string"},"files.filename":{"type":"string"},"gist_id":{"required":true,"type":"string"}},"url":"/gists/:gist_id"},"updateComment":{"method":"PATCH","params":{"body":{"required":true,"type":"string"},"comment_id":{"required":true,"type":"integer"},"gist_id":{"required":true,"type":"string"}},"url":"/gists/:gist_id/comments/:comment_id"}},"git":{"createBlob":{"method":"POST","params":{"content":{"required":true,"type":"string"},"encoding":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/blobs"},"createCommit":{"method":"POST","params":{"author":{"type":"object"},"author.date":{"type":"string"},"author.email":{"type":"string"},"author.name":{"type":"string"},"committer":{"type":"object"},"committer.date":{"type":"string"},"committer.email":{"type":"string"},"committer.name":{"type":"string"},"message":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"parents":{"required":true,"type":"string[]"},"repo":{"required":true,"type":"string"},"signature":{"type":"string"},"tree":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/commits"},"createRef":{"method":"POST","params":{"owner":{"required":true,"type":"string"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"sha":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/refs"},"createTag":{"method":"POST","params":{"message":{"required":true,"type":"string"},"object":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"tag":{"required":true,"type":"string"},"tagger":{"type":"object"},"tagger.date":{"type":"string"},"tagger.email":{"type":"string"},"tagger.name":{"type":"string"},"type":{"enum":["commit","tree","blob"],"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/tags"},"createTree":{"method":"POST","params":{"base_tree":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"tree":{"required":true,"type":"object[]"},"tree[].content":{"type":"string"},"tree[].mode":{"enum":["100644","100755","040000","160000","120000"],"type":"string"},"tree[].path":{"type":"string"},"tree[].sha":{"allowNull":true,"type":"string"},"tree[].type":{"enum":["blob","tree","commit"],"type":"string"}},"url":"/repos/:owner/:repo/git/trees"},"deleteRef":{"method":"DELETE","params":{"owner":{"required":true,"type":"string"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/refs/:ref"},"getBlob":{"method":"GET","params":{"file_sha":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/blobs/:file_sha"},"getCommit":{"method":"GET","params":{"commit_sha":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/commits/:commit_sha"},"getRef":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/ref/:ref"},"getTag":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"tag_sha":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/tags/:tag_sha"},"getTree":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"recursive":{"enum":["1"],"type":"integer"},"repo":{"required":true,"type":"string"},"tree_sha":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/trees/:tree_sha"},"listMatchingRefs":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/matching-refs/:ref"},"listRefs":{"method":"GET","params":{"namespace":{"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/refs/:namespace"},"updateRef":{"method":"PATCH","params":{"force":{"type":"boolean"},"owner":{"required":true,"type":"string"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"sha":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/git/refs/:ref"}},"gitignore":{"getTemplate":{"method":"GET","params":{"name":{"required":true,"type":"string"}},"url":"/gitignore/templates/:name"},"listTemplates":{"method":"GET","params":{},"url":"/gitignore/templates"}},"interactions":{"addOrUpdateRestrictionsForOrg":{"headers":{"accept":"application/vnd.github.sombra-preview+json"},"method":"PUT","params":{"limit":{"enum":["existing_users","contributors_only","collaborators_only"],"required":true,"type":"string"},"org":{"required":true,"type":"string"}},"url":"/orgs/:org/interaction-limits"},"addOrUpdateRestrictionsForRepo":{"headers":{"accept":"application/vnd.github.sombra-preview+json"},"method":"PUT","params":{"limit":{"enum":["existing_users","contributors_only","collaborators_only"],"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/interaction-limits"},"getRestrictionsForOrg":{"headers":{"accept":"application/vnd.github.sombra-preview+json"},"method":"GET","params":{"org":{"required":true,"type":"string"}},"url":"/orgs/:org/interaction-limits"},"getRestrictionsForRepo":{"headers":{"accept":"application/vnd.github.sombra-preview+json"},"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/interaction-limits"},"removeRestrictionsForOrg":{"headers":{"accept":"application/vnd.github.sombra-preview+json"},"method":"DELETE","params":{"org":{"required":true,"type":"string"}},"url":"/orgs/:org/interaction-limits"},"removeRestrictionsForRepo":{"headers":{"accept":"application/vnd.github.sombra-preview+json"},"method":"DELETE","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/interaction-limits"}},"issues":{"addAssignees":{"method":"POST","params":{"assignees":{"type":"string[]"},"issue_number":{"required":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/assignees"},"addLabels":{"method":"POST","params":{"issue_number":{"required":true,"type":"integer"},"labels":{"required":true,"type":"string[]"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/labels"},"checkAssignee":{"method":"GET","params":{"assignee":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/assignees/:assignee"},"create":{"method":"POST","params":{"assignee":{"type":"string"},"assignees":{"type":"string[]"},"body":{"type":"string"},"labels":{"type":"string[]"},"milestone":{"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"title":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues"},"createComment":{"method":"POST","params":{"body":{"required":true,"type":"string"},"issue_number":{"required":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/comments"},"createLabel":{"method":"POST","params":{"color":{"required":true,"type":"string"},"description":{"type":"string"},"name":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/labels"},"createMilestone":{"method":"POST","params":{"description":{"type":"string"},"due_on":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"state":{"enum":["open","closed"],"type":"string"},"title":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/milestones"},"deleteComment":{"method":"DELETE","params":{"comment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/comments/:comment_id"},"deleteLabel":{"method":"DELETE","params":{"name":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/labels/:name"},"deleteMilestone":{"method":"DELETE","params":{"milestone_number":{"required":true,"type":"integer"},"number":{"alias":"milestone_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/milestones/:milestone_number"},"get":{"method":"GET","params":{"issue_number":{"required":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number"},"getComment":{"method":"GET","params":{"comment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/comments/:comment_id"},"getEvent":{"method":"GET","params":{"event_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/events/:event_id"},"getLabel":{"method":"GET","params":{"name":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/labels/:name"},"getMilestone":{"method":"GET","params":{"milestone_number":{"required":true,"type":"integer"},"number":{"alias":"milestone_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/milestones/:milestone_number"},"list":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"filter":{"enum":["assigned","created","mentioned","subscribed","all"],"type":"string"},"labels":{"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"since":{"type":"string"},"sort":{"enum":["created","updated","comments"],"type":"string"},"state":{"enum":["open","closed","all"],"type":"string"}},"url":"/issues"},"listAssignees":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/assignees"},"listComments":{"method":"GET","params":{"issue_number":{"required":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"},"since":{"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/comments"},"listCommentsForRepo":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"since":{"type":"string"},"sort":{"enum":["created","updated"],"type":"string"}},"url":"/repos/:owner/:repo/issues/comments"},"listEvents":{"method":"GET","params":{"issue_number":{"required":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/events"},"listEventsForRepo":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/events"},"listEventsForTimeline":{"headers":{"accept":"application/vnd.github.mockingbird-preview+json"},"method":"GET","params":{"issue_number":{"required":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/timeline"},"listForAuthenticatedUser":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"filter":{"enum":["assigned","created","mentioned","subscribed","all"],"type":"string"},"labels":{"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"since":{"type":"string"},"sort":{"enum":["created","updated","comments"],"type":"string"},"state":{"enum":["open","closed","all"],"type":"string"}},"url":"/user/issues"},"listForOrg":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"filter":{"enum":["assigned","created","mentioned","subscribed","all"],"type":"string"},"labels":{"type":"string"},"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"since":{"type":"string"},"sort":{"enum":["created","updated","comments"],"type":"string"},"state":{"enum":["open","closed","all"],"type":"string"}},"url":"/orgs/:org/issues"},"listForRepo":{"method":"GET","params":{"assignee":{"type":"string"},"creator":{"type":"string"},"direction":{"enum":["asc","desc"],"type":"string"},"labels":{"type":"string"},"mentioned":{"type":"string"},"milestone":{"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"},"since":{"type":"string"},"sort":{"enum":["created","updated","comments"],"type":"string"},"state":{"enum":["open","closed","all"],"type":"string"}},"url":"/repos/:owner/:repo/issues"},"listLabelsForMilestone":{"method":"GET","params":{"milestone_number":{"required":true,"type":"integer"},"number":{"alias":"milestone_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/milestones/:milestone_number/labels"},"listLabelsForRepo":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/labels"},"listLabelsOnIssue":{"method":"GET","params":{"issue_number":{"required":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/labels"},"listMilestonesForRepo":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"},"sort":{"enum":["due_on","completeness"],"type":"string"},"state":{"enum":["open","closed","all"],"type":"string"}},"url":"/repos/:owner/:repo/milestones"},"lock":{"method":"PUT","params":{"issue_number":{"required":true,"type":"integer"},"lock_reason":{"enum":["off-topic","too heated","resolved","spam"],"type":"string"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/lock"},"removeAssignees":{"method":"DELETE","params":{"assignees":{"type":"string[]"},"issue_number":{"required":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/assignees"},"removeLabel":{"method":"DELETE","params":{"issue_number":{"required":true,"type":"integer"},"name":{"required":true,"type":"string"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/labels/:name"},"removeLabels":{"method":"DELETE","params":{"issue_number":{"required":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/labels"},"replaceLabels":{"method":"PUT","params":{"issue_number":{"required":true,"type":"integer"},"labels":{"type":"string[]"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/labels"},"unlock":{"method":"DELETE","params":{"issue_number":{"required":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/lock"},"update":{"method":"PATCH","params":{"assignee":{"type":"string"},"assignees":{"type":"string[]"},"body":{"type":"string"},"issue_number":{"required":true,"type":"integer"},"labels":{"type":"string[]"},"milestone":{"allowNull":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"state":{"enum":["open","closed"],"type":"string"},"title":{"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number"},"updateComment":{"method":"PATCH","params":{"body":{"required":true,"type":"string"},"comment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/comments/:comment_id"},"updateLabel":{"method":"PATCH","params":{"color":{"type":"string"},"current_name":{"required":true,"type":"string"},"description":{"type":"string"},"name":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/labels/:current_name"},"updateMilestone":{"method":"PATCH","params":{"description":{"type":"string"},"due_on":{"type":"string"},"milestone_number":{"required":true,"type":"integer"},"number":{"alias":"milestone_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"state":{"enum":["open","closed"],"type":"string"},"title":{"type":"string"}},"url":"/repos/:owner/:repo/milestones/:milestone_number"}},"licenses":{"get":{"method":"GET","params":{"license":{"required":true,"type":"string"}},"url":"/licenses/:license"},"getForRepo":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/license"},"list":{"deprecated":"octokit.licenses.list() has been renamed to octokit.licenses.listCommonlyUsed() (2019-03-05)","method":"GET","params":{},"url":"/licenses"},"listCommonlyUsed":{"method":"GET","params":{},"url":"/licenses"}},"markdown":{"render":{"method":"POST","params":{"context":{"type":"string"},"mode":{"enum":["markdown","gfm"],"type":"string"},"text":{"required":true,"type":"string"}},"url":"/markdown"},"renderRaw":{"headers":{"content-type":"text/plain; charset=utf-8"},"method":"POST","params":{"data":{"mapTo":"data","required":true,"type":"string"}},"url":"/markdown/raw"}},"meta":{"get":{"method":"GET","params":{},"url":"/meta"}},"migrations":{"cancelImport":{"method":"DELETE","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/import"},"deleteArchiveForAuthenticatedUser":{"headers":{"accept":"application/vnd.github.wyandotte-preview+json"},"method":"DELETE","params":{"migration_id":{"required":true,"type":"integer"}},"url":"/user/migrations/:migration_id/archive"},"deleteArchiveForOrg":{"headers":{"accept":"application/vnd.github.wyandotte-preview+json"},"method":"DELETE","params":{"migration_id":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"}},"url":"/orgs/:org/migrations/:migration_id/archive"},"getArchiveForAuthenticatedUser":{"headers":{"accept":"application/vnd.github.wyandotte-preview+json"},"method":"GET","params":{"migration_id":{"required":true,"type":"integer"}},"url":"/user/migrations/:migration_id/archive"},"getArchiveForOrg":{"headers":{"accept":"application/vnd.github.wyandotte-preview+json"},"method":"GET","params":{"migration_id":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"}},"url":"/orgs/:org/migrations/:migration_id/archive"},"getCommitAuthors":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"since":{"type":"string"}},"url":"/repos/:owner/:repo/import/authors"},"getImportProgress":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/import"},"getLargeFiles":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/import/large_files"},"getStatusForAuthenticatedUser":{"headers":{"accept":"application/vnd.github.wyandotte-preview+json"},"method":"GET","params":{"migration_id":{"required":true,"type":"integer"}},"url":"/user/migrations/:migration_id"},"getStatusForOrg":{"headers":{"accept":"application/vnd.github.wyandotte-preview+json"},"method":"GET","params":{"migration_id":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"}},"url":"/orgs/:org/migrations/:migration_id"},"listForAuthenticatedUser":{"headers":{"accept":"application/vnd.github.wyandotte-preview+json"},"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/migrations"},"listForOrg":{"headers":{"accept":"application/vnd.github.wyandotte-preview+json"},"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/orgs/:org/migrations"},"listReposForOrg":{"headers":{"accept":"application/vnd.github.wyandotte-preview+json"},"method":"GET","params":{"migration_id":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/orgs/:org/migrations/:migration_id/repositories"},"listReposForUser":{"headers":{"accept":"application/vnd.github.wyandotte-preview+json"},"method":"GET","params":{"migration_id":{"required":true,"type":"integer"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/:migration_id/repositories"},"mapCommitAuthor":{"method":"PATCH","params":{"author_id":{"required":true,"type":"integer"},"email":{"type":"string"},"name":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/import/authors/:author_id"},"setLfsPreference":{"method":"PATCH","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"use_lfs":{"enum":["opt_in","opt_out"],"required":true,"type":"string"}},"url":"/repos/:owner/:repo/import/lfs"},"startForAuthenticatedUser":{"method":"POST","params":{"exclude_attachments":{"type":"boolean"},"lock_repositories":{"type":"boolean"},"repositories":{"required":true,"type":"string[]"}},"url":"/user/migrations"},"startForOrg":{"method":"POST","params":{"exclude_attachments":{"type":"boolean"},"lock_repositories":{"type":"boolean"},"org":{"required":true,"type":"string"},"repositories":{"required":true,"type":"string[]"}},"url":"/orgs/:org/migrations"},"startImport":{"method":"PUT","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"tfvc_project":{"type":"string"},"vcs":{"enum":["subversion","git","mercurial","tfvc"],"type":"string"},"vcs_password":{"type":"string"},"vcs_url":{"required":true,"type":"string"},"vcs_username":{"type":"string"}},"url":"/repos/:owner/:repo/import"},"unlockRepoForAuthenticatedUser":{"headers":{"accept":"application/vnd.github.wyandotte-preview+json"},"method":"DELETE","params":{"migration_id":{"required":true,"type":"integer"},"repo_name":{"required":true,"type":"string"}},"url":"/user/migrations/:migration_id/repos/:repo_name/lock"},"unlockRepoForOrg":{"headers":{"accept":"application/vnd.github.wyandotte-preview+json"},"method":"DELETE","params":{"migration_id":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"repo_name":{"required":true,"type":"string"}},"url":"/orgs/:org/migrations/:migration_id/repos/:repo_name/lock"},"updateImport":{"method":"PATCH","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"vcs_password":{"type":"string"},"vcs_username":{"type":"string"}},"url":"/repos/:owner/:repo/import"}},"oauthAuthorizations":{"checkAuthorization":{"deprecated":"octokit.oauthAuthorizations.checkAuthorization() has been renamed to octokit.apps.checkAuthorization() (2019-11-05)","method":"GET","params":{"access_token":{"required":true,"type":"string"},"client_id":{"required":true,"type":"string"}},"url":"/applications/:client_id/tokens/:access_token"},"createAuthorization":{"deprecated":"octokit.oauthAuthorizations.createAuthorization() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#create-a-new-authorization","method":"POST","params":{"client_id":{"type":"string"},"client_secret":{"type":"string"},"fingerprint":{"type":"string"},"note":{"required":true,"type":"string"},"note_url":{"type":"string"},"scopes":{"type":"string[]"}},"url":"/authorizations"},"deleteAuthorization":{"deprecated":"octokit.oauthAuthorizations.deleteAuthorization() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#delete-an-authorization","method":"DELETE","params":{"authorization_id":{"required":true,"type":"integer"}},"url":"/authorizations/:authorization_id"},"deleteGrant":{"deprecated":"octokit.oauthAuthorizations.deleteGrant() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#delete-a-grant","method":"DELETE","params":{"grant_id":{"required":true,"type":"integer"}},"url":"/applications/grants/:grant_id"},"getAuthorization":{"deprecated":"octokit.oauthAuthorizations.getAuthorization() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#get-a-single-authorization","method":"GET","params":{"authorization_id":{"required":true,"type":"integer"}},"url":"/authorizations/:authorization_id"},"getGrant":{"deprecated":"octokit.oauthAuthorizations.getGrant() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#get-a-single-grant","method":"GET","params":{"grant_id":{"required":true,"type":"integer"}},"url":"/applications/grants/:grant_id"},"getOrCreateAuthorizationForApp":{"deprecated":"octokit.oauthAuthorizations.getOrCreateAuthorizationForApp() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#get-or-create-an-authorization-for-a-specific-app","method":"PUT","params":{"client_id":{"required":true,"type":"string"},"client_secret":{"required":true,"type":"string"},"fingerprint":{"type":"string"},"note":{"type":"string"},"note_url":{"type":"string"},"scopes":{"type":"string[]"}},"url":"/authorizations/clients/:client_id"},"getOrCreateAuthorizationForAppAndFingerprint":{"deprecated":"octokit.oauthAuthorizations.getOrCreateAuthorizationForAppAndFingerprint() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#get-or-create-an-authorization-for-a-specific-app-and-fingerprint","method":"PUT","params":{"client_id":{"required":true,"type":"string"},"client_secret":{"required":true,"type":"string"},"fingerprint":{"required":true,"type":"string"},"note":{"type":"string"},"note_url":{"type":"string"},"scopes":{"type":"string[]"}},"url":"/authorizations/clients/:client_id/:fingerprint"},"getOrCreateAuthorizationForAppFingerprint":{"deprecated":"octokit.oauthAuthorizations.getOrCreateAuthorizationForAppFingerprint() has been renamed to octokit.oauthAuthorizations.getOrCreateAuthorizationForAppAndFingerprint() (2018-12-27)","method":"PUT","params":{"client_id":{"required":true,"type":"string"},"client_secret":{"required":true,"type":"string"},"fingerprint":{"required":true,"type":"string"},"note":{"type":"string"},"note_url":{"type":"string"},"scopes":{"type":"string[]"}},"url":"/authorizations/clients/:client_id/:fingerprint"},"listAuthorizations":{"deprecated":"octokit.oauthAuthorizations.listAuthorizations() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#list-your-authorizations","method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/authorizations"},"listGrants":{"deprecated":"octokit.oauthAuthorizations.listGrants() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#list-your-grants","method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/applications/grants"},"resetAuthorization":{"deprecated":"octokit.oauthAuthorizations.resetAuthorization() has been renamed to octokit.apps.resetAuthorization() (2019-11-05)","method":"POST","params":{"access_token":{"required":true,"type":"string"},"client_id":{"required":true,"type":"string"}},"url":"/applications/:client_id/tokens/:access_token"},"revokeAuthorizationForApplication":{"deprecated":"octokit.oauthAuthorizations.revokeAuthorizationForApplication() has been renamed to octokit.apps.revokeAuthorizationForApplication() (2019-11-05)","method":"DELETE","params":{"access_token":{"required":true,"type":"string"},"client_id":{"required":true,"type":"string"}},"url":"/applications/:client_id/tokens/:access_token"},"revokeGrantForApplication":{"deprecated":"octokit.oauthAuthorizations.revokeGrantForApplication() has been renamed to octokit.apps.revokeGrantForApplication() (2019-11-05)","method":"DELETE","params":{"access_token":{"required":true,"type":"string"},"client_id":{"required":true,"type":"string"}},"url":"/applications/:client_id/grants/:access_token"},"updateAuthorization":{"deprecated":"octokit.oauthAuthorizations.updateAuthorization() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#update-an-existing-authorization","method":"PATCH","params":{"add_scopes":{"type":"string[]"},"authorization_id":{"required":true,"type":"integer"},"fingerprint":{"type":"string"},"note":{"type":"string"},"note_url":{"type":"string"},"remove_scopes":{"type":"string[]"},"scopes":{"type":"string[]"}},"url":"/authorizations/:authorization_id"}},"orgs":{"addOrUpdateMembership":{"method":"PUT","params":{"org":{"required":true,"type":"string"},"role":{"enum":["admin","member"],"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/memberships/:username"},"blockUser":{"method":"PUT","params":{"org":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/blocks/:username"},"checkBlockedUser":{"method":"GET","params":{"org":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/blocks/:username"},"checkMembership":{"method":"GET","params":{"org":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/members/:username"},"checkPublicMembership":{"method":"GET","params":{"org":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/public_members/:username"},"concealMembership":{"method":"DELETE","params":{"org":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/public_members/:username"},"convertMemberToOutsideCollaborator":{"method":"PUT","params":{"org":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/outside_collaborators/:username"},"createHook":{"method":"POST","params":{"active":{"type":"boolean"},"config":{"required":true,"type":"object"},"config.content_type":{"type":"string"},"config.insecure_ssl":{"type":"string"},"config.secret":{"type":"string"},"config.url":{"required":true,"type":"string"},"events":{"type":"string[]"},"name":{"required":true,"type":"string"},"org":{"required":true,"type":"string"}},"url":"/orgs/:org/hooks"},"createInvitation":{"method":"POST","params":{"email":{"type":"string"},"invitee_id":{"type":"integer"},"org":{"required":true,"type":"string"},"role":{"enum":["admin","direct_member","billing_manager"],"type":"string"},"team_ids":{"type":"integer[]"}},"url":"/orgs/:org/invitations"},"deleteHook":{"method":"DELETE","params":{"hook_id":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"}},"url":"/orgs/:org/hooks/:hook_id"},"get":{"method":"GET","params":{"org":{"required":true,"type":"string"}},"url":"/orgs/:org"},"getHook":{"method":"GET","params":{"hook_id":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"}},"url":"/orgs/:org/hooks/:hook_id"},"getMembership":{"method":"GET","params":{"org":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/memberships/:username"},"getMembershipForAuthenticatedUser":{"method":"GET","params":{"org":{"required":true,"type":"string"}},"url":"/user/memberships/orgs/:org"},"list":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"since":{"type":"string"}},"url":"/organizations"},"listBlockedUsers":{"method":"GET","params":{"org":{"required":true,"type":"string"}},"url":"/orgs/:org/blocks"},"listForAuthenticatedUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/orgs"},"listForUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/users/:username/orgs"},"listHooks":{"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/orgs/:org/hooks"},"listInstallations":{"headers":{"accept":"application/vnd.github.machine-man-preview+json"},"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/orgs/:org/installations"},"listInvitationTeams":{"method":"GET","params":{"invitation_id":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/orgs/:org/invitations/:invitation_id/teams"},"listMembers":{"method":"GET","params":{"filter":{"enum":["2fa_disabled","all"],"type":"string"},"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"role":{"enum":["all","admin","member"],"type":"string"}},"url":"/orgs/:org/members"},"listMemberships":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"state":{"enum":["active","pending"],"type":"string"}},"url":"/user/memberships/orgs"},"listOutsideCollaborators":{"method":"GET","params":{"filter":{"enum":["2fa_disabled","all"],"type":"string"},"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/orgs/:org/outside_collaborators"},"listPendingInvitations":{"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/orgs/:org/invitations"},"listPublicMembers":{"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/orgs/:org/public_members"},"pingHook":{"method":"POST","params":{"hook_id":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"}},"url":"/orgs/:org/hooks/:hook_id/pings"},"publicizeMembership":{"method":"PUT","params":{"org":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/public_members/:username"},"removeMember":{"method":"DELETE","params":{"org":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/members/:username"},"removeMembership":{"method":"DELETE","params":{"org":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/memberships/:username"},"removeOutsideCollaborator":{"method":"DELETE","params":{"org":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/outside_collaborators/:username"},"unblockUser":{"method":"DELETE","params":{"org":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/blocks/:username"},"update":{"method":"PATCH","params":{"billing_email":{"type":"string"},"company":{"type":"string"},"default_repository_permission":{"enum":["read","write","admin","none"],"type":"string"},"description":{"type":"string"},"email":{"type":"string"},"has_organization_projects":{"type":"boolean"},"has_repository_projects":{"type":"boolean"},"location":{"type":"string"},"members_allowed_repository_creation_type":{"enum":["all","private","none"],"type":"string"},"members_can_create_internal_repositories":{"type":"boolean"},"members_can_create_private_repositories":{"type":"boolean"},"members_can_create_public_repositories":{"type":"boolean"},"members_can_create_repositories":{"type":"boolean"},"name":{"type":"string"},"org":{"required":true,"type":"string"}},"url":"/orgs/:org"},"updateHook":{"method":"PATCH","params":{"active":{"type":"boolean"},"config":{"type":"object"},"config.content_type":{"type":"string"},"config.insecure_ssl":{"type":"string"},"config.secret":{"type":"string"},"config.url":{"required":true,"type":"string"},"events":{"type":"string[]"},"hook_id":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"}},"url":"/orgs/:org/hooks/:hook_id"},"updateMembership":{"method":"PATCH","params":{"org":{"required":true,"type":"string"},"state":{"enum":["active"],"required":true,"type":"string"}},"url":"/user/memberships/orgs/:org"}},"projects":{"addCollaborator":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"PUT","params":{"permission":{"enum":["read","write","admin"],"type":"string"},"project_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/projects/:project_id/collaborators/:username"},"createCard":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"POST","params":{"column_id":{"required":true,"type":"integer"},"content_id":{"type":"integer"},"content_type":{"type":"string"},"note":{"type":"string"}},"url":"/projects/columns/:column_id/cards"},"createColumn":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"POST","params":{"name":{"required":true,"type":"string"},"project_id":{"required":true,"type":"integer"}},"url":"/projects/:project_id/columns"},"createForAuthenticatedUser":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"POST","params":{"body":{"type":"string"},"name":{"required":true,"type":"string"}},"url":"/user/projects"},"createForOrg":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"POST","params":{"body":{"type":"string"},"name":{"required":true,"type":"string"},"org":{"required":true,"type":"string"}},"url":"/orgs/:org/projects"},"createForRepo":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"POST","params":{"body":{"type":"string"},"name":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/projects"},"delete":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"DELETE","params":{"project_id":{"required":true,"type":"integer"}},"url":"/projects/:project_id"},"deleteCard":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"DELETE","params":{"card_id":{"required":true,"type":"integer"}},"url":"/projects/columns/cards/:card_id"},"deleteColumn":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"DELETE","params":{"column_id":{"required":true,"type":"integer"}},"url":"/projects/columns/:column_id"},"get":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"project_id":{"required":true,"type":"integer"}},"url":"/projects/:project_id"},"getCard":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"card_id":{"required":true,"type":"integer"}},"url":"/projects/columns/cards/:card_id"},"getColumn":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"column_id":{"required":true,"type":"integer"}},"url":"/projects/columns/:column_id"},"listCards":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"archived_state":{"enum":["all","archived","not_archived"],"type":"string"},"column_id":{"required":true,"type":"integer"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/projects/columns/:column_id/cards"},"listCollaborators":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"affiliation":{"enum":["outside","direct","all"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"project_id":{"required":true,"type":"integer"}},"url":"/projects/:project_id/collaborators"},"listColumns":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"project_id":{"required":true,"type":"integer"}},"url":"/projects/:project_id/columns"},"listForOrg":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"state":{"enum":["open","closed","all"],"type":"string"}},"url":"/orgs/:org/projects"},"listForRepo":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"},"state":{"enum":["open","closed","all"],"type":"string"}},"url":"/repos/:owner/:repo/projects"},"listForUser":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"state":{"enum":["open","closed","all"],"type":"string"},"username":{"required":true,"type":"string"}},"url":"/users/:username/projects"},"moveCard":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"POST","params":{"card_id":{"required":true,"type":"integer"},"column_id":{"type":"integer"},"position":{"required":true,"type":"string","validation":"^(top|bottom|after:\\d+)$"}},"url":"/projects/columns/cards/:card_id/moves"},"moveColumn":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"POST","params":{"column_id":{"required":true,"type":"integer"},"position":{"required":true,"type":"string","validation":"^(first|last|after:\\d+)$"}},"url":"/projects/columns/:column_id/moves"},"removeCollaborator":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"DELETE","params":{"project_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/projects/:project_id/collaborators/:username"},"reviewUserPermissionLevel":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"project_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/projects/:project_id/collaborators/:username/permission"},"update":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"PATCH","params":{"body":{"type":"string"},"name":{"type":"string"},"organization_permission":{"type":"string"},"private":{"type":"boolean"},"project_id":{"required":true,"type":"integer"},"state":{"enum":["open","closed"],"type":"string"}},"url":"/projects/:project_id"},"updateCard":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"PATCH","params":{"archived":{"type":"boolean"},"card_id":{"required":true,"type":"integer"},"note":{"type":"string"}},"url":"/projects/columns/cards/:card_id"},"updateColumn":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"PATCH","params":{"column_id":{"required":true,"type":"integer"},"name":{"required":true,"type":"string"}},"url":"/projects/columns/:column_id"}},"pulls":{"checkIfMerged":{"method":"GET","params":{"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number/merge"},"create":{"method":"POST","params":{"base":{"required":true,"type":"string"},"body":{"type":"string"},"draft":{"type":"boolean"},"head":{"required":true,"type":"string"},"maintainer_can_modify":{"type":"boolean"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"title":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls"},"createComment":{"method":"POST","params":{"body":{"required":true,"type":"string"},"commit_id":{"required":true,"type":"string"},"in_reply_to":{"deprecated":true,"description":"The comment ID to reply to. **Note**: This must be the ID of a top-level comment, not a reply to that comment. Replies to replies are not supported.","type":"integer"},"line":{"type":"integer"},"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"path":{"required":true,"type":"string"},"position":{"type":"integer"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"side":{"enum":["LEFT","RIGHT"],"type":"string"},"start_line":{"type":"integer"},"start_side":{"enum":["LEFT","RIGHT","side"],"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number/comments"},"createCommentReply":{"deprecated":"octokit.pulls.createCommentReply() has been renamed to octokit.pulls.createComment() (2019-09-09)","method":"POST","params":{"body":{"required":true,"type":"string"},"commit_id":{"required":true,"type":"string"},"in_reply_to":{"deprecated":true,"description":"The comment ID to reply to. **Note**: This must be the ID of a top-level comment, not a reply to that comment. Replies to replies are not supported.","type":"integer"},"line":{"type":"integer"},"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"path":{"required":true,"type":"string"},"position":{"type":"integer"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"side":{"enum":["LEFT","RIGHT"],"type":"string"},"start_line":{"type":"integer"},"start_side":{"enum":["LEFT","RIGHT","side"],"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number/comments"},"createFromIssue":{"deprecated":"octokit.pulls.createFromIssue() is deprecated, see https://developer.github.com/v3/pulls/#create-a-pull-request","method":"POST","params":{"base":{"required":true,"type":"string"},"draft":{"type":"boolean"},"head":{"required":true,"type":"string"},"issue":{"required":true,"type":"integer"},"maintainer_can_modify":{"type":"boolean"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls"},"createReview":{"method":"POST","params":{"body":{"type":"string"},"comments":{"type":"object[]"},"comments[].body":{"required":true,"type":"string"},"comments[].path":{"required":true,"type":"string"},"comments[].position":{"required":true,"type":"integer"},"commit_id":{"type":"string"},"event":{"enum":["APPROVE","REQUEST_CHANGES","COMMENT"],"type":"string"},"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number/reviews"},"createReviewCommentReply":{"method":"POST","params":{"body":{"required":true,"type":"string"},"comment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number/comments/:comment_id/replies"},"createReviewRequest":{"method":"POST","params":{"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"reviewers":{"type":"string[]"},"team_reviewers":{"type":"string[]"}},"url":"/repos/:owner/:repo/pulls/:pull_number/requested_reviewers"},"deleteComment":{"method":"DELETE","params":{"comment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/comments/:comment_id"},"deletePendingReview":{"method":"DELETE","params":{"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"review_id":{"required":true,"type":"integer"}},"url":"/repos/:owner/:repo/pulls/:pull_number/reviews/:review_id"},"deleteReviewRequest":{"method":"DELETE","params":{"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"reviewers":{"type":"string[]"},"team_reviewers":{"type":"string[]"}},"url":"/repos/:owner/:repo/pulls/:pull_number/requested_reviewers"},"dismissReview":{"method":"PUT","params":{"message":{"required":true,"type":"string"},"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"review_id":{"required":true,"type":"integer"}},"url":"/repos/:owner/:repo/pulls/:pull_number/reviews/:review_id/dismissals"},"get":{"method":"GET","params":{"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number"},"getComment":{"method":"GET","params":{"comment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/comments/:comment_id"},"getCommentsForReview":{"method":"GET","params":{"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"review_id":{"required":true,"type":"integer"}},"url":"/repos/:owner/:repo/pulls/:pull_number/reviews/:review_id/comments"},"getReview":{"method":"GET","params":{"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"review_id":{"required":true,"type":"integer"}},"url":"/repos/:owner/:repo/pulls/:pull_number/reviews/:review_id"},"list":{"method":"GET","params":{"base":{"type":"string"},"direction":{"enum":["asc","desc"],"type":"string"},"head":{"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"},"sort":{"enum":["created","updated","popularity","long-running"],"type":"string"},"state":{"enum":["open","closed","all"],"type":"string"}},"url":"/repos/:owner/:repo/pulls"},"listComments":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"since":{"type":"string"},"sort":{"enum":["created","updated"],"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number/comments"},"listCommentsForRepo":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"},"since":{"type":"string"},"sort":{"enum":["created","updated"],"type":"string"}},"url":"/repos/:owner/:repo/pulls/comments"},"listCommits":{"method":"GET","params":{"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number/commits"},"listFiles":{"method":"GET","params":{"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number/files"},"listReviewRequests":{"method":"GET","params":{"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number/requested_reviewers"},"listReviews":{"method":"GET","params":{"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number/reviews"},"merge":{"method":"PUT","params":{"commit_message":{"type":"string"},"commit_title":{"type":"string"},"merge_method":{"enum":["merge","squash","rebase"],"type":"string"},"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"sha":{"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number/merge"},"submitReview":{"method":"POST","params":{"body":{"type":"string"},"event":{"enum":["APPROVE","REQUEST_CHANGES","COMMENT"],"required":true,"type":"string"},"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"review_id":{"required":true,"type":"integer"}},"url":"/repos/:owner/:repo/pulls/:pull_number/reviews/:review_id/events"},"update":{"method":"PATCH","params":{"base":{"type":"string"},"body":{"type":"string"},"maintainer_can_modify":{"type":"boolean"},"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"state":{"enum":["open","closed"],"type":"string"},"title":{"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number"},"updateBranch":{"headers":{"accept":"application/vnd.github.lydian-preview+json"},"method":"PUT","params":{"expected_head_sha":{"type":"string"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/:pull_number/update-branch"},"updateComment":{"method":"PATCH","params":{"body":{"required":true,"type":"string"},"comment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/comments/:comment_id"},"updateReview":{"method":"PUT","params":{"body":{"required":true,"type":"string"},"number":{"alias":"pull_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"pull_number":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"review_id":{"required":true,"type":"integer"}},"url":"/repos/:owner/:repo/pulls/:pull_number/reviews/:review_id"}},"rateLimit":{"get":{"method":"GET","params":{},"url":"/rate_limit"}},"reactions":{"createForCommitComment":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"POST","params":{"comment_id":{"required":true,"type":"integer"},"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/comments/:comment_id/reactions"},"createForIssue":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"POST","params":{"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"required":true,"type":"string"},"issue_number":{"required":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/reactions"},"createForIssueComment":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"POST","params":{"comment_id":{"required":true,"type":"integer"},"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/comments/:comment_id/reactions"},"createForPullRequestReviewComment":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"POST","params":{"comment_id":{"required":true,"type":"integer"},"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/comments/:comment_id/reactions"},"createForTeamDiscussion":{"deprecated":"octokit.reactions.createForTeamDiscussion() has been renamed to octokit.reactions.createForTeamDiscussionLegacy() (2020-01-16)","headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"POST","params":{"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"required":true,"type":"string"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/reactions"},"createForTeamDiscussionComment":{"deprecated":"octokit.reactions.createForTeamDiscussionComment() has been renamed to octokit.reactions.createForTeamDiscussionCommentLegacy() (2020-01-16)","headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"POST","params":{"comment_number":{"required":true,"type":"integer"},"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"required":true,"type":"string"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments/:comment_number/reactions"},"createForTeamDiscussionCommentInOrg":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"POST","params":{"comment_number":{"required":true,"type":"integer"},"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"required":true,"type":"string"},"discussion_number":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments/:comment_number/reactions"},"createForTeamDiscussionCommentLegacy":{"deprecated":"octokit.reactions.createForTeamDiscussionCommentLegacy() is deprecated, see https://developer.github.com/v3/reactions/#create-reaction-for-a-team-discussion-comment-legacy","headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"POST","params":{"comment_number":{"required":true,"type":"integer"},"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"required":true,"type":"string"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments/:comment_number/reactions"},"createForTeamDiscussionInOrg":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"POST","params":{"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"required":true,"type":"string"},"discussion_number":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions/:discussion_number/reactions"},"createForTeamDiscussionLegacy":{"deprecated":"octokit.reactions.createForTeamDiscussionLegacy() is deprecated, see https://developer.github.com/v3/reactions/#create-reaction-for-a-team-discussion-legacy","headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"POST","params":{"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"required":true,"type":"string"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/reactions"},"delete":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"DELETE","params":{"reaction_id":{"required":true,"type":"integer"}},"url":"/reactions/:reaction_id"},"listForCommitComment":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"GET","params":{"comment_id":{"required":true,"type":"integer"},"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/comments/:comment_id/reactions"},"listForIssue":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"GET","params":{"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"type":"string"},"issue_number":{"required":true,"type":"integer"},"number":{"alias":"issue_number","deprecated":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/:issue_number/reactions"},"listForIssueComment":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"GET","params":{"comment_id":{"required":true,"type":"integer"},"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/issues/comments/:comment_id/reactions"},"listForPullRequestReviewComment":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"GET","params":{"comment_id":{"required":true,"type":"integer"},"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pulls/comments/:comment_id/reactions"},"listForTeamDiscussion":{"deprecated":"octokit.reactions.listForTeamDiscussion() has been renamed to octokit.reactions.listForTeamDiscussionLegacy() (2020-01-16)","headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"GET","params":{"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"type":"string"},"discussion_number":{"required":true,"type":"integer"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/reactions"},"listForTeamDiscussionComment":{"deprecated":"octokit.reactions.listForTeamDiscussionComment() has been renamed to octokit.reactions.listForTeamDiscussionCommentLegacy() (2020-01-16)","headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"GET","params":{"comment_number":{"required":true,"type":"integer"},"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"type":"string"},"discussion_number":{"required":true,"type":"integer"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments/:comment_number/reactions"},"listForTeamDiscussionCommentInOrg":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"GET","params":{"comment_number":{"required":true,"type":"integer"},"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"type":"string"},"discussion_number":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments/:comment_number/reactions"},"listForTeamDiscussionCommentLegacy":{"deprecated":"octokit.reactions.listForTeamDiscussionCommentLegacy() is deprecated, see https://developer.github.com/v3/reactions/#list-reactions-for-a-team-discussion-comment-legacy","headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"GET","params":{"comment_number":{"required":true,"type":"integer"},"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"type":"string"},"discussion_number":{"required":true,"type":"integer"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments/:comment_number/reactions"},"listForTeamDiscussionInOrg":{"headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"GET","params":{"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"type":"string"},"discussion_number":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions/:discussion_number/reactions"},"listForTeamDiscussionLegacy":{"deprecated":"octokit.reactions.listForTeamDiscussionLegacy() is deprecated, see https://developer.github.com/v3/reactions/#list-reactions-for-a-team-discussion-legacy","headers":{"accept":"application/vnd.github.squirrel-girl-preview+json"},"method":"GET","params":{"content":{"enum":["+1","-1","laugh","confused","heart","hooray","rocket","eyes"],"type":"string"},"discussion_number":{"required":true,"type":"integer"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/reactions"}},"repos":{"acceptInvitation":{"method":"PATCH","params":{"invitation_id":{"required":true,"type":"integer"}},"url":"/user/repository_invitations/:invitation_id"},"addCollaborator":{"method":"PUT","params":{"owner":{"required":true,"type":"string"},"permission":{"enum":["pull","push","admin"],"type":"string"},"repo":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/collaborators/:username"},"addDeployKey":{"method":"POST","params":{"key":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"read_only":{"type":"boolean"},"repo":{"required":true,"type":"string"},"title":{"type":"string"}},"url":"/repos/:owner/:repo/keys"},"addProtectedBranchAdminEnforcement":{"method":"POST","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/enforce_admins"},"addProtectedBranchAppRestrictions":{"method":"POST","params":{"apps":{"mapTo":"data","required":true,"type":"string[]"},"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/apps"},"addProtectedBranchRequiredSignatures":{"headers":{"accept":"application/vnd.github.zzzax-preview+json"},"method":"POST","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_signatures"},"addProtectedBranchRequiredStatusChecksContexts":{"method":"POST","params":{"branch":{"required":true,"type":"string"},"contexts":{"mapTo":"data","required":true,"type":"string[]"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_status_checks/contexts"},"addProtectedBranchTeamRestrictions":{"method":"POST","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"teams":{"mapTo":"data","required":true,"type":"string[]"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/teams"},"addProtectedBranchUserRestrictions":{"method":"POST","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"users":{"mapTo":"data","required":true,"type":"string[]"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/users"},"checkCollaborator":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/collaborators/:username"},"checkVulnerabilityAlerts":{"headers":{"accept":"application/vnd.github.dorian-preview+json"},"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/vulnerability-alerts"},"compareCommits":{"method":"GET","params":{"base":{"required":true,"type":"string"},"head":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/compare/:base...:head"},"createCommitComment":{"method":"POST","params":{"body":{"required":true,"type":"string"},"commit_sha":{"required":true,"type":"string"},"line":{"type":"integer"},"owner":{"required":true,"type":"string"},"path":{"type":"string"},"position":{"type":"integer"},"repo":{"required":true,"type":"string"},"sha":{"alias":"commit_sha","deprecated":true,"type":"string"}},"url":"/repos/:owner/:repo/commits/:commit_sha/comments"},"createDeployment":{"method":"POST","params":{"auto_merge":{"type":"boolean"},"description":{"type":"string"},"environment":{"type":"string"},"owner":{"required":true,"type":"string"},"payload":{"type":"string"},"production_environment":{"type":"boolean"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"required_contexts":{"type":"string[]"},"task":{"type":"string"},"transient_environment":{"type":"boolean"}},"url":"/repos/:owner/:repo/deployments"},"createDeploymentStatus":{"method":"POST","params":{"auto_inactive":{"type":"boolean"},"deployment_id":{"required":true,"type":"integer"},"description":{"type":"string"},"environment":{"enum":["production","staging","qa"],"type":"string"},"environment_url":{"type":"string"},"log_url":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"state":{"enum":["error","failure","inactive","in_progress","queued","pending","success"],"required":true,"type":"string"},"target_url":{"type":"string"}},"url":"/repos/:owner/:repo/deployments/:deployment_id/statuses"},"createDispatchEvent":{"headers":{"accept":"application/vnd.github.everest-preview+json"},"method":"POST","params":{"client_payload":{"type":"object"},"event_type":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/dispatches"},"createFile":{"deprecated":"octokit.repos.createFile() has been renamed to octokit.repos.createOrUpdateFile() (2019-06-07)","method":"PUT","params":{"author":{"type":"object"},"author.email":{"required":true,"type":"string"},"author.name":{"required":true,"type":"string"},"branch":{"type":"string"},"committer":{"type":"object"},"committer.email":{"required":true,"type":"string"},"committer.name":{"required":true,"type":"string"},"content":{"required":true,"type":"string"},"message":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"path":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"sha":{"type":"string"}},"url":"/repos/:owner/:repo/contents/:path"},"createForAuthenticatedUser":{"method":"POST","params":{"allow_merge_commit":{"type":"boolean"},"allow_rebase_merge":{"type":"boolean"},"allow_squash_merge":{"type":"boolean"},"auto_init":{"type":"boolean"},"delete_branch_on_merge":{"type":"boolean"},"description":{"type":"string"},"gitignore_template":{"type":"string"},"has_issues":{"type":"boolean"},"has_projects":{"type":"boolean"},"has_wiki":{"type":"boolean"},"homepage":{"type":"string"},"is_template":{"type":"boolean"},"license_template":{"type":"string"},"name":{"required":true,"type":"string"},"private":{"type":"boolean"},"team_id":{"type":"integer"},"visibility":{"enum":["public","private","visibility","internal"],"type":"string"}},"url":"/user/repos"},"createFork":{"method":"POST","params":{"organization":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/forks"},"createHook":{"method":"POST","params":{"active":{"type":"boolean"},"config":{"required":true,"type":"object"},"config.content_type":{"type":"string"},"config.insecure_ssl":{"type":"string"},"config.secret":{"type":"string"},"config.url":{"required":true,"type":"string"},"events":{"type":"string[]"},"name":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/hooks"},"createInOrg":{"method":"POST","params":{"allow_merge_commit":{"type":"boolean"},"allow_rebase_merge":{"type":"boolean"},"allow_squash_merge":{"type":"boolean"},"auto_init":{"type":"boolean"},"delete_branch_on_merge":{"type":"boolean"},"description":{"type":"string"},"gitignore_template":{"type":"string"},"has_issues":{"type":"boolean"},"has_projects":{"type":"boolean"},"has_wiki":{"type":"boolean"},"homepage":{"type":"string"},"is_template":{"type":"boolean"},"license_template":{"type":"string"},"name":{"required":true,"type":"string"},"org":{"required":true,"type":"string"},"private":{"type":"boolean"},"team_id":{"type":"integer"},"visibility":{"enum":["public","private","visibility","internal"],"type":"string"}},"url":"/orgs/:org/repos"},"createOrUpdateFile":{"method":"PUT","params":{"author":{"type":"object"},"author.email":{"required":true,"type":"string"},"author.name":{"required":true,"type":"string"},"branch":{"type":"string"},"committer":{"type":"object"},"committer.email":{"required":true,"type":"string"},"committer.name":{"required":true,"type":"string"},"content":{"required":true,"type":"string"},"message":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"path":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"sha":{"type":"string"}},"url":"/repos/:owner/:repo/contents/:path"},"createRelease":{"method":"POST","params":{"body":{"type":"string"},"draft":{"type":"boolean"},"name":{"type":"string"},"owner":{"required":true,"type":"string"},"prerelease":{"type":"boolean"},"repo":{"required":true,"type":"string"},"tag_name":{"required":true,"type":"string"},"target_commitish":{"type":"string"}},"url":"/repos/:owner/:repo/releases"},"createStatus":{"method":"POST","params":{"context":{"type":"string"},"description":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"sha":{"required":true,"type":"string"},"state":{"enum":["error","failure","pending","success"],"required":true,"type":"string"},"target_url":{"type":"string"}},"url":"/repos/:owner/:repo/statuses/:sha"},"createUsingTemplate":{"headers":{"accept":"application/vnd.github.baptiste-preview+json"},"method":"POST","params":{"description":{"type":"string"},"name":{"required":true,"type":"string"},"owner":{"type":"string"},"private":{"type":"boolean"},"template_owner":{"required":true,"type":"string"},"template_repo":{"required":true,"type":"string"}},"url":"/repos/:template_owner/:template_repo/generate"},"declineInvitation":{"method":"DELETE","params":{"invitation_id":{"required":true,"type":"integer"}},"url":"/user/repository_invitations/:invitation_id"},"delete":{"method":"DELETE","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo"},"deleteCommitComment":{"method":"DELETE","params":{"comment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/comments/:comment_id"},"deleteDownload":{"method":"DELETE","params":{"download_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/downloads/:download_id"},"deleteFile":{"method":"DELETE","params":{"author":{"type":"object"},"author.email":{"type":"string"},"author.name":{"type":"string"},"branch":{"type":"string"},"committer":{"type":"object"},"committer.email":{"type":"string"},"committer.name":{"type":"string"},"message":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"path":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"sha":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/contents/:path"},"deleteHook":{"method":"DELETE","params":{"hook_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/hooks/:hook_id"},"deleteInvitation":{"method":"DELETE","params":{"invitation_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/invitations/:invitation_id"},"deleteRelease":{"method":"DELETE","params":{"owner":{"required":true,"type":"string"},"release_id":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/releases/:release_id"},"deleteReleaseAsset":{"method":"DELETE","params":{"asset_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/releases/assets/:asset_id"},"disableAutomatedSecurityFixes":{"headers":{"accept":"application/vnd.github.london-preview+json"},"method":"DELETE","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/automated-security-fixes"},"disablePagesSite":{"headers":{"accept":"application/vnd.github.switcheroo-preview+json"},"method":"DELETE","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pages"},"disableVulnerabilityAlerts":{"headers":{"accept":"application/vnd.github.dorian-preview+json"},"method":"DELETE","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/vulnerability-alerts"},"enableAutomatedSecurityFixes":{"headers":{"accept":"application/vnd.github.london-preview+json"},"method":"PUT","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/automated-security-fixes"},"enablePagesSite":{"headers":{"accept":"application/vnd.github.switcheroo-preview+json"},"method":"POST","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"source":{"type":"object"},"source.branch":{"enum":["master","gh-pages"],"type":"string"},"source.path":{"type":"string"}},"url":"/repos/:owner/:repo/pages"},"enableVulnerabilityAlerts":{"headers":{"accept":"application/vnd.github.dorian-preview+json"},"method":"PUT","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/vulnerability-alerts"},"get":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo"},"getAppsWithAccessToProtectedBranch":{"method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/apps"},"getArchiveLink":{"method":"GET","params":{"archive_format":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/:archive_format/:ref"},"getBranch":{"method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch"},"getBranchProtection":{"method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection"},"getClones":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"per":{"enum":["day","week"],"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/traffic/clones"},"getCodeFrequencyStats":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/stats/code_frequency"},"getCollaboratorPermissionLevel":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/collaborators/:username/permission"},"getCombinedStatusForRef":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/commits/:ref/status"},"getCommit":{"method":"GET","params":{"commit_sha":{"alias":"ref","deprecated":true,"type":"string"},"owner":{"required":true,"type":"string"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"sha":{"alias":"ref","deprecated":true,"type":"string"}},"url":"/repos/:owner/:repo/commits/:ref"},"getCommitActivityStats":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/stats/commit_activity"},"getCommitComment":{"method":"GET","params":{"comment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/comments/:comment_id"},"getCommitRefSha":{"deprecated":"octokit.repos.getCommitRefSha() is deprecated, see https://developer.github.com/v3/repos/commits/#get-a-single-commit","headers":{"accept":"application/vnd.github.v3.sha"},"method":"GET","params":{"owner":{"required":true,"type":"string"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/commits/:ref"},"getContents":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"path":{"required":true,"type":"string"},"ref":{"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/contents/:path"},"getContributorsStats":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/stats/contributors"},"getDeployKey":{"method":"GET","params":{"key_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/keys/:key_id"},"getDeployment":{"method":"GET","params":{"deployment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/deployments/:deployment_id"},"getDeploymentStatus":{"method":"GET","params":{"deployment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"status_id":{"required":true,"type":"integer"}},"url":"/repos/:owner/:repo/deployments/:deployment_id/statuses/:status_id"},"getDownload":{"method":"GET","params":{"download_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/downloads/:download_id"},"getHook":{"method":"GET","params":{"hook_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/hooks/:hook_id"},"getLatestPagesBuild":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pages/builds/latest"},"getLatestRelease":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/releases/latest"},"getPages":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pages"},"getPagesBuild":{"method":"GET","params":{"build_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pages/builds/:build_id"},"getParticipationStats":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/stats/participation"},"getProtectedBranchAdminEnforcement":{"method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/enforce_admins"},"getProtectedBranchPullRequestReviewEnforcement":{"method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_pull_request_reviews"},"getProtectedBranchRequiredSignatures":{"headers":{"accept":"application/vnd.github.zzzax-preview+json"},"method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_signatures"},"getProtectedBranchRequiredStatusChecks":{"method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_status_checks"},"getProtectedBranchRestrictions":{"method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions"},"getPunchCardStats":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/stats/punch_card"},"getReadme":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"ref":{"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/readme"},"getRelease":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"release_id":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/releases/:release_id"},"getReleaseAsset":{"method":"GET","params":{"asset_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/releases/assets/:asset_id"},"getReleaseByTag":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"tag":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/releases/tags/:tag"},"getTeamsWithAccessToProtectedBranch":{"method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/teams"},"getTopPaths":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/traffic/popular/paths"},"getTopReferrers":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/traffic/popular/referrers"},"getUsersWithAccessToProtectedBranch":{"method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/users"},"getViews":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"per":{"enum":["day","week"],"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/traffic/views"},"list":{"method":"GET","params":{"affiliation":{"type":"string"},"direction":{"enum":["asc","desc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"sort":{"enum":["created","updated","pushed","full_name"],"type":"string"},"type":{"enum":["all","owner","public","private","member"],"type":"string"},"visibility":{"enum":["all","public","private"],"type":"string"}},"url":"/user/repos"},"listAppsWithAccessToProtectedBranch":{"deprecated":"octokit.repos.listAppsWithAccessToProtectedBranch() has been renamed to octokit.repos.getAppsWithAccessToProtectedBranch() (2019-09-13)","method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/apps"},"listAssetsForRelease":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"release_id":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/releases/:release_id/assets"},"listBranches":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"protected":{"type":"boolean"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches"},"listBranchesForHeadCommit":{"headers":{"accept":"application/vnd.github.groot-preview+json"},"method":"GET","params":{"commit_sha":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/commits/:commit_sha/branches-where-head"},"listCollaborators":{"method":"GET","params":{"affiliation":{"enum":["outside","direct","all"],"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/collaborators"},"listCommentsForCommit":{"method":"GET","params":{"commit_sha":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"ref":{"alias":"commit_sha","deprecated":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/commits/:commit_sha/comments"},"listCommitComments":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/comments"},"listCommits":{"method":"GET","params":{"author":{"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"path":{"type":"string"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"},"sha":{"type":"string"},"since":{"type":"string"},"until":{"type":"string"}},"url":"/repos/:owner/:repo/commits"},"listContributors":{"method":"GET","params":{"anon":{"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/contributors"},"listDeployKeys":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/keys"},"listDeploymentStatuses":{"method":"GET","params":{"deployment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/deployments/:deployment_id/statuses"},"listDeployments":{"method":"GET","params":{"environment":{"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"ref":{"type":"string"},"repo":{"required":true,"type":"string"},"sha":{"type":"string"},"task":{"type":"string"}},"url":"/repos/:owner/:repo/deployments"},"listDownloads":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/downloads"},"listForOrg":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"sort":{"enum":["created","updated","pushed","full_name"],"type":"string"},"type":{"enum":["all","public","private","forks","sources","member","internal"],"type":"string"}},"url":"/orgs/:org/repos"},"listForUser":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"sort":{"enum":["created","updated","pushed","full_name"],"type":"string"},"type":{"enum":["all","owner","member"],"type":"string"},"username":{"required":true,"type":"string"}},"url":"/users/:username/repos"},"listForks":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"},"sort":{"enum":["newest","oldest","stargazers"],"type":"string"}},"url":"/repos/:owner/:repo/forks"},"listHooks":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/hooks"},"listInvitations":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/invitations"},"listInvitationsForAuthenticatedUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/repository_invitations"},"listLanguages":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/languages"},"listPagesBuilds":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pages/builds"},"listProtectedBranchRequiredStatusChecksContexts":{"method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_status_checks/contexts"},"listProtectedBranchTeamRestrictions":{"deprecated":"octokit.repos.listProtectedBranchTeamRestrictions() has been renamed to octokit.repos.getTeamsWithAccessToProtectedBranch() (2019-09-09)","method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/teams"},"listProtectedBranchUserRestrictions":{"deprecated":"octokit.repos.listProtectedBranchUserRestrictions() has been renamed to octokit.repos.getUsersWithAccessToProtectedBranch() (2019-09-09)","method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/users"},"listPublic":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"since":{"type":"string"}},"url":"/repositories"},"listPullRequestsAssociatedWithCommit":{"headers":{"accept":"application/vnd.github.groot-preview+json"},"method":"GET","params":{"commit_sha":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/commits/:commit_sha/pulls"},"listReleases":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/releases"},"listStatusesForRef":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"ref":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/commits/:ref/statuses"},"listTags":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/tags"},"listTeams":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/teams"},"listTeamsWithAccessToProtectedBranch":{"deprecated":"octokit.repos.listTeamsWithAccessToProtectedBranch() has been renamed to octokit.repos.getTeamsWithAccessToProtectedBranch() (2019-09-13)","method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/teams"},"listTopics":{"headers":{"accept":"application/vnd.github.mercy-preview+json"},"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/topics"},"listUsersWithAccessToProtectedBranch":{"deprecated":"octokit.repos.listUsersWithAccessToProtectedBranch() has been renamed to octokit.repos.getUsersWithAccessToProtectedBranch() (2019-09-13)","method":"GET","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/users"},"merge":{"method":"POST","params":{"base":{"required":true,"type":"string"},"commit_message":{"type":"string"},"head":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/merges"},"pingHook":{"method":"POST","params":{"hook_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/hooks/:hook_id/pings"},"removeBranchProtection":{"method":"DELETE","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection"},"removeCollaborator":{"method":"DELETE","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/collaborators/:username"},"removeDeployKey":{"method":"DELETE","params":{"key_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/keys/:key_id"},"removeProtectedBranchAdminEnforcement":{"method":"DELETE","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/enforce_admins"},"removeProtectedBranchAppRestrictions":{"method":"DELETE","params":{"apps":{"mapTo":"data","required":true,"type":"string[]"},"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/apps"},"removeProtectedBranchPullRequestReviewEnforcement":{"method":"DELETE","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_pull_request_reviews"},"removeProtectedBranchRequiredSignatures":{"headers":{"accept":"application/vnd.github.zzzax-preview+json"},"method":"DELETE","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_signatures"},"removeProtectedBranchRequiredStatusChecks":{"method":"DELETE","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_status_checks"},"removeProtectedBranchRequiredStatusChecksContexts":{"method":"DELETE","params":{"branch":{"required":true,"type":"string"},"contexts":{"mapTo":"data","required":true,"type":"string[]"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_status_checks/contexts"},"removeProtectedBranchRestrictions":{"method":"DELETE","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions"},"removeProtectedBranchTeamRestrictions":{"method":"DELETE","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"teams":{"mapTo":"data","required":true,"type":"string[]"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/teams"},"removeProtectedBranchUserRestrictions":{"method":"DELETE","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"users":{"mapTo":"data","required":true,"type":"string[]"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/users"},"replaceProtectedBranchAppRestrictions":{"method":"PUT","params":{"apps":{"mapTo":"data","required":true,"type":"string[]"},"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/apps"},"replaceProtectedBranchRequiredStatusChecksContexts":{"method":"PUT","params":{"branch":{"required":true,"type":"string"},"contexts":{"mapTo":"data","required":true,"type":"string[]"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_status_checks/contexts"},"replaceProtectedBranchTeamRestrictions":{"method":"PUT","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"teams":{"mapTo":"data","required":true,"type":"string[]"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/teams"},"replaceProtectedBranchUserRestrictions":{"method":"PUT","params":{"branch":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"users":{"mapTo":"data","required":true,"type":"string[]"}},"url":"/repos/:owner/:repo/branches/:branch/protection/restrictions/users"},"replaceTopics":{"headers":{"accept":"application/vnd.github.mercy-preview+json"},"method":"PUT","params":{"names":{"required":true,"type":"string[]"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/topics"},"requestPageBuild":{"method":"POST","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/pages/builds"},"retrieveCommunityProfileMetrics":{"method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/community/profile"},"testPushHook":{"method":"POST","params":{"hook_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/hooks/:hook_id/tests"},"transfer":{"method":"POST","params":{"new_owner":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"team_ids":{"type":"integer[]"}},"url":"/repos/:owner/:repo/transfer"},"update":{"method":"PATCH","params":{"allow_merge_commit":{"type":"boolean"},"allow_rebase_merge":{"type":"boolean"},"allow_squash_merge":{"type":"boolean"},"archived":{"type":"boolean"},"default_branch":{"type":"string"},"delete_branch_on_merge":{"type":"boolean"},"description":{"type":"string"},"has_issues":{"type":"boolean"},"has_projects":{"type":"boolean"},"has_wiki":{"type":"boolean"},"homepage":{"type":"string"},"is_template":{"type":"boolean"},"name":{"type":"string"},"owner":{"required":true,"type":"string"},"private":{"type":"boolean"},"repo":{"required":true,"type":"string"},"visibility":{"enum":["public","private","visibility","internal"],"type":"string"}},"url":"/repos/:owner/:repo"},"updateBranchProtection":{"method":"PUT","params":{"allow_deletions":{"type":"boolean"},"allow_force_pushes":{"allowNull":true,"type":"boolean"},"branch":{"required":true,"type":"string"},"enforce_admins":{"allowNull":true,"required":true,"type":"boolean"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"required_linear_history":{"type":"boolean"},"required_pull_request_reviews":{"allowNull":true,"required":true,"type":"object"},"required_pull_request_reviews.dismiss_stale_reviews":{"type":"boolean"},"required_pull_request_reviews.dismissal_restrictions":{"type":"object"},"required_pull_request_reviews.dismissal_restrictions.teams":{"type":"string[]"},"required_pull_request_reviews.dismissal_restrictions.users":{"type":"string[]"},"required_pull_request_reviews.require_code_owner_reviews":{"type":"boolean"},"required_pull_request_reviews.required_approving_review_count":{"type":"integer"},"required_status_checks":{"allowNull":true,"required":true,"type":"object"},"required_status_checks.contexts":{"required":true,"type":"string[]"},"required_status_checks.strict":{"required":true,"type":"boolean"},"restrictions":{"allowNull":true,"required":true,"type":"object"},"restrictions.apps":{"type":"string[]"},"restrictions.teams":{"required":true,"type":"string[]"},"restrictions.users":{"required":true,"type":"string[]"}},"url":"/repos/:owner/:repo/branches/:branch/protection"},"updateCommitComment":{"method":"PATCH","params":{"body":{"required":true,"type":"string"},"comment_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/comments/:comment_id"},"updateFile":{"deprecated":"octokit.repos.updateFile() has been renamed to octokit.repos.createOrUpdateFile() (2019-06-07)","method":"PUT","params":{"author":{"type":"object"},"author.email":{"required":true,"type":"string"},"author.name":{"required":true,"type":"string"},"branch":{"type":"string"},"committer":{"type":"object"},"committer.email":{"required":true,"type":"string"},"committer.name":{"required":true,"type":"string"},"content":{"required":true,"type":"string"},"message":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"path":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"sha":{"type":"string"}},"url":"/repos/:owner/:repo/contents/:path"},"updateHook":{"method":"PATCH","params":{"active":{"type":"boolean"},"add_events":{"type":"string[]"},"config":{"type":"object"},"config.content_type":{"type":"string"},"config.insecure_ssl":{"type":"string"},"config.secret":{"type":"string"},"config.url":{"required":true,"type":"string"},"events":{"type":"string[]"},"hook_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"remove_events":{"type":"string[]"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/hooks/:hook_id"},"updateInformationAboutPagesSite":{"method":"PUT","params":{"cname":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"source":{"enum":["\"gh-pages\"","\"master\"","\"master /docs\""],"type":"string"}},"url":"/repos/:owner/:repo/pages"},"updateInvitation":{"method":"PATCH","params":{"invitation_id":{"required":true,"type":"integer"},"owner":{"required":true,"type":"string"},"permissions":{"enum":["read","write","admin"],"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/invitations/:invitation_id"},"updateProtectedBranchPullRequestReviewEnforcement":{"method":"PATCH","params":{"branch":{"required":true,"type":"string"},"dismiss_stale_reviews":{"type":"boolean"},"dismissal_restrictions":{"type":"object"},"dismissal_restrictions.teams":{"type":"string[]"},"dismissal_restrictions.users":{"type":"string[]"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"require_code_owner_reviews":{"type":"boolean"},"required_approving_review_count":{"type":"integer"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_pull_request_reviews"},"updateProtectedBranchRequiredStatusChecks":{"method":"PATCH","params":{"branch":{"required":true,"type":"string"},"contexts":{"type":"string[]"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"strict":{"type":"boolean"}},"url":"/repos/:owner/:repo/branches/:branch/protection/required_status_checks"},"updateRelease":{"method":"PATCH","params":{"body":{"type":"string"},"draft":{"type":"boolean"},"name":{"type":"string"},"owner":{"required":true,"type":"string"},"prerelease":{"type":"boolean"},"release_id":{"required":true,"type":"integer"},"repo":{"required":true,"type":"string"},"tag_name":{"type":"string"},"target_commitish":{"type":"string"}},"url":"/repos/:owner/:repo/releases/:release_id"},"updateReleaseAsset":{"method":"PATCH","params":{"asset_id":{"required":true,"type":"integer"},"label":{"type":"string"},"name":{"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"}},"url":"/repos/:owner/:repo/releases/assets/:asset_id"},"uploadReleaseAsset":{"method":"POST","params":{"file":{"mapTo":"data","required":true,"type":"string | object"},"headers":{"required":true,"type":"object"},"headers.content-length":{"required":true,"type":"integer"},"headers.content-type":{"required":true,"type":"string"},"label":{"type":"string"},"name":{"required":true,"type":"string"},"url":{"required":true,"type":"string"}},"url":":url"}},"search":{"code":{"method":"GET","params":{"order":{"enum":["desc","asc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"q":{"required":true,"type":"string"},"sort":{"enum":["indexed"],"type":"string"}},"url":"/search/code"},"commits":{"headers":{"accept":"application/vnd.github.cloak-preview+json"},"method":"GET","params":{"order":{"enum":["desc","asc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"q":{"required":true,"type":"string"},"sort":{"enum":["author-date","committer-date"],"type":"string"}},"url":"/search/commits"},"issues":{"deprecated":"octokit.search.issues() has been renamed to octokit.search.issuesAndPullRequests() (2018-12-27)","method":"GET","params":{"order":{"enum":["desc","asc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"q":{"required":true,"type":"string"},"sort":{"enum":["comments","reactions","reactions-+1","reactions--1","reactions-smile","reactions-thinking_face","reactions-heart","reactions-tada","interactions","created","updated"],"type":"string"}},"url":"/search/issues"},"issuesAndPullRequests":{"method":"GET","params":{"order":{"enum":["desc","asc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"q":{"required":true,"type":"string"},"sort":{"enum":["comments","reactions","reactions-+1","reactions--1","reactions-smile","reactions-thinking_face","reactions-heart","reactions-tada","interactions","created","updated"],"type":"string"}},"url":"/search/issues"},"labels":{"method":"GET","params":{"order":{"enum":["desc","asc"],"type":"string"},"q":{"required":true,"type":"string"},"repository_id":{"required":true,"type":"integer"},"sort":{"enum":["created","updated"],"type":"string"}},"url":"/search/labels"},"repos":{"method":"GET","params":{"order":{"enum":["desc","asc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"q":{"required":true,"type":"string"},"sort":{"enum":["stars","forks","help-wanted-issues","updated"],"type":"string"}},"url":"/search/repositories"},"topics":{"method":"GET","params":{"q":{"required":true,"type":"string"}},"url":"/search/topics"},"users":{"method":"GET","params":{"order":{"enum":["desc","asc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"q":{"required":true,"type":"string"},"sort":{"enum":["followers","repositories","joined"],"type":"string"}},"url":"/search/users"}},"teams":{"addMember":{"deprecated":"octokit.teams.addMember() has been renamed to octokit.teams.addMemberLegacy() (2020-01-16)","method":"PUT","params":{"team_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/teams/:team_id/members/:username"},"addMemberLegacy":{"deprecated":"octokit.teams.addMemberLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#add-team-member-legacy","method":"PUT","params":{"team_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/teams/:team_id/members/:username"},"addOrUpdateMembership":{"deprecated":"octokit.teams.addOrUpdateMembership() has been renamed to octokit.teams.addOrUpdateMembershipLegacy() (2020-01-16)","method":"PUT","params":{"role":{"enum":["member","maintainer"],"type":"string"},"team_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/teams/:team_id/memberships/:username"},"addOrUpdateMembershipInOrg":{"method":"PUT","params":{"org":{"required":true,"type":"string"},"role":{"enum":["member","maintainer"],"type":"string"},"team_slug":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/memberships/:username"},"addOrUpdateMembershipLegacy":{"deprecated":"octokit.teams.addOrUpdateMembershipLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#add-or-update-team-membership-legacy","method":"PUT","params":{"role":{"enum":["member","maintainer"],"type":"string"},"team_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/teams/:team_id/memberships/:username"},"addOrUpdateProject":{"deprecated":"octokit.teams.addOrUpdateProject() has been renamed to octokit.teams.addOrUpdateProjectLegacy() (2020-01-16)","headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"PUT","params":{"permission":{"enum":["read","write","admin"],"type":"string"},"project_id":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/projects/:project_id"},"addOrUpdateProjectInOrg":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"PUT","params":{"org":{"required":true,"type":"string"},"permission":{"enum":["read","write","admin"],"type":"string"},"project_id":{"required":true,"type":"integer"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/projects/:project_id"},"addOrUpdateProjectLegacy":{"deprecated":"octokit.teams.addOrUpdateProjectLegacy() is deprecated, see https://developer.github.com/v3/teams/#add-or-update-team-project-legacy","headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"PUT","params":{"permission":{"enum":["read","write","admin"],"type":"string"},"project_id":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/projects/:project_id"},"addOrUpdateRepo":{"deprecated":"octokit.teams.addOrUpdateRepo() has been renamed to octokit.teams.addOrUpdateRepoLegacy() (2020-01-16)","method":"PUT","params":{"owner":{"required":true,"type":"string"},"permission":{"enum":["pull","push","admin"],"type":"string"},"repo":{"required":true,"type":"string"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/repos/:owner/:repo"},"addOrUpdateRepoInOrg":{"method":"PUT","params":{"org":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"permission":{"enum":["pull","push","admin"],"type":"string"},"repo":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/repos/:owner/:repo"},"addOrUpdateRepoLegacy":{"deprecated":"octokit.teams.addOrUpdateRepoLegacy() is deprecated, see https://developer.github.com/v3/teams/#add-or-update-team-repository-legacy","method":"PUT","params":{"owner":{"required":true,"type":"string"},"permission":{"enum":["pull","push","admin"],"type":"string"},"repo":{"required":true,"type":"string"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/repos/:owner/:repo"},"checkManagesRepo":{"deprecated":"octokit.teams.checkManagesRepo() has been renamed to octokit.teams.checkManagesRepoLegacy() (2020-01-16)","method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/repos/:owner/:repo"},"checkManagesRepoInOrg":{"method":"GET","params":{"org":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/repos/:owner/:repo"},"checkManagesRepoLegacy":{"deprecated":"octokit.teams.checkManagesRepoLegacy() is deprecated, see https://developer.github.com/v3/teams/#check-if-a-team-manages-a-repository-legacy","method":"GET","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/repos/:owner/:repo"},"create":{"method":"POST","params":{"description":{"type":"string"},"maintainers":{"type":"string[]"},"name":{"required":true,"type":"string"},"org":{"required":true,"type":"string"},"parent_team_id":{"type":"integer"},"permission":{"enum":["pull","push","admin"],"type":"string"},"privacy":{"enum":["secret","closed"],"type":"string"},"repo_names":{"type":"string[]"}},"url":"/orgs/:org/teams"},"createDiscussion":{"deprecated":"octokit.teams.createDiscussion() has been renamed to octokit.teams.createDiscussionLegacy() (2020-01-16)","method":"POST","params":{"body":{"required":true,"type":"string"},"private":{"type":"boolean"},"team_id":{"required":true,"type":"integer"},"title":{"required":true,"type":"string"}},"url":"/teams/:team_id/discussions"},"createDiscussionComment":{"deprecated":"octokit.teams.createDiscussionComment() has been renamed to octokit.teams.createDiscussionCommentLegacy() (2020-01-16)","method":"POST","params":{"body":{"required":true,"type":"string"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments"},"createDiscussionCommentInOrg":{"method":"POST","params":{"body":{"required":true,"type":"string"},"discussion_number":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments"},"createDiscussionCommentLegacy":{"deprecated":"octokit.teams.createDiscussionCommentLegacy() is deprecated, see https://developer.github.com/v3/teams/discussion_comments/#create-a-comment-legacy","method":"POST","params":{"body":{"required":true,"type":"string"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments"},"createDiscussionInOrg":{"method":"POST","params":{"body":{"required":true,"type":"string"},"org":{"required":true,"type":"string"},"private":{"type":"boolean"},"team_slug":{"required":true,"type":"string"},"title":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions"},"createDiscussionLegacy":{"deprecated":"octokit.teams.createDiscussionLegacy() is deprecated, see https://developer.github.com/v3/teams/discussions/#create-a-discussion-legacy","method":"POST","params":{"body":{"required":true,"type":"string"},"private":{"type":"boolean"},"team_id":{"required":true,"type":"integer"},"title":{"required":true,"type":"string"}},"url":"/teams/:team_id/discussions"},"delete":{"deprecated":"octokit.teams.delete() has been renamed to octokit.teams.deleteLegacy() (2020-01-16)","method":"DELETE","params":{"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id"},"deleteDiscussion":{"deprecated":"octokit.teams.deleteDiscussion() has been renamed to octokit.teams.deleteDiscussionLegacy() (2020-01-16)","method":"DELETE","params":{"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number"},"deleteDiscussionComment":{"deprecated":"octokit.teams.deleteDiscussionComment() has been renamed to octokit.teams.deleteDiscussionCommentLegacy() (2020-01-16)","method":"DELETE","params":{"comment_number":{"required":true,"type":"integer"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments/:comment_number"},"deleteDiscussionCommentInOrg":{"method":"DELETE","params":{"comment_number":{"required":true,"type":"integer"},"discussion_number":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments/:comment_number"},"deleteDiscussionCommentLegacy":{"deprecated":"octokit.teams.deleteDiscussionCommentLegacy() is deprecated, see https://developer.github.com/v3/teams/discussion_comments/#delete-a-comment-legacy","method":"DELETE","params":{"comment_number":{"required":true,"type":"integer"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments/:comment_number"},"deleteDiscussionInOrg":{"method":"DELETE","params":{"discussion_number":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions/:discussion_number"},"deleteDiscussionLegacy":{"deprecated":"octokit.teams.deleteDiscussionLegacy() is deprecated, see https://developer.github.com/v3/teams/discussions/#delete-a-discussion-legacy","method":"DELETE","params":{"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number"},"deleteInOrg":{"method":"DELETE","params":{"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug"},"deleteLegacy":{"deprecated":"octokit.teams.deleteLegacy() is deprecated, see https://developer.github.com/v3/teams/#delete-team-legacy","method":"DELETE","params":{"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id"},"get":{"deprecated":"octokit.teams.get() has been renamed to octokit.teams.getLegacy() (2020-01-16)","method":"GET","params":{"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id"},"getByName":{"method":"GET","params":{"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug"},"getDiscussion":{"deprecated":"octokit.teams.getDiscussion() has been renamed to octokit.teams.getDiscussionLegacy() (2020-01-16)","method":"GET","params":{"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number"},"getDiscussionComment":{"deprecated":"octokit.teams.getDiscussionComment() has been renamed to octokit.teams.getDiscussionCommentLegacy() (2020-01-16)","method":"GET","params":{"comment_number":{"required":true,"type":"integer"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments/:comment_number"},"getDiscussionCommentInOrg":{"method":"GET","params":{"comment_number":{"required":true,"type":"integer"},"discussion_number":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments/:comment_number"},"getDiscussionCommentLegacy":{"deprecated":"octokit.teams.getDiscussionCommentLegacy() is deprecated, see https://developer.github.com/v3/teams/discussion_comments/#get-a-single-comment-legacy","method":"GET","params":{"comment_number":{"required":true,"type":"integer"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments/:comment_number"},"getDiscussionInOrg":{"method":"GET","params":{"discussion_number":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions/:discussion_number"},"getDiscussionLegacy":{"deprecated":"octokit.teams.getDiscussionLegacy() is deprecated, see https://developer.github.com/v3/teams/discussions/#get-a-single-discussion-legacy","method":"GET","params":{"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number"},"getLegacy":{"deprecated":"octokit.teams.getLegacy() is deprecated, see https://developer.github.com/v3/teams/#get-team-legacy","method":"GET","params":{"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id"},"getMember":{"deprecated":"octokit.teams.getMember() has been renamed to octokit.teams.getMemberLegacy() (2020-01-16)","method":"GET","params":{"team_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/teams/:team_id/members/:username"},"getMemberLegacy":{"deprecated":"octokit.teams.getMemberLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#get-team-member-legacy","method":"GET","params":{"team_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/teams/:team_id/members/:username"},"getMembership":{"deprecated":"octokit.teams.getMembership() has been renamed to octokit.teams.getMembershipLegacy() (2020-01-16)","method":"GET","params":{"team_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/teams/:team_id/memberships/:username"},"getMembershipInOrg":{"method":"GET","params":{"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/memberships/:username"},"getMembershipLegacy":{"deprecated":"octokit.teams.getMembershipLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#get-team-membership-legacy","method":"GET","params":{"team_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/teams/:team_id/memberships/:username"},"list":{"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/orgs/:org/teams"},"listChild":{"deprecated":"octokit.teams.listChild() has been renamed to octokit.teams.listChildLegacy() (2020-01-16)","method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/teams"},"listChildInOrg":{"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/teams"},"listChildLegacy":{"deprecated":"octokit.teams.listChildLegacy() is deprecated, see https://developer.github.com/v3/teams/#list-child-teams-legacy","method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/teams"},"listDiscussionComments":{"deprecated":"octokit.teams.listDiscussionComments() has been renamed to octokit.teams.listDiscussionCommentsLegacy() (2020-01-16)","method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"discussion_number":{"required":true,"type":"integer"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments"},"listDiscussionCommentsInOrg":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"discussion_number":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments"},"listDiscussionCommentsLegacy":{"deprecated":"octokit.teams.listDiscussionCommentsLegacy() is deprecated, see https://developer.github.com/v3/teams/discussion_comments/#list-comments-legacy","method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"discussion_number":{"required":true,"type":"integer"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments"},"listDiscussions":{"deprecated":"octokit.teams.listDiscussions() has been renamed to octokit.teams.listDiscussionsLegacy() (2020-01-16)","method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions"},"listDiscussionsInOrg":{"method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions"},"listDiscussionsLegacy":{"deprecated":"octokit.teams.listDiscussionsLegacy() is deprecated, see https://developer.github.com/v3/teams/discussions/#list-discussions-legacy","method":"GET","params":{"direction":{"enum":["asc","desc"],"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions"},"listForAuthenticatedUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/teams"},"listMembers":{"deprecated":"octokit.teams.listMembers() has been renamed to octokit.teams.listMembersLegacy() (2020-01-16)","method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"role":{"enum":["member","maintainer","all"],"type":"string"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/members"},"listMembersInOrg":{"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"role":{"enum":["member","maintainer","all"],"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/members"},"listMembersLegacy":{"deprecated":"octokit.teams.listMembersLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#list-team-members-legacy","method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"role":{"enum":["member","maintainer","all"],"type":"string"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/members"},"listPendingInvitations":{"deprecated":"octokit.teams.listPendingInvitations() has been renamed to octokit.teams.listPendingInvitationsLegacy() (2020-01-16)","method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/invitations"},"listPendingInvitationsInOrg":{"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/invitations"},"listPendingInvitationsLegacy":{"deprecated":"octokit.teams.listPendingInvitationsLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#list-pending-team-invitations-legacy","method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/invitations"},"listProjects":{"deprecated":"octokit.teams.listProjects() has been renamed to octokit.teams.listProjectsLegacy() (2020-01-16)","headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/projects"},"listProjectsInOrg":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/projects"},"listProjectsLegacy":{"deprecated":"octokit.teams.listProjectsLegacy() is deprecated, see https://developer.github.com/v3/teams/#list-team-projects-legacy","headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/projects"},"listRepos":{"deprecated":"octokit.teams.listRepos() has been renamed to octokit.teams.listReposLegacy() (2020-01-16)","method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/repos"},"listReposInOrg":{"method":"GET","params":{"org":{"required":true,"type":"string"},"page":{"type":"integer"},"per_page":{"type":"integer"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/repos"},"listReposLegacy":{"deprecated":"octokit.teams.listReposLegacy() is deprecated, see https://developer.github.com/v3/teams/#list-team-repos-legacy","method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/repos"},"removeMemberLegacy":{"deprecated":"octokit.teams.removeMemberLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#remove-team-member-legacy","method":"DELETE","params":{"team_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/teams/:team_id/members/:username"},"removeMembershipInOrg":{"method":"DELETE","params":{"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/memberships/:username"},"removeMembershipLegacy":{"deprecated":"octokit.teams.removeMembershipLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#remove-team-membership-legacy","method":"DELETE","params":{"team_id":{"required":true,"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/teams/:team_id/memberships/:username"},"removeProject":{"deprecated":"octokit.teams.removeProject() has been renamed to octokit.teams.removeProjectLegacy() (2020-01-16)","method":"DELETE","params":{"project_id":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/projects/:project_id"},"removeProjectInOrg":{"method":"DELETE","params":{"org":{"required":true,"type":"string"},"project_id":{"required":true,"type":"integer"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/projects/:project_id"},"removeProjectLegacy":{"deprecated":"octokit.teams.removeProjectLegacy() is deprecated, see https://developer.github.com/v3/teams/#remove-team-project-legacy","method":"DELETE","params":{"project_id":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/projects/:project_id"},"removeRepo":{"deprecated":"octokit.teams.removeRepo() has been renamed to octokit.teams.removeRepoLegacy() (2020-01-16)","method":"DELETE","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/repos/:owner/:repo"},"removeRepoInOrg":{"method":"DELETE","params":{"org":{"required":true,"type":"string"},"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/repos/:owner/:repo"},"removeRepoLegacy":{"deprecated":"octokit.teams.removeRepoLegacy() is deprecated, see https://developer.github.com/v3/teams/#remove-team-repository-legacy","method":"DELETE","params":{"owner":{"required":true,"type":"string"},"repo":{"required":true,"type":"string"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/repos/:owner/:repo"},"reviewProject":{"deprecated":"octokit.teams.reviewProject() has been renamed to octokit.teams.reviewProjectLegacy() (2020-01-16)","headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"project_id":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/projects/:project_id"},"reviewProjectInOrg":{"headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"org":{"required":true,"type":"string"},"project_id":{"required":true,"type":"integer"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/projects/:project_id"},"reviewProjectLegacy":{"deprecated":"octokit.teams.reviewProjectLegacy() is deprecated, see https://developer.github.com/v3/teams/#review-a-team-project-legacy","headers":{"accept":"application/vnd.github.inertia-preview+json"},"method":"GET","params":{"project_id":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/projects/:project_id"},"update":{"deprecated":"octokit.teams.update() has been renamed to octokit.teams.updateLegacy() (2020-01-16)","method":"PATCH","params":{"description":{"type":"string"},"name":{"required":true,"type":"string"},"parent_team_id":{"type":"integer"},"permission":{"enum":["pull","push","admin"],"type":"string"},"privacy":{"enum":["secret","closed"],"type":"string"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id"},"updateDiscussion":{"deprecated":"octokit.teams.updateDiscussion() has been renamed to octokit.teams.updateDiscussionLegacy() (2020-01-16)","method":"PATCH","params":{"body":{"type":"string"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"},"title":{"type":"string"}},"url":"/teams/:team_id/discussions/:discussion_number"},"updateDiscussionComment":{"deprecated":"octokit.teams.updateDiscussionComment() has been renamed to octokit.teams.updateDiscussionCommentLegacy() (2020-01-16)","method":"PATCH","params":{"body":{"required":true,"type":"string"},"comment_number":{"required":true,"type":"integer"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments/:comment_number"},"updateDiscussionCommentInOrg":{"method":"PATCH","params":{"body":{"required":true,"type":"string"},"comment_number":{"required":true,"type":"integer"},"discussion_number":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments/:comment_number"},"updateDiscussionCommentLegacy":{"deprecated":"octokit.teams.updateDiscussionCommentLegacy() is deprecated, see https://developer.github.com/v3/teams/discussion_comments/#edit-a-comment-legacy","method":"PATCH","params":{"body":{"required":true,"type":"string"},"comment_number":{"required":true,"type":"integer"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id/discussions/:discussion_number/comments/:comment_number"},"updateDiscussionInOrg":{"method":"PATCH","params":{"body":{"type":"string"},"discussion_number":{"required":true,"type":"integer"},"org":{"required":true,"type":"string"},"team_slug":{"required":true,"type":"string"},"title":{"type":"string"}},"url":"/orgs/:org/teams/:team_slug/discussions/:discussion_number"},"updateDiscussionLegacy":{"deprecated":"octokit.teams.updateDiscussionLegacy() is deprecated, see https://developer.github.com/v3/teams/discussions/#edit-a-discussion-legacy","method":"PATCH","params":{"body":{"type":"string"},"discussion_number":{"required":true,"type":"integer"},"team_id":{"required":true,"type":"integer"},"title":{"type":"string"}},"url":"/teams/:team_id/discussions/:discussion_number"},"updateInOrg":{"method":"PATCH","params":{"description":{"type":"string"},"name":{"required":true,"type":"string"},"org":{"required":true,"type":"string"},"parent_team_id":{"type":"integer"},"permission":{"enum":["pull","push","admin"],"type":"string"},"privacy":{"enum":["secret","closed"],"type":"string"},"team_slug":{"required":true,"type":"string"}},"url":"/orgs/:org/teams/:team_slug"},"updateLegacy":{"deprecated":"octokit.teams.updateLegacy() is deprecated, see https://developer.github.com/v3/teams/#edit-team-legacy","method":"PATCH","params":{"description":{"type":"string"},"name":{"required":true,"type":"string"},"parent_team_id":{"type":"integer"},"permission":{"enum":["pull","push","admin"],"type":"string"},"privacy":{"enum":["secret","closed"],"type":"string"},"team_id":{"required":true,"type":"integer"}},"url":"/teams/:team_id"}},"users":{"addEmails":{"method":"POST","params":{"emails":{"required":true,"type":"string[]"}},"url":"/user/emails"},"block":{"method":"PUT","params":{"username":{"required":true,"type":"string"}},"url":"/user/blocks/:username"},"checkBlocked":{"method":"GET","params":{"username":{"required":true,"type":"string"}},"url":"/user/blocks/:username"},"checkFollowing":{"method":"GET","params":{"username":{"required":true,"type":"string"}},"url":"/user/following/:username"},"checkFollowingForUser":{"method":"GET","params":{"target_user":{"required":true,"type":"string"},"username":{"required":true,"type":"string"}},"url":"/users/:username/following/:target_user"},"createGpgKey":{"method":"POST","params":{"armored_public_key":{"type":"string"}},"url":"/user/gpg_keys"},"createPublicKey":{"method":"POST","params":{"key":{"type":"string"},"title":{"type":"string"}},"url":"/user/keys"},"deleteEmails":{"method":"DELETE","params":{"emails":{"required":true,"type":"string[]"}},"url":"/user/emails"},"deleteGpgKey":{"method":"DELETE","params":{"gpg_key_id":{"required":true,"type":"integer"}},"url":"/user/gpg_keys/:gpg_key_id"},"deletePublicKey":{"method":"DELETE","params":{"key_id":{"required":true,"type":"integer"}},"url":"/user/keys/:key_id"},"follow":{"method":"PUT","params":{"username":{"required":true,"type":"string"}},"url":"/user/following/:username"},"getAuthenticated":{"method":"GET","params":{},"url":"/user"},"getByUsername":{"method":"GET","params":{"username":{"required":true,"type":"string"}},"url":"/users/:username"},"getContextForUser":{"method":"GET","params":{"subject_id":{"type":"string"},"subject_type":{"enum":["organization","repository","issue","pull_request"],"type":"string"},"username":{"required":true,"type":"string"}},"url":"/users/:username/hovercard"},"getGpgKey":{"method":"GET","params":{"gpg_key_id":{"required":true,"type":"integer"}},"url":"/user/gpg_keys/:gpg_key_id"},"getPublicKey":{"method":"GET","params":{"key_id":{"required":true,"type":"integer"}},"url":"/user/keys/:key_id"},"list":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"since":{"type":"string"}},"url":"/users"},"listBlocked":{"method":"GET","params":{},"url":"/user/blocks"},"listEmails":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/emails"},"listFollowersForAuthenticatedUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/followers"},"listFollowersForUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/users/:username/followers"},"listFollowingForAuthenticatedUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/following"},"listFollowingForUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/users/:username/following"},"listGpgKeys":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/gpg_keys"},"listGpgKeysForUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/users/:username/gpg_keys"},"listPublicEmails":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/public_emails"},"listPublicKeys":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"}},"url":"/user/keys"},"listPublicKeysForUser":{"method":"GET","params":{"page":{"type":"integer"},"per_page":{"type":"integer"},"username":{"required":true,"type":"string"}},"url":"/users/:username/keys"},"togglePrimaryEmailVisibility":{"method":"PATCH","params":{"email":{"required":true,"type":"string"},"visibility":{"required":true,"type":"string"}},"url":"/user/email/visibility"},"unblock":{"method":"DELETE","params":{"username":{"required":true,"type":"string"}},"url":"/user/blocks/:username"},"unfollow":{"method":"DELETE","params":{"username":{"required":true,"type":"string"}},"url":"/user/following/:username"},"updateAuthenticated":{"method":"PATCH","params":{"bio":{"type":"string"},"blog":{"type":"string"},"company":{"type":"string"},"email":{"type":"string"},"hireable":{"type":"boolean"},"location":{"type":"string"},"name":{"type":"string"}},"url":"/user"}}}; - /***/ }), /***/ 722: @@ -13013,12 +13989,12 @@ Object.defineProperty(exports, '__esModule', { value: true }); function _interopDefault (ex) { return (ex && (typeof ex === 'object') && 'default' in ex) ? ex['default'] : ex; } var endpoint = __webpack_require__(385); -var universalUserAgent = __webpack_require__(796); +var universalUserAgent = __webpack_require__(211); var isPlainObject = _interopDefault(__webpack_require__(696)); var nodeFetch = _interopDefault(__webpack_require__(454)); var requestError = __webpack_require__(463); -const VERSION = "5.3.1"; +const VERSION = "5.4.2"; function getBufferResponse(response) { return response.arrayBuffer(); @@ -13048,7 +14024,7 @@ function fetchWrapper(requestOptions) { if (status === 204 || status === 205) { return; - } // GitHub API returns 200 for HEAD requsets + } // GitHub API returns 200 for HEAD requests if (requestOptions.method === "HEAD") { @@ -13079,7 +14055,7 @@ function fetchWrapper(requestOptions) { try { let responseBody = JSON.parse(error.message); Object.assign(error, responseBody); - let errors = responseBody.errors; // Assumption `errors` would always be in Array Fotmat + let errors = responseBody.errors; // Assumption `errors` would always be in Array format error.message = error.message + ": " + errors.map(JSON.stringify).join(", "); } catch (e) {// ignore, see octokit/rest.js#684 @@ -13254,53 +14230,6 @@ exports.getUserAgent = getUserAgent; //# sourceMappingURL=index.js.map -/***/ }), - -/***/ 807: -/***/ (function(module, __unusedexports, __webpack_require__) { - -module.exports = paginate; - -const iterator = __webpack_require__(8); - -function paginate(octokit, route, options, mapFn) { - if (typeof options === "function") { - mapFn = options; - options = undefined; - } - options = octokit.request.endpoint.merge(route, options); - return gather( - octokit, - [], - iterator(octokit, options)[Symbol.asyncIterator](), - mapFn - ); -} - -function gather(octokit, results, iterator, mapFn) { - return iterator.next().then(result => { - if (result.done) { - return results; - } - - let earlyExit = false; - function done() { - earlyExit = true; - } - - results = results.concat( - mapFn ? mapFn(result.value, done) : result.value.data - ); - - if (earlyExit) { - return results; - } - - return gather(octokit, results, iterator, mapFn); - }); -} - - /***/ }), /***/ 813: @@ -13621,9 +14550,6 @@ function getInputs() { result.ref = `refs/heads/${result.ref}`; } } - if (!result.ref && !result.commit) { - result.ref = 'refs/heads/master'; - } } // SHA? else if (result.ref.match(/^[0-9a-fA-F]{40}$/)) { @@ -13635,10 +14561,6 @@ function getInputs() { // Clean result.clean = (core.getInput('clean') || 'true').toUpperCase() === 'TRUE'; core.debug(`clean = ${result.clean}`); - // Submodules - if (core.getInput('submodules')) { - throw new Error("The input 'submodules' is not supported in actions/checkout@v2"); - } // Fetch depth result.fetchDepth = Math.floor(Number(core.getInput('fetch-depth') || '1')); if (isNaN(result.fetchDepth) || result.fetchDepth < 0) { @@ -13648,8 +14570,26 @@ function getInputs() { // LFS result.lfs = (core.getInput('lfs') || 'false').toUpperCase() === 'TRUE'; core.debug(`lfs = ${result.lfs}`); + // Submodules + result.submodules = false; + result.nestedSubmodules = false; + const submodulesString = (core.getInput('submodules') || '').toUpperCase(); + if (submodulesString == 'RECURSIVE') { + result.submodules = true; + result.nestedSubmodules = true; + } + else if (submodulesString == 'TRUE') { + result.submodules = true; + } + core.debug(`submodules = ${result.submodules}`); + core.debug(`recursive submodules = ${result.nestedSubmodules}`); // Auth token - result.authToken = core.getInput('token'); + result.authToken = core.getInput('token', { required: true }); + // SSH + result.sshKey = core.getInput('ssh-key'); + result.sshKnownHosts = core.getInput('ssh-known-hosts'); + result.sshStrict = + (core.getInput('ssh-strict') || 'true').toUpperCase() === 'TRUE'; // Persist credentials result.persistCredentials = (core.getInput('persist-credentials') || 'false').toUpperCase() === 'TRUE'; @@ -13701,6 +14641,13210 @@ module.exports = v4; module.exports = require("url"); +/***/ }), + +/***/ 842: +/***/ (function(__unusedmodule, exports, __webpack_require__) { + +"use strict"; + + +Object.defineProperty(exports, '__esModule', { value: true }); + +var deprecation = __webpack_require__(692); + +var endpointsByScope = { + actions: { + cancelWorkflowRun: { + method: "POST", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + run_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/actions/runs/:run_id/cancel" + }, + createOrUpdateSecretForRepo: { + method: "PUT", + params: { + encrypted_value: { + type: "string" + }, + key_id: { + type: "string" + }, + name: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/secrets/:name" + }, + createRegistrationToken: { + method: "POST", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/runners/registration-token" + }, + createRemoveToken: { + method: "POST", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/runners/remove-token" + }, + deleteArtifact: { + method: "DELETE", + params: { + artifact_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/artifacts/:artifact_id" + }, + deleteSecretFromRepo: { + method: "DELETE", + params: { + name: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/secrets/:name" + }, + downloadArtifact: { + method: "GET", + params: { + archive_format: { + required: true, + type: "string" + }, + artifact_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/artifacts/:artifact_id/:archive_format" + }, + getArtifact: { + method: "GET", + params: { + artifact_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/artifacts/:artifact_id" + }, + getPublicKey: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/secrets/public-key" + }, + getSecret: { + method: "GET", + params: { + name: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/secrets/:name" + }, + getSelfHostedRunner: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + runner_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/actions/runners/:runner_id" + }, + getWorkflow: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + workflow_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/actions/workflows/:workflow_id" + }, + getWorkflowJob: { + method: "GET", + params: { + job_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/jobs/:job_id" + }, + getWorkflowRun: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + run_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/actions/runs/:run_id" + }, + listDownloadsForSelfHostedRunnerApplication: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/runners/downloads" + }, + listJobsForWorkflowRun: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + run_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/actions/runs/:run_id/jobs" + }, + listRepoWorkflowRuns: { + method: "GET", + params: { + actor: { + type: "string" + }, + branch: { + type: "string" + }, + event: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + status: { + enum: ["completed", "status", "conclusion"], + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/runs" + }, + listRepoWorkflows: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/workflows" + }, + listSecretsForRepo: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/secrets" + }, + listSelfHostedRunnersForRepo: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/runners" + }, + listWorkflowJobLogs: { + method: "GET", + params: { + job_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/actions/jobs/:job_id/logs" + }, + listWorkflowRunArtifacts: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + run_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/actions/runs/:run_id/artifacts" + }, + listWorkflowRunLogs: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + run_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/actions/runs/:run_id/logs" + }, + listWorkflowRuns: { + method: "GET", + params: { + actor: { + type: "string" + }, + branch: { + type: "string" + }, + event: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + status: { + enum: ["completed", "status", "conclusion"], + type: "string" + }, + workflow_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/actions/workflows/:workflow_id/runs" + }, + reRunWorkflow: { + method: "POST", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + run_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/actions/runs/:run_id/rerun" + }, + removeSelfHostedRunner: { + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + runner_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/actions/runners/:runner_id" + } + }, + activity: { + checkStarringRepo: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/user/starred/:owner/:repo" + }, + deleteRepoSubscription: { + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/subscription" + }, + deleteThreadSubscription: { + method: "DELETE", + params: { + thread_id: { + required: true, + type: "integer" + } + }, + url: "/notifications/threads/:thread_id/subscription" + }, + getRepoSubscription: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/subscription" + }, + getThread: { + method: "GET", + params: { + thread_id: { + required: true, + type: "integer" + } + }, + url: "/notifications/threads/:thread_id" + }, + getThreadSubscription: { + method: "GET", + params: { + thread_id: { + required: true, + type: "integer" + } + }, + url: "/notifications/threads/:thread_id/subscription" + }, + listEventsForOrg: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/events/orgs/:org" + }, + listEventsForUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/events" + }, + listFeeds: { + method: "GET", + params: {}, + url: "/feeds" + }, + listNotifications: { + method: "GET", + params: { + all: { + type: "boolean" + }, + before: { + type: "string" + }, + page: { + type: "integer" + }, + participating: { + type: "boolean" + }, + per_page: { + type: "integer" + }, + since: { + type: "string" + } + }, + url: "/notifications" + }, + listNotificationsForRepo: { + method: "GET", + params: { + all: { + type: "boolean" + }, + before: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + participating: { + type: "boolean" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + since: { + type: "string" + } + }, + url: "/repos/:owner/:repo/notifications" + }, + listPublicEvents: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/events" + }, + listPublicEventsForOrg: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/orgs/:org/events" + }, + listPublicEventsForRepoNetwork: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/networks/:owner/:repo/events" + }, + listPublicEventsForUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/events/public" + }, + listReceivedEventsForUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/received_events" + }, + listReceivedPublicEventsForUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/received_events/public" + }, + listRepoEvents: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/events" + }, + listReposStarredByAuthenticatedUser: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + sort: { + enum: ["created", "updated"], + type: "string" + } + }, + url: "/user/starred" + }, + listReposStarredByUser: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + sort: { + enum: ["created", "updated"], + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/starred" + }, + listReposWatchedByUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/subscriptions" + }, + listStargazersForRepo: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/stargazers" + }, + listWatchedReposForAuthenticatedUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/subscriptions" + }, + listWatchersForRepo: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/subscribers" + }, + markAsRead: { + method: "PUT", + params: { + last_read_at: { + type: "string" + } + }, + url: "/notifications" + }, + markNotificationsAsReadForRepo: { + method: "PUT", + params: { + last_read_at: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/notifications" + }, + markThreadAsRead: { + method: "PATCH", + params: { + thread_id: { + required: true, + type: "integer" + } + }, + url: "/notifications/threads/:thread_id" + }, + setRepoSubscription: { + method: "PUT", + params: { + ignored: { + type: "boolean" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + subscribed: { + type: "boolean" + } + }, + url: "/repos/:owner/:repo/subscription" + }, + setThreadSubscription: { + method: "PUT", + params: { + ignored: { + type: "boolean" + }, + thread_id: { + required: true, + type: "integer" + } + }, + url: "/notifications/threads/:thread_id/subscription" + }, + starRepo: { + method: "PUT", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/user/starred/:owner/:repo" + }, + unstarRepo: { + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/user/starred/:owner/:repo" + } + }, + apps: { + addRepoToInstallation: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "PUT", + params: { + installation_id: { + required: true, + type: "integer" + }, + repository_id: { + required: true, + type: "integer" + } + }, + url: "/user/installations/:installation_id/repositories/:repository_id" + }, + checkAccountIsAssociatedWithAny: { + method: "GET", + params: { + account_id: { + required: true, + type: "integer" + } + }, + url: "/marketplace_listing/accounts/:account_id" + }, + checkAccountIsAssociatedWithAnyStubbed: { + method: "GET", + params: { + account_id: { + required: true, + type: "integer" + } + }, + url: "/marketplace_listing/stubbed/accounts/:account_id" + }, + checkAuthorization: { + deprecated: "octokit.apps.checkAuthorization() is deprecated, see https://developer.github.com/v3/apps/oauth_applications/#check-an-authorization", + method: "GET", + params: { + access_token: { + required: true, + type: "string" + }, + client_id: { + required: true, + type: "string" + } + }, + url: "/applications/:client_id/tokens/:access_token" + }, + checkToken: { + headers: { + accept: "application/vnd.github.doctor-strange-preview+json" + }, + method: "POST", + params: { + access_token: { + type: "string" + }, + client_id: { + required: true, + type: "string" + } + }, + url: "/applications/:client_id/token" + }, + createContentAttachment: { + headers: { + accept: "application/vnd.github.corsair-preview+json" + }, + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + content_reference_id: { + required: true, + type: "integer" + }, + title: { + required: true, + type: "string" + } + }, + url: "/content_references/:content_reference_id/attachments" + }, + createFromManifest: { + headers: { + accept: "application/vnd.github.fury-preview+json" + }, + method: "POST", + params: { + code: { + required: true, + type: "string" + } + }, + url: "/app-manifests/:code/conversions" + }, + createInstallationToken: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "POST", + params: { + installation_id: { + required: true, + type: "integer" + }, + permissions: { + type: "object" + }, + repository_ids: { + type: "integer[]" + } + }, + url: "/app/installations/:installation_id/access_tokens" + }, + deleteAuthorization: { + headers: { + accept: "application/vnd.github.doctor-strange-preview+json" + }, + method: "DELETE", + params: { + access_token: { + type: "string" + }, + client_id: { + required: true, + type: "string" + } + }, + url: "/applications/:client_id/grant" + }, + deleteInstallation: { + headers: { + accept: "application/vnd.github.gambit-preview+json,application/vnd.github.machine-man-preview+json" + }, + method: "DELETE", + params: { + installation_id: { + required: true, + type: "integer" + } + }, + url: "/app/installations/:installation_id" + }, + deleteToken: { + headers: { + accept: "application/vnd.github.doctor-strange-preview+json" + }, + method: "DELETE", + params: { + access_token: { + type: "string" + }, + client_id: { + required: true, + type: "string" + } + }, + url: "/applications/:client_id/token" + }, + findOrgInstallation: { + deprecated: "octokit.apps.findOrgInstallation() has been renamed to octokit.apps.getOrgInstallation() (2019-04-10)", + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/installation" + }, + findRepoInstallation: { + deprecated: "octokit.apps.findRepoInstallation() has been renamed to octokit.apps.getRepoInstallation() (2019-04-10)", + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/installation" + }, + findUserInstallation: { + deprecated: "octokit.apps.findUserInstallation() has been renamed to octokit.apps.getUserInstallation() (2019-04-10)", + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/installation" + }, + getAuthenticated: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: {}, + url: "/app" + }, + getBySlug: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + app_slug: { + required: true, + type: "string" + } + }, + url: "/apps/:app_slug" + }, + getInstallation: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + installation_id: { + required: true, + type: "integer" + } + }, + url: "/app/installations/:installation_id" + }, + getOrgInstallation: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/installation" + }, + getRepoInstallation: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/installation" + }, + getUserInstallation: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/installation" + }, + listAccountsUserOrOrgOnPlan: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + plan_id: { + required: true, + type: "integer" + }, + sort: { + enum: ["created", "updated"], + type: "string" + } + }, + url: "/marketplace_listing/plans/:plan_id/accounts" + }, + listAccountsUserOrOrgOnPlanStubbed: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + plan_id: { + required: true, + type: "integer" + }, + sort: { + enum: ["created", "updated"], + type: "string" + } + }, + url: "/marketplace_listing/stubbed/plans/:plan_id/accounts" + }, + listInstallationReposForAuthenticatedUser: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + installation_id: { + required: true, + type: "integer" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/installations/:installation_id/repositories" + }, + listInstallations: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/app/installations" + }, + listInstallationsForAuthenticatedUser: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/installations" + }, + listMarketplacePurchasesForAuthenticatedUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/marketplace_purchases" + }, + listMarketplacePurchasesForAuthenticatedUserStubbed: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/marketplace_purchases/stubbed" + }, + listPlans: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/marketplace_listing/plans" + }, + listPlansStubbed: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/marketplace_listing/stubbed/plans" + }, + listRepos: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/installation/repositories" + }, + removeRepoFromInstallation: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "DELETE", + params: { + installation_id: { + required: true, + type: "integer" + }, + repository_id: { + required: true, + type: "integer" + } + }, + url: "/user/installations/:installation_id/repositories/:repository_id" + }, + resetAuthorization: { + deprecated: "octokit.apps.resetAuthorization() is deprecated, see https://developer.github.com/v3/apps/oauth_applications/#reset-an-authorization", + method: "POST", + params: { + access_token: { + required: true, + type: "string" + }, + client_id: { + required: true, + type: "string" + } + }, + url: "/applications/:client_id/tokens/:access_token" + }, + resetToken: { + headers: { + accept: "application/vnd.github.doctor-strange-preview+json" + }, + method: "PATCH", + params: { + access_token: { + type: "string" + }, + client_id: { + required: true, + type: "string" + } + }, + url: "/applications/:client_id/token" + }, + revokeAuthorizationForApplication: { + deprecated: "octokit.apps.revokeAuthorizationForApplication() is deprecated, see https://developer.github.com/v3/apps/oauth_applications/#revoke-an-authorization-for-an-application", + method: "DELETE", + params: { + access_token: { + required: true, + type: "string" + }, + client_id: { + required: true, + type: "string" + } + }, + url: "/applications/:client_id/tokens/:access_token" + }, + revokeGrantForApplication: { + deprecated: "octokit.apps.revokeGrantForApplication() is deprecated, see https://developer.github.com/v3/apps/oauth_applications/#revoke-a-grant-for-an-application", + method: "DELETE", + params: { + access_token: { + required: true, + type: "string" + }, + client_id: { + required: true, + type: "string" + } + }, + url: "/applications/:client_id/grants/:access_token" + }, + revokeInstallationToken: { + headers: { + accept: "application/vnd.github.gambit-preview+json" + }, + method: "DELETE", + params: {}, + url: "/installation/token" + } + }, + checks: { + create: { + headers: { + accept: "application/vnd.github.antiope-preview+json" + }, + method: "POST", + params: { + actions: { + type: "object[]" + }, + "actions[].description": { + required: true, + type: "string" + }, + "actions[].identifier": { + required: true, + type: "string" + }, + "actions[].label": { + required: true, + type: "string" + }, + completed_at: { + type: "string" + }, + conclusion: { + enum: ["success", "failure", "neutral", "cancelled", "timed_out", "action_required"], + type: "string" + }, + details_url: { + type: "string" + }, + external_id: { + type: "string" + }, + head_sha: { + required: true, + type: "string" + }, + name: { + required: true, + type: "string" + }, + output: { + type: "object" + }, + "output.annotations": { + type: "object[]" + }, + "output.annotations[].annotation_level": { + enum: ["notice", "warning", "failure"], + required: true, + type: "string" + }, + "output.annotations[].end_column": { + type: "integer" + }, + "output.annotations[].end_line": { + required: true, + type: "integer" + }, + "output.annotations[].message": { + required: true, + type: "string" + }, + "output.annotations[].path": { + required: true, + type: "string" + }, + "output.annotations[].raw_details": { + type: "string" + }, + "output.annotations[].start_column": { + type: "integer" + }, + "output.annotations[].start_line": { + required: true, + type: "integer" + }, + "output.annotations[].title": { + type: "string" + }, + "output.images": { + type: "object[]" + }, + "output.images[].alt": { + required: true, + type: "string" + }, + "output.images[].caption": { + type: "string" + }, + "output.images[].image_url": { + required: true, + type: "string" + }, + "output.summary": { + required: true, + type: "string" + }, + "output.text": { + type: "string" + }, + "output.title": { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + started_at: { + type: "string" + }, + status: { + enum: ["queued", "in_progress", "completed"], + type: "string" + } + }, + url: "/repos/:owner/:repo/check-runs" + }, + createSuite: { + headers: { + accept: "application/vnd.github.antiope-preview+json" + }, + method: "POST", + params: { + head_sha: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/check-suites" + }, + get: { + headers: { + accept: "application/vnd.github.antiope-preview+json" + }, + method: "GET", + params: { + check_run_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/check-runs/:check_run_id" + }, + getSuite: { + headers: { + accept: "application/vnd.github.antiope-preview+json" + }, + method: "GET", + params: { + check_suite_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/check-suites/:check_suite_id" + }, + listAnnotations: { + headers: { + accept: "application/vnd.github.antiope-preview+json" + }, + method: "GET", + params: { + check_run_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/check-runs/:check_run_id/annotations" + }, + listForRef: { + headers: { + accept: "application/vnd.github.antiope-preview+json" + }, + method: "GET", + params: { + check_name: { + type: "string" + }, + filter: { + enum: ["latest", "all"], + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + status: { + enum: ["queued", "in_progress", "completed"], + type: "string" + } + }, + url: "/repos/:owner/:repo/commits/:ref/check-runs" + }, + listForSuite: { + headers: { + accept: "application/vnd.github.antiope-preview+json" + }, + method: "GET", + params: { + check_name: { + type: "string" + }, + check_suite_id: { + required: true, + type: "integer" + }, + filter: { + enum: ["latest", "all"], + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + status: { + enum: ["queued", "in_progress", "completed"], + type: "string" + } + }, + url: "/repos/:owner/:repo/check-suites/:check_suite_id/check-runs" + }, + listSuitesForRef: { + headers: { + accept: "application/vnd.github.antiope-preview+json" + }, + method: "GET", + params: { + app_id: { + type: "integer" + }, + check_name: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/commits/:ref/check-suites" + }, + rerequestSuite: { + headers: { + accept: "application/vnd.github.antiope-preview+json" + }, + method: "POST", + params: { + check_suite_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/check-suites/:check_suite_id/rerequest" + }, + setSuitesPreferences: { + headers: { + accept: "application/vnd.github.antiope-preview+json" + }, + method: "PATCH", + params: { + auto_trigger_checks: { + type: "object[]" + }, + "auto_trigger_checks[].app_id": { + required: true, + type: "integer" + }, + "auto_trigger_checks[].setting": { + required: true, + type: "boolean" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/check-suites/preferences" + }, + update: { + headers: { + accept: "application/vnd.github.antiope-preview+json" + }, + method: "PATCH", + params: { + actions: { + type: "object[]" + }, + "actions[].description": { + required: true, + type: "string" + }, + "actions[].identifier": { + required: true, + type: "string" + }, + "actions[].label": { + required: true, + type: "string" + }, + check_run_id: { + required: true, + type: "integer" + }, + completed_at: { + type: "string" + }, + conclusion: { + enum: ["success", "failure", "neutral", "cancelled", "timed_out", "action_required"], + type: "string" + }, + details_url: { + type: "string" + }, + external_id: { + type: "string" + }, + name: { + type: "string" + }, + output: { + type: "object" + }, + "output.annotations": { + type: "object[]" + }, + "output.annotations[].annotation_level": { + enum: ["notice", "warning", "failure"], + required: true, + type: "string" + }, + "output.annotations[].end_column": { + type: "integer" + }, + "output.annotations[].end_line": { + required: true, + type: "integer" + }, + "output.annotations[].message": { + required: true, + type: "string" + }, + "output.annotations[].path": { + required: true, + type: "string" + }, + "output.annotations[].raw_details": { + type: "string" + }, + "output.annotations[].start_column": { + type: "integer" + }, + "output.annotations[].start_line": { + required: true, + type: "integer" + }, + "output.annotations[].title": { + type: "string" + }, + "output.images": { + type: "object[]" + }, + "output.images[].alt": { + required: true, + type: "string" + }, + "output.images[].caption": { + type: "string" + }, + "output.images[].image_url": { + required: true, + type: "string" + }, + "output.summary": { + required: true, + type: "string" + }, + "output.text": { + type: "string" + }, + "output.title": { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + started_at: { + type: "string" + }, + status: { + enum: ["queued", "in_progress", "completed"], + type: "string" + } + }, + url: "/repos/:owner/:repo/check-runs/:check_run_id" + } + }, + codesOfConduct: { + getConductCode: { + headers: { + accept: "application/vnd.github.scarlet-witch-preview+json" + }, + method: "GET", + params: { + key: { + required: true, + type: "string" + } + }, + url: "/codes_of_conduct/:key" + }, + getForRepo: { + headers: { + accept: "application/vnd.github.scarlet-witch-preview+json" + }, + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/community/code_of_conduct" + }, + listConductCodes: { + headers: { + accept: "application/vnd.github.scarlet-witch-preview+json" + }, + method: "GET", + params: {}, + url: "/codes_of_conduct" + } + }, + emojis: { + get: { + method: "GET", + params: {}, + url: "/emojis" + } + }, + gists: { + checkIsStarred: { + method: "GET", + params: { + gist_id: { + required: true, + type: "string" + } + }, + url: "/gists/:gist_id/star" + }, + create: { + method: "POST", + params: { + description: { + type: "string" + }, + files: { + required: true, + type: "object" + }, + "files.content": { + type: "string" + }, + public: { + type: "boolean" + } + }, + url: "/gists" + }, + createComment: { + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + gist_id: { + required: true, + type: "string" + } + }, + url: "/gists/:gist_id/comments" + }, + delete: { + method: "DELETE", + params: { + gist_id: { + required: true, + type: "string" + } + }, + url: "/gists/:gist_id" + }, + deleteComment: { + method: "DELETE", + params: { + comment_id: { + required: true, + type: "integer" + }, + gist_id: { + required: true, + type: "string" + } + }, + url: "/gists/:gist_id/comments/:comment_id" + }, + fork: { + method: "POST", + params: { + gist_id: { + required: true, + type: "string" + } + }, + url: "/gists/:gist_id/forks" + }, + get: { + method: "GET", + params: { + gist_id: { + required: true, + type: "string" + } + }, + url: "/gists/:gist_id" + }, + getComment: { + method: "GET", + params: { + comment_id: { + required: true, + type: "integer" + }, + gist_id: { + required: true, + type: "string" + } + }, + url: "/gists/:gist_id/comments/:comment_id" + }, + getRevision: { + method: "GET", + params: { + gist_id: { + required: true, + type: "string" + }, + sha: { + required: true, + type: "string" + } + }, + url: "/gists/:gist_id/:sha" + }, + list: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + since: { + type: "string" + } + }, + url: "/gists" + }, + listComments: { + method: "GET", + params: { + gist_id: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/gists/:gist_id/comments" + }, + listCommits: { + method: "GET", + params: { + gist_id: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/gists/:gist_id/commits" + }, + listForks: { + method: "GET", + params: { + gist_id: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/gists/:gist_id/forks" + }, + listPublic: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + since: { + type: "string" + } + }, + url: "/gists/public" + }, + listPublicForUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + since: { + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/gists" + }, + listStarred: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + since: { + type: "string" + } + }, + url: "/gists/starred" + }, + star: { + method: "PUT", + params: { + gist_id: { + required: true, + type: "string" + } + }, + url: "/gists/:gist_id/star" + }, + unstar: { + method: "DELETE", + params: { + gist_id: { + required: true, + type: "string" + } + }, + url: "/gists/:gist_id/star" + }, + update: { + method: "PATCH", + params: { + description: { + type: "string" + }, + files: { + type: "object" + }, + "files.content": { + type: "string" + }, + "files.filename": { + type: "string" + }, + gist_id: { + required: true, + type: "string" + } + }, + url: "/gists/:gist_id" + }, + updateComment: { + method: "PATCH", + params: { + body: { + required: true, + type: "string" + }, + comment_id: { + required: true, + type: "integer" + }, + gist_id: { + required: true, + type: "string" + } + }, + url: "/gists/:gist_id/comments/:comment_id" + } + }, + git: { + createBlob: { + method: "POST", + params: { + content: { + required: true, + type: "string" + }, + encoding: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/blobs" + }, + createCommit: { + method: "POST", + params: { + author: { + type: "object" + }, + "author.date": { + type: "string" + }, + "author.email": { + type: "string" + }, + "author.name": { + type: "string" + }, + committer: { + type: "object" + }, + "committer.date": { + type: "string" + }, + "committer.email": { + type: "string" + }, + "committer.name": { + type: "string" + }, + message: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + parents: { + required: true, + type: "string[]" + }, + repo: { + required: true, + type: "string" + }, + signature: { + type: "string" + }, + tree: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/commits" + }, + createRef: { + method: "POST", + params: { + owner: { + required: true, + type: "string" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + sha: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/refs" + }, + createTag: { + method: "POST", + params: { + message: { + required: true, + type: "string" + }, + object: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + tag: { + required: true, + type: "string" + }, + tagger: { + type: "object" + }, + "tagger.date": { + type: "string" + }, + "tagger.email": { + type: "string" + }, + "tagger.name": { + type: "string" + }, + type: { + enum: ["commit", "tree", "blob"], + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/tags" + }, + createTree: { + method: "POST", + params: { + base_tree: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + tree: { + required: true, + type: "object[]" + }, + "tree[].content": { + type: "string" + }, + "tree[].mode": { + enum: ["100644", "100755", "040000", "160000", "120000"], + type: "string" + }, + "tree[].path": { + type: "string" + }, + "tree[].sha": { + allowNull: true, + type: "string" + }, + "tree[].type": { + enum: ["blob", "tree", "commit"], + type: "string" + } + }, + url: "/repos/:owner/:repo/git/trees" + }, + deleteRef: { + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/refs/:ref" + }, + getBlob: { + method: "GET", + params: { + file_sha: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/blobs/:file_sha" + }, + getCommit: { + method: "GET", + params: { + commit_sha: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/commits/:commit_sha" + }, + getRef: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/ref/:ref" + }, + getTag: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + tag_sha: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/tags/:tag_sha" + }, + getTree: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + recursive: { + enum: ["1"], + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + tree_sha: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/trees/:tree_sha" + }, + listMatchingRefs: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/matching-refs/:ref" + }, + listRefs: { + method: "GET", + params: { + namespace: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/refs/:namespace" + }, + updateRef: { + method: "PATCH", + params: { + force: { + type: "boolean" + }, + owner: { + required: true, + type: "string" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + sha: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/git/refs/:ref" + } + }, + gitignore: { + getTemplate: { + method: "GET", + params: { + name: { + required: true, + type: "string" + } + }, + url: "/gitignore/templates/:name" + }, + listTemplates: { + method: "GET", + params: {}, + url: "/gitignore/templates" + } + }, + interactions: { + addOrUpdateRestrictionsForOrg: { + headers: { + accept: "application/vnd.github.sombra-preview+json" + }, + method: "PUT", + params: { + limit: { + enum: ["existing_users", "contributors_only", "collaborators_only"], + required: true, + type: "string" + }, + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/interaction-limits" + }, + addOrUpdateRestrictionsForRepo: { + headers: { + accept: "application/vnd.github.sombra-preview+json" + }, + method: "PUT", + params: { + limit: { + enum: ["existing_users", "contributors_only", "collaborators_only"], + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/interaction-limits" + }, + getRestrictionsForOrg: { + headers: { + accept: "application/vnd.github.sombra-preview+json" + }, + method: "GET", + params: { + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/interaction-limits" + }, + getRestrictionsForRepo: { + headers: { + accept: "application/vnd.github.sombra-preview+json" + }, + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/interaction-limits" + }, + removeRestrictionsForOrg: { + headers: { + accept: "application/vnd.github.sombra-preview+json" + }, + method: "DELETE", + params: { + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/interaction-limits" + }, + removeRestrictionsForRepo: { + headers: { + accept: "application/vnd.github.sombra-preview+json" + }, + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/interaction-limits" + } + }, + issues: { + addAssignees: { + method: "POST", + params: { + assignees: { + type: "string[]" + }, + issue_number: { + required: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/assignees" + }, + addLabels: { + method: "POST", + params: { + issue_number: { + required: true, + type: "integer" + }, + labels: { + required: true, + type: "string[]" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/labels" + }, + checkAssignee: { + method: "GET", + params: { + assignee: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/assignees/:assignee" + }, + create: { + method: "POST", + params: { + assignee: { + type: "string" + }, + assignees: { + type: "string[]" + }, + body: { + type: "string" + }, + labels: { + type: "string[]" + }, + milestone: { + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + title: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues" + }, + createComment: { + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + issue_number: { + required: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/comments" + }, + createLabel: { + method: "POST", + params: { + color: { + required: true, + type: "string" + }, + description: { + type: "string" + }, + name: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/labels" + }, + createMilestone: { + method: "POST", + params: { + description: { + type: "string" + }, + due_on: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + state: { + enum: ["open", "closed"], + type: "string" + }, + title: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/milestones" + }, + deleteComment: { + method: "DELETE", + params: { + comment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/comments/:comment_id" + }, + deleteLabel: { + method: "DELETE", + params: { + name: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/labels/:name" + }, + deleteMilestone: { + method: "DELETE", + params: { + milestone_number: { + required: true, + type: "integer" + }, + number: { + alias: "milestone_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/milestones/:milestone_number" + }, + get: { + method: "GET", + params: { + issue_number: { + required: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number" + }, + getComment: { + method: "GET", + params: { + comment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/comments/:comment_id" + }, + getEvent: { + method: "GET", + params: { + event_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/events/:event_id" + }, + getLabel: { + method: "GET", + params: { + name: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/labels/:name" + }, + getMilestone: { + method: "GET", + params: { + milestone_number: { + required: true, + type: "integer" + }, + number: { + alias: "milestone_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/milestones/:milestone_number" + }, + list: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + filter: { + enum: ["assigned", "created", "mentioned", "subscribed", "all"], + type: "string" + }, + labels: { + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + since: { + type: "string" + }, + sort: { + enum: ["created", "updated", "comments"], + type: "string" + }, + state: { + enum: ["open", "closed", "all"], + type: "string" + } + }, + url: "/issues" + }, + listAssignees: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/assignees" + }, + listComments: { + method: "GET", + params: { + issue_number: { + required: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + since: { + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/comments" + }, + listCommentsForRepo: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + since: { + type: "string" + }, + sort: { + enum: ["created", "updated"], + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/comments" + }, + listEvents: { + method: "GET", + params: { + issue_number: { + required: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/events" + }, + listEventsForRepo: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/events" + }, + listEventsForTimeline: { + headers: { + accept: "application/vnd.github.mockingbird-preview+json" + }, + method: "GET", + params: { + issue_number: { + required: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/timeline" + }, + listForAuthenticatedUser: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + filter: { + enum: ["assigned", "created", "mentioned", "subscribed", "all"], + type: "string" + }, + labels: { + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + since: { + type: "string" + }, + sort: { + enum: ["created", "updated", "comments"], + type: "string" + }, + state: { + enum: ["open", "closed", "all"], + type: "string" + } + }, + url: "/user/issues" + }, + listForOrg: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + filter: { + enum: ["assigned", "created", "mentioned", "subscribed", "all"], + type: "string" + }, + labels: { + type: "string" + }, + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + since: { + type: "string" + }, + sort: { + enum: ["created", "updated", "comments"], + type: "string" + }, + state: { + enum: ["open", "closed", "all"], + type: "string" + } + }, + url: "/orgs/:org/issues" + }, + listForRepo: { + method: "GET", + params: { + assignee: { + type: "string" + }, + creator: { + type: "string" + }, + direction: { + enum: ["asc", "desc"], + type: "string" + }, + labels: { + type: "string" + }, + mentioned: { + type: "string" + }, + milestone: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + since: { + type: "string" + }, + sort: { + enum: ["created", "updated", "comments"], + type: "string" + }, + state: { + enum: ["open", "closed", "all"], + type: "string" + } + }, + url: "/repos/:owner/:repo/issues" + }, + listLabelsForMilestone: { + method: "GET", + params: { + milestone_number: { + required: true, + type: "integer" + }, + number: { + alias: "milestone_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/milestones/:milestone_number/labels" + }, + listLabelsForRepo: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/labels" + }, + listLabelsOnIssue: { + method: "GET", + params: { + issue_number: { + required: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/labels" + }, + listMilestonesForRepo: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + sort: { + enum: ["due_on", "completeness"], + type: "string" + }, + state: { + enum: ["open", "closed", "all"], + type: "string" + } + }, + url: "/repos/:owner/:repo/milestones" + }, + lock: { + method: "PUT", + params: { + issue_number: { + required: true, + type: "integer" + }, + lock_reason: { + enum: ["off-topic", "too heated", "resolved", "spam"], + type: "string" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/lock" + }, + removeAssignees: { + method: "DELETE", + params: { + assignees: { + type: "string[]" + }, + issue_number: { + required: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/assignees" + }, + removeLabel: { + method: "DELETE", + params: { + issue_number: { + required: true, + type: "integer" + }, + name: { + required: true, + type: "string" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/labels/:name" + }, + removeLabels: { + method: "DELETE", + params: { + issue_number: { + required: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/labels" + }, + replaceLabels: { + method: "PUT", + params: { + issue_number: { + required: true, + type: "integer" + }, + labels: { + type: "string[]" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/labels" + }, + unlock: { + method: "DELETE", + params: { + issue_number: { + required: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/lock" + }, + update: { + method: "PATCH", + params: { + assignee: { + type: "string" + }, + assignees: { + type: "string[]" + }, + body: { + type: "string" + }, + issue_number: { + required: true, + type: "integer" + }, + labels: { + type: "string[]" + }, + milestone: { + allowNull: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + state: { + enum: ["open", "closed"], + type: "string" + }, + title: { + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number" + }, + updateComment: { + method: "PATCH", + params: { + body: { + required: true, + type: "string" + }, + comment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/comments/:comment_id" + }, + updateLabel: { + method: "PATCH", + params: { + color: { + type: "string" + }, + current_name: { + required: true, + type: "string" + }, + description: { + type: "string" + }, + name: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/labels/:current_name" + }, + updateMilestone: { + method: "PATCH", + params: { + description: { + type: "string" + }, + due_on: { + type: "string" + }, + milestone_number: { + required: true, + type: "integer" + }, + number: { + alias: "milestone_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + state: { + enum: ["open", "closed"], + type: "string" + }, + title: { + type: "string" + } + }, + url: "/repos/:owner/:repo/milestones/:milestone_number" + } + }, + licenses: { + get: { + method: "GET", + params: { + license: { + required: true, + type: "string" + } + }, + url: "/licenses/:license" + }, + getForRepo: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/license" + }, + list: { + deprecated: "octokit.licenses.list() has been renamed to octokit.licenses.listCommonlyUsed() (2019-03-05)", + method: "GET", + params: {}, + url: "/licenses" + }, + listCommonlyUsed: { + method: "GET", + params: {}, + url: "/licenses" + } + }, + markdown: { + render: { + method: "POST", + params: { + context: { + type: "string" + }, + mode: { + enum: ["markdown", "gfm"], + type: "string" + }, + text: { + required: true, + type: "string" + } + }, + url: "/markdown" + }, + renderRaw: { + headers: { + "content-type": "text/plain; charset=utf-8" + }, + method: "POST", + params: { + data: { + mapTo: "data", + required: true, + type: "string" + } + }, + url: "/markdown/raw" + } + }, + meta: { + get: { + method: "GET", + params: {}, + url: "/meta" + } + }, + migrations: { + cancelImport: { + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/import" + }, + deleteArchiveForAuthenticatedUser: { + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "DELETE", + params: { + migration_id: { + required: true, + type: "integer" + } + }, + url: "/user/migrations/:migration_id/archive" + }, + deleteArchiveForOrg: { + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "DELETE", + params: { + migration_id: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/migrations/:migration_id/archive" + }, + downloadArchiveForOrg: { + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "GET", + params: { + migration_id: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/migrations/:migration_id/archive" + }, + getArchiveForAuthenticatedUser: { + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "GET", + params: { + migration_id: { + required: true, + type: "integer" + } + }, + url: "/user/migrations/:migration_id/archive" + }, + getArchiveForOrg: { + deprecated: "octokit.migrations.getArchiveForOrg() has been renamed to octokit.migrations.downloadArchiveForOrg() (2020-01-27)", + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "GET", + params: { + migration_id: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/migrations/:migration_id/archive" + }, + getCommitAuthors: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + since: { + type: "string" + } + }, + url: "/repos/:owner/:repo/import/authors" + }, + getImportProgress: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/import" + }, + getLargeFiles: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/import/large_files" + }, + getStatusForAuthenticatedUser: { + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "GET", + params: { + migration_id: { + required: true, + type: "integer" + } + }, + url: "/user/migrations/:migration_id" + }, + getStatusForOrg: { + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "GET", + params: { + migration_id: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/migrations/:migration_id" + }, + listForAuthenticatedUser: { + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/migrations" + }, + listForOrg: { + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/orgs/:org/migrations" + }, + listReposForOrg: { + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "GET", + params: { + migration_id: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/orgs/:org/migrations/:migration_id/repositories" + }, + listReposForUser: { + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "GET", + params: { + migration_id: { + required: true, + type: "integer" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/:migration_id/repositories" + }, + mapCommitAuthor: { + method: "PATCH", + params: { + author_id: { + required: true, + type: "integer" + }, + email: { + type: "string" + }, + name: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/import/authors/:author_id" + }, + setLfsPreference: { + method: "PATCH", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + use_lfs: { + enum: ["opt_in", "opt_out"], + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/import/lfs" + }, + startForAuthenticatedUser: { + method: "POST", + params: { + exclude_attachments: { + type: "boolean" + }, + lock_repositories: { + type: "boolean" + }, + repositories: { + required: true, + type: "string[]" + } + }, + url: "/user/migrations" + }, + startForOrg: { + method: "POST", + params: { + exclude_attachments: { + type: "boolean" + }, + lock_repositories: { + type: "boolean" + }, + org: { + required: true, + type: "string" + }, + repositories: { + required: true, + type: "string[]" + } + }, + url: "/orgs/:org/migrations" + }, + startImport: { + method: "PUT", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + tfvc_project: { + type: "string" + }, + vcs: { + enum: ["subversion", "git", "mercurial", "tfvc"], + type: "string" + }, + vcs_password: { + type: "string" + }, + vcs_url: { + required: true, + type: "string" + }, + vcs_username: { + type: "string" + } + }, + url: "/repos/:owner/:repo/import" + }, + unlockRepoForAuthenticatedUser: { + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "DELETE", + params: { + migration_id: { + required: true, + type: "integer" + }, + repo_name: { + required: true, + type: "string" + } + }, + url: "/user/migrations/:migration_id/repos/:repo_name/lock" + }, + unlockRepoForOrg: { + headers: { + accept: "application/vnd.github.wyandotte-preview+json" + }, + method: "DELETE", + params: { + migration_id: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + repo_name: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/migrations/:migration_id/repos/:repo_name/lock" + }, + updateImport: { + method: "PATCH", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + vcs_password: { + type: "string" + }, + vcs_username: { + type: "string" + } + }, + url: "/repos/:owner/:repo/import" + } + }, + oauthAuthorizations: { + checkAuthorization: { + deprecated: "octokit.oauthAuthorizations.checkAuthorization() has been renamed to octokit.apps.checkAuthorization() (2019-11-05)", + method: "GET", + params: { + access_token: { + required: true, + type: "string" + }, + client_id: { + required: true, + type: "string" + } + }, + url: "/applications/:client_id/tokens/:access_token" + }, + createAuthorization: { + deprecated: "octokit.oauthAuthorizations.createAuthorization() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#create-a-new-authorization", + method: "POST", + params: { + client_id: { + type: "string" + }, + client_secret: { + type: "string" + }, + fingerprint: { + type: "string" + }, + note: { + required: true, + type: "string" + }, + note_url: { + type: "string" + }, + scopes: { + type: "string[]" + } + }, + url: "/authorizations" + }, + deleteAuthorization: { + deprecated: "octokit.oauthAuthorizations.deleteAuthorization() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#delete-an-authorization", + method: "DELETE", + params: { + authorization_id: { + required: true, + type: "integer" + } + }, + url: "/authorizations/:authorization_id" + }, + deleteGrant: { + deprecated: "octokit.oauthAuthorizations.deleteGrant() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#delete-a-grant", + method: "DELETE", + params: { + grant_id: { + required: true, + type: "integer" + } + }, + url: "/applications/grants/:grant_id" + }, + getAuthorization: { + deprecated: "octokit.oauthAuthorizations.getAuthorization() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#get-a-single-authorization", + method: "GET", + params: { + authorization_id: { + required: true, + type: "integer" + } + }, + url: "/authorizations/:authorization_id" + }, + getGrant: { + deprecated: "octokit.oauthAuthorizations.getGrant() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#get-a-single-grant", + method: "GET", + params: { + grant_id: { + required: true, + type: "integer" + } + }, + url: "/applications/grants/:grant_id" + }, + getOrCreateAuthorizationForApp: { + deprecated: "octokit.oauthAuthorizations.getOrCreateAuthorizationForApp() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#get-or-create-an-authorization-for-a-specific-app", + method: "PUT", + params: { + client_id: { + required: true, + type: "string" + }, + client_secret: { + required: true, + type: "string" + }, + fingerprint: { + type: "string" + }, + note: { + type: "string" + }, + note_url: { + type: "string" + }, + scopes: { + type: "string[]" + } + }, + url: "/authorizations/clients/:client_id" + }, + getOrCreateAuthorizationForAppAndFingerprint: { + deprecated: "octokit.oauthAuthorizations.getOrCreateAuthorizationForAppAndFingerprint() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#get-or-create-an-authorization-for-a-specific-app-and-fingerprint", + method: "PUT", + params: { + client_id: { + required: true, + type: "string" + }, + client_secret: { + required: true, + type: "string" + }, + fingerprint: { + required: true, + type: "string" + }, + note: { + type: "string" + }, + note_url: { + type: "string" + }, + scopes: { + type: "string[]" + } + }, + url: "/authorizations/clients/:client_id/:fingerprint" + }, + getOrCreateAuthorizationForAppFingerprint: { + deprecated: "octokit.oauthAuthorizations.getOrCreateAuthorizationForAppFingerprint() has been renamed to octokit.oauthAuthorizations.getOrCreateAuthorizationForAppAndFingerprint() (2018-12-27)", + method: "PUT", + params: { + client_id: { + required: true, + type: "string" + }, + client_secret: { + required: true, + type: "string" + }, + fingerprint: { + required: true, + type: "string" + }, + note: { + type: "string" + }, + note_url: { + type: "string" + }, + scopes: { + type: "string[]" + } + }, + url: "/authorizations/clients/:client_id/:fingerprint" + }, + listAuthorizations: { + deprecated: "octokit.oauthAuthorizations.listAuthorizations() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#list-your-authorizations", + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/authorizations" + }, + listGrants: { + deprecated: "octokit.oauthAuthorizations.listGrants() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#list-your-grants", + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/applications/grants" + }, + resetAuthorization: { + deprecated: "octokit.oauthAuthorizations.resetAuthorization() has been renamed to octokit.apps.resetAuthorization() (2019-11-05)", + method: "POST", + params: { + access_token: { + required: true, + type: "string" + }, + client_id: { + required: true, + type: "string" + } + }, + url: "/applications/:client_id/tokens/:access_token" + }, + revokeAuthorizationForApplication: { + deprecated: "octokit.oauthAuthorizations.revokeAuthorizationForApplication() has been renamed to octokit.apps.revokeAuthorizationForApplication() (2019-11-05)", + method: "DELETE", + params: { + access_token: { + required: true, + type: "string" + }, + client_id: { + required: true, + type: "string" + } + }, + url: "/applications/:client_id/tokens/:access_token" + }, + revokeGrantForApplication: { + deprecated: "octokit.oauthAuthorizations.revokeGrantForApplication() has been renamed to octokit.apps.revokeGrantForApplication() (2019-11-05)", + method: "DELETE", + params: { + access_token: { + required: true, + type: "string" + }, + client_id: { + required: true, + type: "string" + } + }, + url: "/applications/:client_id/grants/:access_token" + }, + updateAuthorization: { + deprecated: "octokit.oauthAuthorizations.updateAuthorization() is deprecated, see https://developer.github.com/v3/oauth_authorizations/#update-an-existing-authorization", + method: "PATCH", + params: { + add_scopes: { + type: "string[]" + }, + authorization_id: { + required: true, + type: "integer" + }, + fingerprint: { + type: "string" + }, + note: { + type: "string" + }, + note_url: { + type: "string" + }, + remove_scopes: { + type: "string[]" + }, + scopes: { + type: "string[]" + } + }, + url: "/authorizations/:authorization_id" + } + }, + orgs: { + addOrUpdateMembership: { + method: "PUT", + params: { + org: { + required: true, + type: "string" + }, + role: { + enum: ["admin", "member"], + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/memberships/:username" + }, + blockUser: { + method: "PUT", + params: { + org: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/blocks/:username" + }, + checkBlockedUser: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/blocks/:username" + }, + checkMembership: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/members/:username" + }, + checkPublicMembership: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/public_members/:username" + }, + concealMembership: { + method: "DELETE", + params: { + org: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/public_members/:username" + }, + convertMemberToOutsideCollaborator: { + method: "PUT", + params: { + org: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/outside_collaborators/:username" + }, + createHook: { + method: "POST", + params: { + active: { + type: "boolean" + }, + config: { + required: true, + type: "object" + }, + "config.content_type": { + type: "string" + }, + "config.insecure_ssl": { + type: "string" + }, + "config.secret": { + type: "string" + }, + "config.url": { + required: true, + type: "string" + }, + events: { + type: "string[]" + }, + name: { + required: true, + type: "string" + }, + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/hooks" + }, + createInvitation: { + method: "POST", + params: { + email: { + type: "string" + }, + invitee_id: { + type: "integer" + }, + org: { + required: true, + type: "string" + }, + role: { + enum: ["admin", "direct_member", "billing_manager"], + type: "string" + }, + team_ids: { + type: "integer[]" + } + }, + url: "/orgs/:org/invitations" + }, + deleteHook: { + method: "DELETE", + params: { + hook_id: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/hooks/:hook_id" + }, + get: { + method: "GET", + params: { + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org" + }, + getHook: { + method: "GET", + params: { + hook_id: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/hooks/:hook_id" + }, + getMembership: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/memberships/:username" + }, + getMembershipForAuthenticatedUser: { + method: "GET", + params: { + org: { + required: true, + type: "string" + } + }, + url: "/user/memberships/orgs/:org" + }, + list: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + since: { + type: "integer" + } + }, + url: "/organizations" + }, + listBlockedUsers: { + method: "GET", + params: { + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/blocks" + }, + listForAuthenticatedUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/orgs" + }, + listForUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/orgs" + }, + listHooks: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/orgs/:org/hooks" + }, + listInstallations: { + headers: { + accept: "application/vnd.github.machine-man-preview+json" + }, + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/orgs/:org/installations" + }, + listInvitationTeams: { + method: "GET", + params: { + invitation_id: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/orgs/:org/invitations/:invitation_id/teams" + }, + listMembers: { + method: "GET", + params: { + filter: { + enum: ["2fa_disabled", "all"], + type: "string" + }, + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + role: { + enum: ["all", "admin", "member"], + type: "string" + } + }, + url: "/orgs/:org/members" + }, + listMemberships: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + state: { + enum: ["active", "pending"], + type: "string" + } + }, + url: "/user/memberships/orgs" + }, + listOutsideCollaborators: { + method: "GET", + params: { + filter: { + enum: ["2fa_disabled", "all"], + type: "string" + }, + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/orgs/:org/outside_collaborators" + }, + listPendingInvitations: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/orgs/:org/invitations" + }, + listPublicMembers: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/orgs/:org/public_members" + }, + pingHook: { + method: "POST", + params: { + hook_id: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/hooks/:hook_id/pings" + }, + publicizeMembership: { + method: "PUT", + params: { + org: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/public_members/:username" + }, + removeMember: { + method: "DELETE", + params: { + org: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/members/:username" + }, + removeMembership: { + method: "DELETE", + params: { + org: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/memberships/:username" + }, + removeOutsideCollaborator: { + method: "DELETE", + params: { + org: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/outside_collaborators/:username" + }, + unblockUser: { + method: "DELETE", + params: { + org: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/blocks/:username" + }, + update: { + method: "PATCH", + params: { + billing_email: { + type: "string" + }, + company: { + type: "string" + }, + default_repository_permission: { + enum: ["read", "write", "admin", "none"], + type: "string" + }, + description: { + type: "string" + }, + email: { + type: "string" + }, + has_organization_projects: { + type: "boolean" + }, + has_repository_projects: { + type: "boolean" + }, + location: { + type: "string" + }, + members_allowed_repository_creation_type: { + enum: ["all", "private", "none"], + type: "string" + }, + members_can_create_internal_repositories: { + type: "boolean" + }, + members_can_create_private_repositories: { + type: "boolean" + }, + members_can_create_public_repositories: { + type: "boolean" + }, + members_can_create_repositories: { + type: "boolean" + }, + name: { + type: "string" + }, + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org" + }, + updateHook: { + method: "PATCH", + params: { + active: { + type: "boolean" + }, + config: { + type: "object" + }, + "config.content_type": { + type: "string" + }, + "config.insecure_ssl": { + type: "string" + }, + "config.secret": { + type: "string" + }, + "config.url": { + required: true, + type: "string" + }, + events: { + type: "string[]" + }, + hook_id: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/hooks/:hook_id" + }, + updateMembership: { + method: "PATCH", + params: { + org: { + required: true, + type: "string" + }, + state: { + enum: ["active"], + required: true, + type: "string" + } + }, + url: "/user/memberships/orgs/:org" + } + }, + projects: { + addCollaborator: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "PUT", + params: { + permission: { + enum: ["read", "write", "admin"], + type: "string" + }, + project_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/projects/:project_id/collaborators/:username" + }, + createCard: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "POST", + params: { + column_id: { + required: true, + type: "integer" + }, + content_id: { + type: "integer" + }, + content_type: { + type: "string" + }, + note: { + type: "string" + } + }, + url: "/projects/columns/:column_id/cards" + }, + createColumn: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "POST", + params: { + name: { + required: true, + type: "string" + }, + project_id: { + required: true, + type: "integer" + } + }, + url: "/projects/:project_id/columns" + }, + createForAuthenticatedUser: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "POST", + params: { + body: { + type: "string" + }, + name: { + required: true, + type: "string" + } + }, + url: "/user/projects" + }, + createForOrg: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "POST", + params: { + body: { + type: "string" + }, + name: { + required: true, + type: "string" + }, + org: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/projects" + }, + createForRepo: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "POST", + params: { + body: { + type: "string" + }, + name: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/projects" + }, + delete: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "DELETE", + params: { + project_id: { + required: true, + type: "integer" + } + }, + url: "/projects/:project_id" + }, + deleteCard: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "DELETE", + params: { + card_id: { + required: true, + type: "integer" + } + }, + url: "/projects/columns/cards/:card_id" + }, + deleteColumn: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "DELETE", + params: { + column_id: { + required: true, + type: "integer" + } + }, + url: "/projects/columns/:column_id" + }, + get: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + project_id: { + required: true, + type: "integer" + } + }, + url: "/projects/:project_id" + }, + getCard: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + card_id: { + required: true, + type: "integer" + } + }, + url: "/projects/columns/cards/:card_id" + }, + getColumn: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + column_id: { + required: true, + type: "integer" + } + }, + url: "/projects/columns/:column_id" + }, + listCards: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + archived_state: { + enum: ["all", "archived", "not_archived"], + type: "string" + }, + column_id: { + required: true, + type: "integer" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/projects/columns/:column_id/cards" + }, + listCollaborators: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + affiliation: { + enum: ["outside", "direct", "all"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + project_id: { + required: true, + type: "integer" + } + }, + url: "/projects/:project_id/collaborators" + }, + listColumns: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + project_id: { + required: true, + type: "integer" + } + }, + url: "/projects/:project_id/columns" + }, + listForOrg: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + state: { + enum: ["open", "closed", "all"], + type: "string" + } + }, + url: "/orgs/:org/projects" + }, + listForRepo: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + state: { + enum: ["open", "closed", "all"], + type: "string" + } + }, + url: "/repos/:owner/:repo/projects" + }, + listForUser: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + state: { + enum: ["open", "closed", "all"], + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/projects" + }, + moveCard: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "POST", + params: { + card_id: { + required: true, + type: "integer" + }, + column_id: { + type: "integer" + }, + position: { + required: true, + type: "string", + validation: "^(top|bottom|after:\\d+)$" + } + }, + url: "/projects/columns/cards/:card_id/moves" + }, + moveColumn: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "POST", + params: { + column_id: { + required: true, + type: "integer" + }, + position: { + required: true, + type: "string", + validation: "^(first|last|after:\\d+)$" + } + }, + url: "/projects/columns/:column_id/moves" + }, + removeCollaborator: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "DELETE", + params: { + project_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/projects/:project_id/collaborators/:username" + }, + reviewUserPermissionLevel: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + project_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/projects/:project_id/collaborators/:username/permission" + }, + update: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "PATCH", + params: { + body: { + type: "string" + }, + name: { + type: "string" + }, + organization_permission: { + type: "string" + }, + private: { + type: "boolean" + }, + project_id: { + required: true, + type: "integer" + }, + state: { + enum: ["open", "closed"], + type: "string" + } + }, + url: "/projects/:project_id" + }, + updateCard: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "PATCH", + params: { + archived: { + type: "boolean" + }, + card_id: { + required: true, + type: "integer" + }, + note: { + type: "string" + } + }, + url: "/projects/columns/cards/:card_id" + }, + updateColumn: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "PATCH", + params: { + column_id: { + required: true, + type: "integer" + }, + name: { + required: true, + type: "string" + } + }, + url: "/projects/columns/:column_id" + } + }, + pulls: { + checkIfMerged: { + method: "GET", + params: { + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/merge" + }, + create: { + method: "POST", + params: { + base: { + required: true, + type: "string" + }, + body: { + type: "string" + }, + draft: { + type: "boolean" + }, + head: { + required: true, + type: "string" + }, + maintainer_can_modify: { + type: "boolean" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + title: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls" + }, + createComment: { + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + commit_id: { + required: true, + type: "string" + }, + in_reply_to: { + deprecated: true, + description: "The comment ID to reply to. **Note**: This must be the ID of a top-level comment, not a reply to that comment. Replies to replies are not supported.", + type: "integer" + }, + line: { + type: "integer" + }, + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + path: { + required: true, + type: "string" + }, + position: { + type: "integer" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + side: { + enum: ["LEFT", "RIGHT"], + type: "string" + }, + start_line: { + type: "integer" + }, + start_side: { + enum: ["LEFT", "RIGHT", "side"], + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/comments" + }, + createCommentReply: { + deprecated: "octokit.pulls.createCommentReply() has been renamed to octokit.pulls.createComment() (2019-09-09)", + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + commit_id: { + required: true, + type: "string" + }, + in_reply_to: { + deprecated: true, + description: "The comment ID to reply to. **Note**: This must be the ID of a top-level comment, not a reply to that comment. Replies to replies are not supported.", + type: "integer" + }, + line: { + type: "integer" + }, + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + path: { + required: true, + type: "string" + }, + position: { + type: "integer" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + side: { + enum: ["LEFT", "RIGHT"], + type: "string" + }, + start_line: { + type: "integer" + }, + start_side: { + enum: ["LEFT", "RIGHT", "side"], + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/comments" + }, + createFromIssue: { + deprecated: "octokit.pulls.createFromIssue() is deprecated, see https://developer.github.com/v3/pulls/#create-a-pull-request", + method: "POST", + params: { + base: { + required: true, + type: "string" + }, + draft: { + type: "boolean" + }, + head: { + required: true, + type: "string" + }, + issue: { + required: true, + type: "integer" + }, + maintainer_can_modify: { + type: "boolean" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls" + }, + createReview: { + method: "POST", + params: { + body: { + type: "string" + }, + comments: { + type: "object[]" + }, + "comments[].body": { + required: true, + type: "string" + }, + "comments[].path": { + required: true, + type: "string" + }, + "comments[].position": { + required: true, + type: "integer" + }, + commit_id: { + type: "string" + }, + event: { + enum: ["APPROVE", "REQUEST_CHANGES", "COMMENT"], + type: "string" + }, + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/reviews" + }, + createReviewCommentReply: { + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + comment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/comments/:comment_id/replies" + }, + createReviewRequest: { + method: "POST", + params: { + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + reviewers: { + type: "string[]" + }, + team_reviewers: { + type: "string[]" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/requested_reviewers" + }, + deleteComment: { + method: "DELETE", + params: { + comment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/comments/:comment_id" + }, + deletePendingReview: { + method: "DELETE", + params: { + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + review_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/reviews/:review_id" + }, + deleteReviewRequest: { + method: "DELETE", + params: { + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + reviewers: { + type: "string[]" + }, + team_reviewers: { + type: "string[]" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/requested_reviewers" + }, + dismissReview: { + method: "PUT", + params: { + message: { + required: true, + type: "string" + }, + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + review_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/reviews/:review_id/dismissals" + }, + get: { + method: "GET", + params: { + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number" + }, + getComment: { + method: "GET", + params: { + comment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/comments/:comment_id" + }, + getCommentsForReview: { + method: "GET", + params: { + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + review_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/reviews/:review_id/comments" + }, + getReview: { + method: "GET", + params: { + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + review_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/reviews/:review_id" + }, + list: { + method: "GET", + params: { + base: { + type: "string" + }, + direction: { + enum: ["asc", "desc"], + type: "string" + }, + head: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + sort: { + enum: ["created", "updated", "popularity", "long-running"], + type: "string" + }, + state: { + enum: ["open", "closed", "all"], + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls" + }, + listComments: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + since: { + type: "string" + }, + sort: { + enum: ["created", "updated"], + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/comments" + }, + listCommentsForRepo: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + since: { + type: "string" + }, + sort: { + enum: ["created", "updated"], + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/comments" + }, + listCommits: { + method: "GET", + params: { + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/commits" + }, + listFiles: { + method: "GET", + params: { + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/files" + }, + listReviewRequests: { + method: "GET", + params: { + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/requested_reviewers" + }, + listReviews: { + method: "GET", + params: { + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/reviews" + }, + merge: { + method: "PUT", + params: { + commit_message: { + type: "string" + }, + commit_title: { + type: "string" + }, + merge_method: { + enum: ["merge", "squash", "rebase"], + type: "string" + }, + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + sha: { + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/merge" + }, + submitReview: { + method: "POST", + params: { + body: { + type: "string" + }, + event: { + enum: ["APPROVE", "REQUEST_CHANGES", "COMMENT"], + required: true, + type: "string" + }, + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + review_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/reviews/:review_id/events" + }, + update: { + method: "PATCH", + params: { + base: { + type: "string" + }, + body: { + type: "string" + }, + maintainer_can_modify: { + type: "boolean" + }, + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + state: { + enum: ["open", "closed"], + type: "string" + }, + title: { + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number" + }, + updateBranch: { + headers: { + accept: "application/vnd.github.lydian-preview+json" + }, + method: "PUT", + params: { + expected_head_sha: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/update-branch" + }, + updateComment: { + method: "PATCH", + params: { + body: { + required: true, + type: "string" + }, + comment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/comments/:comment_id" + }, + updateReview: { + method: "PUT", + params: { + body: { + required: true, + type: "string" + }, + number: { + alias: "pull_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + pull_number: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + review_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/pulls/:pull_number/reviews/:review_id" + } + }, + rateLimit: { + get: { + method: "GET", + params: {}, + url: "/rate_limit" + } + }, + reactions: { + createForCommitComment: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "POST", + params: { + comment_id: { + required: true, + type: "integer" + }, + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/comments/:comment_id/reactions" + }, + createForIssue: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "POST", + params: { + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + required: true, + type: "string" + }, + issue_number: { + required: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/reactions" + }, + createForIssueComment: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "POST", + params: { + comment_id: { + required: true, + type: "integer" + }, + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/comments/:comment_id/reactions" + }, + createForPullRequestReviewComment: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "POST", + params: { + comment_id: { + required: true, + type: "integer" + }, + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/comments/:comment_id/reactions" + }, + createForTeamDiscussion: { + deprecated: "octokit.reactions.createForTeamDiscussion() has been renamed to octokit.reactions.createForTeamDiscussionLegacy() (2020-01-16)", + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "POST", + params: { + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + required: true, + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/reactions" + }, + createForTeamDiscussionComment: { + deprecated: "octokit.reactions.createForTeamDiscussionComment() has been renamed to octokit.reactions.createForTeamDiscussionCommentLegacy() (2020-01-16)", + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "POST", + params: { + comment_number: { + required: true, + type: "integer" + }, + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + required: true, + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments/:comment_number/reactions" + }, + createForTeamDiscussionCommentInOrg: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "POST", + params: { + comment_number: { + required: true, + type: "integer" + }, + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + required: true, + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments/:comment_number/reactions" + }, + createForTeamDiscussionCommentLegacy: { + deprecated: "octokit.reactions.createForTeamDiscussionCommentLegacy() is deprecated, see https://developer.github.com/v3/reactions/#create-reaction-for-a-team-discussion-comment-legacy", + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "POST", + params: { + comment_number: { + required: true, + type: "integer" + }, + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + required: true, + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments/:comment_number/reactions" + }, + createForTeamDiscussionInOrg: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "POST", + params: { + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + required: true, + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions/:discussion_number/reactions" + }, + createForTeamDiscussionLegacy: { + deprecated: "octokit.reactions.createForTeamDiscussionLegacy() is deprecated, see https://developer.github.com/v3/reactions/#create-reaction-for-a-team-discussion-legacy", + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "POST", + params: { + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + required: true, + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/reactions" + }, + delete: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "DELETE", + params: { + reaction_id: { + required: true, + type: "integer" + } + }, + url: "/reactions/:reaction_id" + }, + listForCommitComment: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "GET", + params: { + comment_id: { + required: true, + type: "integer" + }, + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/comments/:comment_id/reactions" + }, + listForIssue: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "GET", + params: { + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + type: "string" + }, + issue_number: { + required: true, + type: "integer" + }, + number: { + alias: "issue_number", + deprecated: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/:issue_number/reactions" + }, + listForIssueComment: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "GET", + params: { + comment_id: { + required: true, + type: "integer" + }, + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/issues/comments/:comment_id/reactions" + }, + listForPullRequestReviewComment: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "GET", + params: { + comment_id: { + required: true, + type: "integer" + }, + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pulls/comments/:comment_id/reactions" + }, + listForTeamDiscussion: { + deprecated: "octokit.reactions.listForTeamDiscussion() has been renamed to octokit.reactions.listForTeamDiscussionLegacy() (2020-01-16)", + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "GET", + params: { + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/reactions" + }, + listForTeamDiscussionComment: { + deprecated: "octokit.reactions.listForTeamDiscussionComment() has been renamed to octokit.reactions.listForTeamDiscussionCommentLegacy() (2020-01-16)", + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "GET", + params: { + comment_number: { + required: true, + type: "integer" + }, + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments/:comment_number/reactions" + }, + listForTeamDiscussionCommentInOrg: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "GET", + params: { + comment_number: { + required: true, + type: "integer" + }, + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments/:comment_number/reactions" + }, + listForTeamDiscussionCommentLegacy: { + deprecated: "octokit.reactions.listForTeamDiscussionCommentLegacy() is deprecated, see https://developer.github.com/v3/reactions/#list-reactions-for-a-team-discussion-comment-legacy", + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "GET", + params: { + comment_number: { + required: true, + type: "integer" + }, + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments/:comment_number/reactions" + }, + listForTeamDiscussionInOrg: { + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "GET", + params: { + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions/:discussion_number/reactions" + }, + listForTeamDiscussionLegacy: { + deprecated: "octokit.reactions.listForTeamDiscussionLegacy() is deprecated, see https://developer.github.com/v3/reactions/#list-reactions-for-a-team-discussion-legacy", + headers: { + accept: "application/vnd.github.squirrel-girl-preview+json" + }, + method: "GET", + params: { + content: { + enum: ["+1", "-1", "laugh", "confused", "heart", "hooray", "rocket", "eyes"], + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/reactions" + } + }, + repos: { + acceptInvitation: { + method: "PATCH", + params: { + invitation_id: { + required: true, + type: "integer" + } + }, + url: "/user/repository_invitations/:invitation_id" + }, + addCollaborator: { + method: "PUT", + params: { + owner: { + required: true, + type: "string" + }, + permission: { + enum: ["pull", "push", "admin"], + type: "string" + }, + repo: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/collaborators/:username" + }, + addDeployKey: { + method: "POST", + params: { + key: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + read_only: { + type: "boolean" + }, + repo: { + required: true, + type: "string" + }, + title: { + type: "string" + } + }, + url: "/repos/:owner/:repo/keys" + }, + addProtectedBranchAdminEnforcement: { + method: "POST", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/enforce_admins" + }, + addProtectedBranchAppRestrictions: { + method: "POST", + params: { + apps: { + mapTo: "data", + required: true, + type: "string[]" + }, + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/apps" + }, + addProtectedBranchRequiredSignatures: { + headers: { + accept: "application/vnd.github.zzzax-preview+json" + }, + method: "POST", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_signatures" + }, + addProtectedBranchRequiredStatusChecksContexts: { + method: "POST", + params: { + branch: { + required: true, + type: "string" + }, + contexts: { + mapTo: "data", + required: true, + type: "string[]" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_status_checks/contexts" + }, + addProtectedBranchTeamRestrictions: { + method: "POST", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + teams: { + mapTo: "data", + required: true, + type: "string[]" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/teams" + }, + addProtectedBranchUserRestrictions: { + method: "POST", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + users: { + mapTo: "data", + required: true, + type: "string[]" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/users" + }, + checkCollaborator: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/collaborators/:username" + }, + checkVulnerabilityAlerts: { + headers: { + accept: "application/vnd.github.dorian-preview+json" + }, + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/vulnerability-alerts" + }, + compareCommits: { + method: "GET", + params: { + base: { + required: true, + type: "string" + }, + head: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/compare/:base...:head" + }, + createCommitComment: { + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + commit_sha: { + required: true, + type: "string" + }, + line: { + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + path: { + type: "string" + }, + position: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + sha: { + alias: "commit_sha", + deprecated: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/commits/:commit_sha/comments" + }, + createDeployment: { + method: "POST", + params: { + auto_merge: { + type: "boolean" + }, + description: { + type: "string" + }, + environment: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + payload: { + type: "string" + }, + production_environment: { + type: "boolean" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + required_contexts: { + type: "string[]" + }, + task: { + type: "string" + }, + transient_environment: { + type: "boolean" + } + }, + url: "/repos/:owner/:repo/deployments" + }, + createDeploymentStatus: { + method: "POST", + params: { + auto_inactive: { + type: "boolean" + }, + deployment_id: { + required: true, + type: "integer" + }, + description: { + type: "string" + }, + environment: { + enum: ["production", "staging", "qa"], + type: "string" + }, + environment_url: { + type: "string" + }, + log_url: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + state: { + enum: ["error", "failure", "inactive", "in_progress", "queued", "pending", "success"], + required: true, + type: "string" + }, + target_url: { + type: "string" + } + }, + url: "/repos/:owner/:repo/deployments/:deployment_id/statuses" + }, + createDispatchEvent: { + method: "POST", + params: { + client_payload: { + type: "object" + }, + event_type: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/dispatches" + }, + createFile: { + deprecated: "octokit.repos.createFile() has been renamed to octokit.repos.createOrUpdateFile() (2019-06-07)", + method: "PUT", + params: { + author: { + type: "object" + }, + "author.email": { + required: true, + type: "string" + }, + "author.name": { + required: true, + type: "string" + }, + branch: { + type: "string" + }, + committer: { + type: "object" + }, + "committer.email": { + required: true, + type: "string" + }, + "committer.name": { + required: true, + type: "string" + }, + content: { + required: true, + type: "string" + }, + message: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + path: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + sha: { + type: "string" + } + }, + url: "/repos/:owner/:repo/contents/:path" + }, + createForAuthenticatedUser: { + method: "POST", + params: { + allow_merge_commit: { + type: "boolean" + }, + allow_rebase_merge: { + type: "boolean" + }, + allow_squash_merge: { + type: "boolean" + }, + auto_init: { + type: "boolean" + }, + delete_branch_on_merge: { + type: "boolean" + }, + description: { + type: "string" + }, + gitignore_template: { + type: "string" + }, + has_issues: { + type: "boolean" + }, + has_projects: { + type: "boolean" + }, + has_wiki: { + type: "boolean" + }, + homepage: { + type: "string" + }, + is_template: { + type: "boolean" + }, + license_template: { + type: "string" + }, + name: { + required: true, + type: "string" + }, + private: { + type: "boolean" + }, + team_id: { + type: "integer" + }, + visibility: { + enum: ["public", "private", "visibility", "internal"], + type: "string" + } + }, + url: "/user/repos" + }, + createFork: { + method: "POST", + params: { + organization: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/forks" + }, + createHook: { + method: "POST", + params: { + active: { + type: "boolean" + }, + config: { + required: true, + type: "object" + }, + "config.content_type": { + type: "string" + }, + "config.insecure_ssl": { + type: "string" + }, + "config.secret": { + type: "string" + }, + "config.url": { + required: true, + type: "string" + }, + events: { + type: "string[]" + }, + name: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/hooks" + }, + createInOrg: { + method: "POST", + params: { + allow_merge_commit: { + type: "boolean" + }, + allow_rebase_merge: { + type: "boolean" + }, + allow_squash_merge: { + type: "boolean" + }, + auto_init: { + type: "boolean" + }, + delete_branch_on_merge: { + type: "boolean" + }, + description: { + type: "string" + }, + gitignore_template: { + type: "string" + }, + has_issues: { + type: "boolean" + }, + has_projects: { + type: "boolean" + }, + has_wiki: { + type: "boolean" + }, + homepage: { + type: "string" + }, + is_template: { + type: "boolean" + }, + license_template: { + type: "string" + }, + name: { + required: true, + type: "string" + }, + org: { + required: true, + type: "string" + }, + private: { + type: "boolean" + }, + team_id: { + type: "integer" + }, + visibility: { + enum: ["public", "private", "visibility", "internal"], + type: "string" + } + }, + url: "/orgs/:org/repos" + }, + createOrUpdateFile: { + method: "PUT", + params: { + author: { + type: "object" + }, + "author.email": { + required: true, + type: "string" + }, + "author.name": { + required: true, + type: "string" + }, + branch: { + type: "string" + }, + committer: { + type: "object" + }, + "committer.email": { + required: true, + type: "string" + }, + "committer.name": { + required: true, + type: "string" + }, + content: { + required: true, + type: "string" + }, + message: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + path: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + sha: { + type: "string" + } + }, + url: "/repos/:owner/:repo/contents/:path" + }, + createRelease: { + method: "POST", + params: { + body: { + type: "string" + }, + draft: { + type: "boolean" + }, + name: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + prerelease: { + type: "boolean" + }, + repo: { + required: true, + type: "string" + }, + tag_name: { + required: true, + type: "string" + }, + target_commitish: { + type: "string" + } + }, + url: "/repos/:owner/:repo/releases" + }, + createStatus: { + method: "POST", + params: { + context: { + type: "string" + }, + description: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + sha: { + required: true, + type: "string" + }, + state: { + enum: ["error", "failure", "pending", "success"], + required: true, + type: "string" + }, + target_url: { + type: "string" + } + }, + url: "/repos/:owner/:repo/statuses/:sha" + }, + createUsingTemplate: { + headers: { + accept: "application/vnd.github.baptiste-preview+json" + }, + method: "POST", + params: { + description: { + type: "string" + }, + name: { + required: true, + type: "string" + }, + owner: { + type: "string" + }, + private: { + type: "boolean" + }, + template_owner: { + required: true, + type: "string" + }, + template_repo: { + required: true, + type: "string" + } + }, + url: "/repos/:template_owner/:template_repo/generate" + }, + declineInvitation: { + method: "DELETE", + params: { + invitation_id: { + required: true, + type: "integer" + } + }, + url: "/user/repository_invitations/:invitation_id" + }, + delete: { + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo" + }, + deleteCommitComment: { + method: "DELETE", + params: { + comment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/comments/:comment_id" + }, + deleteDownload: { + method: "DELETE", + params: { + download_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/downloads/:download_id" + }, + deleteFile: { + method: "DELETE", + params: { + author: { + type: "object" + }, + "author.email": { + type: "string" + }, + "author.name": { + type: "string" + }, + branch: { + type: "string" + }, + committer: { + type: "object" + }, + "committer.email": { + type: "string" + }, + "committer.name": { + type: "string" + }, + message: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + path: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + sha: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/contents/:path" + }, + deleteHook: { + method: "DELETE", + params: { + hook_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/hooks/:hook_id" + }, + deleteInvitation: { + method: "DELETE", + params: { + invitation_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/invitations/:invitation_id" + }, + deleteRelease: { + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + release_id: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/releases/:release_id" + }, + deleteReleaseAsset: { + method: "DELETE", + params: { + asset_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/releases/assets/:asset_id" + }, + disableAutomatedSecurityFixes: { + headers: { + accept: "application/vnd.github.london-preview+json" + }, + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/automated-security-fixes" + }, + disablePagesSite: { + headers: { + accept: "application/vnd.github.switcheroo-preview+json" + }, + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pages" + }, + disableVulnerabilityAlerts: { + headers: { + accept: "application/vnd.github.dorian-preview+json" + }, + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/vulnerability-alerts" + }, + enableAutomatedSecurityFixes: { + headers: { + accept: "application/vnd.github.london-preview+json" + }, + method: "PUT", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/automated-security-fixes" + }, + enablePagesSite: { + headers: { + accept: "application/vnd.github.switcheroo-preview+json" + }, + method: "POST", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + source: { + type: "object" + }, + "source.branch": { + enum: ["master", "gh-pages"], + type: "string" + }, + "source.path": { + type: "string" + } + }, + url: "/repos/:owner/:repo/pages" + }, + enableVulnerabilityAlerts: { + headers: { + accept: "application/vnd.github.dorian-preview+json" + }, + method: "PUT", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/vulnerability-alerts" + }, + get: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo" + }, + getAppsWithAccessToProtectedBranch: { + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/apps" + }, + getArchiveLink: { + method: "GET", + params: { + archive_format: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/:archive_format/:ref" + }, + getBranch: { + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch" + }, + getBranchProtection: { + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection" + }, + getClones: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + per: { + enum: ["day", "week"], + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/traffic/clones" + }, + getCodeFrequencyStats: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/stats/code_frequency" + }, + getCollaboratorPermissionLevel: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/collaborators/:username/permission" + }, + getCombinedStatusForRef: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/commits/:ref/status" + }, + getCommit: { + method: "GET", + params: { + commit_sha: { + alias: "ref", + deprecated: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + sha: { + alias: "ref", + deprecated: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/commits/:ref" + }, + getCommitActivityStats: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/stats/commit_activity" + }, + getCommitComment: { + method: "GET", + params: { + comment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/comments/:comment_id" + }, + getCommitRefSha: { + deprecated: "octokit.repos.getCommitRefSha() is deprecated, see https://developer.github.com/v3/repos/commits/#get-a-single-commit", + headers: { + accept: "application/vnd.github.v3.sha" + }, + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/commits/:ref" + }, + getContents: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + path: { + required: true, + type: "string" + }, + ref: { + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/contents/:path" + }, + getContributorsStats: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/stats/contributors" + }, + getDeployKey: { + method: "GET", + params: { + key_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/keys/:key_id" + }, + getDeployment: { + method: "GET", + params: { + deployment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/deployments/:deployment_id" + }, + getDeploymentStatus: { + method: "GET", + params: { + deployment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + status_id: { + required: true, + type: "integer" + } + }, + url: "/repos/:owner/:repo/deployments/:deployment_id/statuses/:status_id" + }, + getDownload: { + method: "GET", + params: { + download_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/downloads/:download_id" + }, + getHook: { + method: "GET", + params: { + hook_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/hooks/:hook_id" + }, + getLatestPagesBuild: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pages/builds/latest" + }, + getLatestRelease: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/releases/latest" + }, + getPages: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pages" + }, + getPagesBuild: { + method: "GET", + params: { + build_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pages/builds/:build_id" + }, + getParticipationStats: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/stats/participation" + }, + getProtectedBranchAdminEnforcement: { + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/enforce_admins" + }, + getProtectedBranchPullRequestReviewEnforcement: { + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_pull_request_reviews" + }, + getProtectedBranchRequiredSignatures: { + headers: { + accept: "application/vnd.github.zzzax-preview+json" + }, + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_signatures" + }, + getProtectedBranchRequiredStatusChecks: { + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_status_checks" + }, + getProtectedBranchRestrictions: { + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions" + }, + getPunchCardStats: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/stats/punch_card" + }, + getReadme: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + ref: { + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/readme" + }, + getRelease: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + release_id: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/releases/:release_id" + }, + getReleaseAsset: { + method: "GET", + params: { + asset_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/releases/assets/:asset_id" + }, + getReleaseByTag: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + tag: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/releases/tags/:tag" + }, + getTeamsWithAccessToProtectedBranch: { + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/teams" + }, + getTopPaths: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/traffic/popular/paths" + }, + getTopReferrers: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/traffic/popular/referrers" + }, + getUsersWithAccessToProtectedBranch: { + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/users" + }, + getViews: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + per: { + enum: ["day", "week"], + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/traffic/views" + }, + list: { + method: "GET", + params: { + affiliation: { + type: "string" + }, + direction: { + enum: ["asc", "desc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + sort: { + enum: ["created", "updated", "pushed", "full_name"], + type: "string" + }, + type: { + enum: ["all", "owner", "public", "private", "member"], + type: "string" + }, + visibility: { + enum: ["all", "public", "private"], + type: "string" + } + }, + url: "/user/repos" + }, + listAppsWithAccessToProtectedBranch: { + deprecated: "octokit.repos.listAppsWithAccessToProtectedBranch() has been renamed to octokit.repos.getAppsWithAccessToProtectedBranch() (2019-09-13)", + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/apps" + }, + listAssetsForRelease: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + release_id: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/releases/:release_id/assets" + }, + listBranches: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + protected: { + type: "boolean" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches" + }, + listBranchesForHeadCommit: { + headers: { + accept: "application/vnd.github.groot-preview+json" + }, + method: "GET", + params: { + commit_sha: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/commits/:commit_sha/branches-where-head" + }, + listCollaborators: { + method: "GET", + params: { + affiliation: { + enum: ["outside", "direct", "all"], + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/collaborators" + }, + listCommentsForCommit: { + method: "GET", + params: { + commit_sha: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + ref: { + alias: "commit_sha", + deprecated: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/commits/:commit_sha/comments" + }, + listCommitComments: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/comments" + }, + listCommits: { + method: "GET", + params: { + author: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + path: { + type: "string" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + sha: { + type: "string" + }, + since: { + type: "string" + }, + until: { + type: "string" + } + }, + url: "/repos/:owner/:repo/commits" + }, + listContributors: { + method: "GET", + params: { + anon: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/contributors" + }, + listDeployKeys: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/keys" + }, + listDeploymentStatuses: { + method: "GET", + params: { + deployment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/deployments/:deployment_id/statuses" + }, + listDeployments: { + method: "GET", + params: { + environment: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + ref: { + type: "string" + }, + repo: { + required: true, + type: "string" + }, + sha: { + type: "string" + }, + task: { + type: "string" + } + }, + url: "/repos/:owner/:repo/deployments" + }, + listDownloads: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/downloads" + }, + listForOrg: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + sort: { + enum: ["created", "updated", "pushed", "full_name"], + type: "string" + }, + type: { + enum: ["all", "public", "private", "forks", "sources", "member", "internal"], + type: "string" + } + }, + url: "/orgs/:org/repos" + }, + listForUser: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + sort: { + enum: ["created", "updated", "pushed", "full_name"], + type: "string" + }, + type: { + enum: ["all", "owner", "member"], + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/repos" + }, + listForks: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + sort: { + enum: ["newest", "oldest", "stargazers"], + type: "string" + } + }, + url: "/repos/:owner/:repo/forks" + }, + listHooks: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/hooks" + }, + listInvitations: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/invitations" + }, + listInvitationsForAuthenticatedUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/repository_invitations" + }, + listLanguages: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/languages" + }, + listPagesBuilds: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pages/builds" + }, + listProtectedBranchRequiredStatusChecksContexts: { + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_status_checks/contexts" + }, + listProtectedBranchTeamRestrictions: { + deprecated: "octokit.repos.listProtectedBranchTeamRestrictions() has been renamed to octokit.repos.getTeamsWithAccessToProtectedBranch() (2019-09-09)", + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/teams" + }, + listProtectedBranchUserRestrictions: { + deprecated: "octokit.repos.listProtectedBranchUserRestrictions() has been renamed to octokit.repos.getUsersWithAccessToProtectedBranch() (2019-09-09)", + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/users" + }, + listPublic: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + since: { + type: "integer" + } + }, + url: "/repositories" + }, + listPullRequestsAssociatedWithCommit: { + headers: { + accept: "application/vnd.github.groot-preview+json" + }, + method: "GET", + params: { + commit_sha: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/commits/:commit_sha/pulls" + }, + listReleases: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/releases" + }, + listStatusesForRef: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + ref: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/commits/:ref/statuses" + }, + listTags: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/tags" + }, + listTeams: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/teams" + }, + listTeamsWithAccessToProtectedBranch: { + deprecated: "octokit.repos.listTeamsWithAccessToProtectedBranch() has been renamed to octokit.repos.getTeamsWithAccessToProtectedBranch() (2019-09-13)", + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/teams" + }, + listTopics: { + headers: { + accept: "application/vnd.github.mercy-preview+json" + }, + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/topics" + }, + listUsersWithAccessToProtectedBranch: { + deprecated: "octokit.repos.listUsersWithAccessToProtectedBranch() has been renamed to octokit.repos.getUsersWithAccessToProtectedBranch() (2019-09-13)", + method: "GET", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/users" + }, + merge: { + method: "POST", + params: { + base: { + required: true, + type: "string" + }, + commit_message: { + type: "string" + }, + head: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/merges" + }, + pingHook: { + method: "POST", + params: { + hook_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/hooks/:hook_id/pings" + }, + removeBranchProtection: { + method: "DELETE", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection" + }, + removeCollaborator: { + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/collaborators/:username" + }, + removeDeployKey: { + method: "DELETE", + params: { + key_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/keys/:key_id" + }, + removeProtectedBranchAdminEnforcement: { + method: "DELETE", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/enforce_admins" + }, + removeProtectedBranchAppRestrictions: { + method: "DELETE", + params: { + apps: { + mapTo: "data", + required: true, + type: "string[]" + }, + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/apps" + }, + removeProtectedBranchPullRequestReviewEnforcement: { + method: "DELETE", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_pull_request_reviews" + }, + removeProtectedBranchRequiredSignatures: { + headers: { + accept: "application/vnd.github.zzzax-preview+json" + }, + method: "DELETE", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_signatures" + }, + removeProtectedBranchRequiredStatusChecks: { + method: "DELETE", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_status_checks" + }, + removeProtectedBranchRequiredStatusChecksContexts: { + method: "DELETE", + params: { + branch: { + required: true, + type: "string" + }, + contexts: { + mapTo: "data", + required: true, + type: "string[]" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_status_checks/contexts" + }, + removeProtectedBranchRestrictions: { + method: "DELETE", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions" + }, + removeProtectedBranchTeamRestrictions: { + method: "DELETE", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + teams: { + mapTo: "data", + required: true, + type: "string[]" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/teams" + }, + removeProtectedBranchUserRestrictions: { + method: "DELETE", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + users: { + mapTo: "data", + required: true, + type: "string[]" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/users" + }, + replaceProtectedBranchAppRestrictions: { + method: "PUT", + params: { + apps: { + mapTo: "data", + required: true, + type: "string[]" + }, + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/apps" + }, + replaceProtectedBranchRequiredStatusChecksContexts: { + method: "PUT", + params: { + branch: { + required: true, + type: "string" + }, + contexts: { + mapTo: "data", + required: true, + type: "string[]" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_status_checks/contexts" + }, + replaceProtectedBranchTeamRestrictions: { + method: "PUT", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + teams: { + mapTo: "data", + required: true, + type: "string[]" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/teams" + }, + replaceProtectedBranchUserRestrictions: { + method: "PUT", + params: { + branch: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + users: { + mapTo: "data", + required: true, + type: "string[]" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/restrictions/users" + }, + replaceTopics: { + headers: { + accept: "application/vnd.github.mercy-preview+json" + }, + method: "PUT", + params: { + names: { + required: true, + type: "string[]" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/topics" + }, + requestPageBuild: { + method: "POST", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/pages/builds" + }, + retrieveCommunityProfileMetrics: { + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/community/profile" + }, + testPushHook: { + method: "POST", + params: { + hook_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/hooks/:hook_id/tests" + }, + transfer: { + method: "POST", + params: { + new_owner: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + team_ids: { + type: "integer[]" + } + }, + url: "/repos/:owner/:repo/transfer" + }, + update: { + method: "PATCH", + params: { + allow_merge_commit: { + type: "boolean" + }, + allow_rebase_merge: { + type: "boolean" + }, + allow_squash_merge: { + type: "boolean" + }, + archived: { + type: "boolean" + }, + default_branch: { + type: "string" + }, + delete_branch_on_merge: { + type: "boolean" + }, + description: { + type: "string" + }, + has_issues: { + type: "boolean" + }, + has_projects: { + type: "boolean" + }, + has_wiki: { + type: "boolean" + }, + homepage: { + type: "string" + }, + is_template: { + type: "boolean" + }, + name: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + private: { + type: "boolean" + }, + repo: { + required: true, + type: "string" + }, + visibility: { + enum: ["public", "private", "visibility", "internal"], + type: "string" + } + }, + url: "/repos/:owner/:repo" + }, + updateBranchProtection: { + method: "PUT", + params: { + allow_deletions: { + type: "boolean" + }, + allow_force_pushes: { + allowNull: true, + type: "boolean" + }, + branch: { + required: true, + type: "string" + }, + enforce_admins: { + allowNull: true, + required: true, + type: "boolean" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + required_linear_history: { + type: "boolean" + }, + required_pull_request_reviews: { + allowNull: true, + required: true, + type: "object" + }, + "required_pull_request_reviews.dismiss_stale_reviews": { + type: "boolean" + }, + "required_pull_request_reviews.dismissal_restrictions": { + type: "object" + }, + "required_pull_request_reviews.dismissal_restrictions.teams": { + type: "string[]" + }, + "required_pull_request_reviews.dismissal_restrictions.users": { + type: "string[]" + }, + "required_pull_request_reviews.require_code_owner_reviews": { + type: "boolean" + }, + "required_pull_request_reviews.required_approving_review_count": { + type: "integer" + }, + required_status_checks: { + allowNull: true, + required: true, + type: "object" + }, + "required_status_checks.contexts": { + required: true, + type: "string[]" + }, + "required_status_checks.strict": { + required: true, + type: "boolean" + }, + restrictions: { + allowNull: true, + required: true, + type: "object" + }, + "restrictions.apps": { + type: "string[]" + }, + "restrictions.teams": { + required: true, + type: "string[]" + }, + "restrictions.users": { + required: true, + type: "string[]" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection" + }, + updateCommitComment: { + method: "PATCH", + params: { + body: { + required: true, + type: "string" + }, + comment_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/comments/:comment_id" + }, + updateFile: { + deprecated: "octokit.repos.updateFile() has been renamed to octokit.repos.createOrUpdateFile() (2019-06-07)", + method: "PUT", + params: { + author: { + type: "object" + }, + "author.email": { + required: true, + type: "string" + }, + "author.name": { + required: true, + type: "string" + }, + branch: { + type: "string" + }, + committer: { + type: "object" + }, + "committer.email": { + required: true, + type: "string" + }, + "committer.name": { + required: true, + type: "string" + }, + content: { + required: true, + type: "string" + }, + message: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + path: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + sha: { + type: "string" + } + }, + url: "/repos/:owner/:repo/contents/:path" + }, + updateHook: { + method: "PATCH", + params: { + active: { + type: "boolean" + }, + add_events: { + type: "string[]" + }, + config: { + type: "object" + }, + "config.content_type": { + type: "string" + }, + "config.insecure_ssl": { + type: "string" + }, + "config.secret": { + type: "string" + }, + "config.url": { + required: true, + type: "string" + }, + events: { + type: "string[]" + }, + hook_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + remove_events: { + type: "string[]" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/hooks/:hook_id" + }, + updateInformationAboutPagesSite: { + method: "PUT", + params: { + cname: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + source: { + enum: ['"gh-pages"', '"master"', '"master /docs"'], + type: "string" + } + }, + url: "/repos/:owner/:repo/pages" + }, + updateInvitation: { + method: "PATCH", + params: { + invitation_id: { + required: true, + type: "integer" + }, + owner: { + required: true, + type: "string" + }, + permissions: { + enum: ["read", "write", "admin"], + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/invitations/:invitation_id" + }, + updateProtectedBranchPullRequestReviewEnforcement: { + method: "PATCH", + params: { + branch: { + required: true, + type: "string" + }, + dismiss_stale_reviews: { + type: "boolean" + }, + dismissal_restrictions: { + type: "object" + }, + "dismissal_restrictions.teams": { + type: "string[]" + }, + "dismissal_restrictions.users": { + type: "string[]" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + require_code_owner_reviews: { + type: "boolean" + }, + required_approving_review_count: { + type: "integer" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_pull_request_reviews" + }, + updateProtectedBranchRequiredStatusChecks: { + method: "PATCH", + params: { + branch: { + required: true, + type: "string" + }, + contexts: { + type: "string[]" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + strict: { + type: "boolean" + } + }, + url: "/repos/:owner/:repo/branches/:branch/protection/required_status_checks" + }, + updateRelease: { + method: "PATCH", + params: { + body: { + type: "string" + }, + draft: { + type: "boolean" + }, + name: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + prerelease: { + type: "boolean" + }, + release_id: { + required: true, + type: "integer" + }, + repo: { + required: true, + type: "string" + }, + tag_name: { + type: "string" + }, + target_commitish: { + type: "string" + } + }, + url: "/repos/:owner/:repo/releases/:release_id" + }, + updateReleaseAsset: { + method: "PATCH", + params: { + asset_id: { + required: true, + type: "integer" + }, + label: { + type: "string" + }, + name: { + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + } + }, + url: "/repos/:owner/:repo/releases/assets/:asset_id" + }, + uploadReleaseAsset: { + method: "POST", + params: { + data: { + mapTo: "data", + required: true, + type: "string | object" + }, + file: { + alias: "data", + deprecated: true, + type: "string | object" + }, + headers: { + required: true, + type: "object" + }, + "headers.content-length": { + required: true, + type: "integer" + }, + "headers.content-type": { + required: true, + type: "string" + }, + label: { + type: "string" + }, + name: { + required: true, + type: "string" + }, + url: { + required: true, + type: "string" + } + }, + url: ":url" + } + }, + search: { + code: { + method: "GET", + params: { + order: { + enum: ["desc", "asc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + q: { + required: true, + type: "string" + }, + sort: { + enum: ["indexed"], + type: "string" + } + }, + url: "/search/code" + }, + commits: { + headers: { + accept: "application/vnd.github.cloak-preview+json" + }, + method: "GET", + params: { + order: { + enum: ["desc", "asc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + q: { + required: true, + type: "string" + }, + sort: { + enum: ["author-date", "committer-date"], + type: "string" + } + }, + url: "/search/commits" + }, + issues: { + deprecated: "octokit.search.issues() has been renamed to octokit.search.issuesAndPullRequests() (2018-12-27)", + method: "GET", + params: { + order: { + enum: ["desc", "asc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + q: { + required: true, + type: "string" + }, + sort: { + enum: ["comments", "reactions", "reactions-+1", "reactions--1", "reactions-smile", "reactions-thinking_face", "reactions-heart", "reactions-tada", "interactions", "created", "updated"], + type: "string" + } + }, + url: "/search/issues" + }, + issuesAndPullRequests: { + method: "GET", + params: { + order: { + enum: ["desc", "asc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + q: { + required: true, + type: "string" + }, + sort: { + enum: ["comments", "reactions", "reactions-+1", "reactions--1", "reactions-smile", "reactions-thinking_face", "reactions-heart", "reactions-tada", "interactions", "created", "updated"], + type: "string" + } + }, + url: "/search/issues" + }, + labels: { + method: "GET", + params: { + order: { + enum: ["desc", "asc"], + type: "string" + }, + q: { + required: true, + type: "string" + }, + repository_id: { + required: true, + type: "integer" + }, + sort: { + enum: ["created", "updated"], + type: "string" + } + }, + url: "/search/labels" + }, + repos: { + method: "GET", + params: { + order: { + enum: ["desc", "asc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + q: { + required: true, + type: "string" + }, + sort: { + enum: ["stars", "forks", "help-wanted-issues", "updated"], + type: "string" + } + }, + url: "/search/repositories" + }, + topics: { + method: "GET", + params: { + q: { + required: true, + type: "string" + } + }, + url: "/search/topics" + }, + users: { + method: "GET", + params: { + order: { + enum: ["desc", "asc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + q: { + required: true, + type: "string" + }, + sort: { + enum: ["followers", "repositories", "joined"], + type: "string" + } + }, + url: "/search/users" + } + }, + teams: { + addMember: { + deprecated: "octokit.teams.addMember() has been renamed to octokit.teams.addMemberLegacy() (2020-01-16)", + method: "PUT", + params: { + team_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/members/:username" + }, + addMemberLegacy: { + deprecated: "octokit.teams.addMemberLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#add-team-member-legacy", + method: "PUT", + params: { + team_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/members/:username" + }, + addOrUpdateMembership: { + deprecated: "octokit.teams.addOrUpdateMembership() has been renamed to octokit.teams.addOrUpdateMembershipLegacy() (2020-01-16)", + method: "PUT", + params: { + role: { + enum: ["member", "maintainer"], + type: "string" + }, + team_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/memberships/:username" + }, + addOrUpdateMembershipInOrg: { + method: "PUT", + params: { + org: { + required: true, + type: "string" + }, + role: { + enum: ["member", "maintainer"], + type: "string" + }, + team_slug: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/memberships/:username" + }, + addOrUpdateMembershipLegacy: { + deprecated: "octokit.teams.addOrUpdateMembershipLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#add-or-update-team-membership-legacy", + method: "PUT", + params: { + role: { + enum: ["member", "maintainer"], + type: "string" + }, + team_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/memberships/:username" + }, + addOrUpdateProject: { + deprecated: "octokit.teams.addOrUpdateProject() has been renamed to octokit.teams.addOrUpdateProjectLegacy() (2020-01-16)", + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "PUT", + params: { + permission: { + enum: ["read", "write", "admin"], + type: "string" + }, + project_id: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/projects/:project_id" + }, + addOrUpdateProjectInOrg: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "PUT", + params: { + org: { + required: true, + type: "string" + }, + permission: { + enum: ["read", "write", "admin"], + type: "string" + }, + project_id: { + required: true, + type: "integer" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/projects/:project_id" + }, + addOrUpdateProjectLegacy: { + deprecated: "octokit.teams.addOrUpdateProjectLegacy() is deprecated, see https://developer.github.com/v3/teams/#add-or-update-team-project-legacy", + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "PUT", + params: { + permission: { + enum: ["read", "write", "admin"], + type: "string" + }, + project_id: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/projects/:project_id" + }, + addOrUpdateRepo: { + deprecated: "octokit.teams.addOrUpdateRepo() has been renamed to octokit.teams.addOrUpdateRepoLegacy() (2020-01-16)", + method: "PUT", + params: { + owner: { + required: true, + type: "string" + }, + permission: { + enum: ["pull", "push", "admin"], + type: "string" + }, + repo: { + required: true, + type: "string" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/repos/:owner/:repo" + }, + addOrUpdateRepoInOrg: { + method: "PUT", + params: { + org: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + permission: { + enum: ["pull", "push", "admin"], + type: "string" + }, + repo: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/repos/:owner/:repo" + }, + addOrUpdateRepoLegacy: { + deprecated: "octokit.teams.addOrUpdateRepoLegacy() is deprecated, see https://developer.github.com/v3/teams/#add-or-update-team-repository-legacy", + method: "PUT", + params: { + owner: { + required: true, + type: "string" + }, + permission: { + enum: ["pull", "push", "admin"], + type: "string" + }, + repo: { + required: true, + type: "string" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/repos/:owner/:repo" + }, + checkManagesRepo: { + deprecated: "octokit.teams.checkManagesRepo() has been renamed to octokit.teams.checkManagesRepoLegacy() (2020-01-16)", + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/repos/:owner/:repo" + }, + checkManagesRepoInOrg: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/repos/:owner/:repo" + }, + checkManagesRepoLegacy: { + deprecated: "octokit.teams.checkManagesRepoLegacy() is deprecated, see https://developer.github.com/v3/teams/#check-if-a-team-manages-a-repository-legacy", + method: "GET", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/repos/:owner/:repo" + }, + create: { + method: "POST", + params: { + description: { + type: "string" + }, + maintainers: { + type: "string[]" + }, + name: { + required: true, + type: "string" + }, + org: { + required: true, + type: "string" + }, + parent_team_id: { + type: "integer" + }, + permission: { + enum: ["pull", "push", "admin"], + type: "string" + }, + privacy: { + enum: ["secret", "closed"], + type: "string" + }, + repo_names: { + type: "string[]" + } + }, + url: "/orgs/:org/teams" + }, + createDiscussion: { + deprecated: "octokit.teams.createDiscussion() has been renamed to octokit.teams.createDiscussionLegacy() (2020-01-16)", + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + private: { + type: "boolean" + }, + team_id: { + required: true, + type: "integer" + }, + title: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/discussions" + }, + createDiscussionComment: { + deprecated: "octokit.teams.createDiscussionComment() has been renamed to octokit.teams.createDiscussionCommentLegacy() (2020-01-16)", + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments" + }, + createDiscussionCommentInOrg: { + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments" + }, + createDiscussionCommentLegacy: { + deprecated: "octokit.teams.createDiscussionCommentLegacy() is deprecated, see https://developer.github.com/v3/teams/discussion_comments/#create-a-comment-legacy", + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments" + }, + createDiscussionInOrg: { + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + org: { + required: true, + type: "string" + }, + private: { + type: "boolean" + }, + team_slug: { + required: true, + type: "string" + }, + title: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions" + }, + createDiscussionLegacy: { + deprecated: "octokit.teams.createDiscussionLegacy() is deprecated, see https://developer.github.com/v3/teams/discussions/#create-a-discussion-legacy", + method: "POST", + params: { + body: { + required: true, + type: "string" + }, + private: { + type: "boolean" + }, + team_id: { + required: true, + type: "integer" + }, + title: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/discussions" + }, + delete: { + deprecated: "octokit.teams.delete() has been renamed to octokit.teams.deleteLegacy() (2020-01-16)", + method: "DELETE", + params: { + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id" + }, + deleteDiscussion: { + deprecated: "octokit.teams.deleteDiscussion() has been renamed to octokit.teams.deleteDiscussionLegacy() (2020-01-16)", + method: "DELETE", + params: { + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number" + }, + deleteDiscussionComment: { + deprecated: "octokit.teams.deleteDiscussionComment() has been renamed to octokit.teams.deleteDiscussionCommentLegacy() (2020-01-16)", + method: "DELETE", + params: { + comment_number: { + required: true, + type: "integer" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments/:comment_number" + }, + deleteDiscussionCommentInOrg: { + method: "DELETE", + params: { + comment_number: { + required: true, + type: "integer" + }, + discussion_number: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments/:comment_number" + }, + deleteDiscussionCommentLegacy: { + deprecated: "octokit.teams.deleteDiscussionCommentLegacy() is deprecated, see https://developer.github.com/v3/teams/discussion_comments/#delete-a-comment-legacy", + method: "DELETE", + params: { + comment_number: { + required: true, + type: "integer" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments/:comment_number" + }, + deleteDiscussionInOrg: { + method: "DELETE", + params: { + discussion_number: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions/:discussion_number" + }, + deleteDiscussionLegacy: { + deprecated: "octokit.teams.deleteDiscussionLegacy() is deprecated, see https://developer.github.com/v3/teams/discussions/#delete-a-discussion-legacy", + method: "DELETE", + params: { + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number" + }, + deleteInOrg: { + method: "DELETE", + params: { + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug" + }, + deleteLegacy: { + deprecated: "octokit.teams.deleteLegacy() is deprecated, see https://developer.github.com/v3/teams/#delete-team-legacy", + method: "DELETE", + params: { + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id" + }, + get: { + deprecated: "octokit.teams.get() has been renamed to octokit.teams.getLegacy() (2020-01-16)", + method: "GET", + params: { + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id" + }, + getByName: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug" + }, + getDiscussion: { + deprecated: "octokit.teams.getDiscussion() has been renamed to octokit.teams.getDiscussionLegacy() (2020-01-16)", + method: "GET", + params: { + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number" + }, + getDiscussionComment: { + deprecated: "octokit.teams.getDiscussionComment() has been renamed to octokit.teams.getDiscussionCommentLegacy() (2020-01-16)", + method: "GET", + params: { + comment_number: { + required: true, + type: "integer" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments/:comment_number" + }, + getDiscussionCommentInOrg: { + method: "GET", + params: { + comment_number: { + required: true, + type: "integer" + }, + discussion_number: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments/:comment_number" + }, + getDiscussionCommentLegacy: { + deprecated: "octokit.teams.getDiscussionCommentLegacy() is deprecated, see https://developer.github.com/v3/teams/discussion_comments/#get-a-single-comment-legacy", + method: "GET", + params: { + comment_number: { + required: true, + type: "integer" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments/:comment_number" + }, + getDiscussionInOrg: { + method: "GET", + params: { + discussion_number: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions/:discussion_number" + }, + getDiscussionLegacy: { + deprecated: "octokit.teams.getDiscussionLegacy() is deprecated, see https://developer.github.com/v3/teams/discussions/#get-a-single-discussion-legacy", + method: "GET", + params: { + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number" + }, + getLegacy: { + deprecated: "octokit.teams.getLegacy() is deprecated, see https://developer.github.com/v3/teams/#get-team-legacy", + method: "GET", + params: { + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id" + }, + getMember: { + deprecated: "octokit.teams.getMember() has been renamed to octokit.teams.getMemberLegacy() (2020-01-16)", + method: "GET", + params: { + team_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/members/:username" + }, + getMemberLegacy: { + deprecated: "octokit.teams.getMemberLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#get-team-member-legacy", + method: "GET", + params: { + team_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/members/:username" + }, + getMembership: { + deprecated: "octokit.teams.getMembership() has been renamed to octokit.teams.getMembershipLegacy() (2020-01-16)", + method: "GET", + params: { + team_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/memberships/:username" + }, + getMembershipInOrg: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/memberships/:username" + }, + getMembershipLegacy: { + deprecated: "octokit.teams.getMembershipLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#get-team-membership-legacy", + method: "GET", + params: { + team_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/memberships/:username" + }, + list: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/orgs/:org/teams" + }, + listChild: { + deprecated: "octokit.teams.listChild() has been renamed to octokit.teams.listChildLegacy() (2020-01-16)", + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/teams" + }, + listChildInOrg: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/teams" + }, + listChildLegacy: { + deprecated: "octokit.teams.listChildLegacy() is deprecated, see https://developer.github.com/v3/teams/#list-child-teams-legacy", + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/teams" + }, + listDiscussionComments: { + deprecated: "octokit.teams.listDiscussionComments() has been renamed to octokit.teams.listDiscussionCommentsLegacy() (2020-01-16)", + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments" + }, + listDiscussionCommentsInOrg: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments" + }, + listDiscussionCommentsLegacy: { + deprecated: "octokit.teams.listDiscussionCommentsLegacy() is deprecated, see https://developer.github.com/v3/teams/discussion_comments/#list-comments-legacy", + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments" + }, + listDiscussions: { + deprecated: "octokit.teams.listDiscussions() has been renamed to octokit.teams.listDiscussionsLegacy() (2020-01-16)", + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions" + }, + listDiscussionsInOrg: { + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions" + }, + listDiscussionsLegacy: { + deprecated: "octokit.teams.listDiscussionsLegacy() is deprecated, see https://developer.github.com/v3/teams/discussions/#list-discussions-legacy", + method: "GET", + params: { + direction: { + enum: ["asc", "desc"], + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions" + }, + listForAuthenticatedUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/teams" + }, + listMembers: { + deprecated: "octokit.teams.listMembers() has been renamed to octokit.teams.listMembersLegacy() (2020-01-16)", + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + role: { + enum: ["member", "maintainer", "all"], + type: "string" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/members" + }, + listMembersInOrg: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + role: { + enum: ["member", "maintainer", "all"], + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/members" + }, + listMembersLegacy: { + deprecated: "octokit.teams.listMembersLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#list-team-members-legacy", + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + role: { + enum: ["member", "maintainer", "all"], + type: "string" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/members" + }, + listPendingInvitations: { + deprecated: "octokit.teams.listPendingInvitations() has been renamed to octokit.teams.listPendingInvitationsLegacy() (2020-01-16)", + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/invitations" + }, + listPendingInvitationsInOrg: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/invitations" + }, + listPendingInvitationsLegacy: { + deprecated: "octokit.teams.listPendingInvitationsLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#list-pending-team-invitations-legacy", + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/invitations" + }, + listProjects: { + deprecated: "octokit.teams.listProjects() has been renamed to octokit.teams.listProjectsLegacy() (2020-01-16)", + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/projects" + }, + listProjectsInOrg: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/projects" + }, + listProjectsLegacy: { + deprecated: "octokit.teams.listProjectsLegacy() is deprecated, see https://developer.github.com/v3/teams/#list-team-projects-legacy", + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/projects" + }, + listRepos: { + deprecated: "octokit.teams.listRepos() has been renamed to octokit.teams.listReposLegacy() (2020-01-16)", + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/repos" + }, + listReposInOrg: { + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/repos" + }, + listReposLegacy: { + deprecated: "octokit.teams.listReposLegacy() is deprecated, see https://developer.github.com/v3/teams/#list-team-repos-legacy", + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/repos" + }, + removeMember: { + deprecated: "octokit.teams.removeMember() has been renamed to octokit.teams.removeMemberLegacy() (2020-01-16)", + method: "DELETE", + params: { + team_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/members/:username" + }, + removeMemberLegacy: { + deprecated: "octokit.teams.removeMemberLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#remove-team-member-legacy", + method: "DELETE", + params: { + team_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/members/:username" + }, + removeMembership: { + deprecated: "octokit.teams.removeMembership() has been renamed to octokit.teams.removeMembershipLegacy() (2020-01-16)", + method: "DELETE", + params: { + team_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/memberships/:username" + }, + removeMembershipInOrg: { + method: "DELETE", + params: { + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/memberships/:username" + }, + removeMembershipLegacy: { + deprecated: "octokit.teams.removeMembershipLegacy() is deprecated, see https://developer.github.com/v3/teams/members/#remove-team-membership-legacy", + method: "DELETE", + params: { + team_id: { + required: true, + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/teams/:team_id/memberships/:username" + }, + removeProject: { + deprecated: "octokit.teams.removeProject() has been renamed to octokit.teams.removeProjectLegacy() (2020-01-16)", + method: "DELETE", + params: { + project_id: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/projects/:project_id" + }, + removeProjectInOrg: { + method: "DELETE", + params: { + org: { + required: true, + type: "string" + }, + project_id: { + required: true, + type: "integer" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/projects/:project_id" + }, + removeProjectLegacy: { + deprecated: "octokit.teams.removeProjectLegacy() is deprecated, see https://developer.github.com/v3/teams/#remove-team-project-legacy", + method: "DELETE", + params: { + project_id: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/projects/:project_id" + }, + removeRepo: { + deprecated: "octokit.teams.removeRepo() has been renamed to octokit.teams.removeRepoLegacy() (2020-01-16)", + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/repos/:owner/:repo" + }, + removeRepoInOrg: { + method: "DELETE", + params: { + org: { + required: true, + type: "string" + }, + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/repos/:owner/:repo" + }, + removeRepoLegacy: { + deprecated: "octokit.teams.removeRepoLegacy() is deprecated, see https://developer.github.com/v3/teams/#remove-team-repository-legacy", + method: "DELETE", + params: { + owner: { + required: true, + type: "string" + }, + repo: { + required: true, + type: "string" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/repos/:owner/:repo" + }, + reviewProject: { + deprecated: "octokit.teams.reviewProject() has been renamed to octokit.teams.reviewProjectLegacy() (2020-01-16)", + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + project_id: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/projects/:project_id" + }, + reviewProjectInOrg: { + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + org: { + required: true, + type: "string" + }, + project_id: { + required: true, + type: "integer" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/projects/:project_id" + }, + reviewProjectLegacy: { + deprecated: "octokit.teams.reviewProjectLegacy() is deprecated, see https://developer.github.com/v3/teams/#review-a-team-project-legacy", + headers: { + accept: "application/vnd.github.inertia-preview+json" + }, + method: "GET", + params: { + project_id: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/projects/:project_id" + }, + update: { + deprecated: "octokit.teams.update() has been renamed to octokit.teams.updateLegacy() (2020-01-16)", + method: "PATCH", + params: { + description: { + type: "string" + }, + name: { + required: true, + type: "string" + }, + parent_team_id: { + type: "integer" + }, + permission: { + enum: ["pull", "push", "admin"], + type: "string" + }, + privacy: { + enum: ["secret", "closed"], + type: "string" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id" + }, + updateDiscussion: { + deprecated: "octokit.teams.updateDiscussion() has been renamed to octokit.teams.updateDiscussionLegacy() (2020-01-16)", + method: "PATCH", + params: { + body: { + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + }, + title: { + type: "string" + } + }, + url: "/teams/:team_id/discussions/:discussion_number" + }, + updateDiscussionComment: { + deprecated: "octokit.teams.updateDiscussionComment() has been renamed to octokit.teams.updateDiscussionCommentLegacy() (2020-01-16)", + method: "PATCH", + params: { + body: { + required: true, + type: "string" + }, + comment_number: { + required: true, + type: "integer" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments/:comment_number" + }, + updateDiscussionCommentInOrg: { + method: "PATCH", + params: { + body: { + required: true, + type: "string" + }, + comment_number: { + required: true, + type: "integer" + }, + discussion_number: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions/:discussion_number/comments/:comment_number" + }, + updateDiscussionCommentLegacy: { + deprecated: "octokit.teams.updateDiscussionCommentLegacy() is deprecated, see https://developer.github.com/v3/teams/discussion_comments/#edit-a-comment-legacy", + method: "PATCH", + params: { + body: { + required: true, + type: "string" + }, + comment_number: { + required: true, + type: "integer" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id/discussions/:discussion_number/comments/:comment_number" + }, + updateDiscussionInOrg: { + method: "PATCH", + params: { + body: { + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + org: { + required: true, + type: "string" + }, + team_slug: { + required: true, + type: "string" + }, + title: { + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug/discussions/:discussion_number" + }, + updateDiscussionLegacy: { + deprecated: "octokit.teams.updateDiscussionLegacy() is deprecated, see https://developer.github.com/v3/teams/discussions/#edit-a-discussion-legacy", + method: "PATCH", + params: { + body: { + type: "string" + }, + discussion_number: { + required: true, + type: "integer" + }, + team_id: { + required: true, + type: "integer" + }, + title: { + type: "string" + } + }, + url: "/teams/:team_id/discussions/:discussion_number" + }, + updateInOrg: { + method: "PATCH", + params: { + description: { + type: "string" + }, + name: { + required: true, + type: "string" + }, + org: { + required: true, + type: "string" + }, + parent_team_id: { + type: "integer" + }, + permission: { + enum: ["pull", "push", "admin"], + type: "string" + }, + privacy: { + enum: ["secret", "closed"], + type: "string" + }, + team_slug: { + required: true, + type: "string" + } + }, + url: "/orgs/:org/teams/:team_slug" + }, + updateLegacy: { + deprecated: "octokit.teams.updateLegacy() is deprecated, see https://developer.github.com/v3/teams/#edit-team-legacy", + method: "PATCH", + params: { + description: { + type: "string" + }, + name: { + required: true, + type: "string" + }, + parent_team_id: { + type: "integer" + }, + permission: { + enum: ["pull", "push", "admin"], + type: "string" + }, + privacy: { + enum: ["secret", "closed"], + type: "string" + }, + team_id: { + required: true, + type: "integer" + } + }, + url: "/teams/:team_id" + } + }, + users: { + addEmails: { + method: "POST", + params: { + emails: { + required: true, + type: "string[]" + } + }, + url: "/user/emails" + }, + block: { + method: "PUT", + params: { + username: { + required: true, + type: "string" + } + }, + url: "/user/blocks/:username" + }, + checkBlocked: { + method: "GET", + params: { + username: { + required: true, + type: "string" + } + }, + url: "/user/blocks/:username" + }, + checkFollowing: { + method: "GET", + params: { + username: { + required: true, + type: "string" + } + }, + url: "/user/following/:username" + }, + checkFollowingForUser: { + method: "GET", + params: { + target_user: { + required: true, + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/following/:target_user" + }, + createGpgKey: { + method: "POST", + params: { + armored_public_key: { + type: "string" + } + }, + url: "/user/gpg_keys" + }, + createPublicKey: { + method: "POST", + params: { + key: { + type: "string" + }, + title: { + type: "string" + } + }, + url: "/user/keys" + }, + deleteEmails: { + method: "DELETE", + params: { + emails: { + required: true, + type: "string[]" + } + }, + url: "/user/emails" + }, + deleteGpgKey: { + method: "DELETE", + params: { + gpg_key_id: { + required: true, + type: "integer" + } + }, + url: "/user/gpg_keys/:gpg_key_id" + }, + deletePublicKey: { + method: "DELETE", + params: { + key_id: { + required: true, + type: "integer" + } + }, + url: "/user/keys/:key_id" + }, + follow: { + method: "PUT", + params: { + username: { + required: true, + type: "string" + } + }, + url: "/user/following/:username" + }, + getAuthenticated: { + method: "GET", + params: {}, + url: "/user" + }, + getByUsername: { + method: "GET", + params: { + username: { + required: true, + type: "string" + } + }, + url: "/users/:username" + }, + getContextForUser: { + method: "GET", + params: { + subject_id: { + type: "string" + }, + subject_type: { + enum: ["organization", "repository", "issue", "pull_request"], + type: "string" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/hovercard" + }, + getGpgKey: { + method: "GET", + params: { + gpg_key_id: { + required: true, + type: "integer" + } + }, + url: "/user/gpg_keys/:gpg_key_id" + }, + getPublicKey: { + method: "GET", + params: { + key_id: { + required: true, + type: "integer" + } + }, + url: "/user/keys/:key_id" + }, + list: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + since: { + type: "string" + } + }, + url: "/users" + }, + listBlocked: { + method: "GET", + params: {}, + url: "/user/blocks" + }, + listEmails: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/emails" + }, + listFollowersForAuthenticatedUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/followers" + }, + listFollowersForUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/followers" + }, + listFollowingForAuthenticatedUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/following" + }, + listFollowingForUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/following" + }, + listGpgKeys: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/gpg_keys" + }, + listGpgKeysForUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/gpg_keys" + }, + listPublicEmails: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/public_emails" + }, + listPublicKeys: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + } + }, + url: "/user/keys" + }, + listPublicKeysForUser: { + method: "GET", + params: { + page: { + type: "integer" + }, + per_page: { + type: "integer" + }, + username: { + required: true, + type: "string" + } + }, + url: "/users/:username/keys" + }, + togglePrimaryEmailVisibility: { + method: "PATCH", + params: { + email: { + required: true, + type: "string" + }, + visibility: { + required: true, + type: "string" + } + }, + url: "/user/email/visibility" + }, + unblock: { + method: "DELETE", + params: { + username: { + required: true, + type: "string" + } + }, + url: "/user/blocks/:username" + }, + unfollow: { + method: "DELETE", + params: { + username: { + required: true, + type: "string" + } + }, + url: "/user/following/:username" + }, + updateAuthenticated: { + method: "PATCH", + params: { + bio: { + type: "string" + }, + blog: { + type: "string" + }, + company: { + type: "string" + }, + email: { + type: "string" + }, + hireable: { + type: "boolean" + }, + location: { + type: "string" + }, + name: { + type: "string" + } + }, + url: "/user" + } + } +}; + +const VERSION = "2.4.0"; + +function registerEndpoints(octokit, routes) { + Object.keys(routes).forEach(namespaceName => { + if (!octokit[namespaceName]) { + octokit[namespaceName] = {}; + } + + Object.keys(routes[namespaceName]).forEach(apiName => { + const apiOptions = routes[namespaceName][apiName]; + const endpointDefaults = ["method", "url", "headers"].reduce((map, key) => { + if (typeof apiOptions[key] !== "undefined") { + map[key] = apiOptions[key]; + } + + return map; + }, {}); + endpointDefaults.request = { + validate: apiOptions.params + }; + let request = octokit.request.defaults(endpointDefaults); // patch request & endpoint methods to support deprecated parameters. + // Not the most elegant solution, but we don’t want to move deprecation + // logic into octokit/endpoint.js as it’s out of scope + + const hasDeprecatedParam = Object.keys(apiOptions.params || {}).find(key => apiOptions.params[key].deprecated); + + if (hasDeprecatedParam) { + const patch = patchForDeprecation.bind(null, octokit, apiOptions); + request = patch(octokit.request.defaults(endpointDefaults), `.${namespaceName}.${apiName}()`); + request.endpoint = patch(request.endpoint, `.${namespaceName}.${apiName}.endpoint()`); + request.endpoint.merge = patch(request.endpoint.merge, `.${namespaceName}.${apiName}.endpoint.merge()`); + } + + if (apiOptions.deprecated) { + octokit[namespaceName][apiName] = Object.assign(function deprecatedEndpointMethod() { + octokit.log.warn(new deprecation.Deprecation(`[@octokit/rest] ${apiOptions.deprecated}`)); + octokit[namespaceName][apiName] = request; + return request.apply(null, arguments); + }, request); + return; + } + + octokit[namespaceName][apiName] = request; + }); + }); +} + +function patchForDeprecation(octokit, apiOptions, method, methodName) { + const patchedMethod = options => { + options = Object.assign({}, options); + Object.keys(options).forEach(key => { + if (apiOptions.params[key] && apiOptions.params[key].deprecated) { + const aliasKey = apiOptions.params[key].alias; + octokit.log.warn(new deprecation.Deprecation(`[@octokit/rest] "${key}" parameter is deprecated for "${methodName}". Use "${aliasKey}" instead`)); + + if (!(aliasKey in options)) { + options[aliasKey] = options[key]; + } + + delete options[key]; + } + }); + return method(options); + }; + + Object.keys(method).forEach(key => { + patchedMethod[key] = method[key]; + }); + return patchedMethod; +} + +/** + * This plugin is a 1:1 copy of internal @octokit/rest plugins. The primary + * goal is to rebuild @octokit/rest on top of @octokit/core. Once that is + * done, we will remove the registerEndpoints methods and return the methods + * directly as with the other plugins. At that point we will also remove the + * legacy workarounds and deprecations. + * + * See the plan at + * https://github.com/octokit/plugin-rest-endpoint-methods.js/pull/1 + */ + +function restEndpointMethods(octokit) { + // @ts-ignore + octokit.registerEndpoints = registerEndpoints.bind(null, octokit); + registerEndpoints(octokit, endpointsByScope); // Aliasing scopes for backward compatibility + // See https://github.com/octokit/rest.js/pull/1134 + + [["gitdata", "git"], ["authorization", "oauthAuthorizations"], ["pullRequests", "pulls"]].forEach(([deprecatedScope, scope]) => { + Object.defineProperty(octokit, deprecatedScope, { + get() { + octokit.log.warn( // @ts-ignore + new deprecation.Deprecation(`[@octokit/plugin-rest-endpoint-methods] "octokit.${deprecatedScope}.*" methods are deprecated, use "octokit.${scope}.*" instead`)); // @ts-ignore + + return octokit[scope]; + } + + }); + }); + return {}; +} +restEndpointMethods.VERSION = VERSION; + +exports.restEndpointMethods = restEndpointMethods; +//# sourceMappingURL=index.js.map + + /***/ }), /***/ 850: @@ -14789,7 +28933,7 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge Object.defineProperty(exports, "__esModule", { value: true }); const url = __webpack_require__(835); const http = __webpack_require__(605); -const https = __webpack_require__(211); +const https = __webpack_require__(34); let fs; let tunnel; var HttpCodes; @@ -16391,107 +30535,40 @@ exports.withCustomRequest = withCustomRequest; /***/ }), -/***/ 899: -/***/ (function(module, __unusedexports, __webpack_require__) { +/***/ 916: +/***/ (function(__unusedmodule, exports) { -module.exports = registerEndpoints; +"use strict"; -const { Deprecation } = __webpack_require__(692); -function registerEndpoints(octokit, routes) { - Object.keys(routes).forEach(namespaceName => { - if (!octokit[namespaceName]) { - octokit[namespaceName] = {}; - } +Object.defineProperty(exports, '__esModule', { value: true }); - Object.keys(routes[namespaceName]).forEach(apiName => { - const apiOptions = routes[namespaceName][apiName]; +const VERSION = "1.0.0"; - const endpointDefaults = ["method", "url", "headers"].reduce( - (map, key) => { - if (typeof apiOptions[key] !== "undefined") { - map[key] = apiOptions[key]; - } +/** + * @param octokit Octokit instance + * @param options Options passed to Octokit constructor + */ - return map; - }, - {} - ); - - endpointDefaults.request = { - validate: apiOptions.params - }; - - let request = octokit.request.defaults(endpointDefaults); - - // patch request & endpoint methods to support deprecated parameters. - // Not the most elegant solution, but we don’t want to move deprecation - // logic into octokit/endpoint.js as it’s out of scope - const hasDeprecatedParam = Object.keys(apiOptions.params || {}).find( - key => apiOptions.params[key].deprecated - ); - if (hasDeprecatedParam) { - const patch = patchForDeprecation.bind(null, octokit, apiOptions); - request = patch( - octokit.request.defaults(endpointDefaults), - `.${namespaceName}.${apiName}()` - ); - request.endpoint = patch( - request.endpoint, - `.${namespaceName}.${apiName}.endpoint()` - ); - request.endpoint.merge = patch( - request.endpoint.merge, - `.${namespaceName}.${apiName}.endpoint.merge()` - ); - } - - if (apiOptions.deprecated) { - octokit[namespaceName][apiName] = function deprecatedEndpointMethod() { - octokit.log.warn( - new Deprecation(`[@octokit/rest] ${apiOptions.deprecated}`) - ); - octokit[namespaceName][apiName] = request; - return request.apply(null, arguments); - }; - - return; - } - - octokit[namespaceName][apiName] = request; +function requestLog(octokit) { + octokit.hook.wrap("request", (request, options) => { + octokit.log.debug("request", options); + const start = Date.now(); + const requestOptions = octokit.request.endpoint.parse(options); + const path = requestOptions.url.replace(options.baseUrl, ""); + return request(options).then(response => { + octokit.log.info(`${requestOptions.method} ${path} - ${response.status} in ${Date.now() - start}ms`); + return response; + }).catch(error => { + octokit.log.info(`${requestOptions.method} ${path} - ${error.status} in ${Date.now() - start}ms`); + throw error; }); }); } +requestLog.VERSION = VERSION; -function patchForDeprecation(octokit, apiOptions, method, methodName) { - const patchedMethod = options => { - options = Object.assign({}, options); - - Object.keys(options).forEach(key => { - if (apiOptions.params[key] && apiOptions.params[key].deprecated) { - const aliasKey = apiOptions.params[key].alias; - - octokit.log.warn( - new Deprecation( - `[@octokit/rest] "${key}" parameter is deprecated for "${methodName}". Use "${aliasKey}" instead` - ) - ); - - if (!(aliasKey in options)) { - options[aliasKey] = options[key]; - } - delete options[key]; - } - }); - - return method(options); - }; - Object.keys(method).forEach(key => { - patchedMethod[key] = method[key]; - }); - - return patchedMethod; -} +exports.requestLog = requestLog; +//# sourceMappingURL=index.js.map /***/ }), @@ -16546,12 +30623,10 @@ function getProxyUrl(reqUrl) { } let proxyVar; if (usingSsl) { - proxyVar = process.env["https_proxy"] || - process.env["HTTPS_PROXY"]; + proxyVar = process.env['https_proxy'] || process.env['HTTPS_PROXY']; } else { - proxyVar = process.env["http_proxy"] || - process.env["HTTP_PROXY"]; + proxyVar = process.env['http_proxy'] || process.env['HTTP_PROXY']; } if (proxyVar) { proxyUrl = url.parse(proxyVar); @@ -16563,7 +30638,7 @@ function checkBypass(reqUrl) { if (!reqUrl.hostname) { return false; } - let noProxy = process.env["no_proxy"] || process.env["NO_PROXY"] || ''; + let noProxy = process.env['no_proxy'] || process.env['NO_PROXY'] || ''; if (!noProxy) { return false; } @@ -16584,7 +30659,10 @@ function checkBypass(reqUrl) { upperReqHosts.push(`${upperReqHosts[0]}:${reqPort}`); } // Compare request host against noproxy - for (let upperNoProxyItem of noProxy.split(',').map(x => x.trim().toUpperCase()).filter(x => x)) { + for (let upperNoProxyItem of noProxy + .split(',') + .map(x => x.trim().toUpperCase()) + .filter(x => x)) { if (upperReqHosts.some(x => x === upperNoProxyItem)) { return true; } @@ -17150,7 +31228,7 @@ exports.exec = exec; module.exports = authenticationRequestError; -const { RequestError } = __webpack_require__(463); +const { RequestError } = __webpack_require__(497); function authenticationRequestError(state, error, options) { if (!error.headers) throw error; diff --git a/package-lock.json b/package-lock.json index 1042614..5360225 100644 --- a/package-lock.json +++ b/package-lock.json @@ -15,19 +15,19 @@ "integrity": "sha512-nvFkxwiicvpzNiCBF4wFBDfnBvi7xp/as7LE1hBxBxKG2L29+gkIPBiLKMVORL+Hg3JNf07AKRfl0V5djoypjQ==" }, "@actions/github": { - "version": "2.1.0", - "resolved": "https://registry.npmjs.org/@actions/github/-/github-2.1.0.tgz", - "integrity": "sha512-G4ncMlh4pLLAvNgHUYUtpWQ1zPf/VYqmRH9oshxLabdaOOnp7i1hgSgzr2xne2YUaSND3uqemd3YYTIsm2f/KQ==", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/@actions/github/-/github-2.2.0.tgz", + "integrity": "sha512-9UAZqn8ywdR70n3GwVle4N8ALosQs4z50N7XMXrSTUVOmVpaBC5kE3TRTT7qQdi3OaQV24mjGuJZsHUmhD+ZXw==", "requires": { "@actions/http-client": "^1.0.3", "@octokit/graphql": "^4.3.1", - "@octokit/rest": "^16.15.0" + "@octokit/rest": "^16.43.1" } }, "@actions/http-client": { - "version": "1.0.3", - "resolved": "https://registry.npmjs.org/@actions/http-client/-/http-client-1.0.3.tgz", - "integrity": "sha512-wFwh1U4adB/Zsk4cc9kVqaBOHoknhp/pJQk+aWTocbAZWpIl4Zx/At83WFRLXvxB+5HVTWOACM6qjULMZfQSfw==", + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/@actions/http-client/-/http-client-1.0.8.tgz", + "integrity": "sha512-G4JjJ6f9Hb3Zvejj+ewLLKLf99ZC+9v+yCxoYf9vSyH+WkzPLB2LuUtRMGNkooMqdugGBFStIKXOuvH1W+EctA==", "requires": { "tunnel": "0.0.6" }, @@ -622,13 +622,23 @@ } }, "@octokit/endpoint": { - "version": "5.5.1", - "resolved": "https://registry.npmjs.org/@octokit/endpoint/-/endpoint-5.5.1.tgz", - "integrity": "sha512-nBFhRUb5YzVTCX/iAK1MgQ4uWo89Gu0TH00qQHoYRCsE12dWcG1OiLd7v2EIo2+tpUKPMOQ62QFy9hy9Vg2ULg==", + "version": "6.0.1", + "resolved": "https://registry.npmjs.org/@octokit/endpoint/-/endpoint-6.0.1.tgz", + "integrity": "sha512-pOPHaSz57SFT/m3R5P8MUu4wLPszokn5pXcB/pzavLTQf2jbU+6iayTvzaY6/BiotuRS0qyEUkx3QglT4U958A==", "requires": { - "@octokit/types": "^2.0.0", + "@octokit/types": "^2.11.1", "is-plain-object": "^3.0.0", - "universal-user-agent": "^4.0.0" + "universal-user-agent": "^5.0.0" + }, + "dependencies": { + "universal-user-agent": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-5.0.0.tgz", + "integrity": "sha512-B5TPtzZleXyPrUMKCpEHFmVhMN6EhmJYjG5PQna9s7mXeSqGTLap4OpqLl5FCEFUI3UBmllkETwKf/db66Y54Q==", + "requires": { + "os-name": "^3.1.0" + } + } } }, "@octokit/graphql": { @@ -641,25 +651,57 @@ "universal-user-agent": "^4.0.0" } }, - "@octokit/request": { - "version": "5.3.1", - "resolved": "https://registry.npmjs.org/@octokit/request/-/request-5.3.1.tgz", - "integrity": "sha512-5/X0AL1ZgoU32fAepTfEoggFinO3rxsMLtzhlUX+RctLrusn/CApJuGFCd0v7GMFhF+8UiCsTTfsu7Fh1HnEJg==", + "@octokit/plugin-paginate-rest": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/@octokit/plugin-paginate-rest/-/plugin-paginate-rest-1.1.2.tgz", + "integrity": "sha512-jbsSoi5Q1pj63sC16XIUboklNw+8tL9VOnJsWycWYR78TKss5PVpIPb1TUUcMQ+bBh7cY579cVAWmf5qG+dw+Q==", "requires": { - "@octokit/endpoint": "^5.5.0", - "@octokit/request-error": "^1.0.1", - "@octokit/types": "^2.0.0", + "@octokit/types": "^2.0.1" + } + }, + "@octokit/plugin-request-log": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/@octokit/plugin-request-log/-/plugin-request-log-1.0.0.tgz", + "integrity": "sha512-ywoxP68aOT3zHCLgWZgwUJatiENeHE7xJzYjfz8WI0goynp96wETBF+d95b8g/uL4QmS6owPVlaxiz3wyMAzcw==" + }, + "@octokit/plugin-rest-endpoint-methods": { + "version": "2.4.0", + "resolved": "https://registry.npmjs.org/@octokit/plugin-rest-endpoint-methods/-/plugin-rest-endpoint-methods-2.4.0.tgz", + "integrity": "sha512-EZi/AWhtkdfAYi01obpX0DF7U6b1VRr30QNQ5xSFPITMdLSfhcBqjamE3F+sKcxPbD7eZuMHu3Qkk2V+JGxBDQ==", + "requires": { + "@octokit/types": "^2.0.1", + "deprecation": "^2.3.1" + } + }, + "@octokit/request": { + "version": "5.4.2", + "resolved": "https://registry.npmjs.org/@octokit/request/-/request-5.4.2.tgz", + "integrity": "sha512-zKdnGuQ2TQ2vFk9VU8awFT4+EYf92Z/v3OlzRaSh4RIP0H6cvW1BFPXq4XYvNez+TPQjqN+0uSkCYnMFFhcFrw==", + "requires": { + "@octokit/endpoint": "^6.0.1", + "@octokit/request-error": "^2.0.0", + "@octokit/types": "^2.11.1", "deprecation": "^2.0.0", "is-plain-object": "^3.0.0", "node-fetch": "^2.3.0", "once": "^1.4.0", - "universal-user-agent": "^4.0.0" + "universal-user-agent": "^5.0.0" + }, + "dependencies": { + "universal-user-agent": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-5.0.0.tgz", + "integrity": "sha512-B5TPtzZleXyPrUMKCpEHFmVhMN6EhmJYjG5PQna9s7mXeSqGTLap4OpqLl5FCEFUI3UBmllkETwKf/db66Y54Q==", + "requires": { + "os-name": "^3.1.0" + } + } } }, "@octokit/request-error": { - "version": "1.2.0", - "resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-1.2.0.tgz", - "integrity": "sha512-DNBhROBYjjV/I9n7A8kVkmQNkqFAMem90dSxqvPq57e2hBr7mNTX98y3R2zDpqMQHVRpBDjsvsfIGgBzy+4PAg==", + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-2.0.0.tgz", + "integrity": "sha512-rtYicB4Absc60rUv74Rjpzek84UbVHGHJRu4fNVlZ1mCcyUPPuzFfG9Rn6sjHrd95DEsmjSt1Axlc699ZlbDkw==", "requires": { "@octokit/types": "^2.0.0", "deprecation": "^2.0.0", @@ -667,11 +709,14 @@ } }, "@octokit/rest": { - "version": "16.38.1", - "resolved": "https://registry.npmjs.org/@octokit/rest/-/rest-16.38.1.tgz", - "integrity": "sha512-zyNFx+/Bd1EXt7LQjfrc6H4wryBQ/oDuZeZhGMBSFr1eMPFDmpEweFQR3R25zjKwBQpDY7L5GQO6A3XSaOfV1w==", + "version": "16.43.1", + "resolved": "https://registry.npmjs.org/@octokit/rest/-/rest-16.43.1.tgz", + "integrity": "sha512-gfFKwRT/wFxq5qlNjnW2dh+qh74XgTQ2B179UX5K1HYCluioWj8Ndbgqw2PVqa1NnVJkGHp2ovMpVn/DImlmkw==", "requires": { "@octokit/auth-token": "^2.4.0", + "@octokit/plugin-paginate-rest": "^1.1.1", + "@octokit/plugin-request-log": "^1.0.0", + "@octokit/plugin-rest-endpoint-methods": "2.4.0", "@octokit/request": "^5.2.0", "@octokit/request-error": "^1.0.2", "atob-lite": "^2.0.0", @@ -684,12 +729,24 @@ "octokit-pagination-methods": "^1.1.0", "once": "^1.4.0", "universal-user-agent": "^4.0.0" + }, + "dependencies": { + "@octokit/request-error": { + "version": "1.2.1", + "resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-1.2.1.tgz", + "integrity": "sha512-+6yDyk1EES6WK+l3viRDElw96MvwfJxCt45GvmjDUKWjYIb3PJZQkq3i46TwGwoPD4h8NmTrENmtyA1FwbmhRA==", + "requires": { + "@octokit/types": "^2.0.0", + "deprecation": "^2.0.0", + "once": "^1.4.0" + } + } } }, "@octokit/types": { - "version": "2.1.1", - "resolved": "https://registry.npmjs.org/@octokit/types/-/types-2.1.1.tgz", - "integrity": "sha512-89LOYH+d/vsbDX785NOfLxTW88GjNd0lWRz1DVPVsZgg9Yett5O+3MOvwo7iHgvUwbFz0mf/yPIjBkUbs4kxoQ==", + "version": "2.14.0", + "resolved": "https://registry.npmjs.org/@octokit/types/-/types-2.14.0.tgz", + "integrity": "sha512-1w2wxpN45rEXPDFeB7rGain7wcJ/aTRg8bdILITVnS0O7a4zEGELa3JmIe+jeLdekQjvZRbVfNPqS+mi5fKCKQ==", "requires": { "@types/node": ">= 8" } @@ -6720,9 +6777,9 @@ } }, "universal-user-agent": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-4.0.0.tgz", - "integrity": "sha512-eM8knLpev67iBDizr/YtqkJsF3GK8gzDc6st/WKzrTuPtcsOKW/0IdL4cnMBsU69pOx0otavLWBDGTwg+dB0aA==", + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/universal-user-agent/-/universal-user-agent-4.0.1.tgz", + "integrity": "sha512-LnST3ebHwVL2aNe4mejI9IQh2HfZ1RLo8Io2HugSif8ekzD1TlWpHpColOB/eh8JHMLkGH3Akqf040I+4ylNxg==", "requires": { "os-name": "^3.1.0" } @@ -6901,9 +6958,9 @@ "dev": true }, "windows-release": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/windows-release/-/windows-release-3.2.0.tgz", - "integrity": "sha512-QTlz2hKLrdqukrsapKsINzqMgOUpQW268eJ0OaOpJN32h272waxR9fkB9VoWRtK7uKHG5EHJcTXQBD8XZVJkFA==", + "version": "3.3.0", + "resolved": "https://registry.npmjs.org/windows-release/-/windows-release-3.3.0.tgz", + "integrity": "sha512-2HetyTg1Y+R+rUgrKeUEhAG/ZuOmTrI1NBb3ZyAGQMYmOJjBBPe4MTodghRkmLJZHwkuPi02anbeGP+Zf401LQ==", "requires": { "execa": "^1.0.0" } diff --git a/package.json b/package.json index 226b979..f413218 100644 --- a/package.json +++ b/package.json @@ -4,14 +4,11 @@ "description": "checkout action", "main": "lib/main.js", "scripts": { - "build": "tsc", - "format": "prettier --write **/*.ts", - "format-check": "prettier --check **/*.ts", + "build": "tsc && ncc build && node lib/misc/generate-docs.js", + "format": "prettier --write '**/*.ts'", + "format-check": "prettier --check '**/*.ts'", "lint": "eslint src/**/*.ts", - "pack": "ncc build", - "gendocs": "node lib/misc/generate-docs.js", - "test": "jest", - "all": "npm run build && npm run format && npm run lint && npm run pack && npm run gendocs && npm test" + "test": "jest" }, "repository": { "type": "git", @@ -31,7 +28,7 @@ "dependencies": { "@actions/core": "^1.1.3", "@actions/exec": "^1.0.1", - "@actions/github": "^2.0.2", + "@actions/github": "^2.2.0", "@actions/io": "^1.0.1", "@actions/tool-cache": "^1.1.2", "uuid": "^3.3.3" diff --git a/src/git-auth-helper.ts b/src/git-auth-helper.ts new file mode 100644 index 0000000..fc1404c --- /dev/null +++ b/src/git-auth-helper.ts @@ -0,0 +1,350 @@ +import * as assert from 'assert' +import * as core from '@actions/core' +import * as exec from '@actions/exec' +import * as fs from 'fs' +import * as io from '@actions/io' +import * as os from 'os' +import * as path from 'path' +import * as regexpHelper from './regexp-helper' +import * as stateHelper from './state-helper' +import * as urlHelper from './url-helper' +import {default as uuid} from 'uuid/v4' +import {IGitCommandManager} from './git-command-manager' +import {IGitSourceSettings} from './git-source-settings' + +const IS_WINDOWS = process.platform === 'win32' +const SSH_COMMAND_KEY = 'core.sshCommand' + +export interface IGitAuthHelper { + configureAuth(): Promise + configureGlobalAuth(): Promise + configureSubmoduleAuth(): Promise + removeAuth(): Promise + removeGlobalAuth(): Promise +} + +export function createAuthHelper( + git: IGitCommandManager, + settings?: IGitSourceSettings +): IGitAuthHelper { + return new GitAuthHelper(git, settings) +} + +class GitAuthHelper { + private readonly git: IGitCommandManager + private readonly settings: IGitSourceSettings + private readonly tokenConfigKey: string + private readonly tokenConfigValue: string + private readonly tokenPlaceholderConfigValue: string + private readonly insteadOfKey: string + private readonly insteadOfValue: string + private sshCommand = '' + private sshKeyPath = '' + private sshKnownHostsPath = '' + private temporaryHomePath = '' + + constructor( + gitCommandManager: IGitCommandManager, + gitSourceSettings?: IGitSourceSettings + ) { + this.git = gitCommandManager + this.settings = gitSourceSettings || (({} as unknown) as IGitSourceSettings) + + // Token auth header + const serverUrl = urlHelper.getServerUrl() + this.tokenConfigKey = `http.${serverUrl.origin}/.extraheader` // "origin" is SCHEME://HOSTNAME[:PORT] + const basicCredential = Buffer.from( + `x-access-token:${this.settings.authToken}`, + 'utf8' + ).toString('base64') + core.setSecret(basicCredential) + this.tokenPlaceholderConfigValue = `AUTHORIZATION: basic ***` + this.tokenConfigValue = `AUTHORIZATION: basic ${basicCredential}` + + // Instead of SSH URL + this.insteadOfKey = `url.${serverUrl.origin}/.insteadOf` // "origin" is SCHEME://HOSTNAME[:PORT] + this.insteadOfValue = `git@${serverUrl.hostname}:` + } + + async configureAuth(): Promise { + // Remove possible previous values + await this.removeAuth() + + // Configure new values + await this.configureSsh() + await this.configureToken() + } + + async configureGlobalAuth(): Promise { + // Create a temp home directory + const runnerTemp = process.env['RUNNER_TEMP'] || '' + assert.ok(runnerTemp, 'RUNNER_TEMP is not defined') + const uniqueId = uuid() + this.temporaryHomePath = path.join(runnerTemp, uniqueId) + await fs.promises.mkdir(this.temporaryHomePath, {recursive: true}) + + // Copy the global git config + const gitConfigPath = path.join( + process.env['HOME'] || os.homedir(), + '.gitconfig' + ) + const newGitConfigPath = path.join(this.temporaryHomePath, '.gitconfig') + let configExists = false + try { + await fs.promises.stat(gitConfigPath) + configExists = true + } catch (err) { + if (err.code !== 'ENOENT') { + throw err + } + } + if (configExists) { + core.info(`Copying '${gitConfigPath}' to '${newGitConfigPath}'`) + await io.cp(gitConfigPath, newGitConfigPath) + } else { + await fs.promises.writeFile(newGitConfigPath, '') + } + + try { + // Override HOME + core.info( + `Temporarily overriding HOME='${this.temporaryHomePath}' before making global git config changes` + ) + this.git.setEnvironmentVariable('HOME', this.temporaryHomePath) + + // Configure the token + await this.configureToken(newGitConfigPath, true) + + // Configure HTTPS instead of SSH + await this.git.tryConfigUnset(this.insteadOfKey, true) + if (!this.settings.sshKey) { + await this.git.config(this.insteadOfKey, this.insteadOfValue, true) + } + } catch (err) { + // Unset in case somehow written to the real global config + core.info( + 'Encountered an error when attempting to configure token. Attempting unconfigure.' + ) + await this.git.tryConfigUnset(this.tokenConfigKey, true) + throw err + } + } + + async configureSubmoduleAuth(): Promise { + // Remove possible previous HTTPS instead of SSH + await this.removeGitConfig(this.insteadOfKey, true) + + if (this.settings.persistCredentials) { + // Configure a placeholder value. This approach avoids the credential being captured + // by process creation audit events, which are commonly logged. For more information, + // refer to https://docs.microsoft.com/en-us/windows-server/identity/ad-ds/manage/component-updates/command-line-process-auditing + const output = await this.git.submoduleForeach( + `git config --local '${this.tokenConfigKey}' '${this.tokenPlaceholderConfigValue}' && git config --local --show-origin --name-only --get-regexp remote.origin.url`, + this.settings.nestedSubmodules + ) + + // Replace the placeholder + const configPaths: string[] = + output.match(/(?<=(^|\n)file:)[^\t]+(?=\tremote\.origin\.url)/g) || [] + for (const configPath of configPaths) { + core.debug(`Replacing token placeholder in '${configPath}'`) + this.replaceTokenPlaceholder(configPath) + } + + if (this.settings.sshKey) { + // Configure core.sshCommand + await this.git.submoduleForeach( + `git config --local '${SSH_COMMAND_KEY}' '${this.sshCommand}'`, + this.settings.nestedSubmodules + ) + } else { + // Configure HTTPS instead of SSH + await this.git.submoduleForeach( + `git config --local '${this.insteadOfKey}' '${this.insteadOfValue}'`, + this.settings.nestedSubmodules + ) + } + } + } + + async removeAuth(): Promise { + await this.removeSsh() + await this.removeToken() + } + + async removeGlobalAuth(): Promise { + core.debug(`Unsetting HOME override`) + this.git.removeEnvironmentVariable('HOME') + await io.rmRF(this.temporaryHomePath) + } + + private async configureSsh(): Promise { + if (!this.settings.sshKey) { + return + } + + // Write key + const runnerTemp = process.env['RUNNER_TEMP'] || '' + assert.ok(runnerTemp, 'RUNNER_TEMP is not defined') + const uniqueId = uuid() + this.sshKeyPath = path.join(runnerTemp, uniqueId) + stateHelper.setSshKeyPath(this.sshKeyPath) + await fs.promises.mkdir(runnerTemp, {recursive: true}) + await fs.promises.writeFile( + this.sshKeyPath, + this.settings.sshKey.trim() + '\n', + {mode: 0o600} + ) + + // Remove inherited permissions on Windows + if (IS_WINDOWS) { + const icacls = await io.which('icacls.exe') + await exec.exec( + `"${icacls}" "${this.sshKeyPath}" /grant:r "${process.env['USERDOMAIN']}\\${process.env['USERNAME']}:F"` + ) + await exec.exec(`"${icacls}" "${this.sshKeyPath}" /inheritance:r`) + } + + // Write known hosts + const userKnownHostsPath = path.join(os.homedir(), '.ssh', 'known_hosts') + let userKnownHosts = '' + try { + userKnownHosts = ( + await fs.promises.readFile(userKnownHostsPath) + ).toString() + } catch (err) { + if (err.code !== 'ENOENT') { + throw err + } + } + let knownHosts = '' + if (userKnownHosts) { + knownHosts += `# Begin from ${userKnownHostsPath}\n${userKnownHosts}\n# End from ${userKnownHostsPath}\n` + } + if (this.settings.sshKnownHosts) { + knownHosts += `# Begin from input known hosts\n${this.settings.sshKnownHosts}\n# end from input known hosts\n` + } + knownHosts += `# Begin implicitly added github.com\ngithub.com ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEAq2A7hRGmdnm9tUDbO9IDSwBK6TbQa+PXYPCPy6rbTrTtw7PHkccKrpp0yVhp5HdEIcKr6pLlVDBfOLX9QUsyCOV0wzfjIJNlGEYsdlLJizHhbn2mUjvSAHQqZETYP81eFzLQNnPHt4EVVUh7VfDESU84KezmD5QlWpXLmvU31/yMf+Se8xhHTvKSCZIFImWwoG6mbUoWf9nzpIoaSjB+weqqUUmpaaasXVal72J+UX2B+2RPW3RcT0eOzQgqlJL3RKrTJvdsjE3JEAvGq3lGHSZXy28G3skua2SmVi/w4yCE6gbODqnTWlg7+wC604ydGXA8VJiS5ap43JXiUFFAaQ==\n# End implicitly added github.com\n` + this.sshKnownHostsPath = path.join(runnerTemp, `${uniqueId}_known_hosts`) + stateHelper.setSshKnownHostsPath(this.sshKnownHostsPath) + await fs.promises.writeFile(this.sshKnownHostsPath, knownHosts) + + // Configure GIT_SSH_COMMAND + const sshPath = await io.which('ssh', true) + this.sshCommand = `"${sshPath}" -i "$RUNNER_TEMP/${path.basename( + this.sshKeyPath + )}"` + if (this.settings.sshStrict) { + this.sshCommand += ' -o StrictHostKeyChecking=yes -o CheckHostIP=no' + } + this.sshCommand += ` -o "UserKnownHostsFile=$RUNNER_TEMP/${path.basename( + this.sshKnownHostsPath + )}"` + core.info(`Temporarily overriding GIT_SSH_COMMAND=${this.sshCommand}`) + this.git.setEnvironmentVariable('GIT_SSH_COMMAND', this.sshCommand) + + // Configure core.sshCommand + if (this.settings.persistCredentials) { + await this.git.config(SSH_COMMAND_KEY, this.sshCommand) + } + } + + private async configureToken( + configPath?: string, + globalConfig?: boolean + ): Promise { + // Validate args + assert.ok( + (configPath && globalConfig) || (!configPath && !globalConfig), + 'Unexpected configureToken parameter combinations' + ) + + // Default config path + if (!configPath && !globalConfig) { + configPath = path.join(this.git.getWorkingDirectory(), '.git', 'config') + } + + // Configure a placeholder value. This approach avoids the credential being captured + // by process creation audit events, which are commonly logged. For more information, + // refer to https://docs.microsoft.com/en-us/windows-server/identity/ad-ds/manage/component-updates/command-line-process-auditing + await this.git.config( + this.tokenConfigKey, + this.tokenPlaceholderConfigValue, + globalConfig + ) + + // Replace the placeholder + await this.replaceTokenPlaceholder(configPath || '') + } + + private async replaceTokenPlaceholder(configPath: string): Promise { + assert.ok(configPath, 'configPath is not defined') + let content = (await fs.promises.readFile(configPath)).toString() + const placeholderIndex = content.indexOf(this.tokenPlaceholderConfigValue) + if ( + placeholderIndex < 0 || + placeholderIndex != content.lastIndexOf(this.tokenPlaceholderConfigValue) + ) { + throw new Error(`Unable to replace auth placeholder in ${configPath}`) + } + assert.ok(this.tokenConfigValue, 'tokenConfigValue is not defined') + content = content.replace( + this.tokenPlaceholderConfigValue, + this.tokenConfigValue + ) + await fs.promises.writeFile(configPath, content) + } + + private async removeSsh(): Promise { + // SSH key + const keyPath = this.sshKeyPath || stateHelper.SshKeyPath + if (keyPath) { + try { + await io.rmRF(keyPath) + } catch (err) { + core.debug(err.message) + core.warning(`Failed to remove SSH key '${keyPath}'`) + } + } + + // SSH known hosts + const knownHostsPath = + this.sshKnownHostsPath || stateHelper.SshKnownHostsPath + if (knownHostsPath) { + try { + await io.rmRF(knownHostsPath) + } catch { + // Intentionally empty + } + } + + // SSH command + await this.removeGitConfig(SSH_COMMAND_KEY) + } + + private async removeToken(): Promise { + // HTTP extra header + await this.removeGitConfig(this.tokenConfigKey) + } + + private async removeGitConfig( + configKey: string, + submoduleOnly: boolean = false + ): Promise { + if (!submoduleOnly) { + if ( + (await this.git.configExists(configKey)) && + !(await this.git.tryConfigUnset(configKey)) + ) { + // Load the config contents + core.warning(`Failed to remove '${configKey}' from the git config`) + } + } + + const pattern = regexpHelper.escape(configKey) + await this.git.submoduleForeach( + `git config --local --name-only --get-regexp '${pattern}' && git config --local --unset-all '${configKey}' || :`, + true + ) + } +} diff --git a/src/git-command-manager.ts b/src/git-command-manager.ts index 74489c2..8bf3aa1 100644 --- a/src/git-command-manager.ts +++ b/src/git-command-manager.ts @@ -3,6 +3,8 @@ import * as exec from '@actions/exec' import * as fshelper from './fs-helper' import * as io from '@actions/io' import * as path from 'path' +import * as refHelper from './ref-helper' +import * as regexpHelper from './regexp-helper' import * as retryHelper from './retry-helper' import {GitVersion} from './git-version' @@ -16,25 +18,37 @@ export interface IGitCommandManager { branchList(remote: boolean): Promise checkout(ref: string, startPoint: string): Promise checkoutDetach(): Promise - config(configKey: string, configValue: string): Promise - configExists(configKey: string): Promise - fetch(fetchDepth: number, refSpec: string[]): Promise + config( + configKey: string, + configValue: string, + globalConfig?: boolean + ): Promise + configExists(configKey: string, globalConfig?: boolean): Promise + fetch(refSpec: string[], fetchDepth?: number): Promise + getDefaultBranch(repositoryUrl: string): Promise getWorkingDirectory(): string init(): Promise isDetached(): Promise lfsFetch(ref: string): Promise lfsInstall(): Promise - log1(): Promise + log1(): Promise remoteAdd(remoteName: string, remoteUrl: string): Promise + removeEnvironmentVariable(name: string): void + revParse(ref: string): Promise + setEnvironmentVariable(name: string, value: string): void + shaExists(sha: string): Promise + submoduleForeach(command: string, recursive: boolean): Promise + submoduleSync(recursive: boolean): Promise + submoduleUpdate(fetchDepth: number, recursive: boolean): Promise tagExists(pattern: string): Promise tryClean(): Promise - tryConfigUnset(configKey: string): Promise + tryConfigUnset(configKey: string, globalConfig?: boolean): Promise tryDisableAutomaticGarbageCollection(): Promise tryGetFetchUrl(): Promise tryReset(): Promise } -export async function CreateCommandManager( +export async function createCommandManager( workingDirectory: string, lfs: boolean ): Promise { @@ -123,32 +137,45 @@ class GitCommandManager { await this.execGit(args) } - async config(configKey: string, configValue: string): Promise { - await this.execGit(['config', '--local', configKey, configValue]) + async config( + configKey: string, + configValue: string, + globalConfig?: boolean + ): Promise { + await this.execGit([ + 'config', + globalConfig ? '--global' : '--local', + configKey, + configValue + ]) } - async configExists(configKey: string): Promise { - const pattern = configKey.replace(/[^a-zA-Z0-9_]/g, x => { - return `\\${x}` - }) + async configExists( + configKey: string, + globalConfig?: boolean + ): Promise { + const pattern = regexpHelper.escape(configKey) const output = await this.execGit( - ['config', '--local', '--name-only', '--get-regexp', pattern], + [ + 'config', + globalConfig ? '--global' : '--local', + '--name-only', + '--get-regexp', + pattern + ], true ) return output.exitCode === 0 } - async fetch(fetchDepth: number, refSpec: string[]): Promise { - const args = [ - '-c', - 'protocol.version=2', - 'fetch', - '--no-tags', - '--prune', - '--progress', - '--no-recurse-submodules' - ] - if (fetchDepth > 0) { + async fetch(refSpec: string[], fetchDepth?: number): Promise { + const args = ['-c', 'protocol.version=2', 'fetch'] + if (!refSpec.some(x => x === refHelper.tagsRefSpec)) { + args.push('--no-tags') + } + + args.push('--prune', '--progress', '--no-recurse-submodules') + if (fetchDepth && fetchDepth > 0) { args.push(`--depth=${fetchDepth}`) } else if ( fshelper.fileExistsSync( @@ -169,6 +196,34 @@ class GitCommandManager { }) } + async getDefaultBranch(repositoryUrl: string): Promise { + let output: GitOutput | undefined + await retryHelper.execute(async () => { + output = await this.execGit([ + 'ls-remote', + '--quiet', + '--exit-code', + '--symref', + repositoryUrl, + 'HEAD' + ]) + }) + + if (output) { + // Satisfy compiler, will always be set + for (let line of output.stdout.trim().split('\n')) { + line = line.trim() + if (line.startsWith('ref:') || line.endsWith('HEAD')) { + return line + .substr('ref:'.length, line.length - 'ref:'.length - 'HEAD'.length) + .trim() + } + } + } + + throw new Error('Unexpected output when retrieving default branch') + } + getWorkingDirectory(): string { return this.workingDirectory } @@ -199,14 +254,74 @@ class GitCommandManager { await this.execGit(['lfs', 'install', '--local']) } - async log1(): Promise { - await this.execGit(['log', '-1']) + async log1(): Promise { + const output = await this.execGit(['log', '-1']) + return output.stdout } async remoteAdd(remoteName: string, remoteUrl: string): Promise { await this.execGit(['remote', 'add', remoteName, remoteUrl]) } + removeEnvironmentVariable(name: string): void { + delete this.gitEnv[name] + } + + /** + * Resolves a ref to a SHA. For a branch or lightweight tag, the commit SHA is returned. + * For an annotated tag, the tag SHA is returned. + * @param {string} ref For example: 'refs/heads/master' or '/refs/tags/v1' + * @returns {Promise} + */ + async revParse(ref: string): Promise { + const output = await this.execGit(['rev-parse', ref]) + return output.stdout.trim() + } + + setEnvironmentVariable(name: string, value: string): void { + this.gitEnv[name] = value + } + + async shaExists(sha: string): Promise { + const args = ['rev-parse', '--verify', '--quiet', `${sha}^{object}`] + const output = await this.execGit(args, true) + return output.exitCode === 0 + } + + async submoduleForeach(command: string, recursive: boolean): Promise { + const args = ['submodule', 'foreach'] + if (recursive) { + args.push('--recursive') + } + args.push(command) + + const output = await this.execGit(args) + return output.stdout + } + + async submoduleSync(recursive: boolean): Promise { + const args = ['submodule', 'sync'] + if (recursive) { + args.push('--recursive') + } + + await this.execGit(args) + } + + async submoduleUpdate(fetchDepth: number, recursive: boolean): Promise { + const args = ['-c', 'protocol.version=2'] + args.push('submodule', 'update', '--init', '--force') + if (fetchDepth > 0) { + args.push(`--depth=${fetchDepth}`) + } + + if (recursive) { + args.push('--recursive') + } + + await this.execGit(args) + } + async tagExists(pattern: string): Promise { const output = await this.execGit(['tag', '--list', pattern]) return !!output.stdout.trim() @@ -217,9 +332,17 @@ class GitCommandManager { return output.exitCode === 0 } - async tryConfigUnset(configKey: string): Promise { + async tryConfigUnset( + configKey: string, + globalConfig?: boolean + ): Promise { const output = await this.execGit( - ['config', '--local', '--unset-all', configKey], + [ + 'config', + globalConfig ? '--global' : '--local', + '--unset-all', + configKey + ], true ) return output.exitCode === 0 diff --git a/src/git-directory-helper.ts b/src/git-directory-helper.ts new file mode 100644 index 0000000..e792190 --- /dev/null +++ b/src/git-directory-helper.ts @@ -0,0 +1,117 @@ +import * as assert from 'assert' +import * as core from '@actions/core' +import * as fs from 'fs' +import * as fsHelper from './fs-helper' +import * as io from '@actions/io' +import * as path from 'path' +import {IGitCommandManager} from './git-command-manager' + +export async function prepareExistingDirectory( + git: IGitCommandManager | undefined, + repositoryPath: string, + repositoryUrl: string, + clean: boolean, + ref: string +): Promise { + assert.ok(repositoryPath, 'Expected repositoryPath to be defined') + assert.ok(repositoryUrl, 'Expected repositoryUrl to be defined') + + // Indicates whether to delete the directory contents + let remove = false + + // Check whether using git or REST API + if (!git) { + remove = true + } + // Fetch URL does not match + else if ( + !fsHelper.directoryExistsSync(path.join(repositoryPath, '.git')) || + repositoryUrl !== (await git.tryGetFetchUrl()) + ) { + remove = true + } else { + // Delete any index.lock and shallow.lock left by a previously canceled run or crashed git process + const lockPaths = [ + path.join(repositoryPath, '.git', 'index.lock'), + path.join(repositoryPath, '.git', 'shallow.lock') + ] + for (const lockPath of lockPaths) { + try { + await io.rmRF(lockPath) + } catch (error) { + core.debug(`Unable to delete '${lockPath}'. ${error.message}`) + } + } + + try { + core.startGroup('Removing previously created refs, to avoid conflicts') + // Checkout detached HEAD + if (!(await git.isDetached())) { + await git.checkoutDetach() + } + + // Remove all refs/heads/* + let branches = await git.branchList(false) + for (const branch of branches) { + await git.branchDelete(false, branch) + } + + // Remove any conflicting refs/remotes/origin/* + // Example 1: Consider ref is refs/heads/foo and previously fetched refs/remotes/origin/foo/bar + // Example 2: Consider ref is refs/heads/foo/bar and previously fetched refs/remotes/origin/foo + if (ref) { + ref = ref.startsWith('refs/') ? ref : `refs/heads/${ref}` + if (ref.startsWith('refs/heads/')) { + const upperName1 = ref.toUpperCase().substr('REFS/HEADS/'.length) + const upperName1Slash = `${upperName1}/` + branches = await git.branchList(true) + for (const branch of branches) { + const upperName2 = branch.substr('origin/'.length).toUpperCase() + const upperName2Slash = `${upperName2}/` + if ( + upperName1.startsWith(upperName2Slash) || + upperName2.startsWith(upperName1Slash) + ) { + await git.branchDelete(true, branch) + } + } + } + } + core.endGroup() + + // Clean + if (clean) { + core.startGroup('Cleaning the repository') + if (!(await git.tryClean())) { + core.debug( + `The clean command failed. This might be caused by: 1) path too long, 2) permission issue, or 3) file in use. For futher investigation, manually run 'git clean -ffdx' on the directory '${repositoryPath}'.` + ) + remove = true + } else if (!(await git.tryReset())) { + remove = true + } + core.endGroup() + + if (remove) { + core.warning( + `Unable to clean or reset the repository. The repository will be recreated instead.` + ) + } + } + } catch (error) { + core.warning( + `Unable to prepare the existing repository. The repository will be recreated instead.` + ) + remove = true + } + } + + if (remove) { + // Delete the contents of the directory. Don't delete the directory itself + // since it might be the current working directory. + core.info(`Deleting the contents of '${repositoryPath}'`) + for (const file of await fs.promises.readdir(repositoryPath)) { + await io.rmRF(path.join(repositoryPath, file)) + } + } +} diff --git a/src/git-source-provider.ts b/src/git-source-provider.ts index e0dd58e..366ff33 100644 --- a/src/git-source-provider.ts +++ b/src/git-source-provider.ts @@ -1,38 +1,23 @@ import * as core from '@actions/core' -import * as fs from 'fs' import * as fsHelper from './fs-helper' +import * as gitAuthHelper from './git-auth-helper' import * as gitCommandManager from './git-command-manager' +import * as gitDirectoryHelper from './git-directory-helper' import * as githubApiHelper from './github-api-helper' import * as io from '@actions/io' import * as path from 'path' import * as refHelper from './ref-helper' import * as stateHelper from './state-helper' +import * as urlHelper from './url-helper' import {IGitCommandManager} from './git-command-manager' +import {IGitSourceSettings} from './git-source-settings' -const serverUrl = 'https://github.com/' -const authConfigKey = `http.${serverUrl}.extraheader` - -export interface ISourceSettings { - repositoryPath: string - repositoryOwner: string - repositoryName: string - ref: string - commit: string - clean: boolean - fetchDepth: number - lfs: boolean - authToken: string - persistCredentials: boolean -} - -export async function getSource(settings: ISourceSettings): Promise { +export async function getSource(settings: IGitSourceSettings): Promise { // Repository URL core.info( `Syncing repository: ${settings.repositoryOwner}/${settings.repositoryName}` ) - const repositoryUrl = `https://github.com/${encodeURIComponent( - settings.repositoryOwner - )}/${encodeURIComponent(settings.repositoryName)}` + const repositoryUrl = urlHelper.getFetchUrl(settings) // Remove conflicting file path if (fsHelper.fileExistsSync(settings.repositoryPath)) { @@ -47,15 +32,18 @@ export async function getSource(settings: ISourceSettings): Promise { } // Git command manager + core.startGroup('Getting Git version info') const git = await getGitCommandManager(settings) + core.endGroup() // Prepare existing directory, otherwise recreate if (isExisting) { - await prepareExistingDirectory( + await gitDirectoryHelper.prepareExistingDirectory( git, settings.repositoryPath, repositoryUrl, - settings.clean + settings.clean, + settings.ref ) } @@ -65,6 +53,16 @@ export async function getSource(settings: ISourceSettings): Promise { core.info( `To create a local Git repository instead, add Git ${gitCommandManager.MinimumGitVersion} or higher to the PATH` ) + if (settings.submodules) { + throw new Error( + `Input 'submodules' not supported when falling back to download using the GitHub REST API. To create a local Git repository instead, add Git ${gitCommandManager.MinimumGitVersion} or higher to the PATH.` + ) + } else if (settings.sshKey) { + throw new Error( + `Input 'ssh-key' not supported when falling back to download using the GitHub REST API. To create a local Git repository instead, add Git ${gitCommandManager.MinimumGitVersion} or higher to the PATH.` + ) + } + await githubApiHelper.downloadRepository( settings.authToken, settings.repositoryOwner, @@ -73,65 +71,155 @@ export async function getSource(settings: ISourceSettings): Promise { settings.commit, settings.repositoryPath ) - } else { - // Save state for POST action - stateHelper.setRepositoryPath(settings.repositoryPath) + return + } - // Initialize the repository - if ( - !fsHelper.directoryExistsSync(path.join(settings.repositoryPath, '.git')) - ) { - await git.init() - await git.remoteAdd('origin', repositoryUrl) - } + // Save state for POST action + stateHelper.setRepositoryPath(settings.repositoryPath) - // Disable automatic garbage collection - if (!(await git.tryDisableAutomaticGarbageCollection())) { - core.warning( - `Unable to turn off git automatic garbage collection. The git fetch operation may trigger garbage collection and cause a delay.` - ) - } + // Initialize the repository + if ( + !fsHelper.directoryExistsSync(path.join(settings.repositoryPath, '.git')) + ) { + core.startGroup('Initializing the repository') + await git.init() + await git.remoteAdd('origin', repositoryUrl) + core.endGroup() + } - // Remove possible previous extraheader - await removeGitConfig(git, authConfigKey) + // Disable automatic garbage collection + core.startGroup('Disabling automatic garbage collection') + if (!(await git.tryDisableAutomaticGarbageCollection())) { + core.warning( + `Unable to turn off git automatic garbage collection. The git fetch operation may trigger garbage collection and cause a delay.` + ) + } + core.endGroup() - try { - // Config extraheader - await configureAuthToken(git, settings.authToken) + const authHelper = gitAuthHelper.createAuthHelper(git, settings) + try { + // Configure auth + core.startGroup('Setting up auth') + await authHelper.configureAuth() + core.endGroup() - // LFS install - if (settings.lfs) { - await git.lfsInstall() + // Determine the default branch + if (!settings.ref && !settings.commit) { + core.startGroup('Determining the default branch') + if (settings.sshKey) { + settings.ref = await git.getDefaultBranch(repositoryUrl) + } else { + settings.ref = await githubApiHelper.getDefaultBranch( + settings.authToken, + settings.repositoryOwner, + settings.repositoryName + ) } + core.endGroup() + } - // Fetch - const refSpec = refHelper.getRefSpec(settings.ref, settings.commit) - await git.fetch(settings.fetchDepth, refSpec) + // LFS install + if (settings.lfs) { + await git.lfsInstall() + } - // Checkout info - const checkoutInfo = await refHelper.getCheckoutInfo( - git, + // Fetch + core.startGroup('Fetching the repository') + if (settings.fetchDepth <= 0) { + // Fetch all branches and tags + let refSpec = refHelper.getRefSpecForAllHistory( settings.ref, settings.commit ) + await git.fetch(refSpec) - // LFS fetch - // Explicit lfs-fetch to avoid slow checkout (fetches one lfs object at a time). - // Explicit lfs fetch will fetch lfs objects in parallel. - if (settings.lfs) { - await git.lfsFetch(checkoutInfo.startPoint || checkoutInfo.ref) + // When all history is fetched, the ref we're interested in may have moved to a different + // commit (push or force push). If so, fetch again with a targeted refspec. + if (!(await refHelper.testRef(git, settings.ref, settings.commit))) { + refSpec = refHelper.getRefSpec(settings.ref, settings.commit) + await git.fetch(refSpec) } + } else { + const refSpec = refHelper.getRefSpec(settings.ref, settings.commit) + await git.fetch(refSpec, settings.fetchDepth) + } + core.endGroup() - // Checkout - await git.checkout(checkoutInfo.ref, checkoutInfo.startPoint) + // Checkout info + core.startGroup('Determining the checkout info') + const checkoutInfo = await refHelper.getCheckoutInfo( + git, + settings.ref, + settings.commit + ) + core.endGroup() - // Dump some info about the checked out commit - await git.log1() - } finally { - if (!settings.persistCredentials) { - await removeGitConfig(git, authConfigKey) + // LFS fetch + // Explicit lfs-fetch to avoid slow checkout (fetches one lfs object at a time). + // Explicit lfs fetch will fetch lfs objects in parallel. + if (settings.lfs) { + core.startGroup('Fetching LFS objects') + await git.lfsFetch(checkoutInfo.startPoint || checkoutInfo.ref) + core.endGroup() + } + + // Checkout + core.startGroup('Checking out the ref') + await git.checkout(checkoutInfo.ref, checkoutInfo.startPoint) + core.endGroup() + + // Submodules + if (settings.submodules) { + try { + // Temporarily override global config + core.startGroup('Setting up auth for fetching submodules') + await authHelper.configureGlobalAuth() + core.endGroup() + + // Checkout submodules + core.startGroup('Fetching submodules') + await git.submoduleSync(settings.nestedSubmodules) + await git.submoduleUpdate( + settings.fetchDepth, + settings.nestedSubmodules + ) + await git.submoduleForeach( + 'git config --local gc.auto 0', + settings.nestedSubmodules + ) + core.endGroup() + + // Persist credentials + if (settings.persistCredentials) { + core.startGroup('Persisting credentials for submodules') + await authHelper.configureSubmoduleAuth() + core.endGroup() + } + } finally { + // Remove temporary global config override + await authHelper.removeGlobalAuth() } } + + // Dump some info about the checked out commit + const commitInfo = await git.log1() + + // Check for incorrect pull request merge commit + await refHelper.checkCommitInfo( + settings.authToken, + commitInfo, + settings.repositoryOwner, + settings.repositoryName, + settings.ref, + settings.commit + ) + } finally { + // Remove auth + if (!settings.persistCredentials) { + core.startGroup('Removing auth') + await authHelper.removeAuth() + core.endGroup() + } } } @@ -146,22 +234,22 @@ export async function cleanup(repositoryPath: string): Promise { let git: IGitCommandManager try { - git = await gitCommandManager.CreateCommandManager(repositoryPath, false) + git = await gitCommandManager.createCommandManager(repositoryPath, false) } catch { return } - // Remove extraheader - await removeGitConfig(git, authConfigKey) + // Remove auth + const authHelper = gitAuthHelper.createAuthHelper(git) + await authHelper.removeAuth() } async function getGitCommandManager( - settings: ISourceSettings -): Promise { + settings: IGitSourceSettings +): Promise { core.info(`Working directory is '${settings.repositoryPath}'`) - let git = (null as unknown) as IGitCommandManager try { - return await gitCommandManager.CreateCommandManager( + return await gitCommandManager.createCommandManager( settings.repositoryPath, settings.lfs ) @@ -172,138 +260,6 @@ async function getGitCommandManager( } // Otherwise fallback to REST API - return (null as unknown) as IGitCommandManager - } -} - -async function prepareExistingDirectory( - git: IGitCommandManager, - repositoryPath: string, - repositoryUrl: string, - clean: boolean -): Promise { - let remove = false - - // Check whether using git or REST API - if (!git) { - remove = true - } - // Fetch URL does not match - else if ( - !fsHelper.directoryExistsSync(path.join(repositoryPath, '.git')) || - repositoryUrl !== (await git.tryGetFetchUrl()) - ) { - remove = true - } else { - // Delete any index.lock and shallow.lock left by a previously canceled run or crashed git process - const lockPaths = [ - path.join(repositoryPath, '.git', 'index.lock'), - path.join(repositoryPath, '.git', 'shallow.lock') - ] - for (const lockPath of lockPaths) { - try { - await io.rmRF(lockPath) - } catch (error) { - core.debug(`Unable to delete '${lockPath}'. ${error.message}`) - } - } - - try { - // Checkout detached HEAD - if (!(await git.isDetached())) { - await git.checkoutDetach() - } - - // Remove all refs/heads/* - let branches = await git.branchList(false) - for (const branch of branches) { - await git.branchDelete(false, branch) - } - - // Remove all refs/remotes/origin/* to avoid conflicts - branches = await git.branchList(true) - for (const branch of branches) { - await git.branchDelete(true, branch) - } - - // Clean - if (clean) { - if (!(await git.tryClean())) { - core.debug( - `The clean command failed. This might be caused by: 1) path too long, 2) permission issue, or 3) file in use. For futher investigation, manually run 'git clean -ffdx' on the directory '${repositoryPath}'.` - ) - remove = true - } else if (!(await git.tryReset())) { - remove = true - } - - if (remove) { - core.warning( - `Unable to clean or reset the repository. The repository will be recreated instead.` - ) - } - } - } catch (error) { - core.warning( - `Unable to prepare the existing repository. The repository will be recreated instead.` - ) - remove = true - } - } - - if (remove) { - // Delete the contents of the directory. Don't delete the directory itself - // since it might be the current working directory. - core.info(`Deleting the contents of '${repositoryPath}'`) - for (const file of await fs.promises.readdir(repositoryPath)) { - await io.rmRF(path.join(repositoryPath, file)) - } - } -} - -async function configureAuthToken( - git: IGitCommandManager, - authToken: string -): Promise { - // Configure a placeholder value. This approach avoids the credential being captured - // by process creation audit events, which are commonly logged. For more information, - // refer to https://docs.microsoft.com/en-us/windows-server/identity/ad-ds/manage/component-updates/command-line-process-auditing - const placeholder = `AUTHORIZATION: basic ***` - await git.config(authConfigKey, placeholder) - - // Determine the basic credential value - const basicCredential = Buffer.from( - `x-access-token:${authToken}`, - 'utf8' - ).toString('base64') - core.setSecret(basicCredential) - - // Replace the value in the config file - const configPath = path.join(git.getWorkingDirectory(), '.git', 'config') - let content = (await fs.promises.readFile(configPath)).toString() - const placeholderIndex = content.indexOf(placeholder) - if ( - placeholderIndex < 0 || - placeholderIndex != content.lastIndexOf(placeholder) - ) { - throw new Error('Unable to replace auth placeholder in .git/config') - } - content = content.replace( - placeholder, - `AUTHORIZATION: basic ${basicCredential}` - ) - await fs.promises.writeFile(configPath, content) -} - -async function removeGitConfig( - git: IGitCommandManager, - configKey: string -): Promise { - if ( - (await git.configExists(configKey)) && - !(await git.tryConfigUnset(configKey)) - ) { - // Load the config contents - core.warning(`Failed to remove '${configKey}' from the git config`) + return undefined } } diff --git a/src/git-source-settings.ts b/src/git-source-settings.ts new file mode 100644 index 0000000..2786222 --- /dev/null +++ b/src/git-source-settings.ts @@ -0,0 +1,76 @@ +export interface IGitSourceSettings { + /** + * The location on disk where the repository will be placed + */ + repositoryPath: string + + /** + * The repository owner + */ + repositoryOwner: string + + /** + * The repository name + */ + repositoryName: string + + /** + * The ref to fetch + */ + ref: string + + /** + * The commit to checkout + */ + commit: string + + /** + * Indicates whether to clean the repository + */ + clean: boolean + + /** + * The depth when fetching + */ + fetchDepth: number + + /** + * Indicates whether to fetch LFS objects + */ + lfs: boolean + + /** + * Indicates whether to checkout submodules + */ + submodules: boolean + + /** + * Indicates whether to recursively checkout submodules + */ + nestedSubmodules: boolean + + /** + * The auth token to use when fetching the repository + */ + authToken: string + + /** + * The SSH key to configure + */ + sshKey: string + + /** + * Additional SSH known hosts + */ + sshKnownHosts: string + + /** + * Indicates whether the server must be a known host + */ + sshStrict: boolean + + /** + * Indicates whether to persist the credentials on disk to enable scripting authenticated git commands + */ + persistCredentials: boolean +} diff --git a/src/github-api-helper.ts b/src/github-api-helper.ts index 83a2b86..8bbcf2d 100644 --- a/src/github-api-helper.ts +++ b/src/github-api-helper.ts @@ -7,7 +7,7 @@ import * as path from 'path' import * as retryHelper from './retry-helper' import * as toolCache from '@actions/tool-cache' import {default as uuid} from 'uuid/v4' -import {ReposGetArchiveLinkParams} from '@octokit/rest' +import {Octokit} from '@octokit/rest' const IS_WINDOWS = process.platform === 'win32' @@ -19,6 +19,12 @@ export async function downloadRepository( commit: string, repositoryPath: string ): Promise { + // Determine the default branch + if (!ref && !commit) { + core.info('Determining the default branch') + ref = await getDefaultBranch(authToken, owner, repo) + } + // Download the archive let archiveData = await retryHelper.execute(async () => { core.info('Downloading the archive') @@ -67,6 +73,46 @@ export async function downloadRepository( io.rmRF(extractPath) } +/** + * Looks up the default branch name + */ +export async function getDefaultBranch( + authToken: string, + owner: string, + repo: string +): Promise { + return await retryHelper.execute(async () => { + core.info('Retrieving the default branch name') + const octokit = new github.GitHub(authToken) + let result: string + try { + // Get the default branch from the repo info + const response = await octokit.repos.get({owner, repo}) + result = response.data.default_branch + assert.ok(result, 'default_branch cannot be empty') + } catch (err) { + // Handle .wiki repo + if (err['status'] === 404 && repo.toUpperCase().endsWith('.WIKI')) { + result = 'master' + } + // Otherwise error + else { + throw err + } + } + + // Print the default branch + core.info(`Default branch '${result}'`) + + // Prefix with 'refs/heads' + if (!result.startsWith('refs/')) { + result = `refs/heads/${result}` + } + + return result + }) +} + async function downloadArchive( authToken: string, owner: string, @@ -75,7 +121,7 @@ async function downloadArchive( commit: string ): Promise { const octokit = new github.GitHub(authToken) - const params: ReposGetArchiveLinkParams = { + const params: Octokit.ReposGetArchiveLinkParams = { owner: owner, repo: repo, archive_format: IS_WINDOWS ? 'zipball' : 'tarball', diff --git a/src/input-helper.ts b/src/input-helper.ts index 54339da..eabb9e0 100644 --- a/src/input-helper.ts +++ b/src/input-helper.ts @@ -2,10 +2,10 @@ import * as core from '@actions/core' import * as fsHelper from './fs-helper' import * as github from '@actions/github' import * as path from 'path' -import {ISourceSettings} from './git-source-provider' +import {IGitSourceSettings} from './git-source-settings' -export function getInputs(): ISourceSettings { - const result = ({} as unknown) as ISourceSettings +export function getInputs(): IGitSourceSettings { + const result = ({} as unknown) as IGitSourceSettings // GitHub workspace let githubWorkspacePath = process.env['GITHUB_WORKSPACE'] @@ -68,10 +68,6 @@ export function getInputs(): ISourceSettings { result.ref = `refs/heads/${result.ref}` } } - - if (!result.ref && !result.commit) { - result.ref = 'refs/heads/master' - } } // SHA? else if (result.ref.match(/^[0-9a-fA-F]{40}$/)) { @@ -85,13 +81,6 @@ export function getInputs(): ISourceSettings { result.clean = (core.getInput('clean') || 'true').toUpperCase() === 'TRUE' core.debug(`clean = ${result.clean}`) - // Submodules - if (core.getInput('submodules')) { - throw new Error( - "The input 'submodules' is not supported in actions/checkout@v2" - ) - } - // Fetch depth result.fetchDepth = Math.floor(Number(core.getInput('fetch-depth') || '1')) if (isNaN(result.fetchDepth) || result.fetchDepth < 0) { @@ -103,8 +92,27 @@ export function getInputs(): ISourceSettings { result.lfs = (core.getInput('lfs') || 'false').toUpperCase() === 'TRUE' core.debug(`lfs = ${result.lfs}`) + // Submodules + result.submodules = false + result.nestedSubmodules = false + const submodulesString = (core.getInput('submodules') || '').toUpperCase() + if (submodulesString == 'RECURSIVE') { + result.submodules = true + result.nestedSubmodules = true + } else if (submodulesString == 'TRUE') { + result.submodules = true + } + core.debug(`submodules = ${result.submodules}`) + core.debug(`recursive submodules = ${result.nestedSubmodules}`) + // Auth token - result.authToken = core.getInput('token') + result.authToken = core.getInput('token', {required: true}) + + // SSH + result.sshKey = core.getInput('ssh-key') + result.sshKnownHosts = core.getInput('ssh-known-hosts') + result.sshStrict = + (core.getInput('ssh-strict') || 'true').toUpperCase() === 'TRUE' // Persist credentials result.persistCredentials = diff --git a/src/misc/generate-docs.ts b/src/misc/generate-docs.ts index 884d606..defda5a 100644 --- a/src/misc/generate-docs.ts +++ b/src/misc/generate-docs.ts @@ -59,13 +59,17 @@ function updateUsage( // Constrain the width of the description const width = 80 - let description = input.description as string + let description = (input.description as string) + .trimRight() + .replace(/\r\n/g, '\n') // Convert CR to LF + .replace(/ +/g, ' ') // Squash consecutive spaces + .replace(/ \n/g, '\n') // Squash space followed by newline while (description) { // Longer than width? Find a space to break apart let segment: string = description if (description.length > width) { segment = description.substr(0, width + 1) - while (!segment.endsWith(' ') && segment) { + while (!segment.endsWith(' ') && !segment.endsWith('\n') && segment) { segment = segment.substr(0, segment.length - 1) } @@ -77,15 +81,30 @@ function updateUsage( segment = description } - description = description.substr(segment.length) // Remaining - segment = segment.trimRight() // Trim the trailing space - newReadme.push(` # ${segment}`) + // Check for newline + const newlineIndex = segment.indexOf('\n') + if (newlineIndex >= 0) { + segment = segment.substr(0, newlineIndex + 1) + } + + // Append segment + newReadme.push(` # ${segment}`.trimRight()) + + // Remaining + description = description.substr(segment.length) } - // Input and default if (input.default !== undefined) { + // Append blank line if description had paragraphs + if ((input.description as string).trimRight().match(/\n[ ]*\r?\n/)) { + newReadme.push(` #`) + } + + // Default newReadme.push(` # Default: ${input.default}`) } + + // Input name newReadme.push(` ${key}: ''`) firstInput = false diff --git a/src/ref-helper.ts b/src/ref-helper.ts index ff256af..381fa60 100644 --- a/src/ref-helper.ts +++ b/src/ref-helper.ts @@ -1,4 +1,9 @@ +import {URL} from 'url' import {IGitCommandManager} from './git-command-manager' +import * as core from '@actions/core' +import * as github from '@actions/github' + +export const tagsRefSpec = '+refs/tags/*:refs/tags/*' export interface ICheckoutInfo { ref: string @@ -57,6 +62,16 @@ export async function getCheckoutInfo( return result } +export function getRefSpecForAllHistory(ref: string, commit: string): string[] { + const result = ['+refs/heads/*:refs/remotes/origin/*', tagsRefSpec] + if (ref && ref.toUpperCase().startsWith('REFS/PULL/')) { + const branch = ref.substring('refs/pull/'.length) + result.push(`+${commit || ref}:refs/remotes/pull/${branch}`) + } + + return result +} + export function getRefSpec(ref: string, commit: string): string[] { if (!ref && !commit) { throw new Error('Args ref and commit cannot both be empty') @@ -107,3 +122,162 @@ export function getRefSpec(ref: string, commit: string): string[] { return [`+${ref}:${ref}`] } } + +/** + * Tests whether the initial fetch created the ref at the expected commit + */ +export async function testRef( + git: IGitCommandManager, + ref: string, + commit: string +): Promise { + if (!git) { + throw new Error('Arg git cannot be empty') + } + + if (!ref && !commit) { + throw new Error('Args ref and commit cannot both be empty') + } + + // No SHA? Nothing to test + if (!commit) { + return true + } + // SHA only? + else if (!ref) { + return await git.shaExists(commit) + } + + const upperRef = ref.toUpperCase() + + // refs/heads/ + if (upperRef.startsWith('REFS/HEADS/')) { + const branch = ref.substring('refs/heads/'.length) + return ( + (await git.branchExists(true, `origin/${branch}`)) && + commit === (await git.revParse(`refs/remotes/origin/${branch}`)) + ) + } + // refs/pull/ + else if (upperRef.startsWith('REFS/PULL/')) { + // Assume matches because fetched using the commit + return true + } + // refs/tags/ + else if (upperRef.startsWith('REFS/TAGS/')) { + const tagName = ref.substring('refs/tags/'.length) + return ( + (await git.tagExists(tagName)) && commit === (await git.revParse(ref)) + ) + } + // Unexpected + else { + core.debug(`Unexpected ref format '${ref}' when testing ref info`) + return true + } +} + +export async function checkCommitInfo( + token: string, + commitInfo: string, + repositoryOwner: string, + repositoryName: string, + ref: string, + commit: string +): Promise { + try { + // GHES? + if (isGhes()) { + return + } + + // Auth token? + if (!token) { + return + } + + // Public PR synchronize, for workflow repo? + if ( + fromPayload('repository.private') !== false || + github.context.eventName !== 'pull_request' || + fromPayload('action') !== 'synchronize' || + repositoryOwner !== github.context.repo.owner || + repositoryName !== github.context.repo.repo || + ref !== github.context.ref || + !ref.startsWith('refs/pull/') || + commit !== github.context.sha + ) { + return + } + + // Head SHA + const expectedHeadSha = fromPayload('after') + if (!expectedHeadSha) { + core.debug('Unable to determine head sha') + return + } + + // Base SHA + const expectedBaseSha = fromPayload('pull_request.base.sha') + if (!expectedBaseSha) { + core.debug('Unable to determine base sha') + return + } + + // Expected message? + const expectedMessage = `Merge ${expectedHeadSha} into ${expectedBaseSha}` + if (commitInfo.indexOf(expectedMessage) >= 0) { + return + } + + // Extract details from message + const match = commitInfo.match(/Merge ([0-9a-f]{40}) into ([0-9a-f]{40})/) + if (!match) { + core.debug('Unexpected message format') + return + } + + // Post telemetry + const actualHeadSha = match[1] + if (actualHeadSha !== expectedHeadSha) { + core.debug( + `Expected head sha ${expectedHeadSha}; actual head sha ${actualHeadSha}` + ) + const octokit = new github.GitHub(token, { + userAgent: `actions-checkout-tracepoint/1.0 (code=STALE_MERGE;owner=${repositoryOwner};repo=${repositoryName};pr=${fromPayload( + 'number' + )};run_id=${ + process.env['GITHUB_RUN_ID'] + };expected_head_sha=${expectedHeadSha};actual_head_sha=${actualHeadSha})` + }) + await octokit.repos.get({owner: repositoryOwner, repo: repositoryName}) + } + } catch (err) { + core.debug(`Error when validating commit info: ${err.stack}`) + } +} + +function fromPayload(path: string): any { + return select(github.context.payload, path) +} + +function select(obj: any, path: string): any { + if (!obj) { + return undefined + } + + const i = path.indexOf('.') + if (i < 0) { + return obj[path] + } + + const key = path.substr(0, i) + return select(obj[key], path.substr(i + 1)) +} + +function isGhes(): boolean { + const ghUrl = new URL( + process.env['GITHUB_SERVER_URL'] || 'https://github.com' + ) + return ghUrl.hostname.toUpperCase() !== 'GITHUB.COM' +} diff --git a/src/regexp-helper.ts b/src/regexp-helper.ts new file mode 100644 index 0000000..ec76c3a --- /dev/null +++ b/src/regexp-helper.ts @@ -0,0 +1,5 @@ +export function escape(value: string): string { + return value.replace(/[^a-zA-Z0-9_]/g, x => { + return `\\${x}` + }) +} diff --git a/src/state-helper.ts b/src/state-helper.ts index 0f86a14..3c657b1 100644 --- a/src/state-helper.ts +++ b/src/state-helper.ts @@ -1,4 +1,3 @@ -import * as core from '@actions/core' import * as coreCommand from '@actions/core/lib/command' /** @@ -12,6 +11,17 @@ export const IsPost = !!process.env['STATE_isPost'] export const RepositoryPath = (process.env['STATE_repositoryPath'] as string) || '' +/** + * The SSH key path for the POST action. The value is empty during the MAIN action. + */ +export const SshKeyPath = (process.env['STATE_sshKeyPath'] as string) || '' + +/** + * The SSH known hosts path for the POST action. The value is empty during the MAIN action. + */ +export const SshKnownHostsPath = + (process.env['STATE_sshKnownHostsPath'] as string) || '' + /** * Save the repository path so the POST action can retrieve the value. */ @@ -23,6 +33,24 @@ export function setRepositoryPath(repositoryPath: string) { ) } +/** + * Save the SSH key path so the POST action can retrieve the value. + */ +export function setSshKeyPath(sshKeyPath: string) { + coreCommand.issueCommand('save-state', {name: 'sshKeyPath'}, sshKeyPath) +} + +/** + * Save the SSH known hosts path so the POST action can retrieve the value. + */ +export function setSshKnownHostsPath(sshKnownHostsPath: string) { + coreCommand.issueCommand( + 'save-state', + {name: 'sshKnownHostsPath'}, + sshKnownHostsPath + ) +} + // Publish a variable so that when the POST action runs, it can determine it should run the cleanup logic. // This is necessary since we don't have a separate entry point. if (!IsPost) { diff --git a/src/url-helper.ts b/src/url-helper.ts new file mode 100644 index 0000000..05f1cbd --- /dev/null +++ b/src/url-helper.ts @@ -0,0 +1,29 @@ +import * as assert from 'assert' +import {IGitSourceSettings} from './git-source-settings' +import {URL} from 'url' + +export function getFetchUrl(settings: IGitSourceSettings): string { + assert.ok( + settings.repositoryOwner, + 'settings.repositoryOwner must be defined' + ) + assert.ok(settings.repositoryName, 'settings.repositoryName must be defined') + const serviceUrl = getServerUrl() + const encodedOwner = encodeURIComponent(settings.repositoryOwner) + const encodedName = encodeURIComponent(settings.repositoryName) + if (settings.sshKey) { + return `git@${serviceUrl.hostname}:${encodedOwner}/${encodedName}.git` + } + + // "origin" is SCHEME://HOSTNAME[:PORT] + return `${serviceUrl.origin}/${encodedOwner}/${encodedName}` +} + +export function getServerUrl(): URL { + // todo: remove GITHUB_URL after support for GHES Alpha is no longer needed + return new URL( + process.env['GITHUB_SERVER_URL'] || + process.env['GITHUB_URL'] || + 'https://github.com' + ) +}