Initial commit
This commit is contained in:
381
commands/gh-item-add.md
Normal file
381
commands/gh-item-add.md
Normal file
@@ -0,0 +1,381 @@
|
||||
---
|
||||
name: gh-item-add
|
||||
description: Add issues, PRs, or draft items to projects with field assignment
|
||||
tools: Bash, AskUserQuestion, TodoWrite
|
||||
model: inherit
|
||||
---
|
||||
|
||||
# Add Item to GitHub Project
|
||||
|
||||
This command guides you through adding items to GitHub Projects with proper field configuration.
|
||||
|
||||
## Instructions
|
||||
|
||||
### Step 1: Identify Target Project
|
||||
|
||||
Ask the user which project to add items to:
|
||||
|
||||
```bash
|
||||
# List available projects using Python for safe JSON parsing
|
||||
gh project list --owner "@me" --format json | python3 -c "
|
||||
import json, sys
|
||||
projects = json.load(sys.stdin)
|
||||
for p in projects:
|
||||
print(f\"#{p.get('number')} - {p.get('title')}\")
|
||||
"
|
||||
|
||||
# For organization
|
||||
gh project list --owner "org-name" --format json | python3 -c "
|
||||
import json, sys
|
||||
projects = json.load(sys.stdin)
|
||||
for p in projects:
|
||||
print(f\"#{p.get('number')} - {p.get('title')}\")
|
||||
"
|
||||
```
|
||||
|
||||
Get the project ID:
|
||||
```bash
|
||||
PROJECT_ID=$(gh project list --owner "@me" --format json | python3 -c "
|
||||
import json, sys
|
||||
projects = json.load(sys.stdin)
|
||||
target_number = <number> # Replace with actual number
|
||||
for p in projects:
|
||||
if p.get('number') == target_number:
|
||||
print(p.get('id', ''))
|
||||
break
|
||||
")
|
||||
```
|
||||
|
||||
### Step 2: Determine Item Type
|
||||
|
||||
Ask the user what type of item to add:
|
||||
|
||||
1. **Existing Issue**: Add issue from this or another repository
|
||||
2. **Existing PR**: Add pull request from this or another repository
|
||||
3. **Draft Item**: Create new draft item (no issue created)
|
||||
|
||||
### Step 3A: Add Existing Issue or PR
|
||||
|
||||
If adding existing issue/PR:
|
||||
|
||||
1. **Get the URL or number**:
|
||||
- Ask user for issue/PR number or full URL
|
||||
- If just number provided, construct URL: `https://github.com/<owner>/<repo>/issues/<number>`
|
||||
|
||||
2. **Add to project**:
|
||||
```bash
|
||||
gh project item-add <project-number> --owner "<owner>" --url <issue-or-pr-url>
|
||||
```
|
||||
|
||||
3. **Capture item ID** from output or query:
|
||||
```bash
|
||||
ITEM_ID=$(gh project item-list <project-number> --owner "@me" --format json --limit 100 | python3 -c "
|
||||
import json, sys
|
||||
data = json.load(sys.stdin)
|
||||
target_url = '<url>' # Replace with actual URL
|
||||
for item in data.get('items', []):
|
||||
if item.get('content', {}).get('url') == target_url:
|
||||
print(item.get('id', ''))
|
||||
break
|
||||
")
|
||||
```
|
||||
|
||||
### Step 3B: Create Draft Item
|
||||
|
||||
If creating draft item:
|
||||
|
||||
1. **Get title and body**:
|
||||
- Ask user for item title (required)
|
||||
- Ask user for item description/body (optional)
|
||||
|
||||
2. **Create draft**:
|
||||
```bash
|
||||
DRAFT_RESPONSE=$(gh project item-create <project-number> --owner "@me" \
|
||||
--title "<title>" \
|
||||
--body "<body>" \
|
||||
--format json)
|
||||
|
||||
ITEM_ID=$(echo "$DRAFT_RESPONSE" | python3 -c "import json, sys; print(json.load(sys.stdin).get('id', ''))")
|
||||
```
|
||||
|
||||
3. **Note**: Draft items can be converted to issues later when ready
|
||||
|
||||
### Step 4: Get Project Fields
|
||||
|
||||
Fetch available fields for the project:
|
||||
|
||||
```bash
|
||||
FIELDS=$(gh project field-list <project-number> --owner "@me" --format json)
|
||||
|
||||
# Show fields to user using Python
|
||||
echo "$FIELDS" | python3 -c "
|
||||
import json, sys
|
||||
fields = json.load(sys.stdin)
|
||||
for field in fields:
|
||||
print(f\"- {field.get('name')} ({field.get('dataType')})\")
|
||||
"
|
||||
```
|
||||
|
||||
### Step 5: Set Initial Field Values
|
||||
|
||||
Ask user which fields to set initially (optional but recommended):
|
||||
|
||||
#### Set Status
|
||||
```bash
|
||||
# Get Status field ID and options using Python
|
||||
echo "$FIELDS" > /tmp/gh_fields.json
|
||||
|
||||
STATUS_FIELD=$(python3 -c "
|
||||
import json
|
||||
with open('/tmp/gh_fields.json') as f:
|
||||
fields = json.load(f)
|
||||
for field in fields:
|
||||
if field.get('name') == 'Status':
|
||||
print(field.get('id', ''))
|
||||
break
|
||||
")
|
||||
|
||||
# Show options to user
|
||||
python3 -c "
|
||||
import json
|
||||
with open('/tmp/gh_fields.json') as f:
|
||||
fields = json.load(f)
|
||||
for field in fields:
|
||||
if field.get('name') == 'Status':
|
||||
for option in field.get('options', []):
|
||||
print(f\"{option.get('name')}: {option.get('id')}\")
|
||||
break
|
||||
"
|
||||
|
||||
# Then update (after user selects option):
|
||||
gh project item-edit --id $ITEM_ID --project-id $PROJECT_ID \
|
||||
--field-id $STATUS_FIELD --single-select-option-id <option-id>
|
||||
```
|
||||
|
||||
#### Set Priority
|
||||
```bash
|
||||
PRIORITY_FIELD=$(python3 -c "
|
||||
import json
|
||||
with open('/tmp/gh_fields.json') as f:
|
||||
fields = json.load(f)
|
||||
for field in fields:
|
||||
if field.get('name') == 'Priority':
|
||||
print(field.get('id', ''))
|
||||
break
|
||||
")
|
||||
|
||||
# Show options
|
||||
python3 -c "
|
||||
import json
|
||||
with open('/tmp/gh_fields.json') as f:
|
||||
fields = json.load(f)
|
||||
for field in fields:
|
||||
if field.get('name') == 'Priority':
|
||||
for option in field.get('options', []):
|
||||
print(f\"{option.get('name')}: {option.get('id')}\")
|
||||
break
|
||||
"
|
||||
|
||||
# Update after selection
|
||||
gh project item-edit --id $ITEM_ID --project-id $PROJECT_ID \
|
||||
--field-id $PRIORITY_FIELD --single-select-option-id <option-id>
|
||||
```
|
||||
|
||||
#### Set Other Fields (as applicable)
|
||||
|
||||
**Number field** (e.g., Story Points):
|
||||
```bash
|
||||
gh project item-edit --id $ITEM_ID --project-id $PROJECT_ID \
|
||||
--field-id <field-id> --number <value>
|
||||
```
|
||||
|
||||
**Date field** (e.g., Due Date):
|
||||
```bash
|
||||
gh project item-edit --id $ITEM_ID --project-id $PROJECT_ID \
|
||||
--field-id <field-id> --date "YYYY-MM-DD"
|
||||
```
|
||||
|
||||
**Text field** (e.g., Owner):
|
||||
```bash
|
||||
gh project item-edit --id $ITEM_ID --project-id $PROJECT_ID \
|
||||
--field-id <field-id> --text "<value>"
|
||||
```
|
||||
|
||||
**Iteration field** (e.g., Sprint):
|
||||
```bash
|
||||
# Get iteration ID (complex, may need GraphQL)
|
||||
gh project item-edit --id $ITEM_ID --project-id $PROJECT_ID \
|
||||
--field-id <field-id> --iteration-id <iteration-id>
|
||||
```
|
||||
|
||||
### Step 6: Verify Addition
|
||||
|
||||
Confirm the item was added successfully:
|
||||
|
||||
```bash
|
||||
# View the item in the project using Python
|
||||
gh project item-list <project-number> --owner "@me" --format json --limit 100 | python3 -c "
|
||||
import json, sys
|
||||
data = json.load(sys.stdin)
|
||||
target_id = '$ITEM_ID'
|
||||
|
||||
for item in data.get('items', []):
|
||||
if item.get('id') == target_id:
|
||||
content = item.get('content', {})
|
||||
result = {
|
||||
'title': content.get('title'),
|
||||
'type': content.get('type'),
|
||||
'url': content.get('url'),
|
||||
'fieldValues': item.get('fieldValues', [])
|
||||
}
|
||||
print(json.dumps(result, indent=2))
|
||||
break
|
||||
"
|
||||
```
|
||||
|
||||
### Step 7: Provide Summary
|
||||
|
||||
Generate a clear summary for the user:
|
||||
|
||||
```markdown
|
||||
## Item Added Successfully!
|
||||
|
||||
### Item Details
|
||||
- **Title**: [Item Title]
|
||||
- **Type**: [Issue/PR/Draft]
|
||||
- **URL**: [URL if applicable]
|
||||
- **Added to**: [Project Name] (#[Project Number])
|
||||
|
||||
### Initial Field Values
|
||||
- Status: [Value]
|
||||
- Priority: [Value]
|
||||
- [Other fields set...]
|
||||
|
||||
### Next Steps
|
||||
|
||||
1. **View in Project**: [Project URL]
|
||||
2. **Update Additional Fields**: Use project UI or:
|
||||
- Set iteration/sprint
|
||||
- Add estimation (story points)
|
||||
- Assign team member
|
||||
3. **Start Work**: Move to "In Progress" when ready
|
||||
4. **Link to PR**: When you create a PR for this issue
|
||||
|
||||
### Quick Commands
|
||||
- View project: `/gh-project-view`
|
||||
- Update fields: Use project-manager agent
|
||||
- View item details: `gh issue view <number>` or `gh pr view <number>`
|
||||
```
|
||||
|
||||
## Batch Adding Items
|
||||
|
||||
If user wants to add multiple items:
|
||||
|
||||
1. **Get list of items to add**:
|
||||
- From issue search: `gh issue list --repo owner/repo --label feature --limit 20`
|
||||
- From PR list: `gh pr list --repo owner/repo --limit 20`
|
||||
- From user input: Array of issue numbers
|
||||
|
||||
2. **Loop through items**:
|
||||
```bash
|
||||
for ISSUE_NUM in $ISSUES; do
|
||||
ISSUE_URL="https://github.com/<owner>/<repo>/issues/$ISSUE_NUM"
|
||||
gh project item-add <project-number> --owner "@me" --url $ISSUE_URL
|
||||
echo "Added issue #$ISSUE_NUM"
|
||||
done
|
||||
```
|
||||
|
||||
3. **Set common fields** (if requested):
|
||||
- Get all newly added item IDs
|
||||
- Apply same field values to all
|
||||
- Report batch results
|
||||
|
||||
## Smart Field Assignment
|
||||
|
||||
Suggest field values based on context:
|
||||
|
||||
### Auto-Priority from Issue Labels
|
||||
```bash
|
||||
# If issue has 'critical' or 'blocking' label → P0
|
||||
# If issue has 'bug' or 'urgent' label → P1
|
||||
# If issue has 'enhancement' label → P2
|
||||
# Default → P3
|
||||
|
||||
LABELS=$(gh issue view <number> --json labels --jq '.labels[].name')
|
||||
if echo $LABELS | grep -q "critical\|blocking"; then
|
||||
SUGGESTED_PRIORITY="P0"
|
||||
elif echo $LABELS | grep -q "bug\|urgent"; then
|
||||
SUGGESTED_PRIORITY="P1"
|
||||
else
|
||||
SUGGESTED_PRIORITY="P2"
|
||||
fi
|
||||
```
|
||||
|
||||
### Auto-Status from Issue State
|
||||
```bash
|
||||
# If issue is OPEN → Backlog or Todo
|
||||
# If PR is OPEN → In Review
|
||||
# If closed → Done or Archived
|
||||
|
||||
ISSUE_STATE=$(gh issue view <number> --json state --jq '.state')
|
||||
if [ "$ISSUE_STATE" = "OPEN" ]; then
|
||||
SUGGESTED_STATUS="Backlog"
|
||||
else
|
||||
SUGGESTED_STATUS="Done"
|
||||
fi
|
||||
```
|
||||
|
||||
## Important Notes
|
||||
|
||||
- **Item IDs vs Issue Numbers**: Item IDs are project-specific identifiers, different from issue numbers
|
||||
- **Field IDs**: Must fetch field IDs for each project, they're not universal
|
||||
- **Option IDs**: Single-select fields require option IDs, not option names
|
||||
- **Permissions**: Ensure 'project' scope is enabled: `gh auth status`
|
||||
- **Rate Limits**: When batch adding, respect API rate limits (pause if needed)
|
||||
|
||||
## Definition of Done
|
||||
|
||||
- [ ] Target project identified
|
||||
- [ ] Item type determined (issue/PR/draft)
|
||||
- [ ] Item added to project successfully
|
||||
- [ ] Item ID captured
|
||||
- [ ] Initial field values set (at minimum: Status, Priority)
|
||||
- [ ] Addition verified
|
||||
- [ ] Comprehensive summary provided
|
||||
- [ ] Next steps documented
|
||||
|
||||
## Error Handling
|
||||
|
||||
- If project not found: List available projects, let user choose
|
||||
- If issue/PR not found: Verify URL/number, check repository access
|
||||
- If item already in project: Report duplicate, ask if should update fields
|
||||
- If field update fails: Verify field ID and option ID are correct
|
||||
- If permission denied: Check project access and gh auth scopes
|
||||
|
||||
## Special Cases
|
||||
|
||||
### Converting Draft to Issue
|
||||
|
||||
When user is ready to convert draft to real issue:
|
||||
|
||||
```bash
|
||||
# This requires GraphQL API call (gh CLI doesn't have direct command)
|
||||
# Provide instructions for manual conversion via GitHub UI
|
||||
# Or use gh api graphql with mutation
|
||||
```
|
||||
|
||||
### Linking PR to Issue Item
|
||||
|
||||
When adding a PR that closes an issue already in the project:
|
||||
- Note the relationship
|
||||
- Suggest linking them in descriptions
|
||||
- Consider setting up automation for status sync
|
||||
|
||||
### Cross-Repository Items
|
||||
|
||||
When adding items from different repositories:
|
||||
- Verify project is linked to target repository: `gh project link`
|
||||
- If not linked, link it first
|
||||
- Then add items
|
||||
|
||||
Remember: Proper field assignment at addition time saves triage work later. Take the extra minute to set Status and Priority correctly from the start.
|
||||
244
commands/gh-project-create.md
Normal file
244
commands/gh-project-create.md
Normal file
@@ -0,0 +1,244 @@
|
||||
---
|
||||
name: gh-project-create
|
||||
description: Create new GitHub project with guided workflow and field configuration
|
||||
tools: Bash, AskUserQuestion, TodoWrite
|
||||
model: inherit
|
||||
---
|
||||
|
||||
# Create GitHub Project
|
||||
|
||||
This command guides you through creating a new GitHub Project V2 with proper field configuration and best practices.
|
||||
|
||||
## Instructions
|
||||
|
||||
Follow this workflow to create a well-structured project:
|
||||
|
||||
### Step 1: Gather Project Information
|
||||
|
||||
Ask the user for key information:
|
||||
1. **Project Name**: Clear, descriptive title (e.g., "Q1 2025 Roadmap", "Bug Triage", "Sprint 12")
|
||||
2. **Project Type**:
|
||||
- Agile Sprint (for iterative development)
|
||||
- Product Roadmap (for long-term planning)
|
||||
- Bug Tracking (for issue triage)
|
||||
- Custom (user-defined structure)
|
||||
3. **Owner**: "@me" (personal) or organization name
|
||||
4. **Repository Link** (optional): Repository to link to project
|
||||
|
||||
### Step 2: Create the Project
|
||||
|
||||
Use the gh CLI to create the project:
|
||||
|
||||
```bash
|
||||
gh project create --owner "<owner>" --title "<title>" --format json
|
||||
```
|
||||
|
||||
Parse the output to get the project ID and number:
|
||||
```bash
|
||||
# Create project and capture output
|
||||
PROJECT_JSON=$(gh project create --owner "@me" --title "Q1 2025 Roadmap" --format json)
|
||||
|
||||
# Use Python helper to parse JSON safely
|
||||
PROJECT_ID=$(echo "$PROJECT_JSON" | python3 -c "import json, sys; data=json.load(sys.stdin); print(data.get('id', ''))")
|
||||
|
||||
# Get project number from list
|
||||
PROJECT_LIST=$(gh project list --owner "@me" --format json)
|
||||
PROJECT_NUMBER=$(echo "$PROJECT_LIST" | python3 -c "
|
||||
import json, sys
|
||||
data = json.load(sys.stdin)
|
||||
for project in data:
|
||||
if project.get('title') == 'Q1 2025 Roadmap':
|
||||
print(project.get('number', ''))
|
||||
break
|
||||
")
|
||||
```
|
||||
|
||||
### Step 3: Create Core Fields
|
||||
|
||||
Based on the project type, create appropriate fields:
|
||||
|
||||
**IMPORTANT NOTES**:
|
||||
- The "Status" field is a **built-in default field** that already exists in new projects. Do NOT create it.
|
||||
- For SINGLE_SELECT fields, options must be provided at creation time using `--single-select-options`
|
||||
- Options are comma-separated, no spaces after commas
|
||||
|
||||
#### For All Project Types:
|
||||
|
||||
**Priority Field** (Status already exists):
|
||||
```bash
|
||||
# Priority field with options
|
||||
gh project field-create $PROJECT_ID --owner "<owner>" \
|
||||
--data-type SINGLE_SELECT \
|
||||
--name "Priority" \
|
||||
--single-select-options "P0 (Critical),P1 (High),P2 (Medium),P3 (Low)"
|
||||
```
|
||||
|
||||
#### Additional Fields by Type:
|
||||
|
||||
**Agile Sprint**:
|
||||
```bash
|
||||
# Story Points
|
||||
gh project field-create $PROJECT_ID --owner "<owner>" \
|
||||
--data-type NUMBER --name "Story Points"
|
||||
|
||||
# Sprint (Iteration)
|
||||
gh project field-create $PROJECT_ID --owner "<owner>" \
|
||||
--data-type ITERATION --name "Sprint"
|
||||
|
||||
# Team Member
|
||||
gh project field-create $PROJECT_ID --owner "<owner>" \
|
||||
--data-type SINGLE_SELECT \
|
||||
--name "Team Member" \
|
||||
--single-select-options "Alice,Bob,Charlie,Diana"
|
||||
```
|
||||
|
||||
**Product Roadmap**:
|
||||
```bash
|
||||
# Quarter
|
||||
gh project field-create $PROJECT_ID --owner "<owner>" \
|
||||
--data-type SINGLE_SELECT \
|
||||
--name "Quarter" \
|
||||
--single-select-options "Q1 2025,Q2 2025,Q3 2025,Q4 2025"
|
||||
|
||||
# Launch Date
|
||||
gh project field-create $PROJECT_ID --owner "<owner>" \
|
||||
--data-type DATE --name "Launch Date"
|
||||
|
||||
# Impact (customer count)
|
||||
gh project field-create $PROJECT_ID --owner "<owner>" \
|
||||
--data-type NUMBER --name "Impact"
|
||||
|
||||
# Owner
|
||||
gh project field-create $PROJECT_ID --owner "<owner>" \
|
||||
--data-type TEXT --name "Owner"
|
||||
```
|
||||
|
||||
**Bug Tracking**:
|
||||
```bash
|
||||
# Severity
|
||||
gh project field-create $PROJECT_ID --owner "<owner>" \
|
||||
--data-type SINGLE_SELECT \
|
||||
--name "Severity" \
|
||||
--single-select-options "Critical,High,Medium,Low"
|
||||
|
||||
# Component
|
||||
gh project field-create $PROJECT_ID --owner "<owner>" \
|
||||
--data-type SINGLE_SELECT \
|
||||
--name "Component" \
|
||||
--single-select-options "Frontend,Backend,API,Database,Infrastructure"
|
||||
|
||||
# Affected Users
|
||||
gh project field-create $PROJECT_ID --owner "<owner>" \
|
||||
--data-type NUMBER --name "Affected Users"
|
||||
|
||||
# Reported Date
|
||||
gh project field-create $PROJECT_ID --owner "<owner>" \
|
||||
--data-type DATE --name "Reported Date"
|
||||
```
|
||||
|
||||
### Step 4: Link to Repository (if provided)
|
||||
|
||||
**IMPORTANT**: The `--owner` parameter must match the repository owner:
|
||||
- For personal repos: Use your GitHub username (not "@me")
|
||||
- For organization repos: Use the org name
|
||||
|
||||
```bash
|
||||
# Extract owner from repository string (handles owner/repo format)
|
||||
REPO_OWNER=$(echo "$REPOSITORY" | python3 -c "
|
||||
import sys
|
||||
repo = sys.stdin.read().strip()
|
||||
# Handle owner/repo format
|
||||
if '/' in repo:
|
||||
# Strip any URL prefix if present
|
||||
if 'github.com/' in repo:
|
||||
repo = repo.split('github.com/')[-1]
|
||||
owner = repo.split('/')[0]
|
||||
print(owner)
|
||||
else:
|
||||
print(repo)
|
||||
")
|
||||
|
||||
# Link project to repository
|
||||
gh project link $PROJECT_NUMBER --owner "$REPO_OWNER" --repo "$REPOSITORY"
|
||||
|
||||
# Example for specific cases:
|
||||
# Personal repo: gh project link $PROJECT_NUMBER --owner "your-username" --repo your-username/repo-name
|
||||
# Organization repo: gh project link $PROJECT_NUMBER --owner "org-name" --repo org-name/repo-name
|
||||
```
|
||||
|
||||
### Step 5: Generate Setup Summary
|
||||
|
||||
Provide the user with a comprehensive summary:
|
||||
|
||||
```markdown
|
||||
## Project Created Successfully!
|
||||
|
||||
### Project Details
|
||||
- **Name**: [Project Name]
|
||||
- **Number**: #[Project Number]
|
||||
- **Owner**: [Owner]
|
||||
- **URL**: https://github.com/users/[owner]/projects/[number] (or org URL)
|
||||
|
||||
### Fields Created
|
||||
- Status (Built-in default field - already exists)
|
||||
- Priority (Single Select with P0-P3 options)
|
||||
- [Additional fields based on type...]
|
||||
|
||||
### Next Steps
|
||||
|
||||
1. **Customize Status Field Options** (via GitHub UI):
|
||||
- Status field exists by default with basic options
|
||||
- Go to project settings to customize options if needed
|
||||
- Recommended options by type:
|
||||
* Agile: Backlog, Todo, In Progress, In Review, Done
|
||||
* Roadmap: Idea, Planned, In Development, Launched
|
||||
* Bug Tracking: New, Triaged, In Progress, Fixed, Verified
|
||||
|
||||
2. **Create Views**:
|
||||
- Board View: Group by Status for kanban workflow
|
||||
- Table View: Sort by Priority for backlog management
|
||||
- [Additional views based on type...]
|
||||
|
||||
3. **Add Items**:
|
||||
- Use `/gh-item-add` to add existing issues/PRs
|
||||
- Use `gh project item-create` for draft items
|
||||
- Or manually add via GitHub UI
|
||||
|
||||
4. **Setup Automation** (optional):
|
||||
- Configure auto-archive for Done items
|
||||
- Set default field values for new items
|
||||
- Link to GitHub Actions for status sync
|
||||
|
||||
### Project Type: [Type]
|
||||
[Type-specific guidance on usage, workflow, and best practices]
|
||||
```
|
||||
|
||||
## Important Notes
|
||||
|
||||
- **Status Field**: The "Status" field is a built-in default field that already exists in new projects. Do NOT attempt to create it.
|
||||
- **SINGLE_SELECT Fields**: Options MUST be provided at creation time using `--single-select-options` parameter. Options cannot be added later via CLI.
|
||||
- **Field Options Format**: Comma-separated, no spaces after commas: `"Option1,Option2,Option3"`
|
||||
- **Repository Linking**: The `--owner` parameter must match the repository owner exactly (cannot use "@me" for org repos)
|
||||
- **Validation**: Verify the project was created successfully by viewing it: `gh project view [number] --owner [owner]`
|
||||
- **Permissions**: Ensure the user has the 'project' scope: `gh auth status`
|
||||
- If missing: `gh auth refresh -s project`
|
||||
|
||||
## Definition of Done
|
||||
|
||||
- [ ] Project created with unique title
|
||||
- [ ] Project ID and number captured
|
||||
- [ ] Priority field created with options
|
||||
- [ ] Type-specific fields created
|
||||
- [ ] Repository linked (if applicable)
|
||||
- [ ] Comprehensive setup summary provided
|
||||
- [ ] Next steps documented for the user
|
||||
- [ ] Status field customization instructions provided (if needed)
|
||||
|
||||
## Error Handling
|
||||
|
||||
- If `gh auth` fails: Guide user to run `gh auth refresh -s project`
|
||||
- If project creation fails: Check for duplicate names, verify owner exists
|
||||
- If field creation fails: Verify project ID is correct, check permissions
|
||||
- If linking fails: Verify repository exists and user has access
|
||||
|
||||
Remember: A well-structured project from the start saves hours of reorganization later. Take time to set it up right!
|
||||
482
commands/gh-project-status.md
Normal file
482
commands/gh-project-status.md
Normal file
@@ -0,0 +1,482 @@
|
||||
---
|
||||
name: gh-project-status
|
||||
description: Generate comprehensive status report of project progress and metrics
|
||||
tools: Bash, Read, Write
|
||||
model: inherit
|
||||
---
|
||||
|
||||
# Generate Project Status Report
|
||||
|
||||
This command generates comprehensive status reports for GitHub Projects with metrics, insights, and actionable items.
|
||||
|
||||
## Instructions
|
||||
|
||||
### Step 1: Identify Project and Timeframe
|
||||
|
||||
Ask the user:
|
||||
1. Which project to report on (name or number)
|
||||
2. Timeframe for analysis (optional):
|
||||
- Current sprint/iteration
|
||||
- Last 7 days
|
||||
- Last 30 days
|
||||
- All time (default)
|
||||
|
||||
### Step 2: Gather Project Data
|
||||
|
||||
Collect comprehensive project information:
|
||||
|
||||
```bash
|
||||
# Get project metadata
|
||||
PROJECT_DATA=$(gh project view <number> --owner "@me" --format json)
|
||||
PROJECT_TITLE=$(echo $PROJECT_DATA | jq -r '.title')
|
||||
PROJECT_URL=$(echo $PROJECT_DATA | jq -r '.url')
|
||||
|
||||
# Get all fields
|
||||
FIELDS=$(gh project field-list <number> --owner "@me" --format json --limit 50)
|
||||
|
||||
# Get all items
|
||||
ITEMS=$(gh project item-list <number> --owner "@me" --format json --limit 100)
|
||||
TOTAL_ITEMS=$(echo $ITEMS | jq '.items | length')
|
||||
```
|
||||
|
||||
### Step 3: Calculate Core Metrics
|
||||
|
||||
#### Status Distribution
|
||||
```bash
|
||||
STATUS_METRICS=$(echo $ITEMS | jq -r '
|
||||
[.items[].fieldValues[] | select(.name=="Status")] |
|
||||
group_by(.name) |
|
||||
map({
|
||||
status: .[0].name,
|
||||
count: length,
|
||||
percentage: ((length / ('$TOTAL_ITEMS' | tonumber)) * 100 | floor)
|
||||
})
|
||||
')
|
||||
```
|
||||
|
||||
#### Priority Breakdown
|
||||
```bash
|
||||
PRIORITY_METRICS=$(echo $ITEMS | jq -r '
|
||||
[.items[].fieldValues[] | select(.name=="Priority")] |
|
||||
group_by(.name) |
|
||||
map({
|
||||
priority: .[0].name,
|
||||
count: length
|
||||
})
|
||||
')
|
||||
```
|
||||
|
||||
#### Item Types
|
||||
```bash
|
||||
ISSUE_COUNT=$(echo $ITEMS | jq '[.items[] | select(.content.type=="Issue")] | length')
|
||||
PR_COUNT=$(echo $ITEMS | jq '[.items[] | select(.content.type=="PullRequest")] | length')
|
||||
DRAFT_COUNT=$(echo $ITEMS | jq '[.items[] | select(.content.type=="DraftIssue")] | length')
|
||||
```
|
||||
|
||||
### Step 4: Identify Critical Items
|
||||
|
||||
#### Blockers & High Priority
|
||||
```bash
|
||||
# P0 items (critical)
|
||||
P0_ITEMS=$(echo $ITEMS | jq -r '
|
||||
.items[] |
|
||||
select(.fieldValues[] | select(.name=="Priority" and .name=="P0")) |
|
||||
{
|
||||
title: .content.title,
|
||||
number: .content.number,
|
||||
status: (.fieldValues[] | select(.name=="Status") | .name),
|
||||
url: .content.url
|
||||
}
|
||||
')
|
||||
|
||||
P0_COUNT=$(echo $P0_ITEMS | jq -s 'length')
|
||||
|
||||
# P1 items not in progress
|
||||
P1_TODO=$(echo $ITEMS | jq -r '
|
||||
.items[] |
|
||||
select(
|
||||
(.fieldValues[] | select(.name=="Priority" and .name=="P1")) and
|
||||
(.fieldValues[] | select(.name=="Status" and (.name=="Backlog" or .name=="Todo")))
|
||||
) |
|
||||
{
|
||||
title: .content.title,
|
||||
number: .content.number,
|
||||
status: (.fieldValues[] | select(.name=="Status") | .name)
|
||||
}
|
||||
')
|
||||
|
||||
P1_TODO_COUNT=$(echo $P1_TODO | jq -s 'length')
|
||||
```
|
||||
|
||||
#### Stale Items
|
||||
```bash
|
||||
# Items in progress > 7 days without update
|
||||
THRESHOLD_DATE=$(date -v-7d +%Y-%m-%d)
|
||||
|
||||
STALE_ITEMS=$(echo $ITEMS | jq -r --arg threshold "$THRESHOLD_DATE" '
|
||||
.items[] |
|
||||
select(
|
||||
(.fieldValues[] | select(.name=="Status" and (.name=="In Progress" or .name=="In Review"))) and
|
||||
(.content.updatedAt | split("T")[0] < $threshold)
|
||||
) |
|
||||
{
|
||||
title: .content.title,
|
||||
number: .content.number,
|
||||
status: (.fieldValues[] | select(.name=="Status") | .name),
|
||||
lastUpdated: (.content.updatedAt | split("T")[0]),
|
||||
daysSinceUpdate: (now - (.content.updatedAt | fromdateiso8601)) / 86400 | floor
|
||||
}
|
||||
')
|
||||
|
||||
STALE_COUNT=$(echo $STALE_ITEMS | jq -s 'length')
|
||||
```
|
||||
|
||||
#### Items in Review
|
||||
```bash
|
||||
REVIEW_ITEMS=$(echo $ITEMS | jq -r '
|
||||
.items[] |
|
||||
select(.fieldValues[] | select(.name=="Status" and .name=="In Review")) |
|
||||
{
|
||||
title: .content.title,
|
||||
number: .content.number,
|
||||
type: .content.type,
|
||||
url: .content.url
|
||||
}
|
||||
')
|
||||
|
||||
REVIEW_COUNT=$(echo $REVIEW_ITEMS | jq -s 'length')
|
||||
```
|
||||
|
||||
### Step 5: Calculate Velocity (if applicable)
|
||||
|
||||
If project has Story Points or similar estimation:
|
||||
|
||||
```bash
|
||||
# Completed items with story points
|
||||
COMPLETED_POINTS=$(echo $ITEMS | jq '
|
||||
[.items[] |
|
||||
select(.fieldValues[] | select(.name=="Status" and .name=="Done")) |
|
||||
.fieldValues[] |
|
||||
select(.name=="Story Points") |
|
||||
.number
|
||||
] | add // 0
|
||||
')
|
||||
|
||||
# In progress points
|
||||
IN_PROGRESS_POINTS=$(echo $ITEMS | jq '
|
||||
[.items[] |
|
||||
select(.fieldValues[] | select(.name=="Status" and .name=="In Progress")) |
|
||||
.fieldValues[] |
|
||||
select(.name=="Story Points") |
|
||||
.number
|
||||
] | add // 0
|
||||
')
|
||||
|
||||
# Total estimated points
|
||||
TOTAL_POINTS=$(echo $ITEMS | jq '
|
||||
[.items[] |
|
||||
.fieldValues[] |
|
||||
select(.name=="Story Points") |
|
||||
.number
|
||||
] | add // 0
|
||||
')
|
||||
|
||||
# Completion percentage
|
||||
if [ "$TOTAL_POINTS" -gt 0 ]; then
|
||||
COMPLETION_PCT=$(echo "scale=1; ($COMPLETED_POINTS / $TOTAL_POINTS) * 100" | bc)
|
||||
else
|
||||
COMPLETION_PCT="N/A"
|
||||
fi
|
||||
```
|
||||
|
||||
### Step 6: Analyze Health Indicators
|
||||
|
||||
Calculate project health score based on:
|
||||
|
||||
```bash
|
||||
# Work distribution (ideal: balanced across statuses)
|
||||
# Priority coverage (good: all items have priority)
|
||||
# Stale item ratio (good: < 10% stale)
|
||||
# Review bottleneck (warning: > 5 items in review)
|
||||
# P0/P1 attention (critical: all P0/P1 should be active)
|
||||
|
||||
UNPRIORITIZED=$(echo $ITEMS | jq '
|
||||
[.items[] |
|
||||
select(.fieldValues[] | select(.name=="Priority") | not)
|
||||
] | length
|
||||
')
|
||||
|
||||
UNPRIORITIZED_PCT=$(echo "scale=1; ($UNPRIORITIZED / $TOTAL_ITEMS) * 100" | bc)
|
||||
|
||||
# Health score (0-100)
|
||||
HEALTH_SCORE=100
|
||||
[ "$STALE_COUNT" -gt $(echo "$TOTAL_ITEMS * 0.1" | bc | cut -d. -f1) ] && HEALTH_SCORE=$((HEALTH_SCORE - 20))
|
||||
[ "$REVIEW_COUNT" -gt 5 ] && HEALTH_SCORE=$((HEALTH_SCORE - 15))
|
||||
[ "$P1_TODO_COUNT" -gt 3 ] && HEALTH_SCORE=$((HEALTH_SCORE - 15))
|
||||
[ "$UNPRIORITIZED" -gt 0 ] && HEALTH_SCORE=$((HEALTH_SCORE - 10))
|
||||
```
|
||||
|
||||
### Step 7: Generate Comprehensive Report
|
||||
|
||||
Present the analysis in a clear, executive-friendly format:
|
||||
|
||||
```markdown
|
||||
# Project Status Report
|
||||
## [Project Title]
|
||||
|
||||
**Generated**: [Current Date/Time]
|
||||
**Project**: #[Number] | [URL]
|
||||
**Timeframe**: [Specified timeframe or "All time"]
|
||||
|
||||
---
|
||||
|
||||
## Executive Summary
|
||||
|
||||
**Overall Health**: [Excellent/Good/Fair/Poor] ([Health Score]/100)
|
||||
|
||||
**Key Metrics**:
|
||||
- Total Items: [count]
|
||||
- Completion: [X]% ([Completed]/[Total] points) [if applicable]
|
||||
- Active Work: [In Progress count] items
|
||||
- Awaiting Review: [Review count] items
|
||||
- Blocked/Critical: [P0 count] items
|
||||
|
||||
**Status**: [1-2 sentence summary of project state]
|
||||
|
||||
---
|
||||
|
||||
## 📊 Item Distribution
|
||||
|
||||
### By Status
|
||||
| Status | Count | Percentage |
|
||||
|--------|-------|------------|
|
||||
[For each status: | Status | X | Y% |]
|
||||
| **Total** | **[Total]** | **100%** |
|
||||
|
||||
### By Priority
|
||||
| Priority | Count | In Progress | Done |
|
||||
|----------|-------|-------------|------|
|
||||
[For each priority: | PX | X | Y | Z |]
|
||||
|
||||
### By Type
|
||||
- Issues: [count]
|
||||
- Pull Requests: [count]
|
||||
- Draft Items: [count]
|
||||
|
||||
---
|
||||
|
||||
## 🎯 Velocity & Progress
|
||||
|
||||
[If story points available:]
|
||||
- **Sprint Goal**: [X] points
|
||||
- **Completed**: [Y] points ([Z]%)
|
||||
- **In Progress**: [A] points
|
||||
- **Remaining**: [B] points
|
||||
|
||||
**Projected Completion**: [On track / At risk / Behind]
|
||||
|
||||
[Visual progress bar:]
|
||||
```
|
||||
Backlog Todo In Progress Review Done
|
||||
▓ ▓ ▓ ▓ ████████
|
||||
[X] [Y] [Z] [A] [B]
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## ⚠️ Items Requiring Attention
|
||||
|
||||
### 🚨 Critical (P0) - [count]
|
||||
[If any P0 items exist, list them with status:]
|
||||
- #[number] [title] - Status: [status]
|
||||
[Otherwise: ✅ No critical items]
|
||||
|
||||
### ⏰ High Priority Not Started (P1) - [count]
|
||||
[If any P1 in Backlog/Todo:]
|
||||
- #[number] [title] - [status]
|
||||
[Otherwise: ✅ All P1 items are in progress or done]
|
||||
|
||||
### 🐌 Stale Items (>7 days) - [count]
|
||||
[If any stale items:]
|
||||
- #[number] [title] - In Progress for [X] days
|
||||
[Otherwise: ✅ No stale items]
|
||||
|
||||
### 👀 Awaiting Review - [count]
|
||||
[If items in review:]
|
||||
- #[number] [title] - [type] - [URL]
|
||||
[Otherwise: ✅ No items in review]
|
||||
|
||||
### 🏷️ Missing Priority - [count]
|
||||
[If unprioritized items exist:]
|
||||
- [X]% of items lack priority assignment
|
||||
- Action: Run `/gh-project-triage` to assign priorities
|
||||
[Otherwise: ✅ All items prioritized]
|
||||
|
||||
---
|
||||
|
||||
## 📈 Trends & Insights
|
||||
|
||||
### Work Distribution
|
||||
[Analysis of status distribution:]
|
||||
- Healthy backlog: [Yes/No] ([X] items ready for work)
|
||||
- Work in progress: [Appropriate/Too high/Too low] ([Y] items)
|
||||
- Review bottleneck: [Yes/No] ([Z] items awaiting review)
|
||||
|
||||
### Priority Balance
|
||||
- Critical items: [Appropriate/High] attention
|
||||
- High priority: [Well-managed/Needs attention]
|
||||
- Backlog refinement: [Current/Overdue]
|
||||
|
||||
### Completion Rate
|
||||
[If velocity data available:]
|
||||
- Current sprint: [X]% complete
|
||||
- Average velocity: [Y] points/sprint
|
||||
- Projected completion: [Date or "On track"]
|
||||
|
||||
---
|
||||
|
||||
## 🎬 Recommended Actions
|
||||
|
||||
1. **Immediate** (Do today):
|
||||
[List urgent actions based on analysis, e.g.:]
|
||||
- Review and prioritize [X] P0 items
|
||||
- Unblock [Y] stale items in progress
|
||||
- Review [Z] PRs awaiting review
|
||||
|
||||
2. **Short-term** (This week):
|
||||
[List important actions:]
|
||||
- Triage [X] unprioritized items
|
||||
- Start work on [Y] P1 items in backlog
|
||||
- Archive [Z] completed items from last sprint
|
||||
|
||||
3. **Ongoing**:
|
||||
- Maintain < 5 items in review
|
||||
- Keep P0/P1 items actively progressing
|
||||
- Regular backlog refinement (weekly)
|
||||
|
||||
---
|
||||
|
||||
## 📅 Next Review
|
||||
|
||||
**Recommended**: [Date - 1 week from now]
|
||||
|
||||
**Focus areas for next review**:
|
||||
- P0 item resolution
|
||||
- Velocity trend
|
||||
- Stale item reduction
|
||||
|
||||
---
|
||||
|
||||
## Quick Actions
|
||||
|
||||
- View project: [URL]
|
||||
- Triage backlog: `/gh-project-triage`
|
||||
- Add items: `/gh-item-add`
|
||||
- Update items: Use project-manager agent
|
||||
|
||||
---
|
||||
|
||||
*Report generated by GitHub Project Manager plugin*
|
||||
```
|
||||
|
||||
### Step 8: Offer Drill-Down Options
|
||||
|
||||
After presenting the report, ask if the user wants:
|
||||
- Detailed list of items in specific status
|
||||
- Individual item analysis
|
||||
- Trend comparison (if historical data available)
|
||||
- Export report to file
|
||||
- Share report (formatted for team distribution)
|
||||
|
||||
## Advanced Analysis
|
||||
|
||||
### Cycle Time Analysis
|
||||
If timestamp data available, calculate:
|
||||
- Average time from Todo → Done
|
||||
- Average time in each status
|
||||
- Bottleneck identification
|
||||
|
||||
### Burndown Chart (text-based)
|
||||
For sprint projects with story points:
|
||||
```
|
||||
Sprint Burndown (Story Points)
|
||||
|
||||
40 |•
|
||||
35 | •
|
||||
30 | ••
|
||||
25 | ••
|
||||
20 | •••
|
||||
15 | ••
|
||||
10 | ••
|
||||
5 | •
|
||||
0 |______________•____
|
||||
D1 D3 D5 D7 D9 D11 D13
|
||||
|
||||
Ideal: --- | Actual: •••
|
||||
```
|
||||
|
||||
### Team Contribution
|
||||
If assignee data available:
|
||||
```
|
||||
Items by Team Member:
|
||||
- Alice: 8 (5 done, 2 in progress, 1 in review)
|
||||
- Bob: 6 (4 done, 2 in progress)
|
||||
- Charlie: 5 (3 done, 2 in review)
|
||||
- Unassigned: 12
|
||||
```
|
||||
|
||||
## Export Options
|
||||
|
||||
### Markdown File
|
||||
```bash
|
||||
# Save report to file
|
||||
cat > "project-status-$(date +%Y-%m-%d).md" <<EOF
|
||||
[Report content]
|
||||
EOF
|
||||
```
|
||||
|
||||
### CSV Export
|
||||
```bash
|
||||
# Export items to CSV
|
||||
echo $ITEMS | jq -r '
|
||||
["Title", "Number", "Status", "Priority", "Type", "URL"],
|
||||
(.items[] | [
|
||||
.content.title,
|
||||
.content.number // "draft",
|
||||
(.fieldValues[] | select(.name=="Status") | .name),
|
||||
(.fieldValues[] | select(.name=="Priority") | .name // "Unset"),
|
||||
.content.type,
|
||||
.content.url // ""
|
||||
]) | @csv
|
||||
' > project-items.csv
|
||||
```
|
||||
|
||||
## Important Notes
|
||||
|
||||
- **Refresh Data**: Fetch latest data at report time
|
||||
- **Caching**: For large projects, consider caching field IDs
|
||||
- **Pagination**: Handle projects with >100 items
|
||||
- **Privacy**: Don't expose sensitive item details in team reports
|
||||
- **Frequency**: Weekly status reports are typical
|
||||
- **Stakeholder Version**: Create executive summary for non-technical stakeholders
|
||||
|
||||
## Definition of Done
|
||||
|
||||
- [ ] Project identified and data fetched
|
||||
- [ ] Core metrics calculated (status, priority, types)
|
||||
- [ ] Critical items identified (P0, stale, blocked)
|
||||
- [ ] Velocity calculated (if applicable)
|
||||
- [ ] Health score determined
|
||||
- [ ] Comprehensive report generated
|
||||
- [ ] Actionable recommendations provided
|
||||
- [ ] Drill-down options offered
|
||||
- [ ] Export option offered if requested
|
||||
|
||||
## Error Handling
|
||||
|
||||
- If no items: Report empty project, suggest adding items
|
||||
- If missing fields: Handle gracefully, note in report
|
||||
- If API limits hit: Show partial results, suggest retry
|
||||
- If calculations fail: Use fallback values, note in report
|
||||
|
||||
Remember: A great status report tells a story - where we are, how we got here, and what we should do next. Make it scannable, actionable, and insightful.
|
||||
429
commands/gh-project-triage.md
Normal file
429
commands/gh-project-triage.md
Normal file
@@ -0,0 +1,429 @@
|
||||
---
|
||||
name: gh-project-triage
|
||||
description: Triage project items and ensure proper status and priority assignment
|
||||
tools: Bash, AskUserQuestion, TodoWrite
|
||||
model: inherit
|
||||
---
|
||||
|
||||
# Triage GitHub Project Items
|
||||
|
||||
This command facilitates systematic triage of project items, ensuring all items have proper priority, status, and other critical field assignments.
|
||||
|
||||
## Instructions
|
||||
|
||||
### Step 1: Initialize Triage Session
|
||||
|
||||
Ask the user what scope of triage they want:
|
||||
|
||||
1. **Full Triage**: Review all items in the project
|
||||
2. **Backlog Only**: Focus on Backlog status items
|
||||
3. **Unprioritized**: Only items missing priority
|
||||
4. **New Items**: Items added in last N days
|
||||
5. **Custom Filter**: User-specified criteria
|
||||
|
||||
### Step 2: Gather Project Data
|
||||
|
||||
```bash
|
||||
# Get project info
|
||||
PROJECT_DATA=$(gh project view <number> --owner "@me" --format json)
|
||||
PROJECT_ID=$(echo $PROJECT_DATA | jq -r '.id')
|
||||
PROJECT_TITLE=$(echo $PROJECT_DATA | jq -r '.title')
|
||||
|
||||
# Get fields and options
|
||||
FIELDS=$(gh project field-list <number> --owner "@me" --format json)
|
||||
|
||||
# Extract field IDs
|
||||
STATUS_FIELD=$(echo $FIELDS | jq -r '.[] | select(.name=="Status") | .id')
|
||||
PRIORITY_FIELD=$(echo $FIELDS | jq -r '.[] | select(.name=="Priority") | .id')
|
||||
|
||||
# Get field options
|
||||
STATUS_OPTIONS=$(echo $FIELDS | jq -r '.[] | select(.name=="Status") | .options[] | {name: .name, id: .id}')
|
||||
PRIORITY_OPTIONS=$(echo $FIELDS | jq -r '.[] | select(.name=="Priority") | .options[] | {name: .name, id: .id}')
|
||||
|
||||
# Get all items
|
||||
ITEMS=$(gh project item-list <number> --owner "@me" --format json --limit 100)
|
||||
```
|
||||
|
||||
### Step 3: Filter Items Based on Triage Scope
|
||||
|
||||
```bash
|
||||
# Example: Unprioritized items
|
||||
TRIAGE_ITEMS=$(echo $ITEMS | jq -r '
|
||||
.items[] |
|
||||
select(
|
||||
(.fieldValues[] | select(.name=="Priority")) == null
|
||||
) |
|
||||
{
|
||||
id: .id,
|
||||
title: .content.title,
|
||||
number: .content.number,
|
||||
type: .content.type,
|
||||
url: .content.url,
|
||||
body: .content.body,
|
||||
labels: .content.labels,
|
||||
status: (.fieldValues[] | select(.name=="Status") | .name)
|
||||
}
|
||||
')
|
||||
|
||||
TRIAGE_COUNT=$(echo $TRIAGE_ITEMS | jq -s 'length')
|
||||
```
|
||||
|
||||
### Step 4: Present Triage Summary
|
||||
|
||||
Show user what needs triage:
|
||||
|
||||
```markdown
|
||||
## Triage Summary
|
||||
|
||||
**Project**: [Project Title] (#[Number])
|
||||
**Scope**: [Triage scope selected]
|
||||
**Items to Triage**: [Count]
|
||||
|
||||
### Breakdown
|
||||
- Unprioritized: [X]
|
||||
- Without status: [Y]
|
||||
- Missing estimation: [Z] (if applicable)
|
||||
- No assignee: [A] (if applicable)
|
||||
|
||||
**Proceeding with triage...**
|
||||
```
|
||||
|
||||
### Step 5: Interactive Triage Loop
|
||||
|
||||
For each item requiring triage:
|
||||
|
||||
#### A. Present Item Details
|
||||
|
||||
```markdown
|
||||
---
|
||||
## Item [current]/[total]
|
||||
|
||||
**Title**: [Item title]
|
||||
**Number**: #[number] (or "draft")
|
||||
**Type**: [Issue/PR/Draft]
|
||||
**Current Status**: [Status or "Not set"]
|
||||
**Current Priority**: [Priority or "Not set"]
|
||||
**URL**: [URL if available]
|
||||
|
||||
### Description
|
||||
[First 200 chars of body...]
|
||||
|
||||
### Labels
|
||||
[List issue labels if any]
|
||||
|
||||
### Context Hints
|
||||
[Analyze title/description for priority hints:]
|
||||
- Contains "critical", "blocking", "urgent" → Suggests P0/P1
|
||||
- Contains "bug", "error", "broken" → Suggests P1/P2
|
||||
- Contains "enhancement", "feature" → Suggests P2/P3
|
||||
- Contains "nice-to-have", "someday" → Suggests P3
|
||||
```
|
||||
|
||||
#### B. Assess Priority
|
||||
|
||||
Use intelligent priority suggestion:
|
||||
|
||||
```bash
|
||||
# Auto-suggest priority based on keywords
|
||||
TITLE_LOWER=$(echo "$ITEM_TITLE" | tr '[:upper:]' '[:lower:]')
|
||||
BODY_LOWER=$(echo "$ITEM_BODY" | tr '[:upper:]' '[:lower:]')
|
||||
COMBINED="$TITLE_LOWER $BODY_LOWER"
|
||||
|
||||
if echo "$COMBINED" | grep -qE "critical|blocking|urgent|security|production down|data loss"; then
|
||||
SUGGESTED_PRIORITY="P0"
|
||||
REASON="Critical keywords detected (blocking, security, urgent)"
|
||||
elif echo "$COMBINED" | grep -qE "bug|error|broken|failing|regression"; then
|
||||
SUGGESTED_PRIORITY="P1"
|
||||
REASON="Bug-related keywords detected"
|
||||
elif echo "$COMBINED" | grep -qE "enhancement|feature|improve"; then
|
||||
SUGGESTED_PRIORITY="P2"
|
||||
REASON="Enhancement/feature keywords detected"
|
||||
else
|
||||
SUGGESTED_PRIORITY="P3"
|
||||
REASON="Standard priority (no high-urgency indicators)"
|
||||
fi
|
||||
|
||||
# Check issue labels for additional hints
|
||||
if echo "$LABELS" | grep -qE "critical|p0"; then
|
||||
SUGGESTED_PRIORITY="P0"
|
||||
REASON="Critical label found"
|
||||
elif echo "$LABELS" | grep -qE "bug|urgent|p1"; then
|
||||
SUGGESTED_PRIORITY="P1"
|
||||
REASON="Bug/urgent label found"
|
||||
fi
|
||||
```
|
||||
|
||||
Present suggestion and ask for confirmation:
|
||||
|
||||
```markdown
|
||||
### Suggested Priority: [P0/P1/P2/P3]
|
||||
**Reasoning**: [Reason based on analysis]
|
||||
|
||||
**Priority Criteria**:
|
||||
- **P0 (Critical)**: Blocking issues, security vulnerabilities, data loss, production outages
|
||||
- **P1 (High)**: Important bugs, features affecting many users, time-sensitive work
|
||||
- **P2 (Medium)**: Standard enhancements, non-blocking bugs, improvements
|
||||
- **P3 (Low)**: Nice-to-have features, minor improvements, future work
|
||||
|
||||
**Select Priority**: [P0/P1/P2/P3/Skip]
|
||||
```
|
||||
|
||||
#### C. Assess Status
|
||||
|
||||
If status is not set or needs review:
|
||||
|
||||
```markdown
|
||||
### Current Status: [Status or "Not set"]
|
||||
|
||||
**Recommended Status**:
|
||||
- **Backlog**: Not yet refined or scheduled
|
||||
- **Todo**: Refined and ready to start
|
||||
- **In Progress**: Actively being worked on
|
||||
- **In Review**: PR open, awaiting review
|
||||
- **Done**: Completed and merged/deployed
|
||||
|
||||
**Select Status**: [Backlog/Todo/In Progress/In Review/Done/Skip]
|
||||
```
|
||||
|
||||
#### D. Update Item
|
||||
|
||||
Apply the selected field values:
|
||||
|
||||
```bash
|
||||
# Update priority
|
||||
if [ "$SELECTED_PRIORITY" != "Skip" ]; then
|
||||
PRIORITY_OPTION_ID=$(echo $PRIORITY_OPTIONS | jq -r ". | select(.name==\"$SELECTED_PRIORITY\") | .id")
|
||||
|
||||
gh project item-edit --id $ITEM_ID --project-id $PROJECT_ID \
|
||||
--field-id $PRIORITY_FIELD \
|
||||
--single-select-option-id $PRIORITY_OPTION_ID
|
||||
|
||||
echo "✅ Updated priority to $SELECTED_PRIORITY"
|
||||
fi
|
||||
|
||||
# Update status
|
||||
if [ "$SELECTED_STATUS" != "Skip" ]; then
|
||||
STATUS_OPTION_ID=$(echo $STATUS_OPTIONS | jq -r ". | select(.name==\"$SELECTED_STATUS\") | .id")
|
||||
|
||||
gh project item-edit --id $ITEM_ID --project-id $PROJECT_ID \
|
||||
--field-id $STATUS_FIELD \
|
||||
--single-select-option-id $STATUS_OPTION_ID
|
||||
|
||||
echo "✅ Updated status to $SELECTED_STATUS"
|
||||
fi
|
||||
```
|
||||
|
||||
#### E. Ask About Additional Fields
|
||||
|
||||
If project has other important fields:
|
||||
|
||||
```markdown
|
||||
### Additional Fields (Optional)
|
||||
|
||||
- **Story Points**: [1/2/3/5/8/13/Skip]
|
||||
- **Component**: [Frontend/Backend/DevOps/Skip]
|
||||
- **Assignee**: [@username or Skip]
|
||||
- **Sprint/Iteration**: [Current/Next/Later/Skip]
|
||||
|
||||
**Skip all additional fields?** [Yes/No]
|
||||
```
|
||||
|
||||
### Step 6: Batch Mode (Alternative)
|
||||
|
||||
For experienced users or bulk triage, offer batch mode:
|
||||
|
||||
```markdown
|
||||
## Batch Triage Mode
|
||||
|
||||
Applying automatic prioritization based on keywords and labels...
|
||||
|
||||
[For each item:]
|
||||
- #[number] [title]
|
||||
→ Priority: P[X] (reason: [reason])
|
||||
→ Status: [Status]
|
||||
|
||||
**Preview [X] changes. Proceed?** [Yes/No/Review individually]
|
||||
```
|
||||
|
||||
### Step 7: Generate Triage Report
|
||||
|
||||
After completing triage:
|
||||
|
||||
```markdown
|
||||
# Triage Session Complete
|
||||
|
||||
**Project**: [Project Title]
|
||||
**Duration**: [Start time - End time]
|
||||
**Items Processed**: [Count]
|
||||
|
||||
---
|
||||
|
||||
## Summary of Changes
|
||||
|
||||
### Priority Assignment
|
||||
- P0 (Critical): [X] items
|
||||
- P1 (High): [Y] items
|
||||
- P2 (Medium): [Z] items
|
||||
- P3 (Low): [A] items
|
||||
- Skipped: [B] items
|
||||
|
||||
### Status Assignment
|
||||
- Backlog: [X] items
|
||||
- Todo: [Y] items
|
||||
- In Progress: [Z] items
|
||||
- Skipped: [A] items
|
||||
|
||||
### Field Updates Total
|
||||
- [X] items updated
|
||||
- [Y] items skipped
|
||||
- [Z] items had errors
|
||||
|
||||
---
|
||||
|
||||
## Items Still Requiring Attention
|
||||
|
||||
[If any items were skipped or errored:]
|
||||
- #[number] [title] - [Reason for skip/error]
|
||||
|
||||
---
|
||||
|
||||
## Project Health After Triage
|
||||
|
||||
**Priority Coverage**: [X]% of items now have priority
|
||||
**Status Coverage**: [Y]% of items have appropriate status
|
||||
**Recommendations**:
|
||||
[Provide 2-3 recommendations based on triage results]
|
||||
|
||||
---
|
||||
|
||||
## Next Steps
|
||||
|
||||
1. **Review P0/P1 items**: Ensure critical items are scheduled
|
||||
2. **Sprint planning**: Move refined items from Backlog to Todo
|
||||
3. **Assign work**: Distribute items to team members
|
||||
4. **Regular triage**: Schedule weekly triage sessions
|
||||
|
||||
**View updated project**: [Project URL]
|
||||
```
|
||||
|
||||
## Triage Best Practices
|
||||
|
||||
### Priority Assessment Guidelines
|
||||
|
||||
**P0 Criteria** (Critical - Immediate attention):
|
||||
- Production is down or severely degraded
|
||||
- Data loss or corruption risk
|
||||
- Security vulnerability
|
||||
- Blocking all users from core functionality
|
||||
- Legal or compliance risk
|
||||
|
||||
**P1 Criteria** (High - This week):
|
||||
- Significant user impact (>25% of users)
|
||||
- Important feature broken
|
||||
- High-value customer request
|
||||
- Sprint commitment
|
||||
- Dependency for other work
|
||||
|
||||
**P2 Criteria** (Medium - This month):
|
||||
- Moderate user impact
|
||||
- Standard feature request
|
||||
- Improvement to existing feature
|
||||
- Non-blocking bug
|
||||
- Technical debt with visible impact
|
||||
|
||||
**P3 Criteria** (Low - Backlog):
|
||||
- Nice-to-have feature
|
||||
- Minor cosmetic issue
|
||||
- Optimization without user impact
|
||||
- Long-term improvements
|
||||
- Ideas for future exploration
|
||||
|
||||
### Status Assessment Guidelines
|
||||
|
||||
**When to use Backlog**:
|
||||
- Item needs more information
|
||||
- Not yet refined or estimated
|
||||
- Awaiting dependencies
|
||||
- Future work, not committed
|
||||
|
||||
**When to use Todo**:
|
||||
- Fully refined and ready to start
|
||||
- Acceptance criteria defined
|
||||
- No blockers
|
||||
- Can be pulled into current sprint
|
||||
|
||||
**When to use In Progress**:
|
||||
- Work has actively started
|
||||
- Assignee is working on it
|
||||
- PR may or may not exist yet
|
||||
|
||||
**When to use In Review**:
|
||||
- PR is open
|
||||
- Awaiting code review
|
||||
- Testing in progress
|
||||
- Documentation pending
|
||||
|
||||
**When to use Done**:
|
||||
- Code merged
|
||||
- Tests passing
|
||||
- Deployed to production (if applicable)
|
||||
- Acceptance criteria met
|
||||
|
||||
## Automation Suggestions
|
||||
|
||||
After triage, suggest automation rules:
|
||||
|
||||
```markdown
|
||||
### Recommended Automation
|
||||
|
||||
Based on this triage session, consider setting up:
|
||||
|
||||
1. **Auto-priority for labeled issues**:
|
||||
- Issues with "critical" label → P0
|
||||
- Issues with "bug" label → P1
|
||||
- Issues with "enhancement" label → P2
|
||||
|
||||
2. **Auto-status from PR state**:
|
||||
- When PR opens → Move to "In Review"
|
||||
- When PR merges → Move to "Done"
|
||||
|
||||
3. **Auto-archive**:
|
||||
- Items in "Done" for >30 days → Archive
|
||||
|
||||
4. **Notifications**:
|
||||
- Alert on new P0 items
|
||||
- Daily digest of P1 items in Backlog
|
||||
|
||||
[Link to automation setup guide]
|
||||
```
|
||||
|
||||
## Important Notes
|
||||
|
||||
- **Context Matters**: Item priority depends on project goals and current sprint
|
||||
- **Team Alignment**: Ensure team agrees on priority definitions
|
||||
- **Regular Cadence**: Weekly triage prevents backlog chaos
|
||||
- **Don't Over-Triage**: It's okay to leave P3 items rough until needed
|
||||
- **Save Time**: Use batch mode for obvious cases, interactive for complex items
|
||||
- **Document Decisions**: Add comments to items explaining priority rationale
|
||||
|
||||
## Definition of Done
|
||||
|
||||
- [ ] Triage scope determined
|
||||
- [ ] Items fetched and filtered
|
||||
- [ ] Each item assessed for priority
|
||||
- [ ] Each item assessed for status
|
||||
- [ ] Field values updated successfully
|
||||
- [ ] Changes verified
|
||||
- [ ] Triage report generated
|
||||
- [ ] Remaining items noted
|
||||
- [ ] Next steps provided
|
||||
- [ ] Automation suggestions offered
|
||||
|
||||
## Error Handling
|
||||
|
||||
- If item update fails: Log error, continue to next item, report at end
|
||||
- If field options missing: Alert user, skip that field for affected items
|
||||
- If user cancels mid-triage: Save progress, provide partial report
|
||||
- If API rate limit: Pause, wait, resume from last item
|
||||
|
||||
Remember: Good triage is the foundation of effective project management. Taking time to properly prioritize and organize items saves hours of confusion and misprioritized work later.
|
||||
398
commands/gh-project-view.md
Normal file
398
commands/gh-project-view.md
Normal file
@@ -0,0 +1,398 @@
|
||||
---
|
||||
name: gh-project-view
|
||||
description: View project details, items, and status with comprehensive reporting
|
||||
tools: Bash, Read, Write
|
||||
model: inherit
|
||||
---
|
||||
|
||||
# View GitHub Project
|
||||
|
||||
This command provides comprehensive views of GitHub Projects with detailed reporting and analysis.
|
||||
|
||||
## Instructions
|
||||
|
||||
### Step 1: Identify the Project
|
||||
|
||||
Ask the user which project they want to view. Options:
|
||||
1. **By Name**: "Sprint 5", "Q1 Roadmap", etc.
|
||||
2. **By Number**: Project #3
|
||||
3. **Interactive**: List all projects and let user choose
|
||||
|
||||
If listing projects:
|
||||
```bash
|
||||
gh project list --owner "@me" --format json | python3 -c "
|
||||
import json, sys
|
||||
projects = json.load(sys.stdin)
|
||||
for p in projects:
|
||||
print(f\"#{p.get('number')} - {p.get('title')}\")
|
||||
"
|
||||
```
|
||||
|
||||
For organization projects:
|
||||
```bash
|
||||
gh project list --owner "org-name" --format json | python3 -c "
|
||||
import json, sys
|
||||
projects = json.load(sys.stdin)
|
||||
for p in projects:
|
||||
print(f\"#{p.get('number')} - {p.get('title')}\")
|
||||
"
|
||||
```
|
||||
|
||||
### Step 2: Get Project Details
|
||||
|
||||
Fetch comprehensive project information:
|
||||
|
||||
```bash
|
||||
# Get project metadata
|
||||
PROJECT_DATA=$(gh project view <number> --owner "<owner>" --format json)
|
||||
|
||||
# Parse key details using Python (safer than jq)
|
||||
PROJECT_ID=$(echo "$PROJECT_DATA" | python3 -c "import json, sys; print(json.load(sys.stdin).get('id', ''))")
|
||||
PROJECT_TITLE=$(echo "$PROJECT_DATA" | python3 -c "import json, sys; print(json.load(sys.stdin).get('title', ''))")
|
||||
PROJECT_URL=$(echo "$PROJECT_DATA" | python3 -c "import json, sys; print(json.load(sys.stdin).get('url', ''))")
|
||||
CREATED_AT=$(echo "$PROJECT_DATA" | python3 -c "import json, sys; print(json.load(sys.stdin).get('createdAt', ''))")
|
||||
UPDATED_AT=$(echo "$PROJECT_DATA" | python3 -c "import json, sys; print(json.load(sys.stdin).get('updatedAt', ''))")
|
||||
```
|
||||
|
||||
### Step 3: Get Project Fields
|
||||
|
||||
Fetch all custom fields:
|
||||
|
||||
```bash
|
||||
FIELDS=$(gh project field-list <number> --owner "<owner>" --format json --limit 50)
|
||||
|
||||
# Parse field details using Python
|
||||
echo "$FIELDS" | python3 -c "
|
||||
import json, sys
|
||||
fields = json.load(sys.stdin)
|
||||
for field in fields:
|
||||
print(f\"- {field.get('name')} ({field.get('dataType')})\")
|
||||
"
|
||||
```
|
||||
|
||||
### Step 4: Get Project Items
|
||||
|
||||
Fetch all items with their field values:
|
||||
|
||||
```bash
|
||||
ITEMS=$(gh project item-list <number> --owner "<owner>" --format json --limit 100)
|
||||
|
||||
# Count total items using Python
|
||||
ITEM_COUNT=$(echo "$ITEMS" | python3 -c "import json, sys; data=json.load(sys.stdin); print(len(data.get('items', [])))")
|
||||
```
|
||||
|
||||
### Step 5: Analyze Item Distribution
|
||||
|
||||
Generate comprehensive statistics:
|
||||
|
||||
#### Status Distribution
|
||||
```bash
|
||||
# Save items to temp file for helper processing
|
||||
echo "$ITEMS" > /tmp/gh_items.json
|
||||
|
||||
# Use Python helper to count by field
|
||||
python3 -c "
|
||||
import json, sys
|
||||
with open('/tmp/gh_items.json') as f:
|
||||
data = json.load(f)
|
||||
items = data.get('items', [])
|
||||
|
||||
# Count by Status
|
||||
status_counts = {}
|
||||
for item in items:
|
||||
for fv in item.get('fieldValues', []):
|
||||
if fv.get('name') == 'Status':
|
||||
status = fv.get('name') or 'Unset'
|
||||
status_counts[status] = status_counts.get(status, 0) + 1
|
||||
break
|
||||
|
||||
for status, count in sorted(status_counts.items()):
|
||||
print(f' {status}: {count}')
|
||||
"
|
||||
```
|
||||
|
||||
#### Priority Distribution
|
||||
```bash
|
||||
python3 -c "
|
||||
import json
|
||||
with open('/tmp/gh_items.json') as f:
|
||||
data = json.load(f)
|
||||
items = data.get('items', [])
|
||||
|
||||
# Count by Priority
|
||||
priority_counts = {}
|
||||
for item in items:
|
||||
for fv in item.get('fieldValues', []):
|
||||
if fv.get('name') == 'Priority':
|
||||
priority = fv.get('name') or 'Unset'
|
||||
priority_counts[priority] = priority_counts.get(priority, 0) + 1
|
||||
break
|
||||
|
||||
for priority, count in sorted(priority_counts.items()):
|
||||
print(f' {priority}: {count}')
|
||||
"
|
||||
```
|
||||
|
||||
#### Item Types
|
||||
```bash
|
||||
# Count issues vs PRs vs drafts using Python
|
||||
ISSUE_COUNT=$(python3 -c "import json; data=json.load(open('/tmp/gh_items.json')); print(len([i for i in data.get('items', []) if i.get('content', {}).get('type') == 'Issue']))")
|
||||
PR_COUNT=$(python3 -c "import json; data=json.load(open('/tmp/gh_items.json')); print(len([i for i in data.get('items', []) if i.get('content', {}).get('type') == 'PullRequest']))")
|
||||
DRAFT_COUNT=$(python3 -c "import json; data=json.load(open('/tmp/gh_items.json')); print(len([i for i in data.get('items', []) if i.get('content', {}).get('type') == 'DraftIssue']))")
|
||||
```
|
||||
|
||||
### Step 6: Identify Items Requiring Attention
|
||||
|
||||
#### High Priority Items Not Started
|
||||
```bash
|
||||
# P0/P1 items in Backlog or Todo using Python
|
||||
python3 -c "
|
||||
import json
|
||||
with open('/tmp/gh_items.json') as f:
|
||||
data = json.load(f)
|
||||
items = data.get('items', [])
|
||||
|
||||
for item in items:
|
||||
priority = None
|
||||
status = None
|
||||
|
||||
for fv in item.get('fieldValues', []):
|
||||
if fv.get('name') == 'Priority':
|
||||
priority = fv.get('name')
|
||||
elif fv.get('name') == 'Status':
|
||||
status = fv.get('name')
|
||||
|
||||
# Check if P0 or P1 and in Backlog or Todo
|
||||
if priority in ['P0', 'P1'] and status in ['Backlog', 'Todo']:
|
||||
content = item.get('content', {})
|
||||
number = content.get('number', 'draft')
|
||||
title = content.get('title', 'Untitled')
|
||||
print(f' - #{number} {title}')
|
||||
"
|
||||
```
|
||||
|
||||
#### Stale Items (In Progress > 7 days)
|
||||
```bash
|
||||
THRESHOLD_DATE=$(date -v-7d +%Y-%m-%d 2>/dev/null || date -d '7 days ago' +%Y-%m-%d)
|
||||
|
||||
python3 -c "
|
||||
import json
|
||||
from datetime import datetime, timedelta
|
||||
|
||||
with open('/tmp/gh_items.json') as f:
|
||||
data = json.load(f)
|
||||
items = data.get('items', [])
|
||||
threshold = datetime.now() - timedelta(days=7)
|
||||
|
||||
for item in items:
|
||||
status = None
|
||||
for fv in item.get('fieldValues', []):
|
||||
if fv.get('name') == 'Status':
|
||||
status = fv.get('name')
|
||||
break
|
||||
|
||||
if status in ['In Progress', 'In Review']:
|
||||
content = item.get('content', {})
|
||||
updated_str = content.get('updatedAt', '')
|
||||
|
||||
if updated_str:
|
||||
try:
|
||||
updated_at = datetime.fromisoformat(updated_str.replace('Z', '+00:00'))
|
||||
if updated_at < threshold:
|
||||
number = content.get('number', 'draft')
|
||||
title = content.get('title', 'Untitled')
|
||||
updated_date = updated_str.split('T')[0]
|
||||
days_old = (datetime.now() - updated_at).days
|
||||
print(f' - #{number} {title} (updated: {updated_date}, {days_old} days ago)')
|
||||
except:
|
||||
pass
|
||||
"
|
||||
```
|
||||
|
||||
#### Items in Review
|
||||
```bash
|
||||
python3 -c "
|
||||
import json
|
||||
with open('/tmp/gh_items.json') as f:
|
||||
data = json.load(f)
|
||||
items = data.get('items', [])
|
||||
|
||||
for item in items:
|
||||
status = None
|
||||
for fv in item.get('fieldValues', []):
|
||||
if fv.get('name') == 'Status':
|
||||
status = fv.get('name')
|
||||
break
|
||||
|
||||
if status == 'In Review':
|
||||
content = item.get('content', {})
|
||||
number = content.get('number', 'draft')
|
||||
title = content.get('title', 'Untitled')
|
||||
print(f' - #{number} {title}')
|
||||
"
|
||||
```
|
||||
|
||||
### Step 7: Generate Comprehensive Report
|
||||
|
||||
Present results in a clear, scannable format:
|
||||
|
||||
```markdown
|
||||
# Project Report: [Project Title]
|
||||
|
||||
**Project #[Number]** | [Owner] | [URL]
|
||||
Created: [Date] | Last Updated: [Date]
|
||||
|
||||
---
|
||||
|
||||
## Summary Statistics
|
||||
|
||||
- **Total Items**: [count]
|
||||
- **Issues**: [count]
|
||||
- **Pull Requests**: [count]
|
||||
- **Draft Items**: [count]
|
||||
|
||||
---
|
||||
|
||||
## Item Distribution
|
||||
|
||||
### By Status
|
||||
[Status distribution with counts]
|
||||
|
||||
### By Priority
|
||||
[Priority distribution with counts]
|
||||
|
||||
---
|
||||
|
||||
## Items by Status
|
||||
|
||||
### Backlog ([count])
|
||||
[List of backlog items with priority indicators]
|
||||
|
||||
### In Progress ([count])
|
||||
[List of in-progress items with assignees if available]
|
||||
|
||||
### In Review ([count])
|
||||
[List of items in review]
|
||||
|
||||
### Done ([count])
|
||||
[Recently completed items]
|
||||
|
||||
---
|
||||
|
||||
## Items Requiring Attention
|
||||
|
||||
### 🚨 High Priority Not Started
|
||||
[P0/P1 items in Backlog/Todo]
|
||||
|
||||
### ⚠️ Stale Items (In Progress > 7 days)
|
||||
[List with last update dates]
|
||||
|
||||
### 👀 Awaiting Review
|
||||
[Items in Review status]
|
||||
|
||||
### 🔍 Missing Priority
|
||||
[Items without priority assignment]
|
||||
|
||||
---
|
||||
|
||||
## Field Summary
|
||||
|
||||
### Custom Fields
|
||||
[List all custom fields with their types]
|
||||
|
||||
---
|
||||
|
||||
## Quick Actions
|
||||
|
||||
- Add items: `/gh-item-add`
|
||||
- Update status: Use project-manager agent
|
||||
- Triage backlog: `/gh-project-triage`
|
||||
- Generate status report: `/gh-project-status`
|
||||
|
||||
---
|
||||
|
||||
## Project Health
|
||||
|
||||
[Overall assessment of project health based on metrics]
|
||||
- Item distribution balance
|
||||
- Priority coverage
|
||||
- Stale item count
|
||||
- Workflow bottlenecks
|
||||
```
|
||||
|
||||
### Step 8: Offer Drill-Down Options
|
||||
|
||||
Ask the user if they want to see:
|
||||
- Specific items by status or priority
|
||||
- Details of particular items
|
||||
- Field values for all items
|
||||
- Items assigned to specific person
|
||||
- Items in specific iteration/sprint
|
||||
|
||||
## View Modes
|
||||
|
||||
Support different view modes based on user needs:
|
||||
|
||||
### Quick View
|
||||
- Project title and number
|
||||
- Total item count
|
||||
- Status distribution only
|
||||
|
||||
### Standard View (default)
|
||||
- All summary statistics
|
||||
- Status and priority distributions
|
||||
- Items requiring attention
|
||||
|
||||
### Detailed View
|
||||
- Everything from standard view
|
||||
- Individual item listings by status
|
||||
- Field analysis
|
||||
- Health metrics
|
||||
- Recommendations
|
||||
|
||||
### Custom View
|
||||
Ask user what specific information they need:
|
||||
- Filter by field values
|
||||
- Show only certain item types
|
||||
- Focus on specific time ranges
|
||||
- Compare iterations/sprints
|
||||
|
||||
## Important Notes
|
||||
|
||||
- Use `--format json` for all gh commands to enable parsing
|
||||
- Handle missing fields gracefully (not all projects have same fields)
|
||||
- Limit item fetching to 100 by default, offer pagination for larger projects
|
||||
- Format dates consistently (YYYY-MM-DD)
|
||||
- Use emoji sparingly for visual hierarchy
|
||||
- Make URLs clickable where possible
|
||||
|
||||
## Definition of Done
|
||||
|
||||
- [ ] Project identified (by name or number)
|
||||
- [ ] Project metadata retrieved
|
||||
- [ ] Fields listed and parsed
|
||||
- [ ] Items fetched and analyzed
|
||||
- [ ] Status distribution calculated
|
||||
- [ ] Priority distribution calculated
|
||||
- [ ] Items requiring attention identified
|
||||
- [ ] Comprehensive report generated
|
||||
- [ ] Drill-down options offered
|
||||
- [ ] Report is clear, scannable, and actionable
|
||||
|
||||
## Error Handling
|
||||
|
||||
- If project not found: List available projects, ask user to choose
|
||||
- If no items: Report empty project, offer to add items
|
||||
- If fields missing: Handle gracefully, report field setup status
|
||||
- If API rate limit hit: Advise user to wait, show partial results
|
||||
- If authentication fails: Check `gh auth status`, guide to refresh
|
||||
|
||||
## Output Format Options
|
||||
|
||||
Ask user preference:
|
||||
1. **Markdown** (default): Rich formatted text for terminal/web
|
||||
2. **JSON**: Machine-readable for scripting
|
||||
3. **CSV**: Export to spreadsheet
|
||||
4. **Summary**: One-line overview for quick checks
|
||||
|
||||
Remember: A good project view provides both overview and insight, enabling users to understand status at a glance and identify action items immediately.
|
||||
Reference in New Issue
Block a user