Files
dashy/.github/workflows/close-stale-issues.yml
2026-04-09 21:00:00 +01:00

133 lines
5.5 KiB
YAML

# Closes issues that are inactive, likely non-issues, or awaiting a response that never came.
# Runs daily. Skips issues with active discussion (3+ non-bot comments), reopened issues,
# milestones, or assignees.
name: 🎯 Close Stale Issues
on:
workflow_dispatch:
schedule:
- cron: '0 1 * * *'
permissions:
issues: write
pull-requests: write
jobs:
stale:
runs-on: ubuntu-latest
steps:
- name: Exempt actively discussed or reopened issues 💬
uses: actions/github-script@v8
with:
github-token: ${{ secrets.BOT_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
script: |
const { owner, repo } = context.repo;
const KEEP_OPEN = '📌 Keep Open';
const BOT = 'liss-bot';
const MIN = 3;
const exempt = (number, reason) => github.rest.issues
.addLabels({ owner, repo, issue_number: number, labels: [KEEP_OPEN] })
.then(() => core.info(`Exempted #${number} (${reason})`));
const hasEnoughHumanComments = async (issue) => {
if (issue.comments < MIN) return false;
const comments = await github.paginate(github.rest.issues.listComments, {
owner, repo, issue_number: issue.number, per_page: 100,
});
return comments.filter(c => c.user?.login !== BOT).length >= MIN;
};
const wasReopened = async (number) => {
const { data } = await github.rest.issues.listEvents({
owner, repo, issue_number: number, per_page: 100,
});
return data.some(e => e.event === 'reopened');
};
const issues = await github.paginate(github.rest.issues.listForRepo, {
owner, repo, state: 'open', per_page: 100,
});
for (const issue of issues) {
if (issue.pull_request) continue;
if (issue.labels.some(l => l.name === KEEP_OPEN)) continue;
try {
if (await hasEnoughHumanComments(issue)) {
await exempt(issue.number, '3+ non-bot comments');
} else if (await wasReopened(issue.number)) {
await exempt(issue.number, 'previously reopened');
}
} catch (e) {
core.warning(`Failed to process #${issue.number}: ${e.message}`);
}
}
- name: Close stale issues ⚰️
uses: actions/stale@v10
with:
repo-token: ${{ secrets.BOT_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
days-before-stale: 120
days-before-close: 7
days-before-pr-stale: -1
operations-per-run: 30
remove-stale-when-updated: true
enable-statistics: true
exempt-issue-labels: '📌 Keep Open,✅ Fixed'
exempt-all-milestones: true
close-issue-reason: not_planned
stale-issue-message: >
This issue has gone 4 months without an update. To keep the ticket
open, please indicate that it is still relevant in a comment below.
Otherwise it will be closed in 7 days.
close-issue-message: >
This issue was automatically closed because it has been inactive
for over 4 months with no activity.
stale-issue-label: '⚰️ Stale'
close-issue-label: '🕸️ Inactive'
labels-to-add-when-unstale: '📌 Keep Open'
- name: Close issues without response 🚏
uses: actions/stale@v10
with:
repo-token: ${{ secrets.BOT_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
days-before-stale: 7
days-before-close: 3
days-before-pr-stale: -1
operations-per-run: 30
remove-stale-when-updated: true
exempt-issue-labels: '📌 Keep Open,✅ Fixed'
exempt-all-milestones: true
only-labels: '🚏 Awaiting User Response'
stale-issue-message: >
Hello! Looks like additional info is required for this issue to be
addressed. Don't forget to provide this within the next few days to
keep your ticket open.
close-issue-message: 'Issue closed due to no response from user.'
stale-issue-label: '🛑 No Response'
close-issue-label: '🕸️ Inactive'
labels-to-remove-when-unstale: '🚏 Awaiting User Response,🛑 No Response'
- name: Notify repo owner to respond 👤
uses: actions/stale@v10
with:
repo-token: ${{ secrets.BOT_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
days-before-stale: 7
days-before-close: 365
operations-per-run: 30
remove-stale-when-updated: true
exempt-all-milestones: true
exempt-issue-labels: '📌 Keep Open'
exempt-pr-labels: '📌 Keep Open'
only-labels: '👤 Awaiting Maintainer Response'
stale-issue-message: Hey @Lissy93 - Don't forget to respond!
stale-pr-message: Hey @Lissy93 - Don't forget to respond!
close-issue-message: 'Closed due to no response from repo author for over a year'
close-pr-message: 'Closed due to no response from repo author for over a year'
stale-issue-label: '👤 Awaiting Maintainer Response'
stale-pr-label: '👤 Awaiting Maintainer Response'
close-issue-label: '🕸️ Inactive'
close-pr-label: '🕸️ Inactive'
labels-to-remove-when-unstale: '👤 Awaiting Maintainer Response'