86 lines
3 KiB
YAML
86 lines
3 KiB
YAML
name: Mark released issues on close
|
|
|
|
on:
|
|
issues:
|
|
types: [closed]
|
|
|
|
permissions:
|
|
contents: read
|
|
issues: write
|
|
|
|
jobs:
|
|
mark-released:
|
|
# Run only if closed as completed AND has at least one "status:" label
|
|
if: ${{ github.event.issue.state_reason == 'completed' && contains(toJSON(github.event.issue.labels), 'status:') }}
|
|
runs-on: ubuntu-latest
|
|
steps:
|
|
- name: Set "released" label when closed completed and was ready for release
|
|
uses: actions/github-script@v7
|
|
with:
|
|
script: |
|
|
// Helpers
|
|
const owner = context.repo.owner;
|
|
const repo = context.repo.repo;
|
|
const issue = context.payload.issue;
|
|
if (!issue) {
|
|
core.info('No issue payload found, skipping.');
|
|
return;
|
|
}
|
|
|
|
// Only proceed if closed as "completed" (not "not_planned")
|
|
const isCompleted = issue.state_reason === 'completed';
|
|
if (!isCompleted) {
|
|
core.info('Issue state_reason is not "completed"; skipping.');
|
|
return;
|
|
}
|
|
|
|
const getName = (l) => typeof l === 'string' ? l : l.name;
|
|
const labels = (issue.labels || []).map(getName);
|
|
|
|
// Status detection (robust to case/spacing)
|
|
const isStatusLabel = (name) => /^status:\s*/i.test(String(name || ''));
|
|
const hasAnyStatus = labels.some(isStatusLabel);
|
|
if (!hasAnyStatus) {
|
|
core.info('Issue has no "status:*" label; skipping.');
|
|
return;
|
|
}
|
|
|
|
const READY_REGEX = /^status:\s*ready\s*for\s*release$/i;
|
|
const hasReady = labels.some((n) => READY_REGEX.test(String(n || '')));
|
|
if (!hasReady) {
|
|
core.info('Issue is not "status: ready for release"; nothing to do.');
|
|
return;
|
|
}
|
|
|
|
const releasedLabel = 'status: released';
|
|
|
|
// Ensure "released" label exists
|
|
try {
|
|
await github.rest.issues.getLabel({ owner, repo, name: releasedLabel });
|
|
} catch (e) {
|
|
if (e.status === 404) {
|
|
core.info(`Label "${releasedLabel}" not found. Creating it.`);
|
|
await github.rest.issues.createLabel({
|
|
owner,
|
|
repo,
|
|
name: releasedLabel,
|
|
color: '184738', // deep green from your palette
|
|
description: 'Feature released.'
|
|
});
|
|
} else {
|
|
throw e;
|
|
}
|
|
}
|
|
|
|
// Remove all status:* labels, add "status: released"
|
|
const filtered = labels.filter((name) => !isStatusLabel(name));
|
|
const newLabels = [...new Set([...filtered, releasedLabel])];
|
|
|
|
await github.rest.issues.update({
|
|
owner,
|
|
repo,
|
|
issue_number: issue.number,
|
|
labels: newLabels
|
|
});
|
|
|
|
core.info(`Issue #${issue.number} relabeled as "${releasedLabel}".`);
|