diff --git a/.github/actions-scripts/purge-old-workflow-runs.js b/.github/actions-scripts/purge-old-workflow-runs.js index 6129335fab63..382290ef7a2e 100755 --- a/.github/actions-scripts/purge-old-workflow-runs.js +++ b/.github/actions-scripts/purge-old-workflow-runs.js @@ -25,6 +25,7 @@ import fs from 'fs' import assert from 'node:assert/strict' import { getOctokit } from '@actions/github' +import { RequestError } from '@octokit/request-error' main() async function main() { @@ -51,10 +52,12 @@ async function main() { repo, }) + const validWorkflows = allWorkflows.filter((w) => !w.path.startsWith('dynamic/')) + const sortByDate = (a, b) => a.updated_at.localeCompare(b.updated_at) const workflows = [ - ...allWorkflows.filter((w) => !fs.existsSync(w.path)).sort(sortByDate), - ...allWorkflows.filter((w) => fs.existsSync(w.path)).sort(sortByDate), + ...validWorkflows.filter((w) => !fs.existsSync(w.path)).sort(sortByDate), + ...validWorkflows.filter((w) => fs.existsSync(w.path)).sort(sortByDate), ] let deletions = 0 @@ -65,11 +68,25 @@ async function main() { ? `${workflow.path} still exists on disk` : `${workflow.path} no longer exists on disk`, ) - deletions += await deleteWorkflowRuns(github, owner, repo, workflow, { - dryRun: DRY_RUN, - minAgeDays: MIN_AGE_DAYS, - maxDeletions: MAX_DELETIONS - deletions, - }) + try { + deletions += await deleteWorkflowRuns(github, owner, repo, workflow, { + dryRun: DRY_RUN, + minAgeDays: MIN_AGE_DAYS, + maxDeletions: MAX_DELETIONS - deletions, + }) + } catch (error) { + // Generally, if it fails, it's because of a network error or + // because busy servers. It's not our fault, but considering that + // this script is supposed to run on frequent schedule, we don't + // need to fret. We'll just try again next time. + if (error instanceof RequestError && error.status >= 500) { + console.log(`RequestError: ${error.message}`) + console.log(` status: ${error.status}`) + break + } else { + throw error + } + } if (deletions >= MAX_DELETIONS) { console.log(`Reached max number of deletions: ${MAX_DELETIONS}`) diff --git a/content/communities/using-templates-to-encourage-useful-issues-and-pull-requests/syntax-for-githubs-form-schema.md b/content/communities/using-templates-to-encourage-useful-issues-and-pull-requests/syntax-for-githubs-form-schema.md index e8b040d5a2b2..bbc967de9119 100644 --- a/content/communities/using-templates-to-encourage-useful-issues-and-pull-requests/syntax-for-githubs-form-schema.md +++ b/content/communities/using-templates-to-encourage-useful-issues-and-pull-requests/syntax-for-githubs-form-schema.md @@ -39,7 +39,8 @@ For example, the following form definition includes four form elements: a text a multiple: false options: - 1.0.2 (Default) - - 1.0.3 (Edge) + - 1.0.3 (Edge){% ifversion issue-form-dropdown-defaults %} + default: 0{% endif %} validations: required: true - type: checkboxes @@ -203,6 +204,7 @@ You can use a `dropdown` element to add a dropdown menu in your form. | `description` | A description of the dropdown to provide extra context or guidance, which is displayed in the form. | {% octicon "x" aria-label="Optional" %} | String | Empty String | {% octicon "dash" aria-label="Not applicable" %} | | `multiple` | Determines if the user can select more than one option. | {% octicon "x" aria-label="Optional" %} | Boolean | false | {% octicon "dash" aria-label="Not applicable" %} | | `options` | An array of options the user can choose from. Cannot be empty and all choices must be distinct. | {% octicon "check" aria-label="Required" %} | String array | {% octicon "dash" aria-label="Not applicable" %} | {% octicon "dash" aria-label="Not applicable" %} | +| `default` | Index of the preselected option in the `options` array. When a default option is specified, you cannot include "None" or "n/a" as options. | {% octicon "x" aria-label="Optional" %} | Integer | {% octicon "dash" aria-label="Not applicable" %} | {% octicon "dash" aria-label="Not applicable" %} | #### Validations for `dropdown` @@ -221,10 +223,11 @@ body: attributes: label: How did you download the software? options: + - Built from source - Homebrew - MacPorts - - apt-get - - Built from source + - apt-get{% ifversion issue-form-dropdown-defaults %} + default: 0{% endif %} validations: required: true ``` diff --git a/content/communities/using-templates-to-encourage-useful-issues-and-pull-requests/syntax-for-issue-forms.md b/content/communities/using-templates-to-encourage-useful-issues-and-pull-requests/syntax-for-issue-forms.md index 92732a209724..c49e782e0e07 100644 --- a/content/communities/using-templates-to-encourage-useful-issues-and-pull-requests/syntax-for-issue-forms.md +++ b/content/communities/using-templates-to-encourage-useful-issues-and-pull-requests/syntax-for-issue-forms.md @@ -46,7 +46,9 @@ You can set the following top-level keys for each issue form. | `body` | Definition of the input types in the form. | Required | Array | | `assignees` | People who will be automatically assigned to issues created with this template. | Optional | Array or comma-delimited string | | `labels` | Labels that will automatically be added to issues created with this template. If a label does not already exist in the repository, it will not be automatically added to the issue. | Optional | Array or comma-delimited string | -| `title` | A default title that will be pre-populated in the issue submission form. | Optional | String | +| `title` | A default title that will be pre-populated in the issue submission form. | Optional | String |{% ifversion projects-in-issue-forms %} +| `projects` | Projects that any issues created with this template will automatically be added to. | Optional | Array or comma-delimited string |{% endif %} + For the available `body` input types and their syntaxes, see "[AUTOTITLE](/communities/using-templates-to-encourage-useful-issues-and-pull-requests/syntax-for-githubs-form-schema)." diff --git a/content/issues/tracking-your-work-with-issues/creating-an-issue.md b/content/issues/tracking-your-work-with-issues/creating-an-issue.md index efa2bbc40d44..4e3a899cd4ed 100644 --- a/content/issues/tracking-your-work-with-issues/creating-an-issue.md +++ b/content/issues/tracking-your-work-with-issues/creating-an-issue.md @@ -165,7 +165,7 @@ Query parameter | Example `labels` | `https://github.com/octo-org/octo-repo/issues/new?labels=help+wanted,bug` creates an issue with the labels "help wanted" and "bug". `milestone` | `https://github.com/octo-org/octo-repo/issues/new?milestone=testing+milestones` creates an issue with the milestone "testing milestones." `assignees` | `https://github.com/octo-org/octo-repo/issues/new?assignees=octocat` creates an issue and assigns it to @octocat. -`projects` | `https://github.com/octo-org/octo-repo/issues/new?title=Bug+fix&projects=octo-org/1` creates an issue with the title "Bug fix" and adds it to the organization's project board 1. +`projects` | `https://github.com/octo-org/octo-repo/issues/new?title=Bug+fix&projects=octo-org/1` creates an issue with the title "Bug fix" and adds it to the organization's project board 1. {% ifversion projects-v2 and projects-v1 %}{% ifversion projects-in-issue-forms %}{% else %}Only {% data variables.projects.projects_v1_boards %} can currently be specified in URL queries.{% endif %}{% endif %} `template` | `https://github.com/octo-org/octo-repo/issues/new?template=issue_template.md` creates an issue with a template in the issue body. The `template` query parameter works with templates stored in an `ISSUE_TEMPLATE` subdirectory within the root, `docs/` or `.github/` directory in a repository. For more information, see "[AUTOTITLE](/communities/using-templates-to-encourage-useful-issues-and-pull-requests)." {% ifversion fpt or ghec %} diff --git a/data/features/issue-form-dropdown-defaults.yml b/data/features/issue-form-dropdown-defaults.yml new file mode 100644 index 000000000000..ce63850f9fe7 --- /dev/null +++ b/data/features/issue-form-dropdown-defaults.yml @@ -0,0 +1,6 @@ +# Ability to set a default in issue form dropdowns (#11231) +versions: + fpt: '*' + ghec: '*' + ghes: '>=3.11' + ghae: '>=3.11' diff --git a/data/features/projects-in-issue-forms.yml b/data/features/projects-in-issue-forms.yml new file mode 100644 index 000000000000..27bac8a18071 --- /dev/null +++ b/data/features/projects-in-issue-forms.yml @@ -0,0 +1,6 @@ +# Ability to set projects in issue forms (#11231) +versions: + fpt: '*' + ghec: '*' + ghes: '>=3.11' + ghae: '>=3.11' diff --git a/data/reusables/community/issue-forms-sample.md b/data/reusables/community/issue-forms-sample.md index 2c1ef37932cc..a72f44d5b89e 100644 --- a/data/reusables/community/issue-forms-sample.md +++ b/data/reusables/community/issue-forms-sample.md @@ -2,7 +2,8 @@ name: Bug Report description: File a bug report title: "[Bug]: " -labels: ["bug", "triage"] +labels: ["bug", "triage"]{% ifversion projects-in-issue-forms %} +projects: ["octo-org/1", "octo-org/44"]{% endif %} assignees: - octocat body: @@ -34,7 +35,8 @@ body: description: What version of our software are you running? options: - 1.0.2 (Default) - - 1.0.3 (Edge) + - 1.0.3 (Edge){% ifversion issue-form-dropdown-defaults %} + default: 0{% endif %} validations: required: true - type: dropdown diff --git a/package-lock.json b/package-lock.json index 348713aede25..7c61f84b9016 100644 --- a/package-lock.json +++ b/package-lock.json @@ -9,6 +9,7 @@ "dependencies": { "@elastic/elasticsearch": "7.11.0", "@github/failbot": "0.8.3", + "@octokit/request-error": "5.0.0", "@primer/behaviors": "^1.3.3", "@primer/css": "^21.0.1", "@primer/octicons": "^19.1.0", @@ -1953,6 +1954,17 @@ "universal-user-agent": "^6.0.0" } }, + "node_modules/@octokit/core/node_modules/@octokit/request-error": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-2.1.0.tgz", + "integrity": "sha512-1VIvgXxs9WHSjicsRwq8PlR2LR2x6DwsJAaFgzdi0JfJoGSO8mYI/cHJQ+9FbN21aa+DrgNLnwObmyeSC8Rmpg==", + "dev": true, + "dependencies": { + "@octokit/types": "^6.0.3", + "deprecation": "^2.0.0", + "once": "^1.4.0" + } + }, "node_modules/@octokit/endpoint": { "version": "6.0.12", "dev": true, @@ -2081,9 +2093,36 @@ } }, "node_modules/@octokit/request-error": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-5.0.0.tgz", + "integrity": "sha512-1ue0DH0Lif5iEqT52+Rf/hf0RmGO9NWFjrzmrkArpG9trFfDM/efx00BJHdLGuro4BR/gECxCU2Twf5OKrRFsQ==", + "dependencies": { + "@octokit/types": "^11.0.0", + "deprecation": "^2.0.0", + "once": "^1.4.0" + }, + "engines": { + "node": ">= 18" + } + }, + "node_modules/@octokit/request-error/node_modules/@octokit/openapi-types": { + "version": "18.0.0", + "resolved": "https://registry.npmjs.org/@octokit/openapi-types/-/openapi-types-18.0.0.tgz", + "integrity": "sha512-V8GImKs3TeQRxRtXFpG2wl19V7444NIOTDF24AWuIbmNaNYOQMWRbjcGDXV5B+0n887fgDcuMNOmlul+k+oJtw==" + }, + "node_modules/@octokit/request-error/node_modules/@octokit/types": { + "version": "11.1.0", + "resolved": "https://registry.npmjs.org/@octokit/types/-/types-11.1.0.tgz", + "integrity": "sha512-Fz0+7GyLm/bHt8fwEqgvRBWwIV1S6wRRyq+V6exRKLVWaKGsuy6H9QFYeBVDV7rK6fO3XwHgQOPxv+cLj2zpXQ==", + "dependencies": { + "@octokit/openapi-types": "^18.0.0" + } + }, + "node_modules/@octokit/request/node_modules/@octokit/request-error": { "version": "2.1.0", + "resolved": "https://registry.npmjs.org/@octokit/request-error/-/request-error-2.1.0.tgz", + "integrity": "sha512-1VIvgXxs9WHSjicsRwq8PlR2LR2x6DwsJAaFgzdi0JfJoGSO8mYI/cHJQ+9FbN21aa+DrgNLnwObmyeSC8Rmpg==", "dev": true, - "license": "MIT", "dependencies": { "@octokit/types": "^6.0.3", "deprecation": "^2.0.0", @@ -4878,7 +4917,6 @@ }, "node_modules/deprecation": { "version": "2.3.1", - "dev": true, "license": "ISC" }, "node_modules/dequal": { diff --git a/package.json b/package.json index fd50fbe6fa51..51343774cd16 100644 --- a/package.json +++ b/package.json @@ -58,6 +58,7 @@ "dependencies": { "@elastic/elasticsearch": "7.11.0", "@github/failbot": "0.8.3", + "@octokit/request-error": "5.0.0", "@primer/behaviors": "^1.3.3", "@primer/css": "^21.0.1", "@primer/octicons": "^19.1.0",