Files
2025-11-29 18:48:05 +08:00

13 KiB

GitHub Project Board (Kanban) Management Command

You are helping the user create, manage, and organize GitHub Project boards (Kanbans) following Sngular's agile project management best practices.

Instructions

  1. Determine the action:

    • Create a new project board
    • View existing project boards
    • Add issues/PRs to a board
    • Move items between columns
    • Update project fields (status, priority, etc.)
    • Generate project reports
    • Archive or close projects
  2. Verify GitHub access:

    • Check if in a GitHub repository
    • Verify gh CLI is installed and authenticated
    • Confirm user has appropriate permissions
    • Check for GitHub Projects (V2) availability
  3. Understand project structure:

    • Board name and purpose
    • Workflow stages (columns/status)
    • Custom fields (priority, size, sprint, etc.)
    • Automation rules
    • Views and filters

GitHub Projects Overview

Project Types

Repository Project: Attached to a single repository

  • Good for: Single product development
  • Access: Repository collaborators

Organization Project: Spans multiple repositories

  • Good for: Cross-team initiatives, programs
  • Access: Organization members

User Project: Personal project boards

  • Good for: Individual task tracking

Board Layouts

Board View: Classic kanban columns (Todo, In Progress, Done) Table View: Spreadsheet-like view with custom fields Roadmap View: Timeline view for planning

GitHub CLI Commands

Viewing Projects

# List all projects in organization
gh project list --owner ORGANIZATION

# List projects for current repository
gh project list

# View specific project
gh project view PROJECT_NUMBER

# View project in browser
gh project view PROJECT_NUMBER --web

# View project as JSON for scripting
gh project view PROJECT_NUMBER --format json

Creating Projects

# Create repository project
gh project create --owner OWNER --title "Sprint 24" --body "Sprint 24 work items"

# Create organization project
gh project create --org ORGANIZATION --title "Q4 Roadmap" --body "Q4 2024 initiatives"

# Create project with specific format
gh project create --title "Product Backlog" --format board

Managing Project Items

# Add issue to project
gh project item-add PROJECT_NUMBER --owner OWNER --url https://github.com/owner/repo/issues/123

# Add PR to project
gh project item-add PROJECT_NUMBER --owner OWNER --url https://github.com/owner/repo/pull/456

# Remove item from project
gh project item-delete --id ITEM_ID --project-id PROJECT_ID

# List items in project
gh project item-list PROJECT_NUMBER --owner OWNER

# List items with specific status
gh project item-list PROJECT_NUMBER --owner OWNER --format json | \
  jq '.items[] | select(.status == "In Progress")'

Updating Item Fields

# Update item status
gh project item-edit \
  --project-id PROJECT_ID \
  --id ITEM_ID \
  --field-id STATUS_FIELD_ID \
  --value "In Progress"

# Update priority
gh project item-edit \
  --project-id PROJECT_ID \
  --id ITEM_ID \
  --field-id PRIORITY_FIELD_ID \
  --value "High"

# Update sprint
gh project item-edit \
  --project-id PROJECT_ID \
  --id ITEM_ID \
  --field-id SPRINT_FIELD_ID \
  --value "Sprint 24"

# Update multiple fields
gh project item-edit \
  --project-id PROJECT_ID \
  --id ITEM_ID \
  --field-id STATUS_FIELD_ID \
  --value "Done" \
  --field-id COMPLETED_DATE_FIELD_ID \
  --value "2024-11-04"

Managing Project Fields

# List all fields in project
gh project field-list PROJECT_NUMBER --owner OWNER

# Create new field
gh project field-create PROJECT_NUMBER \
  --owner OWNER \
  --name "Story Points" \
  --data-type "NUMBER"

# Create single-select field
gh project field-create PROJECT_NUMBER \
  --owner OWNER \
  --name "Priority" \
  --data-type "SINGLE_SELECT" \
  --options "High,Medium,Low"

# Delete field
gh project field-delete PROJECT_NUMBER --field-id FIELD_ID

Common Kanban Board Configurations

Basic Scrum Board

Columns:

  1. Backlog: All items not yet started
  2. Sprint Backlog: Items planned for current sprint
  3. In Progress: Actively being worked on
  4. In Review: Code review or testing
  5. Done: Completed items

Custom Fields:

  • Priority: High / Medium / Low
  • Story Points: 1, 2, 3, 5, 8, 13
  • Sprint: Sprint 1, Sprint 2, etc.
  • Assignee: Team member

Feature Development Board

Columns:

  1. Ideas: Proposals and feature requests
  2. Refined: Requirements documented
  3. Ready: Approved and ready for development
  4. In Development: Active coding
  5. In Review: Code review
  6. In Testing: QA testing
  7. Deployed: Live in production

Custom Fields:

  • Feature Area: Frontend / Backend / DevOps
  • Size: Small / Medium / Large
  • Target Release: v1.0, v1.1, etc.
  • Customer Impact: High / Medium / Low

Bug Tracking Board

Columns:

  1. Triage: New bugs needing review
  2. Confirmed: Verified and reproduced
  3. Prioritized: Assigned priority
  4. In Progress: Being fixed
  5. Fixed: Code merged
  6. Verified: QA confirmed fix

Custom Fields:

  • Severity: Critical / High / Medium / Low
  • Affected Version: Version numbers
  • Root Cause: Code bug / Configuration / External
  • Customer Reported: Yes / No

Workflow Automation

Automated Column Movements

Auto-move to "In Progress" when:

  • Issue is assigned
  • PR is opened
  • Branch is created

Auto-move to "In Review" when:

  • PR is ready for review
  • Issue is labeled "review"

Auto-move to "Done" when:

  • PR is merged
  • Issue is closed

Example Automation Setup

While GitHub Projects V2 automation is typically configured via the UI, you can use GitHub Actions:

# .github/workflows/project-automation.yml
name: Project Board Automation

on:
  issues:
    types: [opened, assigned, closed]
  pull_request:
    types: [opened, ready_for_review, closed]

jobs:
  update-project:
    runs-on: ubuntu-latest
    steps:
      - name: Move issue to In Progress
        if: github.event_name == 'issues' && github.event.action == 'assigned'
        uses: actions/github-script@v7
        with:
          script: |
            // Update project item status
            // (Implementation depends on project structure)

      - name: Move PR to In Review
        if: github.event_name == 'pull_request' && github.event.action == 'ready_for_review'
        uses: actions/github-script@v7
        with:
          script: |
            // Update project item status

      - name: Move to Done
        if: (github.event_name == 'issues' && github.event.action == 'closed') || (github.event_name == 'pull_request' && github.event.pull_request.merged)
        uses: actions/github-script@v7
        with:
          script: |
            // Update project item status to Done

Project Management Workflows

Sprint Planning

  1. Review backlog:

    gh project item-list PROJECT_NUMBER --owner OWNER --format json | \
      jq '.items[] | select(.status == "Backlog")'
    
  2. Select items for sprint:

    # Move items to Sprint Backlog
    gh project item-edit \
      --project-id PROJECT_ID \
      --id ITEM_ID \
      --field-id STATUS_FIELD_ID \
      --value "Sprint Backlog" \
      --field-id SPRINT_FIELD_ID \
      --value "Sprint 24"
    
  3. Assign to team members:

    gh issue edit 123 --add-assignee username
    
  4. Set priorities and estimates:

    gh project item-edit \
      --project-id PROJECT_ID \
      --id ITEM_ID \
      --field-id STORY_POINTS_FIELD_ID \
      --value 5
    

Daily Standup Report

# Items in progress
echo "In Progress:"
gh project item-list PROJECT_NUMBER --owner OWNER --format json | \
  jq -r '.items[] | select(.status == "In Progress") | "- #\(.content.number): \(.content.title) (@\(.assignees[0].login))"'

# Items in review
echo "\nIn Review:"
gh project item-list PROJECT_NUMBER --owner OWNER --format json | \
  jq -r '.items[] | select(.status == "In Review") | "- #\(.content.number): \(.content.title)"'

# Blocked items
echo "\nBlocked:"
gh issue list --label "status: blocked" --json number,title,assignees

Sprint Retrospective

# Completed items count
COMPLETED=$(gh project item-list PROJECT_NUMBER --owner OWNER --format json | \
  jq '[.items[] | select(.status == "Done")] | length')

echo "Completed items: $COMPLETED"

# Velocity calculation
STORY_POINTS=$(gh project item-list PROJECT_NUMBER --owner OWNER --format json | \
  jq '[.items[] | select(.status == "Done" and .storyPoints != null) | .storyPoints] | add')

echo "Total story points: $STORY_POINTS"

# Cycle time (for closed issues)
gh issue list --state closed --search "closed:>=$(date -v-14d +%Y-%m-%d)" --json number,closedAt,createdAt

Best Practices

Board Organization

  1. Keep columns focused: 3-7 columns is optimal
  2. Define column criteria: Clear rules for when items move
  3. Limit WIP: Set work-in-progress limits per column
  4. Regular grooming: Weekly backlog refinement
  5. Clear ownership: Each item should have an assignee

Field Usage

  1. Consistent values: Use predefined options for consistency
  2. Required fields: Priority, Status, Assignee as minimum
  3. Meaningful estimates: Story points or t-shirt sizes
  4. Track progress: Use dates, sprints, milestones

Team Workflows

  1. Daily updates: Team members update their items daily
  2. Pull model: Team members pull work from backlog
  3. Visual management: Use labels and colors effectively
  4. Transparency: Keep board public and accessible
  5. Retrospectives: Review and improve process regularly

Reporting

Generate insights from your board:

# Sprint burndown data
gh project item-list PROJECT_NUMBER --format json | \
  jq '[.items[] | select(.sprint == "Sprint 24")] |
      {total: length, done: [.[] | select(.status == "Done")] | length}'

# Items by priority
gh project item-list PROJECT_NUMBER --format json | \
  jq 'group_by(.priority) | map({priority: .[0].priority, count: length})'

# Team workload
gh issue list --assignee username --json state | \
  jq 'group_by(.state) | map({state: .[0].state, count: length})'

Example Workflows

Create New Sprint Board

# Create project
PROJECT_NUMBER=$(gh project create \
  --owner ORGANIZATION \
  --title "Sprint 24 - Nov 4-17" \
  --body "Sprint 24 work items for Product Team" \
  --format json | jq -r '.number')

echo "Created project #$PROJECT_NUMBER"

# Add backlog items to sprint
gh issue list --label "sprint-24" --json number --jq '.[].number' | \
while read issue_number; do
  gh project item-add $PROJECT_NUMBER \
    --owner ORGANIZATION \
    --url "https://github.com/OWNER/REPO/issues/$issue_number"
  echo "Added issue #$issue_number"
done

Move All Ready Items to Sprint

# Get all items with status "Ready"
gh project item-list PROJECT_NUMBER --format json | \
  jq -r '.items[] | select(.status == "Ready") | .id' | \
while read item_id; do
  gh project item-edit \
    --project-id PROJECT_ID \
    --id $item_id \
    --field-id STATUS_FIELD_ID \
    --value "Sprint Backlog"
  echo "Moved item $item_id to Sprint Backlog"
done

Generate Sprint Report

#!/bin/bash
# sprint-report.sh

PROJECT_NUMBER=$1
SPRINT_NAME=$2

echo "# Sprint Report: $SPRINT_NAME"
echo "Generated: $(date)"
echo ""

# Get all items
ITEMS=$(gh project item-list $PROJECT_NUMBER --format json)

# Total items
TOTAL=$(echo "$ITEMS" | jq '[.items[] | select(.sprint == "'$SPRINT_NAME'")] | length')
echo "Total items: $TOTAL"

# Completed items
COMPLETED=$(echo "$ITEMS" | jq '[.items[] | select(.sprint == "'$SPRINT_NAME'" and .status == "Done")] | length')
echo "Completed: $COMPLETED"

# In progress
IN_PROGRESS=$(echo "$ITEMS" | jq '[.items[] | select(.sprint == "'$SPRINT_NAME'" and .status == "In Progress")] | length')
echo "In progress: $IN_PROGRESS"

# Completion rate
RATE=$(echo "scale=2; $COMPLETED * 100 / $TOTAL" | bc)
echo "Completion rate: ${RATE}%"

# Story points
TOTAL_POINTS=$(echo "$ITEMS" | jq '[.items[] | select(.sprint == "'$SPRINT_NAME'" and .storyPoints != null) | .storyPoints] | add')
COMPLETED_POINTS=$(echo "$ITEMS" | jq '[.items[] | select(.sprint == "'$SPRINT_NAME'" and .status == "Done" and .storyPoints != null) | .storyPoints] | add')
echo ""
echo "Total story points: $TOTAL_POINTS"
echo "Completed points: $COMPLETED_POINTS"

Integration with Issues

# Create issue and add to project in one workflow
ISSUE_NUMBER=$(gh issue create \
  --title "Implement user dashboard" \
  --body "Requirements..." \
  --label "feature,frontend" \
  --assignee username \
  --json number --jq '.number')

gh project item-add PROJECT_NUMBER \
  --owner OWNER \
  --url "https://github.com/OWNER/REPO/issues/$ISSUE_NUMBER"

echo "Created issue #$ISSUE_NUMBER and added to project"

Questions to Ask

Before managing project boards:

  1. "What is the purpose of this project board?"
  2. "What workflow stages do you need? (e.g., Todo, In Progress, Done)"
  3. "What custom fields should we track? (priority, sprint, story points)"
  4. "Is this a repository or organization-level project?"
  5. "Should we set up any automation rules?"
  6. "Do you want to add existing issues to this board?"
  7. "What views do you need? (Board, Table, Roadmap)"

Ask the user: "What would you like to do with GitHub project boards?"