Compare commits

..

1 Commits

Author SHA1 Message Date
Claude
8842a4c1b5 Add comprehensive accessibility guidance to frontend-design skill
- Update skill description to emphasize accessibility as a core principle
- Add accessibility to the Design Thinking checklist
- Add full 'Accessibility Excellence' section covering:
  - Semantic Structure (HTML elements, heading hierarchy, landmarks)
  - Keyboard Navigation (tab order, focus indicators, skip links)
  - Visual Accessibility (contrast, color independence, reduced motion)
  - ARIA & Screen Readers (labels, live regions, state attributes)
  - Interactive Components (buttons vs links, form labels, modals)
  - Testing Checklist for verification
- Emphasize that accessibility and bold design are not in conflict
- Update closing statement to reference serving all users
2026-01-30 20:25:48 +00:00
11 changed files with 280 additions and 502 deletions

View File

@@ -1,20 +1,13 @@
name: Claude Issue Triage
description: Automatically triage GitHub issues using Claude Code
on:
issues:
types: [opened]
issue_comment:
types: [created]
jobs:
triage-issue:
runs-on: ubuntu-latest
timeout-minutes: 10
if: >-
github.event_name == 'issues' ||
(github.event_name == 'issue_comment' && !github.event.issue.pull_request && github.event.comment.user.type != 'Bot')
concurrency:
group: issue-triage-${{ github.event.issue.number }}
cancel-in-progress: true
permissions:
contents: read
issues: write
@@ -24,6 +17,30 @@ jobs:
- name: Checkout repository
uses: actions/checkout@v4
- name: Setup GitHub MCP Server
run: |
mkdir -p /tmp/mcp-config
cat > /tmp/mcp-config/mcp-servers.json << 'EOF'
{
"mcpServers": {
"github": {
"command": "docker",
"args": [
"run",
"-i",
"--rm",
"-e",
"GITHUB_PERSONAL_ACCESS_TOKEN",
"ghcr.io/github/github-mcp-server:sha-7aced2b"
],
"env": {
"GITHUB_PERSONAL_ACCESS_TOKEN": "${{ secrets.GITHUB_TOKEN }}"
}
}
}
}
EOF
- name: Run Claude Code for Issue Triage
timeout-minutes: 5
uses: anthropics/claude-code-action@v1
@@ -33,72 +50,56 @@ jobs:
github_token: ${{ secrets.GITHUB_TOKEN }}
allowed_non_write_users: "*"
prompt: |
You're an issue triage assistant. Analyze the issue and manage labels.
You're an issue triage assistant for GitHub issues. Your task is to analyze the issue and select appropriate labels from the provided list.
IMPORTANT: Don't post any comments or messages to the issue. Your only actions are adding or removing labels.
IMPORTANT: Don't post any comments or messages to the issue. Your only action should be to apply labels.
Context:
Issue Information:
- REPO: ${{ github.repository }}
- ISSUE_NUMBER: ${{ github.event.issue.number }}
- EVENT: ${{ github.event_name }}
ALLOWED LABELS — you may ONLY use labels from this list. Never invent new labels.
TASK OVERVIEW:
Type: bug, enhancement, question, documentation, duplicate, invalid
Lifecycle: needs-repro, needs-info
Platform: platform:linux, platform:macos, platform:windows, platform:wsl, platform:ios, platform:android, platform:vscode, platform:intellij, platform:web, platform:aws-bedrock
API: api:bedrock, api:vertex
1. First, fetch the list of labels available in this repository by running: `gh label list`. Run exactly this command with nothing else.
TOOLS:
- `gh issue view NUMBER`: Read the issue title, body, and labels
- `gh issue view NUMBER --comments`: Read the conversation
- `gh search issues QUERY`: Find similar or duplicate issues
- `gh issue edit NUMBER --add-label` / `--remove-label`: Add or remove labels
2. Next, use the GitHub tools to get context about the issue:
- You have access to these tools:
- mcp__github__get_issue: Use this to retrieve the current issue's details including title, description, and existing labels
- mcp__github__get_issue_comments: Use this to read any discussion or additional context provided in the comments
- mcp__github__update_issue: Use this to apply labels to the issue (do not use this for commenting)
- mcp__github__search_issues: Use this to find similar issues that might provide context for proper categorization and to identify potential duplicate issues
- mcp__github__list_issues: Use this to understand patterns in how other issues are labeled
- Start by using mcp__github__get_issue to get the issue details
TASK:
3. Analyze the issue content, considering:
- The issue title and description
- The type of issue (bug report, feature request, question, etc.)
- Technical areas mentioned
- Severity or priority indicators
- User impact
- Components affected
1. Run `gh issue view ${{ github.event.issue.number }}` to read the issue details.
2. Run `gh issue view ${{ github.event.issue.number }} --comments` to read the conversation.
4. Select appropriate labels from the available labels list provided above:
- Choose labels that accurately reflect the issue's nature
- Be specific but comprehensive
- Select priority labels if you can determine urgency (high-priority, med-priority, or low-priority)
- Consider platform labels (android, ios) if applicable
- If you find similar issues using mcp__github__search_issues, consider using a "duplicate" label if appropriate. Only do so if the issue is a duplicate of another OPEN issue.
**If EVENT is "issues" (new issue):**
5. Apply the selected labels:
- Use mcp__github__update_issue to apply your selected labels
- DO NOT post any comments explaining your decision
- DO NOT communicate directly with users
- If no labels are clearly applicable, do not apply any labels
3. First, check if this issue is actually about Claude Code (the CLI/IDE tool). Issues about the Claude API, claude.ai, the Claude app, Anthropic billing, or other Anthropic products should be labeled `invalid`. If invalid, apply only that label and stop.
4. Analyze and apply category labels:
- Type (bug, enhancement, question, etc.)
- Technical areas and platform
- Check for duplicates with `gh search issues`. Only mark as duplicate of OPEN issues.
5. Evaluate lifecycle labels:
- `needs-repro` (bugs only, 7 days): Bug reports without clear steps to reproduce. A good repro has specific, followable steps that someone else could use to see the same issue.
Do NOT apply if the user already provided error messages, logs, file paths, or a description of what they did. Don't require a specific format — narrative descriptions count.
For model behavior issues (e.g. "Claude does X when it should do Y"), don't require traditional repro steps — examples and patterns are sufficient.
- `needs-info` (bugs only, 7 days): The issue needs something from the community before it can progress — e.g. error messages, versions, environment details, or answers to follow-up questions. Don't apply to questions or enhancements.
Do NOT apply if the user already provided version, environment, and error details. If the issue just needs engineering investigation, that's not `needs-info`.
Issues with these labels are automatically closed after the timeout if there's no response.
The goal is to avoid issues lingering without a clear next step.
6. Apply all selected labels:
`gh issue edit ${{ github.event.issue.number }} --add-label "label1" --add-label "label2"`
**If EVENT is "issue_comment" (comment on existing issue):**
3. Evaluate lifecycle labels based on the full conversation:
- If the issue has `needs-repro` or `needs-info` and the missing information has now been provided, remove the label:
`gh issue edit ${{ github.event.issue.number }} --remove-label "needs-repro"`
- If the issue doesn't have lifecycle labels but clearly needs them (e.g., a maintainer asked for repro steps or more details), add the appropriate label.
- Comments like "+1", "me too", "same here", or emoji reactions are NOT the missing information. Only remove labels when substantive details are actually provided.
- Do NOT add or remove category labels (bug, enhancement, etc.) on comment events.
GUIDELINES:
- ONLY use labels from the ALLOWED LABELS list above — never create or guess label names
IMPORTANT GUIDELINES:
- Be thorough in your analysis
- Only select labels from the provided list above
- DO NOT post any comments to the issue
- Be conservative with lifecycle labels — only apply when clearly warranted
- Only apply lifecycle labels (`needs-repro`, `needs-info`) to bugs — never to questions or enhancements
- When in doubt, don't apply a lifecycle label — false positives are worse than missing labels
- Your ONLY action should be to apply labels using mcp__github__update_issue
- It's okay to not add any labels if none are clearly applicable
anthropic_api_key: ${{ secrets.ANTHROPIC_API_KEY }}
claude_args: |
--model claude-opus-4-6
--allowedTools "Bash(gh issue view:*),Bash(gh issue edit:*),Bash(gh search issues:*)"
--model claude-sonnet-4-5-20250929
--mcp-config /tmp/mcp-config/mcp-servers.json
--allowedTools "Bash(gh label list),mcp__github__get_issue,mcp__github__get_issue_comments,mcp__github__update_issue,mcp__github__search_issues,mcp__github__list_issues"

View File

@@ -0,0 +1,157 @@
name: "Manage Stale Issues"
on:
schedule:
# 2am Pacific = 9am UTC (10am UTC during DST)
- cron: "0 10 * * *"
workflow_dispatch:
permissions:
issues: write
concurrency:
group: stale-issue-manager
jobs:
manage-stale-issues:
runs-on: ubuntu-latest
steps:
- name: Manage stale issues
uses: actions/github-script@v7
with:
script: |
const oneMonthAgo = new Date();
oneMonthAgo.setDate(oneMonthAgo.getDate() - 30);
const twoMonthsAgo = new Date();
twoMonthsAgo.setDate(twoMonthsAgo.getDate() - 60);
const warningComment = `This issue has been inactive for 30 days. If the issue is still occurring, please comment to let us know. Otherwise, this issue will be automatically closed in 30 days for housekeeping purposes.`;
const closingComment = `This issue has been automatically closed due to 60 days of inactivity. If you're still experiencing this issue, please open a new issue with updated information.`;
let page = 1;
let hasMore = true;
let totalWarned = 0;
let totalClosed = 0;
let totalLabeled = 0;
while (hasMore) {
// Get open issues sorted by last updated (oldest first)
const { data: issues } = await github.rest.issues.listForRepo({
owner: context.repo.owner,
repo: context.repo.repo,
state: 'open',
sort: 'updated',
direction: 'asc',
per_page: 100,
page: page
});
if (issues.length === 0) {
hasMore = false;
break;
}
for (const issue of issues) {
// Skip if already locked
if (issue.locked) continue;
// Skip pull requests
if (issue.pull_request) continue;
// Check if updated more recently than 30 days ago
const updatedAt = new Date(issue.updated_at);
if (updatedAt > oneMonthAgo) {
// Since issues are sorted by updated_at ascending,
// once we hit a recent issue, all remaining will be recent too
hasMore = false;
break;
}
// Check if issue has autoclose label
const hasAutocloseLabel = issue.labels.some(label =>
typeof label === 'object' && label.name === 'autoclose'
);
try {
// Get comments to check for existing warning
const { data: comments } = await github.rest.issues.listComments({
owner: context.repo.owner,
repo: context.repo.repo,
issue_number: issue.number,
per_page: 100
});
// Find the last comment from github-actions bot
const botComments = comments.filter(comment =>
comment.user && comment.user.login === 'github-actions[bot]' &&
comment.body && comment.body.includes('inactive for 30 days')
);
const lastBotComment = botComments[botComments.length - 1];
if (lastBotComment) {
// Check if the bot comment is older than 30 days (total 60 days of inactivity)
const botCommentDate = new Date(lastBotComment.created_at);
if (botCommentDate < oneMonthAgo) {
// Close the issue - it's been stale for 60+ days
console.log(`Closing issue #${issue.number} (stale for 60+ days): ${issue.title}`);
// Post closing comment
await github.rest.issues.createComment({
owner: context.repo.owner,
repo: context.repo.repo,
issue_number: issue.number,
body: closingComment
});
// Close the issue
await github.rest.issues.update({
owner: context.repo.owner,
repo: context.repo.repo,
issue_number: issue.number,
state: 'closed',
state_reason: 'not_planned'
});
totalClosed++;
}
// If bot comment exists but is recent, issue already has warning
} else if (updatedAt < oneMonthAgo) {
// No bot warning yet, issue is 30+ days old
console.log(`Warning issue #${issue.number} (stale for 30+ days): ${issue.title}`);
// Post warning comment
await github.rest.issues.createComment({
owner: context.repo.owner,
repo: context.repo.repo,
issue_number: issue.number,
body: warningComment
});
totalWarned++;
// Add autoclose label if not present
if (!hasAutocloseLabel) {
await github.rest.issues.addLabels({
owner: context.repo.owner,
repo: context.repo.repo,
issue_number: issue.number,
labels: ['autoclose']
});
totalLabeled++;
}
}
} catch (error) {
console.error(`Failed to process issue #${issue.number}: ${error.message}`);
}
}
page++;
}
console.log(`Summary:`);
console.log(`- Issues warned (30 days stale): ${totalWarned}`);
console.log(`- Issues labeled with autoclose: ${totalLabeled}`);
console.log(`- Issues closed (60 days stale): ${totalClosed}`);

View File

@@ -1,31 +0,0 @@
name: "Issue Sweep"
on:
schedule:
- cron: "0 10,22 * * *"
workflow_dispatch:
permissions:
issues: write
concurrency:
group: daily-issue-sweep
jobs:
sweep:
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Setup Bun
uses: oven-sh/setup-bun@v2
with:
bun-version: latest
- name: Enforce lifecycle timeouts
run: bun run scripts/sweep.ts
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
GITHUB_REPOSITORY_OWNER: ${{ github.repository_owner }}
GITHUB_REPOSITORY_NAME: ${{ github.event.repository.name }}

View File

@@ -1,153 +1,5 @@
# Changelog
## 2.1.41
- Fixed AWS auth refresh hanging indefinitely by adding a 3-minute timeout
- Added `claude auth login`, `claude auth status`, and `claude auth logout` CLI subcommands
- Added Windows ARM64 (win32-arm64) native binary support
- Improved `/rename` to auto-generate session name from conversation context when called without arguments
- Improved narrow terminal layout for prompt footer
- Fixed file resolution failing for @-mentions with anchor fragments (e.g., `@README.md#installation`)
- Fixed FileReadTool blocking the process on FIFOs, `/dev/stdin`, and large files
- Fixed background task notifications not being delivered in streaming Agent SDK mode
- Fixed cursor jumping to end on each keystroke in classifier rule input
- Fixed markdown link display text being dropped for raw URL
- Fixed auto-compact failure error notifications being shown to users
- Fixed permission wait time being included in subagent elapsed time display
- Fixed proactive ticks firing while in plan mode
- Fixed clear stale permission rules when settings change on disk
- Fixed hook blocking errors showing stderr content in UI
## 2.1.39
- Added guard against launching Claude Code inside another Claude Code session
- Fixed Agent Teams using wrong model identifier for Bedrock, Vertex, and Foundry customers
- Fixed a crash when MCP tools return image content during streaming
- Fixed /resume session previews showing raw XML tags instead of readable command names
- Improved model error messages for Bedrock/Vertex/Foundry users with fallback suggestions
- Fixed plugin browse showing misleading "Space to Toggle" hint for already-installed plugins
- Fixed hook blocking errors (exit code 2) not showing stderr to the user
- Added `speed` attribute to OTel events and trace spans for fast mode visibility
- Fixed /resume showing interrupt messages as session titles
- Fixed Opus 4.6 launch announcement showing for Bedrock/Vertex/Foundry users
- Improved error message for many-image dimension limit errors with /compact suggestion
- Fixed structured-outputs beta header being sent unconditionally on Vertex/Bedrock
- Fixed spurious warnings for non-agent markdown files in `.claude/agents/` directory
- Improved terminal rendering performance
- Fixed fatal errors being swallowed instead of displayed
- Fixed process hanging after session close
- Fixed character loss at terminal screen boundary
- Fixed blank lines in verbose transcript view
## 2.1.38
- Fixed VS Code terminal scroll-to-top regression introduced in 2.1.37
- Fixed Tab key queueing slash commands instead of autocompleting
- Fixed bash permission matching for commands using environment variable wrappers
- Fixed text between tool uses disappearing when not using streaming
- Fixed duplicate sessions when resuming in VS Code extension
- Improved heredoc delimiter parsing to prevent command smuggling
- Blocked writes to `.claude/skills` directory in sandbox mode
## 2.1.37
- Fixed an issue where /fast was not immediately available after enabling /extra-usage
## 2.1.36
- Fast mode is now available for Opus 4.6. Learn more at https://code.claude.com/docs/en/fast-mode
## 2.1.34
- Fixed a crash when agent teams setting changed between renders
- Fixed a bug where commands excluded from sandboxing (via `sandbox.excludedCommands` or `dangerouslyDisableSandbox`) could bypass the Bash ask permission rule when `autoAllowBashIfSandboxed` was enabled
## 2.1.33
- Fixed agent teammate sessions in tmux to send and receive messages
- Fixed warnings about agent teams not being available on your current plan
- Added `TeammateIdle` and `TaskCompleted` hook events for multi-agent workflows
- Added support for restricting which sub-agents can be spawned via `Task(agent_type)` syntax in agent "tools" frontmatter
- Added `memory` frontmatter field support for agents, enabling persistent memory with `user`, `project`, or `local` scope
- Added plugin name to skill descriptions and `/skills` menu for better discoverability
- Fixed an issue where submitting a new message while the model was in extended thinking would interrupt the thinking phase
- Fixed an API error that could occur when aborting mid-stream, where whitespace text combined with a thinking block would bypass normalization and produce an invalid request
- Fixed API proxy compatibility issue where 404 errors on streaming endpoints no longer triggered non-streaming fallback
- Fixed an issue where proxy settings configured via `settings.json` environment variables were not applied to WebFetch and other HTTP requests on the Node.js build
- Fixed `/resume` session picker showing raw XML markup instead of clean titles for sessions started with slash commands
- Improved error messages for API connection failures — now shows specific cause (e.g., ECONNREFUSED, SSL errors) instead of generic "Connection error"
- Errors from invalid managed settings are now surfaced
- VSCode: Added support for remote sessions, allowing OAuth users to browse and resume sessions from claude.ai
- VSCode: Added git branch and message count to the session picker, with support for searching by branch name
- VSCode: Fixed scroll-to-bottom under-scrolling on initial session load and session switch
## 2.1.32
- Claude Opus 4.6 is now available!
- Added research preview agent teams feature for multi-agent collaboration (token-intensive feature, requires setting CLAUDE_CODE_EXPERIMENTAL_AGENT_TEAMS=1)
- Claude now automatically records and recalls memories as it works
- Added "Summarize from here" to the message selector, allowing partial conversation summarization.
- Skills defined in `.claude/skills/` within additional directories (`--add-dir`) are now loaded automatically.
- Fixed `@` file completion showing incorrect relative paths when running from a subdirectory
- Updated --resume to re-use --agent value specified in previous conversation by default.
- Fixed: Bash tool no longer throws "Bad substitution" errors when heredocs contain JavaScript template literals like `${index + 1}`, which previously interrupted tool execution
- Skill character budget now scales with context window (2% of context), so users with larger context windows can see more skill descriptions without truncation
- Fixed Thai/Lao spacing vowels (สระ า, ำ) not rendering correctly in the input field
- VSCode: Fixed slash commands incorrectly being executed when pressing Enter with preceding text in the input field
- VSCode: Added spinner when loading past conversations list
## 2.1.31
- Added session resume hint on exit, showing how to continue your conversation later
- Added support for full-width (zenkaku) space input from Japanese IME in checkbox selection
- Fixed PDF too large errors permanently locking up sessions, requiring users to start a new conversation
- Fixed bash commands incorrectly reporting failure with "Read-only file system" errors when sandbox mode was enabled
- Fixed a crash that made sessions unusable after entering plan mode when project config in `~/.claude.json` was missing default fields
- Fixed `temperatureOverride` being silently ignored in the streaming API path, causing all streaming requests to use the default temperature (1) regardless of the configured override
- Fixed LSP shutdown/exit compatibility with strict language servers that reject null params
- Improved system prompts to more clearly guide the model toward using dedicated tools (Read, Edit, Glob, Grep) instead of bash equivalents (`cat`, `sed`, `grep`, `find`), reducing unnecessary bash command usage
- Improved PDF and request size error messages to show actual limits (100 pages, 20MB)
- Reduced layout jitter in the terminal when the spinner appears and disappears during streaming
- Removed misleading Anthropic API pricing from model selector for third-party provider (Bedrock, Vertex, Foundry) users
## 2.1.30
- Added `pages` parameter to the Read tool for PDFs, allowing specific page ranges to be read (e.g., `pages: "1-5"`). Large PDFs (>10 pages) now return a lightweight reference when `@` mentioned instead of being inlined into context.
- Added pre-configured OAuth client credentials for MCP servers that don't support Dynamic Client Registration (e.g., Slack). Use `--client-id` and `--client-secret` with `claude mcp add`.
- Added `/debug` for Claude to help troubleshoot the current session
- Added support for additional `git log` and `git show` flags in read-only mode (e.g., `--topo-order`, `--cherry-pick`, `--format`, `--raw`)
- Added token count, tool uses, and duration metrics to Task tool results
- Added reduced motion mode to the config
- Fixed phantom "(no content)" text blocks appearing in API conversation history, reducing token waste and potential model confusion
- Fixed prompt cache not correctly invalidating when tool descriptions or input schemas changed, only when tool names changed
- Fixed 400 errors that could occur after running `/login` when the conversation contained thinking blocks
- Fixed a hang when resuming sessions with corrupted transcript files containing `parentUuid` cycles
- Fixed rate limit message showing incorrect "/upgrade" suggestion for Max 20x users when extra-usage is unavailable
- Fixed permission dialogs stealing focus while actively typing
- Fixed subagents not being able to access SDK-provided MCP tools because they were not synced to the shared application state
- Fixed a regression where Windows users with a `.bashrc` file could not run bash commands
- Improved memory usage for `--resume` (68% reduction for users with many sessions) by replacing the session index with lightweight stat-based loading and progressive enrichment
- Improved `TaskStop` tool to display the stopped command/task description in the result line instead of a generic "Task stopped" message
- Changed `/model` to execute immediately instead of being queued
- [VSCode] Added multiline input support to the "Other" text input in question dialogs (use Shift+Enter for new lines)
- [VSCode] Fixed duplicate sessions appearing in the session list when starting a new conversation
## 2.1.29
- Fixed startup performance issues when resuming sessions that have `saved_hook_context`
## 2.1.27
- Added tool call failures and denials to debug logs
- Fixed context management validation error for gateway users, ensuring `CLAUDE_CODE_DISABLE_EXPERIMENTAL_BETAS=1` avoids the error
- Added `--from-pr` flag to resume sessions linked to a specific GitHub PR number or URL
- Sessions are now automatically linked to PRs when created via `gh pr create`
- Fixed /context command not displaying colored output
- Fixed status bar duplicating background task indicator when PR status was shown
- Windows: Fixed bash command execution failing for users with `.bashrc` files
- Windows: Fixed console windows flashing when spawning child processes
- VSCode: Fixed OAuth token expiration causing 401 errors after extended sessions
## 2.1.25
- Fixed beta header validation error for gateway users on Bedrock and Vertex, ensuring `CLAUDE_CODE_DISABLE_EXPERIMENTAL_BETAS=1` avoids the error

View File

@@ -1,31 +0,0 @@
# Settings Examples
Example Claude Code settings files, primarily intended for organization-wide deployments. Use these are starting points — adjust them to fit your needs.
These may be applied at any level of the [settings hierarchy](https://code.claude.com/docs/en/settings#settings-files), though certain properties only take effect if specified in enterprise settings (e.g. `strictKnownMarketplaces`, `allowManagedHooksOnly`, `allowManagedPermissionRulesOnly`).
## Configuration Examples
> [!WARNING]
> These examples are community-maintained snippets which may be unsupported or incorrect. You are responsible for the correctness of your own settings configuration.
| Setting | [`settings-lax.json`](./settings-lax.json) | [`settings-strict.json`](./settings-strict.json) | [`settings-bash-sandbox.json`](./settings-bash-sandbox.json) |
|---------|:---:|:---:|:---:|
| Disable `--dangerously-skip-permissions` | ✅ | ✅ | |
| Block plugin marketplaces | ✅ | ✅ | |
| Block user and project-defined permission `allow` / `ask` / `deny` | | ✅ | ✅ |
| Block user and project-defined hooks | | ✅ | |
| Deny web fetch and search tools | | ✅ | |
| Bash tool requires approval | | ✅ | |
| Bash tool must run inside of sandbox | | | ✅ |
## Tips
- Consider merging snippets of the above examples to reach your desired configuration
- Settings files must be valid JSON
- Before deploying configuration files to your organization, test them locally by applying to `managed-settings.json`, `settings.json` or `settings.local.json`
- The `sandbox` property only applies to the `Bash` tool; it does not apply to other tools (like Read, Write, WebSearch, WebFetch, MCPs), hooks, or internal commands
## Full Documentation
See https://code.claude.com/docs/en/settings for complete documentation on all available managed settings.

View File

@@ -1,18 +0,0 @@
{
"allowManagedPermissionRulesOnly": true,
"sandbox": {
"enabled": true,
"autoAllowBashIfSandboxed": false,
"allowUnsandboxedCommands": false,
"excludedCommands": [],
"network": {
"allowUnixSockets": [],
"allowAllUnixSockets": false,
"allowLocalBinding": false,
"allowedDomains": [],
"httpProxyPort": null,
"socksProxyPort": null
},
"enableWeakerNestedSandbox": false
}
}

View File

@@ -1,6 +0,0 @@
{
"permissions": {
"disableBypassPermissionsMode": "disable"
},
"strictKnownMarketplaces": []
}

View File

@@ -1,28 +0,0 @@
{
"permissions": {
"disableBypassPermissionsMode": "disable",
"ask": [
"Bash"
],
"deny": [
"WebSearch",
"WebFetch"
]
},
"allowManagedPermissionRulesOnly": true,
"allowManagedHooksOnly": true,
"strictKnownMarketplaces": [],
"sandbox": {
"autoAllowBashIfSandboxed": false,
"excludedCommands": [],
"network": {
"allowUnixSockets": [],
"allowAllUnixSockets": false,
"allowLocalBinding": false,
"allowedDomains": [],
"httpProxyPort": null,
"socksProxyPort": null
},
"enableWeakerNestedSandbox": false
}
}

View File

@@ -56,15 +56,10 @@ Note: Still review Claude generated PR's.
6. Filter out any issues that were not validated in step 5. This step will give us our list of high signal issues for our review.
7. Output a summary of the review findings to the terminal:
- If issues were found, list each issue with a brief description.
- If no issues were found, state: "No issues found. Checked for bugs and CLAUDE.md compliance."
7. If issues were found, skip to step 8 to post inline comments directly.
If `--comment` argument was NOT provided, stop here. Do not post any GitHub comments.
If `--comment` argument IS provided and NO issues were found, post a summary comment using `gh pr comment` and stop.
If `--comment` argument IS provided and issues were found, continue to step 8.
If NO issues were found, post a summary comment using `gh pr comment` (if `--comment` argument is provided):
"No issues found. Checked for bugs and CLAUDE.md compliance."
8. Create a list of all comments that you plan on leaving. This is only for you to make sure you are comfortable with the comments. Do not post this list anywhere.
@@ -90,7 +85,7 @@ Notes:
- Use gh CLI to interact with GitHub (e.g., fetch pull requests, create comments). Do not use web fetch.
- Create a todo list before starting.
- You must cite and link each issue in inline comments (e.g., if referring to a CLAUDE.md, include a link to it).
- If no issues are found and `--comment` argument is provided, post a comment with the following format:
- If no issues are found, post a comment with the following format:
---

View File

@@ -1,27 +1,28 @@
---
name: frontend-design
description: Create distinctive, production-grade frontend interfaces with high design quality. Use this skill when the user asks to build web components, pages, or applications. Generates creative, polished code that avoids generic AI aesthetics.
description: Create distinctive, production-grade frontend interfaces with high design quality and full accessibility. Use this skill when the user asks to build web components, pages, or applications. Generates creative, polished, accessible code that avoids generic AI aesthetics.
license: Complete terms in LICENSE.txt
---
This skill guides creation of distinctive, production-grade frontend interfaces that avoid generic "AI slop" aesthetics. Implement real working code with exceptional attention to aesthetic details and creative choices.
This skill guides creation of distinctive, production-grade frontend interfaces that avoid generic "AI slop" aesthetics while ensuring full accessibility for all users. Implement real working code with exceptional attention to aesthetic details, creative choices, and inclusive design.
The user provides frontend requirements: a component, page, application, or interface to build. They may include context about the purpose, audience, or technical constraints.
## Design Thinking
Before coding, understand the context and commit to a BOLD aesthetic direction:
- **Purpose**: What problem does this interface solve? Who uses it?
- **Purpose**: What problem does this interface solve? Who uses it? Consider the full spectrum of users including those with disabilities.
- **Tone**: Pick an extreme: brutally minimal, maximalist chaos, retro-futuristic, organic/natural, luxury/refined, playful/toy-like, editorial/magazine, brutalist/raw, art deco/geometric, soft/pastel, industrial/utilitarian, etc. There are so many flavors to choose from. Use these for inspiration but design one that is true to the aesthetic direction.
- **Constraints**: Technical requirements (framework, performance, accessibility).
- **Accessibility**: Accessibility is not a constraint—it's a design opportunity. The best interfaces are both beautiful AND universally usable.
- **Differentiation**: What makes this UNFORGETTABLE? What's the one thing someone will remember?
**CRITICAL**: Choose a clear conceptual direction and execute it with precision. Bold maximalism and refined minimalism both work - the key is intentionality, not intensity.
**CRITICAL**: Choose a clear conceptual direction and execute it with precision. Bold maximalism and refined minimalism both work - the key is intentionality, not intensity. Great design serves everyone.
Then implement working code (HTML/CSS/JS, React, Vue, etc.) that is:
- Production-grade and functional
- Visually striking and memorable
- Cohesive with a clear aesthetic point-of-view
- Fully accessible to all users
- Meticulously refined in every detail
## Frontend Aesthetics Guidelines
@@ -39,4 +40,53 @@ Interpret creatively and make unexpected choices that feel genuinely designed fo
**IMPORTANT**: Match implementation complexity to the aesthetic vision. Maximalist designs need elaborate code with extensive animations and effects. Minimalist or refined designs need restraint, precision, and careful attention to spacing, typography, and subtle details. Elegance comes from executing the vision well.
Remember: Claude is capable of extraordinary creative work. Don't hold back, show what can truly be created when thinking outside the box and committing fully to a distinctive vision.
## Accessibility Excellence
Accessibility is not an afterthought—it's fundamental to great design. Beautiful interfaces must work for everyone. Follow these principles:
### Semantic Structure
- **Use semantic HTML elements**: `<header>`, `<nav>`, `<main>`, `<article>`, `<section>`, `<aside>`, `<footer>`. These provide meaning to assistive technologies.
- **Heading hierarchy**: Use `<h1>` through `<h6>` in logical order. Never skip levels. Screen reader users navigate by headings.
- **Lists and tables**: Use proper `<ul>`, `<ol>`, `<dl>` for lists and `<table>` with `<thead>`, `<tbody>`, `<th scope>` for tabular data.
- **Landmarks**: Ensure main content is in `<main>`, navigation in `<nav>`. Use `role` attributes only when semantic HTML isn't available.
### Keyboard Navigation
- **All interactive elements must be keyboard accessible**: Users must be able to Tab to and activate every button, link, and control.
- **Logical tab order**: Follow visual reading order. Use `tabindex="0"` to make custom elements focusable; avoid positive tabindex values.
- **Visible focus indicators**: Never remove focus outlines without providing a clear alternative. Style `:focus-visible` with distinctive, on-brand styling.
- **Skip links**: Provide "Skip to main content" links for keyboard users to bypass repetitive navigation.
- **Keyboard shortcuts**: For complex interactions, support standard patterns (Escape to close modals, Arrow keys for menus).
### Visual Accessibility
- **Color contrast**: Maintain WCAG AA minimum ratios—4.5:1 for normal text, 3:1 for large text and UI components. Bold color choices CAN meet contrast requirements.
- **Don't rely on color alone**: Use icons, patterns, text labels, or underlines alongside color to convey meaning (errors, status, links).
- **Text sizing**: Use relative units (rem, em) so text scales with user preferences. Never disable zoom.
- **Reduced motion**: Wrap decorative animations in `@media (prefers-reduced-motion: no-preference)`. Essential animations should be subtle.
- **High contrast mode**: Test with `forced-colors` media query. Ensure UI remains usable.
### ARIA & Screen Readers
- **ARIA labels**: Use `aria-label` or `aria-labelledby` for elements without visible text labels. Icon buttons MUST have accessible names.
- **Live regions**: Use `aria-live="polite"` for dynamic content updates (notifications, loading states). Use `aria-live="assertive"` sparingly.
- **State attributes**: Communicate state with `aria-expanded`, `aria-selected`, `aria-checked`, `aria-pressed`, `aria-current`.
- **Hidden content**: Use `aria-hidden="true"` for decorative elements. Use `.visually-hidden` class (not `display: none`) for screen-reader-only text.
- **First rule of ARIA**: Don't use ARIA if native HTML provides the semantics. A `<button>` is better than `<div role="button">`.
### Interactive Components
- **Buttons vs links**: `<button>` for actions, `<a href>` for navigation. Never use `<div>` or `<span>` for interactive elements.
- **Form labels**: Every input needs an associated `<label>` with `for` attribute, or use `aria-label`. Placeholder text is NOT a label.
- **Error handling**: Associate error messages with inputs using `aria-describedby`. Announce errors to screen readers. Don't rely on color alone.
- **Modals and dialogs**: Trap focus inside modals. Return focus to trigger element on close. Use `<dialog>` element or proper ARIA roles.
- **Loading states**: Announce loading with `aria-busy="true"` and `aria-live`. Provide text alternatives to spinners.
### Testing Checklist
Before considering any interface complete, verify:
- [ ] Navigate entire interface using only keyboard (Tab, Enter, Space, Escape, Arrow keys)
- [ ] Test with screen reader (VoiceOver, NVDA, or browser extensions)
- [ ] Check color contrast with browser DevTools or axe
- [ ] Resize text to 200% and ensure layout doesn't break
- [ ] Enable reduced motion and verify animations respect preference
- [ ] Run automated accessibility audit (axe, Lighthouse)
**CRITICAL**: Accessibility and bold design are not in conflict. High contrast ratios work with dramatic color palettes. Semantic structure enhances, not limits, creative layouts. Motion can be both delightful and respectful of preferences. The goal is inclusive excellence.
Remember: Claude is capable of extraordinary creative work. Don't hold back, show what can truly be created when thinking outside the box and committing fully to a distinctive vision that serves all users.

View File

@@ -1,163 +0,0 @@
#!/usr/bin/env bun
// --
const NEW_ISSUE = "https://github.com/anthropics/claude-code/issues/new/choose";
const DRY_RUN = process.argv.includes("--dry-run");
const STALE_DAYS = 14;
const STALE_UPVOTE_THRESHOLD = 10;
const CLOSE_MESSAGE = (reason: string) =>
`Closing for now — ${reason}. Please [open a new issue](${NEW_ISSUE}) if this is still relevant.`;
const lifecycle = [
{ label: "invalid", days: 3, reason: "this doesn't appear to be about Claude Code" },
{ label: "needs-repro", days: 7, reason: "we still need reproduction steps to investigate" },
{ label: "needs-info", days: 7, reason: "we still need a bit more information to move forward" },
{ label: "stale", days: 14, reason: "inactive for too long" },
{ label: "autoclose", days: 14, reason: "inactive for too long" },
];
// --
async function githubRequest<T>(
endpoint: string,
method = "GET",
body?: unknown
): Promise<T> {
const token = process.env.GITHUB_TOKEN;
if (!token) throw new Error("GITHUB_TOKEN required");
const response = await fetch(`https://api.github.com${endpoint}`, {
method,
headers: {
Authorization: `Bearer ${token}`,
Accept: "application/vnd.github.v3+json",
"User-Agent": "sweep",
...(body && { "Content-Type": "application/json" }),
},
...(body && { body: JSON.stringify(body) }),
});
if (!response.ok) {
if (response.status === 404) return {} as T;
const text = await response.text();
throw new Error(`GitHub API ${response.status}: ${text}`);
}
return response.json();
}
// --
async function markStale(owner: string, repo: string) {
const cutoff = new Date();
cutoff.setDate(cutoff.getDate() - STALE_DAYS);
let labeled = 0;
console.log(`\n=== marking stale (${STALE_DAYS}d inactive) ===`);
for (let page = 1; page <= 10; page++) {
const issues = await githubRequest<any[]>(
`/repos/${owner}/${repo}/issues?state=open&sort=updated&direction=asc&per_page=100&page=${page}`
);
if (issues.length === 0) break;
for (const issue of issues) {
if (issue.pull_request) continue;
if (issue.locked) continue;
if (issue.assignees?.length > 0) continue;
const updatedAt = new Date(issue.updated_at);
if (updatedAt > cutoff) return labeled;
const alreadyStale = issue.labels?.some(
(l: any) => l.name === "stale" || l.name === "autoclose"
);
if (alreadyStale) continue;
const isEnhancement = issue.labels?.some(
(l: any) => l.name === "enhancement"
);
const thumbsUp = issue.reactions?.["+1"] ?? 0;
if (isEnhancement && thumbsUp >= STALE_UPVOTE_THRESHOLD) continue;
const base = `/repos/${owner}/${repo}/issues/${issue.number}`;
if (DRY_RUN) {
const age = Math.floor((Date.now() - updatedAt.getTime()) / 86400000);
console.log(`#${issue.number}: would label stale (${age}d inactive) — ${issue.title}`);
} else {
await githubRequest(`${base}/labels`, "POST", { labels: ["stale"] });
console.log(`#${issue.number}: labeled stale — ${issue.title}`);
}
labeled++;
}
}
return labeled;
}
async function closeExpired(owner: string, repo: string) {
let closed = 0;
for (const { label, days, reason } of lifecycle) {
const cutoff = new Date();
cutoff.setDate(cutoff.getDate() - days);
console.log(`\n=== ${label} (${days}d timeout) ===`);
for (let page = 1; page <= 10; page++) {
const issues = await githubRequest<any[]>(
`/repos/${owner}/${repo}/issues?state=open&labels=${label}&sort=updated&direction=asc&per_page=100&page=${page}`
);
if (issues.length === 0) break;
for (const issue of issues) {
if (issue.pull_request) continue;
const base = `/repos/${owner}/${repo}/issues/${issue.number}`;
const events = await githubRequest<any[]>(`${base}/events?per_page=100`);
const labeledAt = events
.filter((e) => e.event === "labeled" && e.label?.name === label)
.map((e) => new Date(e.created_at))
.pop();
if (!labeledAt || labeledAt > cutoff) continue;
if (DRY_RUN) {
const age = Math.floor((Date.now() - labeledAt.getTime()) / 86400000);
console.log(`#${issue.number}: would close (${label}, ${age}d old) — ${issue.title}`);
} else {
await githubRequest(`${base}/comments`, "POST", { body: CLOSE_MESSAGE(reason) });
await githubRequest(base, "PATCH", { state: "closed", state_reason: "not_planned" });
console.log(`#${issue.number}: closed (${label})`);
}
closed++;
}
}
}
return closed;
}
// --
async function main() {
const owner = process.env.GITHUB_REPOSITORY_OWNER;
const repo = process.env.GITHUB_REPOSITORY_NAME;
if (!owner || !repo)
throw new Error("GITHUB_REPOSITORY_OWNER and GITHUB_REPOSITORY_NAME required");
if (DRY_RUN) console.log("DRY RUN — no changes will be made\n");
const labeled = await markStale(owner, repo);
const closed = await closeExpired(owner, repo);
console.log(`\nDone: ${labeled} ${DRY_RUN ? "would be labeled" : "labeled"} stale, ${closed} ${DRY_RUN ? "would be closed" : "closed"}`);
}
main().catch(console.error);
export {};