Unverified Commit 3b14bf26 authored by Michael Daniels's avatar Michael Daniels Committed by GitHub
Browse files

ci/github-script/manual-file-edits: init (#509418)

parents fa5048c1 bd7e8b99
Loading
Loading
Loading
Loading
+35 −0
Original line number Diff line number Diff line
@@ -71,6 +71,41 @@ jobs:
          GH_TOKEN: ${{ github.token }}
        run: gh api /rate_limit | jq

  manual-file-edits:
    if: inputs.baseBranch && inputs.headBranch
    permissions:
      pull-requests: write
    runs-on: ubuntu-slim
    timeout-minutes: 3
    steps:
      - uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
        with:
          persist-credentials: false
          path: trusted
          sparse-checkout: |
            ci/github-script

      - name: Log current API rate limits
        env:
          GH_TOKEN: ${{ github.token }}
        run: gh api /rate_limit | jq

      - name: Discourage manual edits to certain files
        uses: actions/github-script@ed597411d8f924073f98dfc5c65a23a2325f34cd # v8.0.0
        with:
          script: |
            require('./trusted/ci/github-script/manual-file-edits.js')({
              github,
              context,
              core,
              repoPath: 'trusted',
            })

      - name: Log current API rate limits
        env:
          GH_TOKEN: ${{ github.token }}
        run: gh api /rate_limit | jq

  owners:
    runs-on: ubuntu-24.04-arm
    timeout-minutes: 5
+55 −0
Original line number Diff line number Diff line
// @ts-check
const { getCommitDetailsForPR } = require('./get-pr-commit-details')

/**
 * @param {{
 *  github: InstanceType<import('@actions/github/lib/utils').GitHub>,
 *  context: import('@actions/github/lib/context').Context,
 *  core: import('@actions/core'),
 *  repoPath?: string,
 * }} CheckManualFileEditsProps
 */
async function checkManualFileEdits({ github, context, core, repoPath }) {
  const pull_number = context.payload.pull_request?.number
  if (!pull_number) {
    core.info('This is not a pull request. Skipping checks.')
    return
  }

  const pr = (
    await github.rest.pulls.get({
      ...context.repo,
      pull_number,
    })
  ).data

  if (pr.user.login.endsWith('[bot]')) {
    core.info('This is a bot, so these checks do not apply.')
    return
  }

  const details = await getCommitDetailsForPR({ core, pr, repoPath })

  if (
    details.some(({ changedPaths }) =>
      changedPaths.includes('maintainers/github-teams.json'),
    )
  ) {
    core.setFailed(
      [
        'maintainers/github-teams.json is supposed to accurately reflect the state of the teams in GitHub.\n',
        'Therefore, it should not be edited manually.\n',
        'All changes to teams listed in maintainers/github-teams.json should be performed in GitHub by a team maintainer.\n',
        "Team maintainers are listed in the github-teams.json file and in GitHub's UI.\n",
        'If there is no team maintainer available, an org owner can make the needed change, please contact one by',
        'following the instructions at https://github.com/NixOS/org/blob/main/doc/github-org-owners.md#how-to-contact-the-team.\n',
        'Thank you!',
      ].reduce(
        (prev, curr) => prev + (!prev || prev.endsWith('\n') ? '' : ' ') + curr,
        '',
      ),
    )
  }
}

module.exports = checkManualFileEdits
+11 −0
Original line number Diff line number Diff line
@@ -116,4 +116,15 @@ program
    await run(checkCommitMessages, owner, repo, pr, options)
  })

program
  .command('manual-file-edits')
  .description("Error when files that shouldn't be edited manually are")
  .argument('<owner>', 'Owner of the GitHub repository to run on (Example: NixOS)')
  .argument('<repo>', 'Name of the GitHub repository to run on (Example: nixpkgs)')
  .argument('<pr>', 'Number of the Pull Request to run on')
  .action(async (owner, repo, pr, options) => {
    const checkManualFileEdits = (await import('./manual-file-edits.js')).default
    await run(checkManualFileEdits, owner, repo, pr, options)
  })

await program.parse()