diff --git a/.github/agents/ci-fixer.agent.md b/.github/agents/cicd-repair.agent.md
similarity index 98%
rename from .github/agents/ci-fixer.agent.md
rename to .github/agents/cicd-repair.agent.md
index 433e06b..647fe87 100644
--- a/.github/agents/ci-fixer.agent.md
+++ b/.github/agents/cicd-repair.agent.md
@@ -12,6 +12,7 @@ If the fix is ambiguous, propose the most likely solution in the PR description.
- NEVER ask for clarification or additional information. You are operating autonomously and must make decisions based on the available data.
- You MUST open a Pull Request with the proposed fix. If you fail to do so, keep trying with different approaches until successful.
+- Use GitHub MCP tools over CLI commands when possible.
diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml
index f005ec1..80b6416 100644
--- a/.github/workflows/ci.yml
+++ b/.github/workflows/ci.yml
@@ -2,16 +2,14 @@ name: Fake CI
on:
workflow_dispatch:
- # push:
- # branches:
- # - main
+ pull_request:
+ branches:
+ - main
jobs:
build:
runs-on: ubuntu-latest
steps:
- # - uses: actions/checkout@v5
- - run: echo "Hello, world!"
- run: echo "Hello, world!"
- run: exit 1
diff --git a/.github/workflows/copilot-ci-fix.yml b/.github/workflows/copilot-ci-fix.yml
index 3ea293c..42bc16a 100644
--- a/.github/workflows/copilot-ci-fix.yml
+++ b/.github/workflows/copilot-ci-fix.yml
@@ -3,6 +3,8 @@ on:
workflows: ['*'] # All workflow failures
types: [completed]
+permissions: write-all # We need workflow: write
+
jobs:
ci-failure:
runs-on: ubuntu-latest
@@ -12,7 +14,6 @@ jobs:
- uses: austenstone/copilot-cli@main
with:
copilot-token: ${{ secrets.PAT }}
- # enable-all-github-mcp-tools: true
mcp-config: |
{
"mcpServers": {
@@ -27,7 +28,7 @@ jobs:
}
}
}
- agent: ci-fixer
+ agent: cicd-repair
prompt: |
The GitHub Actions workflow run failed.
Please analyze the failure and suggest a fix.
diff --git a/.github/workflows/copilot-dependabot-update.yml b/.github/workflows/copilot-dependabot-update.yml
index 5b67c5c..cc3a802 100644
--- a/.github/workflows/copilot-dependabot-update.yml
+++ b/.github/workflows/copilot-dependabot-update.yml
@@ -9,13 +9,9 @@ jobs:
if: github.event.pull_request.user.login == 'dependabot[bot]'
steps:
- uses: actions/checkout@v6
-
- name: Fetch Dependabot metadata
id: metadata
uses: dependabot/fetch-metadata@v2
- with:
- copilot-token: ${{ secrets.GITHUB_TOKEN }}
-
- name: Generate dependency analysis with Copilot
uses: austenstone/copilot-cli@main
env:
@@ -47,10 +43,16 @@ jobs:
### 2. Provided Context
+ #### Dependabot Metadata
```json
${{ toJson(steps.metadata.outputs) }}
```
+ #### Event Data
+ ```event
+ ${{ toJson(github.event) }}
+ ```
+
### 3. Your Tasks
Based on the context provided above:
diff --git a/.github/workflows/copilot-triage.yml b/.github/workflows/copilot-labeler.yml
similarity index 57%
rename from .github/workflows/copilot-triage.yml
rename to .github/workflows/copilot-labeler.yml
index 991b5f2..c6c97aa 100644
--- a/.github/workflows/copilot-triage.yml
+++ b/.github/workflows/copilot-labeler.yml
@@ -1,52 +1,25 @@
on:
- workflow_call:
- schedule:
- - cron: '0 * * * *' # Runs every hour
issues:
- types: [opened, edited, reopened]
+ types: [opened]
pull_request:
+ types: [opened]
branches:
- 'main'
- workflow_dispatch:
jobs:
triage:
runs-on: ubuntu-latest
timeout-minutes: 7
- outputs:
- available_labels: '${{ steps.get_labels.outputs.available_labels }}'
- selected_labels: '${{ env.SELECTED_LABELS }}'
permissions:
contents: 'read'
id-token: 'write'
issues: 'read'
pull-requests: 'read'
steps:
- - name: 'Get repository labels'
- id: get_labels
- uses: 'actions/github-script@main'
- with:
- script: |-
- const { data: labels } = await github.rest.issues.listLabelsForRepo({
- owner: context.repo.owner,
- repo: context.repo.repo,
- });
-
- if (!labels || labels.length === 0) {
- core.setFailed('There are no issue labels in this repository.')
- }
-
- const labelNames = labels.map(label => label.name).sort();
- core.setOutput('available_labels', labelNames.join(','));
- core.info(`Found ${labelNames.length} labels: ${labelNames.join(', ')}`);
- return labelNames;
- uses: austenstone/copilot-cli@main
- if: steps.get_labels.outputs.available_labels != ''
env:
- GITHUB_TOKEN: '' # Do NOT pass any auth tokens here since this runs on untrusted inputs
ISSUE_TITLE: '${{ github.event.issue.title }}'
ISSUE_BODY: '${{ github.event.issue.body }}'
- AVAILABLE_LABELS: '${{ steps.get_labels.outputs.available_labels }}'
with:
copilot-token: ${{ secrets.PAT }}
prompt: |
@@ -61,11 +34,6 @@ jobs:
## Input Data
- **Available Labels** (comma-separated):
- ```
- ${{ env.AVAILABLE_LABELS }}
- ```
-
**Issue Title**:
```
${{ env.ISSUE_TITLE }}
@@ -83,6 +51,8 @@ jobs:
## Steps
+ 0. Fetch possible labels from the repository.
+
1. Review the issue title, issue body, and available labels provided above.
2. Based on the issue title and issue body, classify the issue and choose all appropriate labels from the list of available labels.
diff --git a/.github/workflows/copilot-research.yml b/.github/workflows/copilot-research.yml
index 67aed3e..3b895a7 100644
--- a/.github/workflows/copilot-research.yml
+++ b/.github/workflows/copilot-research.yml
@@ -1,6 +1,6 @@
on:
issues:
- types: [opened, edited, reopened]
+ types: [opened]
jobs:
research:
diff --git a/.github/workflows/copilot-security-triage.yml b/.github/workflows/copilot-security-triage.yml
index 4782b29..6a50537 100644
--- a/.github/workflows/copilot-security-triage.yml
+++ b/.github/workflows/copilot-security-triage.yml
@@ -9,6 +9,7 @@ jobs:
- uses: austenstone/copilot-cli@main
with:
copilot-token: ${{ secrets.PAT }}
+ enable-all-github-mcp-tools: true
prompt: |
## Role
diff --git a/.github/workflows/copilot-usage-report.yml b/.github/workflows/copilot-usage-report.yml
index 789511a..654a3fd 100644
--- a/.github/workflows/copilot-usage-report.yml
+++ b/.github/workflows/copilot-usage-report.yml
@@ -8,6 +8,7 @@ jobs:
- uses: austenstone/copilot-cli@main
with:
copilot-token: ${{ secrets.PAT }}
+ repo-token: ${{ secrets.PAT }}
prompt: |
## Role
diff --git a/.github/workflows/test-copilot.yml b/.github/workflows/test-copilot.yml
index 2041f4d..5967edc 100644
--- a/.github/workflows/test-copilot.yml
+++ b/.github/workflows/test-copilot.yml
@@ -6,14 +6,15 @@ jobs:
copilot:
runs-on: ubuntu-latest
steps:
- - uses: actions/checkout@v5
+ - uses: actions/checkout@v6
- uses: austenstone/copilot-cli@main
with:
copilot-token: ${{ secrets.PAT }}
- enable-all-github-mcp-tools: true
prompt: |
Who are you?
What is your plan?
What tools do you have? Will you use them?
+
+ Can you test out some github mcp tools?
diff --git a/README.md b/README.md
index 079b47e..3d4e5b3 100644
Binary files a/README.md and b/README.md differ
diff --git a/action.yml b/action.yml
index 2c50e6a..f2b2cbf 100644
--- a/action.yml
+++ b/action.yml
@@ -17,10 +17,6 @@ inputs:
mcp-config:
description: 'MCP configuration for GitHub Copilot [Link](https://docs.github.com/en/copilot/how-tos/use-copilot-agents/coding-agent/extend-coding-agent-with-mcp#writing-a-json-configuration-for-mcp-servers)'
required: false
- default: |
- {
- "mcpServers": { }
- }
copilot-config:
description: 'Configuration for GitHub Copilot'
required: false
@@ -34,7 +30,7 @@ inputs:
allow-all-tools:
description: 'Allow all tools without approval'
required: false
- default: 'true'
+ default: true
allowed-tools:
description: 'Comma-separated list of tools to allow (e.g., "shell(rm),shell(git push)")'
required: false
@@ -57,7 +53,7 @@ inputs:
enable-all-github-mcp-tools:
description: 'Enable all GitHub MCP tools'
required: false
- default: 'false'
+ default: false
resume-session:
description: 'Resume from a previous session ID (use "latest" for most recent)'
required: false
@@ -68,6 +64,13 @@ inputs:
agent:
description: 'Specify a custom agent to use'
required: false
+ log-level:
+ description: 'Set the log level (choices: "none", "error", "warning", "info", "debug", "all", "default")'
+ required: false
+ default: 'all'
+ options:
+ description: 'Additional options to pass to the Copilot CLI (e.g., "--no-custom-instructions --screen-reader --no-color --model gpt-5")'
+ required: false
outputs:
logs-path:
description: 'Path to the copilot logs directory'
@@ -81,146 +84,113 @@ runs:
- uses: actions/setup-node@v6
with:
node-version: '22'
- # - name: Configure Git credentials
- # run: |
- # git config --global user.email "github-actions[bot]@users.noreply.github.com"
- # git config --global user.name "${{ github.workflow }}"
- # shell: bash
- # - name: Cache Copilot CLI
- # uses: actions/cache@v4
- # if: ${{ inputs.cache-cli == 'true' }}
- # with:
- # path: ~/.npm
- # key: ${{ runner.os }}-copilot-cli-${{ inputs.copilot-version }}
- # restore-keys: |
- # ${{ runner.os }}-copilot-cli-
- - name: Install GitHub Copilot CLI
+ - name: Run GitHub Copilot CLI
+ id: copilot
+ shell: bash
run: |
- echo "::group::Installing GitHub Copilot CLI"
+ # Script
+
+ echo "::group::Install GitHub Copilot CLI"
if [ "$COPILOT_VERSION" = "latest" ]; then
npm install -g @github/copilot
else
npm install -g @github/copilot@$COPILOT_VERSION
fi
- copilot --version || echo "Warning: Could not get copilot version"
+ echo "CLI Version: $(copilot --version)"
echo "::endgroup::"
- shell: bash
- env:
- COPILOT_VERSION: ${{ inputs.copilot-version }}
- - name: Configure Copilot
- shell: bash
- run: |
- echo "::group::Configuring Copilot"
- mkdir -p $XDG_CONFIG_HOME/.copilot
- # Create base MCP config with GitHub MCP server (comes pre-configured by default)
- BASE_MCP_CONFIG='{
- "mcpServers": { }
- }'
-
- # Merge user-provided MCP config with base config
- MERGED_MCP_CONFIG=$(echo "$BASE_MCP_CONFIG" | jq --argjson user "$MCP_CONFIG" '.mcpServers += $user.mcpServers')
- echo "$MERGED_MCP_CONFIG" > $XDG_CONFIG_HOME/.copilot/mcp-config.json
- cat $XDG_CONFIG_HOME/.copilot/mcp-config.json
- env:
- CONFIG: ${{ inputs.copilot-config }}
- MCP_CONFIG: ${{ inputs.mcp-config }}
- - name: Run Copilot CLI
- id: copilot
- shell: bash
- run: |
- echo "::group::Verifying GitHub CLI authentication"
- gh auth status
- echo "::endgroup::"
+ if [ -n "$MCP_CONFIG" ]; then
+ echo "::group::Configure Copilot MCP"
+ cat $XDG_CONFIG_HOME/.copilot/mcp-config.json || echo "No existing MCP config found"
+ mkdir -p $XDG_CONFIG_HOME/.copilot
+
+ BASE_MCP_CONFIG='{
+ "mcpServers": { }
+ }'
- set +e # Don't exit on error
+ MERGED_MCP_CONFIG=$(echo "$BASE_MCP_CONFIG" | jq --argjson user "$MCP_CONFIG" '.mcpServers += $user.mcpServers')
+ echo "$MERGED_MCP_CONFIG" > $XDG_CONFIG_HOME/.copilot/mcp-config.json
+ cat $XDG_CONFIG_HOME/.copilot/mcp-config.json
+ echo "::endgroup::"
+ fi
- # Build args array for safer execution with multi-line prompts
- COPILOT_ARGS=(-p "$PROMPT")
+ echo "::group::Copilot Options"
+ COPILOT_ARGS=""
- # Pre-trust common paths that Copilot might need in CI environment
- COPILOT_ARGS+=(--add-dir "/")
-
- # Add additional trusted directories
+ COPILOT_ARGS+="--add-dir / "
if [ -n "$ADDITIONAL_DIRS" ]; then
IFS=',' read -ra DIRS <<< "$ADDITIONAL_DIRS"
for dir in "${DIRS[@]}"; do
- COPILOT_ARGS+=(--add-dir "$dir")
+ COPILOT_ARGS+="--add-dir $dir "
done
fi
-
- # Add disabled MCP servers
if [ -n "$DISABLE_MCP_SERVERS" ]; then
IFS=',' read -ra SERVERS <<< "$DISABLE_MCP_SERVERS"
for server in "${SERVERS[@]}"; do
- COPILOT_ARGS+=(--disable-mcp-server "$server")
+ COPILOT_ARGS+="--disable-mcp-server $server "
done
fi
-
- # Enable all GitHub MCP tools
if [ "$ENABLE_ALL_GITHUB_MCP_TOOLS" = "true" ]; then
- COPILOT_ARGS+=(--enable-all-github-mcp-tools)
+ COPILOT_ARGS+="--enable-all-github-mcp-tools "
fi
-
- # Add tool permissions
if [ "$ALLOW_ALL_TOOLS" = "true" ]; then
- COPILOT_ARGS+=(--allow-all-tools)
+ COPILOT_ARGS+="--allow-all-tools "
fi
-
- # Add allowed tools
if [ -n "$ALLOWED_TOOLS" ]; then
IFS=',' read -ra TOOLS <<< "$ALLOWED_TOOLS"
for tool in "${TOOLS[@]}"; do
- COPILOT_ARGS+=(--allow-tool "$tool")
+ COPILOT_ARGS+="--allow-tool $tool "
done
fi
-
- # Add denied tools
if [ -n "$DENIED_TOOLS" ]; then
IFS=',' read -ra TOOLS <<< "$DENIED_TOOLS"
for tool in "${TOOLS[@]}"; do
- COPILOT_ARGS+=(--deny-tool "$tool")
+ COPILOT_ARGS+="--deny-tool $tool "
done
fi
-
- # Add model selection
if [ -n "$MODEL" ]; then
- COPILOT_ARGS+=(--model "$MODEL")
+ COPILOT_ARGS+="--model $MODEL "
fi
-
- # Add agent selection
if [ -n "$AGENT" ]; then
- COPILOT_ARGS+=(--agent "$AGENT")
+ COPILOT_ARGS+="--agent $AGENT "
fi
-
- # Add resume session
if [ -n "$RESUME_SESSION" ]; then
if [ "$RESUME_SESSION" = "latest" ]; then
- COPILOT_ARGS+=(--continue)
+ COPILOT_ARGS+="--continue "
else
- COPILOT_ARGS+=(--resume "$RESUME_SESSION")
+ COPILOT_ARGS+="--resume $RESUME_SESSION "
fi
fi
-
- # Add other options
- COPILOT_ARGS+=(--log-dir "$HOME/.copilot/logs")
-
- # Debug: Show the full command being executed
- echo "::group::GitHub Copilot CLI command"
- printf '%s\n' "${COPILOT_ARGS[@]}"
+ if [ -n "$LOG_LEVEL" ]; then
+ COPILOT_ARGS+="--log-level $LOG_LEVEL "
+ fi
+ if [ -n "$EXTRA_ARGS" ]; then
+ COPILOT_ARGS+="$EXTRA_ARGS "
+ fi
+ COPILOT_ARGS+="--log-dir $HOME/.copilot/logs"
+
+ echo "$COPILOT_ARGS"
echo "::endgroup::"
-
- # Execute the command with array expansion for proper quoting
- copilot "${COPILOT_ARGS[@]}"
+
+ echo "::group::Prompt"
+ echo "$PROMPT"
+ echo "::endgroup::"
+
+ echo "::group::Run Copilot CLI"
+ set +e
+ copilot -p "$PROMPT" $COPILOT_ARGS
EXIT_CODE=$?
-
- # Set outputs
+ echo "::endgroup::"
+
echo "logs_path=$HOME/.copilot/logs" >> $GITHUB_OUTPUT
echo "exit_code=$EXIT_CODE" >> $GITHUB_OUTPUT
env:
GH_TOKEN: ${{ inputs.repo-token || inputs.copilot-token }}
COPILOT_GITHUB_TOKEN: ${{ inputs.copilot-token }}
PROMPT: ${{ inputs.prompt }}
+ COPILOT_VERSION: ${{ inputs.copilot-version }}
+ CONFIG: ${{ inputs.copilot-config }}
+ MCP_CONFIG: ${{ inputs.mcp-config }}
ALLOW_ALL_TOOLS: ${{ inputs.allow-all-tools }}
ALLOWED_TOOLS: ${{ inputs.allowed-tools }}
DENIED_TOOLS: ${{ inputs.denied-tools }}
@@ -230,8 +200,8 @@ runs:
DISABLE_MCP_SERVERS: ${{ inputs.disable-mcp-servers }}
ENABLE_ALL_GITHUB_MCP_TOOLS: ${{ inputs.enable-all-github-mcp-tools }}
RESUME_SESSION: ${{ inputs.resume-session }}
- TEMP: ${{ runner.temp }}
- GITHUB_WORKSPACE: ${{ github.workspace }}
+ LOG_LEVEL: ${{ inputs.log-level }}
+ EXTRA_ARGS: ${{ inputs.options }}
- name: Upload Copilot Artifacts
uses: actions/upload-artifact@v4
if: ${{ always() && inputs.upload-artifact == 'true' }}