microsoft/gctoolkit

Public

mirrored from https://github.com/microsoft/gctoolkitAvailable

CodeCommitsIssuesPull requestsActionsInsightsSecurity
dependabot/github_actions/actions/cache-6.0.0

Branches

Tags

  • No tags available.
0Branches0Tags
Go to file
Add file
Code

Clone

HTTPS

Download ZIP

.github/workflows/relevance-summary.lock.yml

1076lines · modecode

1#
2# ___ _ _
3# / _ \ | | (_)
4# | |_| | __ _ ___ _ __ | |_ _ ___
5# | _ |/ _` |/ _ \ '_ \| __| |/ __|
6# | | | | (_| | __/ | | | |_| | (__
7# \_| |_/\__, |\___|_| |_|\__|_|\___|
8# __/ |
9# _ _ |___/
10# | | | | / _| |
11# | | | | ___ _ __ _ __| |_| | _____ ____
12# | |/\| |/ _ \ '__| |/ /| _| |/ _ \ \ /\ / / ___|
13# \ /\ / (_) | | | | ( | | | | (_) \ V V /\__ \
14# \/ \/ \___/|_| |_|\_\|_| |_|\___/ \_/\_/ |___/
15#
16# This file was automatically generated by gh-aw (v0.50.4). DO NOT EDIT.
17#
18# To update this file, edit the corresponding .md file and run:
19# gh aw compile
20# Not all edits will cause changes to this file.
21#
22# For more information: https://github.github.com/gh-aw/introduction/overview/
23#
24# Manually triggered workflow that summarizes all open issues and PRs with a /relevance-check response into a single issue
25#
26# gh-aw-metadata: {"schema_version":"v1","frontmatter_hash":"acb2c5ba281b18280cc7244816af8424ca646a45930ea7af81c2d0aa2659bc68","compiler_version":"v0.50.4"}
27
28name: "Relevance Check Summary Report"
29"on":
30 workflow_dispatch:
31
32permissions: {}
33
34concurrency:
35 group: "gh-aw-${{ github.workflow }}"
36
37run-name: "Relevance Check Summary Report"
38
39jobs:
40 activation:
41 runs-on: ubuntu-slim
42 permissions:
43 contents: read
44 outputs:
45 comment_id: ""
46 comment_repo: ""
47 steps:
48 - name: Setup Scripts
49 uses: github/gh-aw/actions/setup@80f243ca31e3f6632caaeae6930f5a00018fd24b # v0.65.0
50 with:
51 destination: /opt/gh-aw/actions
52 - name: Validate context variables
53 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
54 with:
55 script: |
56 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
57 setupGlobals(core, github, context, exec, io);
58 const { main } = require('/opt/gh-aw/actions/validate_context_variables.cjs');
59 await main();
60 - name: Checkout .github and .agents folders
61 uses: actions/checkout@9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0 # v7.0.0
62 with:
63 sparse-checkout: |
64 .github
65 .agents
66 fetch-depth: 1
67 persist-credentials: false
68 - name: Check workflow file timestamps
69 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
70 env:
71 GH_AW_WORKFLOW_FILE: "relevance-summary.lock.yml"
72 with:
73 script: |
74 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
75 setupGlobals(core, github, context, exec, io);
76 const { main } = require('/opt/gh-aw/actions/check_workflow_timestamp_api.cjs');
77 await main();
78 - name: Create prompt with built-in context
79 env:
80 GH_AW_PROMPT: /tmp/gh-aw/aw-prompts/prompt.txt
81 GH_AW_SAFE_OUTPUTS: ${{ env.GH_AW_SAFE_OUTPUTS }}
82 GH_AW_GITHUB_ACTOR: ${{ github.actor }}
83 GH_AW_GITHUB_EVENT_COMMENT_ID: ${{ github.event.comment.id }}
84 GH_AW_GITHUB_EVENT_DISCUSSION_NUMBER: ${{ github.event.discussion.number }}
85 GH_AW_GITHUB_EVENT_ISSUE_NUMBER: ${{ github.event.issue.number }}
86 GH_AW_GITHUB_EVENT_PULL_REQUEST_NUMBER: ${{ github.event.pull_request.number }}
87 GH_AW_GITHUB_REPOSITORY: ${{ github.repository }}
88 GH_AW_GITHUB_RUN_ID: ${{ github.run_id }}
89 GH_AW_GITHUB_WORKSPACE: ${{ github.workspace }}
90 run: |
91 bash /opt/gh-aw/actions/create_prompt_first.sh
92 {
93 cat << 'GH_AW_PROMPT_EOF'
94 <system>
95 GH_AW_PROMPT_EOF
96 cat "/opt/gh-aw/prompts/xpia.md"
97 cat "/opt/gh-aw/prompts/temp_folder_prompt.md"
98 cat "/opt/gh-aw/prompts/markdown.md"
99 cat "/opt/gh-aw/prompts/safe_outputs_prompt.md"
100 cat << 'GH_AW_PROMPT_EOF'
101 <safe-output-tools>
102 Tools: create_issue, missing_tool, missing_data
103 </safe-output-tools>
104 <github-context>
105 The following GitHub context information is available for this workflow:
106 {{#if __GH_AW_GITHUB_ACTOR__ }}
107 - **actor**: __GH_AW_GITHUB_ACTOR__
108 {{/if}}
109 {{#if __GH_AW_GITHUB_REPOSITORY__ }}
110 - **repository**: __GH_AW_GITHUB_REPOSITORY__
111 {{/if}}
112 {{#if __GH_AW_GITHUB_WORKSPACE__ }}
113 - **workspace**: __GH_AW_GITHUB_WORKSPACE__
114 {{/if}}
115 {{#if __GH_AW_GITHUB_EVENT_ISSUE_NUMBER__ }}
116 - **issue-number**: #__GH_AW_GITHUB_EVENT_ISSUE_NUMBER__
117 {{/if}}
118 {{#if __GH_AW_GITHUB_EVENT_DISCUSSION_NUMBER__ }}
119 - **discussion-number**: #__GH_AW_GITHUB_EVENT_DISCUSSION_NUMBER__
120 {{/if}}
121 {{#if __GH_AW_GITHUB_EVENT_PULL_REQUEST_NUMBER__ }}
122 - **pull-request-number**: #__GH_AW_GITHUB_EVENT_PULL_REQUEST_NUMBER__
123 {{/if}}
124 {{#if __GH_AW_GITHUB_EVENT_COMMENT_ID__ }}
125 - **comment-id**: __GH_AW_GITHUB_EVENT_COMMENT_ID__
126 {{/if}}
127 {{#if __GH_AW_GITHUB_RUN_ID__ }}
128 - **workflow-run-id**: __GH_AW_GITHUB_RUN_ID__
129 {{/if}}
130 </github-context>
131
132 GH_AW_PROMPT_EOF
133 cat << 'GH_AW_PROMPT_EOF'
134 </system>
135 GH_AW_PROMPT_EOF
136 cat << 'GH_AW_PROMPT_EOF'
137 {{#runtime-import .github/workflows/relevance-summary.md}}
138 GH_AW_PROMPT_EOF
139 } > "$GH_AW_PROMPT"
140 - name: Interpolate variables and render templates
141 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
142 env:
143 GH_AW_PROMPT: /tmp/gh-aw/aw-prompts/prompt.txt
144 GH_AW_GITHUB_REPOSITORY: ${{ github.repository }}
145 with:
146 script: |
147 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
148 setupGlobals(core, github, context, exec, io);
149 const { main } = require('/opt/gh-aw/actions/interpolate_prompt.cjs');
150 await main();
151 - name: Substitute placeholders
152 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
153 env:
154 GH_AW_PROMPT: /tmp/gh-aw/aw-prompts/prompt.txt
155 GH_AW_GITHUB_ACTOR: ${{ github.actor }}
156 GH_AW_GITHUB_EVENT_COMMENT_ID: ${{ github.event.comment.id }}
157 GH_AW_GITHUB_EVENT_DISCUSSION_NUMBER: ${{ github.event.discussion.number }}
158 GH_AW_GITHUB_EVENT_ISSUE_NUMBER: ${{ github.event.issue.number }}
159 GH_AW_GITHUB_EVENT_PULL_REQUEST_NUMBER: ${{ github.event.pull_request.number }}
160 GH_AW_GITHUB_REPOSITORY: ${{ github.repository }}
161 GH_AW_GITHUB_RUN_ID: ${{ github.run_id }}
162 GH_AW_GITHUB_WORKSPACE: ${{ github.workspace }}
163 with:
164 script: |
165 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
166 setupGlobals(core, github, context, exec, io);
167
168 const substitutePlaceholders = require('/opt/gh-aw/actions/substitute_placeholders.cjs');
169
170 // Call the substitution function
171 return await substitutePlaceholders({
172 file: process.env.GH_AW_PROMPT,
173 substitutions: {
174 GH_AW_GITHUB_ACTOR: process.env.GH_AW_GITHUB_ACTOR,
175 GH_AW_GITHUB_EVENT_COMMENT_ID: process.env.GH_AW_GITHUB_EVENT_COMMENT_ID,
176 GH_AW_GITHUB_EVENT_DISCUSSION_NUMBER: process.env.GH_AW_GITHUB_EVENT_DISCUSSION_NUMBER,
177 GH_AW_GITHUB_EVENT_ISSUE_NUMBER: process.env.GH_AW_GITHUB_EVENT_ISSUE_NUMBER,
178 GH_AW_GITHUB_EVENT_PULL_REQUEST_NUMBER: process.env.GH_AW_GITHUB_EVENT_PULL_REQUEST_NUMBER,
179 GH_AW_GITHUB_REPOSITORY: process.env.GH_AW_GITHUB_REPOSITORY,
180 GH_AW_GITHUB_RUN_ID: process.env.GH_AW_GITHUB_RUN_ID,
181 GH_AW_GITHUB_WORKSPACE: process.env.GH_AW_GITHUB_WORKSPACE
182 }
183 });
184 - name: Validate prompt placeholders
185 env:
186 GH_AW_PROMPT: /tmp/gh-aw/aw-prompts/prompt.txt
187 run: bash /opt/gh-aw/actions/validate_prompt_placeholders.sh
188 - name: Print prompt
189 env:
190 GH_AW_PROMPT: /tmp/gh-aw/aw-prompts/prompt.txt
191 run: bash /opt/gh-aw/actions/print_prompt_summary.sh
192 - name: Upload prompt artifact
193 if: success()
194 uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
195 with:
196 name: prompt
197 path: /tmp/gh-aw/aw-prompts/prompt.txt
198 retention-days: 1
199
200 agent:
201 needs: activation
202 runs-on: ubuntu-latest
203 permissions:
204 contents: read
205 issues: read
206 pull-requests: read
207 env:
208 DEFAULT_BRANCH: ${{ github.event.repository.default_branch }}
209 GH_AW_ASSETS_ALLOWED_EXTS: ""
210 GH_AW_ASSETS_BRANCH: ""
211 GH_AW_ASSETS_MAX_SIZE_KB: 0
212 GH_AW_MCP_LOG_DIR: /tmp/gh-aw/mcp-logs/safeoutputs
213 GH_AW_SAFE_OUTPUTS: /opt/gh-aw/safeoutputs/outputs.jsonl
214 GH_AW_SAFE_OUTPUTS_CONFIG_PATH: /opt/gh-aw/safeoutputs/config.json
215 GH_AW_SAFE_OUTPUTS_TOOLS_PATH: /opt/gh-aw/safeoutputs/tools.json
216 GH_AW_WORKFLOW_ID_SANITIZED: relevancesummary
217 outputs:
218 checkout_pr_success: ${{ steps.checkout-pr.outputs.checkout_pr_success || 'true' }}
219 detection_conclusion: ${{ steps.detection_conclusion.outputs.conclusion }}
220 detection_success: ${{ steps.detection_conclusion.outputs.success }}
221 has_patch: ${{ steps.collect_output.outputs.has_patch }}
222 model: ${{ steps.generate_aw_info.outputs.model }}
223 output: ${{ steps.collect_output.outputs.output }}
224 output_types: ${{ steps.collect_output.outputs.output_types }}
225 secret_verification_result: ${{ steps.validate-secret.outputs.verification_result }}
226 steps:
227 - name: Setup Scripts
228 uses: github/gh-aw/actions/setup@80f243ca31e3f6632caaeae6930f5a00018fd24b # v0.65.0
229 with:
230 destination: /opt/gh-aw/actions
231 - name: Checkout repository
232 uses: actions/checkout@9c091bb21b7c1c1d1991bb908d89e4e9dddfe3e0 # v7.0.0
233 with:
234 persist-credentials: false
235 - name: Create gh-aw temp directory
236 run: bash /opt/gh-aw/actions/create_gh_aw_tmp_dir.sh
237 - name: Configure Git credentials
238 env:
239 REPO_NAME: ${{ github.repository }}
240 SERVER_URL: ${{ github.server_url }}
241 run: |
242 git config --global user.email "github-actions[bot]@users.noreply.github.com"
243 git config --global user.name "github-actions[bot]"
244 git config --global am.keepcr true
245 # Re-authenticate git with GitHub token
246 SERVER_URL_STRIPPED="${SERVER_URL#https://}"
247 git remote set-url origin "https://x-access-token:${{ github.token }}@${SERVER_URL_STRIPPED}/${REPO_NAME}.git"
248 echo "Git configured with standard GitHub Actions identity"
249 - name: Checkout PR branch
250 id: checkout-pr
251 if: |
252 github.event.pull_request
253 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
254 env:
255 GH_TOKEN: ${{ secrets.GH_AW_GITHUB_MCP_SERVER_TOKEN || secrets.GH_AW_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
256 with:
257 github-token: ${{ secrets.GH_AW_GITHUB_MCP_SERVER_TOKEN || secrets.GH_AW_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
258 script: |
259 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
260 setupGlobals(core, github, context, exec, io);
261 const { main } = require('/opt/gh-aw/actions/checkout_pr_branch.cjs');
262 await main();
263 - name: Generate agentic run info
264 id: generate_aw_info
265 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
266 with:
267 script: |
268 const fs = require('fs');
269
270 const awInfo = {
271 engine_id: "copilot",
272 engine_name: "GitHub Copilot CLI",
273 model: "claude-sonnet-4.5",
274 version: "",
275 agent_version: "0.0.417",
276 cli_version: "v0.50.4",
277 workflow_name: "Relevance Check Summary Report",
278 experimental: false,
279 supports_tools_allowlist: true,
280 run_id: context.runId,
281 run_number: context.runNumber,
282 run_attempt: process.env.GITHUB_RUN_ATTEMPT,
283 repository: context.repo.owner + '/' + context.repo.repo,
284 ref: context.ref,
285 sha: context.sha,
286 actor: context.actor,
287 event_name: context.eventName,
288 staged: false,
289 allowed_domains: ["defaults"],
290 firewall_enabled: true,
291 awf_version: "v0.23.0",
292 awmg_version: "v0.1.5",
293 steps: {
294 firewall: "squid"
295 },
296 created_at: new Date().toISOString()
297 };
298
299 // Write to /tmp/gh-aw directory to avoid inclusion in PR
300 const tmpPath = '/tmp/gh-aw/aw_info.json';
301 fs.writeFileSync(tmpPath, JSON.stringify(awInfo, null, 2));
302 console.log('Generated aw_info.json at:', tmpPath);
303 console.log(JSON.stringify(awInfo, null, 2));
304
305 // Set model as output for reuse in other steps/jobs
306 core.setOutput('model', awInfo.model);
307 - name: Validate COPILOT_GITHUB_TOKEN secret
308 id: validate-secret
309 run: /opt/gh-aw/actions/validate_multi_secret.sh COPILOT_GITHUB_TOKEN 'GitHub Copilot CLI' https://github.github.com/gh-aw/reference/engines/#github-copilot-default
310 env:
311 COPILOT_GITHUB_TOKEN: ${{ secrets.COPILOT_GITHUB_TOKEN }}
312 - name: Install GitHub Copilot CLI
313 run: /opt/gh-aw/actions/install_copilot_cli.sh 0.0.417
314 - name: Install awf binary
315 run: bash /opt/gh-aw/actions/install_awf_binary.sh v0.23.0
316 - name: Determine automatic lockdown mode for GitHub MCP Server
317 id: determine-automatic-lockdown
318 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
319 env:
320 GH_AW_GITHUB_TOKEN: ${{ secrets.GH_AW_GITHUB_TOKEN }}
321 GH_AW_GITHUB_MCP_SERVER_TOKEN: ${{ secrets.GH_AW_GITHUB_MCP_SERVER_TOKEN }}
322 with:
323 script: |
324 const determineAutomaticLockdown = require('/opt/gh-aw/actions/determine_automatic_lockdown.cjs');
325 await determineAutomaticLockdown(github, context, core);
326 - name: Download container images
327 run: bash /opt/gh-aw/actions/download_docker_images.sh ghcr.io/github/gh-aw-firewall/agent:0.23.0 ghcr.io/github/gh-aw-firewall/api-proxy:0.23.0 ghcr.io/github/gh-aw-firewall/squid:0.23.0 ghcr.io/github/gh-aw-mcpg:v0.1.5 ghcr.io/github/github-mcp-server:v0.31.0 node:lts-alpine
328 - name: Write Safe Outputs Config
329 run: |
330 mkdir -p /opt/gh-aw/safeoutputs
331 mkdir -p /tmp/gh-aw/safeoutputs
332 mkdir -p /tmp/gh-aw/mcp-logs/safeoutputs
333 cat > /opt/gh-aw/safeoutputs/config.json << 'GH_AW_SAFE_OUTPUTS_CONFIG_EOF'
334 {"create_issue":{"max":1},"missing_data":{},"missing_tool":{},"noop":{"max":1}}
335 GH_AW_SAFE_OUTPUTS_CONFIG_EOF
336 cat > /opt/gh-aw/safeoutputs/tools.json << 'GH_AW_SAFE_OUTPUTS_TOOLS_EOF'
337 [
338 {
339 "description": "Create a new GitHub issue for tracking bugs, feature requests, or tasks. Use this for actionable work items that need assignment, labeling, and status tracking. For reports, announcements, or status updates that don't require task tracking, use create_discussion instead. CONSTRAINTS: Maximum 1 issue(s) can be created. Title will be prefixed with \"Relevance Summary:\". Labels [report] will be automatically added.",
340 "inputSchema": {
341 "additionalProperties": false,
342 "properties": {
343 "body": {
344 "description": "Detailed issue description in Markdown. Do NOT repeat the title as a heading since it already appears as the issue's h1. Include context, reproduction steps, or acceptance criteria as appropriate.",
345 "type": "string"
346 },
347 "labels": {
348 "description": "Labels to categorize the issue (e.g., 'bug', 'enhancement'). Labels must exist in the repository.",
349 "items": {
350 "type": "string"
351 },
352 "type": "array"
353 },
354 "parent": {
355 "description": "Parent issue number for creating sub-issues. This is the numeric ID from the GitHub URL (e.g., 42 in github.com/owner/repo/issues/42). Can also be a temporary_id (e.g., 'aw_abc123', 'aw_Test123') from a previously created issue in the same workflow run.",
356 "type": [
357 "number",
358 "string"
359 ]
360 },
361 "temporary_id": {
362 "description": "Unique temporary identifier for referencing this issue before it's created. Format: 'aw_' followed by 3 to 8 alphanumeric characters (e.g., 'aw_abc1', 'aw_Test123'). Use '#aw_ID' in body text to reference other issues by their temporary_id; these are replaced with actual issue numbers after creation.",
363 "pattern": "^aw_[A-Za-z0-9]{3,8}$",
364 "type": "string"
365 },
366 "title": {
367 "description": "Concise issue title summarizing the bug, feature, or task. The title appears as the main heading, so keep it brief and descriptive.",
368 "type": "string"
369 }
370 },
371 "required": [
372 "title",
373 "body"
374 ],
375 "type": "object"
376 },
377 "name": "create_issue"
378 },
379 {
380 "description": "Report that a tool or capability needed to complete the task is not available, or share any information you deem important about missing functionality or limitations. Use this when you cannot accomplish what was requested because the required functionality is missing or access is restricted.",
381 "inputSchema": {
382 "additionalProperties": false,
383 "properties": {
384 "alternatives": {
385 "description": "Any workarounds, manual steps, or alternative approaches the user could take (max 256 characters).",
386 "type": "string"
387 },
388 "reason": {
389 "description": "Explanation of why this tool is needed or what information you want to share about the limitation (max 256 characters).",
390 "type": "string"
391 },
392 "tool": {
393 "description": "Optional: Name or description of the missing tool or capability (max 128 characters). Be specific about what functionality is needed.",
394 "type": "string"
395 }
396 },
397 "required": [
398 "reason"
399 ],
400 "type": "object"
401 },
402 "name": "missing_tool"
403 },
404 {
405 "description": "Log a transparency message when no significant actions are needed. Use this to confirm workflow completion and provide visibility when analysis is complete but no changes or outputs are required (e.g., 'No issues found', 'All checks passed'). This ensures the workflow produces human-visible output even when no other actions are taken.",
406 "inputSchema": {
407 "additionalProperties": false,
408 "properties": {
409 "message": {
410 "description": "Status or completion message to log. Should explain what was analyzed and the outcome (e.g., 'Code review complete - no issues found', 'Analysis complete - all tests passing').",
411 "type": "string"
412 }
413 },
414 "required": [
415 "message"
416 ],
417 "type": "object"
418 },
419 "name": "noop"
420 },
421 {
422 "description": "Report that data or information needed to complete the task is not available. Use this when you cannot accomplish what was requested because required data, context, or information is missing.",
423 "inputSchema": {
424 "additionalProperties": false,
425 "properties": {
426 "alternatives": {
427 "description": "Any workarounds, manual steps, or alternative approaches the user could take (max 256 characters).",
428 "type": "string"
429 },
430 "context": {
431 "description": "Additional context about the missing data or where it should come from (max 256 characters).",
432 "type": "string"
433 },
434 "data_type": {
435 "description": "Type or description of the missing data or information (max 128 characters). Be specific about what data is needed.",
436 "type": "string"
437 },
438 "reason": {
439 "description": "Explanation of why this data is needed to complete the task (max 256 characters).",
440 "type": "string"
441 }
442 },
443 "required": [],
444 "type": "object"
445 },
446 "name": "missing_data"
447 }
448 ]
449 GH_AW_SAFE_OUTPUTS_TOOLS_EOF
450 cat > /opt/gh-aw/safeoutputs/validation.json << 'GH_AW_SAFE_OUTPUTS_VALIDATION_EOF'
451 {
452 "create_issue": {
453 "defaultMax": 1,
454 "fields": {
455 "body": {
456 "required": true,
457 "type": "string",
458 "sanitize": true,
459 "maxLength": 65000
460 },
461 "labels": {
462 "type": "array",
463 "itemType": "string",
464 "itemSanitize": true,
465 "itemMaxLength": 128
466 },
467 "parent": {
468 "issueOrPRNumber": true
469 },
470 "repo": {
471 "type": "string",
472 "maxLength": 256
473 },
474 "temporary_id": {
475 "type": "string"
476 },
477 "title": {
478 "required": true,
479 "type": "string",
480 "sanitize": true,
481 "maxLength": 128
482 }
483 }
484 },
485 "missing_data": {
486 "defaultMax": 20,
487 "fields": {
488 "alternatives": {
489 "type": "string",
490 "sanitize": true,
491 "maxLength": 256
492 },
493 "context": {
494 "type": "string",
495 "sanitize": true,
496 "maxLength": 256
497 },
498 "data_type": {
499 "type": "string",
500 "sanitize": true,
501 "maxLength": 128
502 },
503 "reason": {
504 "type": "string",
505 "sanitize": true,
506 "maxLength": 256
507 }
508 }
509 },
510 "missing_tool": {
511 "defaultMax": 20,
512 "fields": {
513 "alternatives": {
514 "type": "string",
515 "sanitize": true,
516 "maxLength": 512
517 },
518 "reason": {
519 "required": true,
520 "type": "string",
521 "sanitize": true,
522 "maxLength": 256
523 },
524 "tool": {
525 "type": "string",
526 "sanitize": true,
527 "maxLength": 128
528 }
529 }
530 },
531 "noop": {
532 "defaultMax": 1,
533 "fields": {
534 "message": {
535 "required": true,
536 "type": "string",
537 "sanitize": true,
538 "maxLength": 65000
539 }
540 }
541 }
542 }
543 GH_AW_SAFE_OUTPUTS_VALIDATION_EOF
544 - name: Generate Safe Outputs MCP Server Config
545 id: safe-outputs-config
546 run: |
547 # Generate a secure random API key (360 bits of entropy, 40+ chars)
548 # Mask immediately to prevent timing vulnerabilities
549 API_KEY=$(openssl rand -base64 45 | tr -d '/+=')
550 echo "::add-mask::${API_KEY}"
551
552 PORT=3001
553
554 # Set outputs for next steps
555 {
556 echo "safe_outputs_api_key=${API_KEY}"
557 echo "safe_outputs_port=${PORT}"
558 } >> "$GITHUB_OUTPUT"
559
560 echo "Safe Outputs MCP server will run on port ${PORT}"
561
562 - name: Start Safe Outputs MCP HTTP Server
563 id: safe-outputs-start
564 env:
565 DEBUG: '*'
566 GH_AW_SAFE_OUTPUTS_PORT: ${{ steps.safe-outputs-config.outputs.safe_outputs_port }}
567 GH_AW_SAFE_OUTPUTS_API_KEY: ${{ steps.safe-outputs-config.outputs.safe_outputs_api_key }}
568 GH_AW_SAFE_OUTPUTS_TOOLS_PATH: /opt/gh-aw/safeoutputs/tools.json
569 GH_AW_SAFE_OUTPUTS_CONFIG_PATH: /opt/gh-aw/safeoutputs/config.json
570 GH_AW_MCP_LOG_DIR: /tmp/gh-aw/mcp-logs/safeoutputs
571 run: |
572 # Environment variables are set above to prevent template injection
573 export DEBUG
574 export GH_AW_SAFE_OUTPUTS_PORT
575 export GH_AW_SAFE_OUTPUTS_API_KEY
576 export GH_AW_SAFE_OUTPUTS_TOOLS_PATH
577 export GH_AW_SAFE_OUTPUTS_CONFIG_PATH
578 export GH_AW_MCP_LOG_DIR
579
580 bash /opt/gh-aw/actions/start_safe_outputs_server.sh
581
582 - name: Start MCP Gateway
583 id: start-mcp-gateway
584 env:
585 GH_AW_SAFE_OUTPUTS: ${{ env.GH_AW_SAFE_OUTPUTS }}
586 GH_AW_SAFE_OUTPUTS_API_KEY: ${{ steps.safe-outputs-start.outputs.api_key }}
587 GH_AW_SAFE_OUTPUTS_PORT: ${{ steps.safe-outputs-start.outputs.port }}
588 GITHUB_MCP_LOCKDOWN: ${{ steps.determine-automatic-lockdown.outputs.lockdown == 'true' && '1' || '0' }}
589 GITHUB_MCP_SERVER_TOKEN: ${{ secrets.GH_AW_GITHUB_MCP_SERVER_TOKEN || secrets.GH_AW_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
590 run: |
591 set -eo pipefail
592 mkdir -p /tmp/gh-aw/mcp-config
593
594 # Export gateway environment variables for MCP config and gateway script
595 export MCP_GATEWAY_PORT="80"
596 export MCP_GATEWAY_DOMAIN="host.docker.internal"
597 MCP_GATEWAY_API_KEY=$(openssl rand -base64 45 | tr -d '/+=')
598 echo "::add-mask::${MCP_GATEWAY_API_KEY}"
599 export MCP_GATEWAY_API_KEY
600 export MCP_GATEWAY_PAYLOAD_DIR="/tmp/gh-aw/mcp-payloads"
601 mkdir -p "${MCP_GATEWAY_PAYLOAD_DIR}"
602 export DEBUG="*"
603
604 export GH_AW_ENGINE="copilot"
605 export MCP_GATEWAY_DOCKER_COMMAND='docker run -i --rm --network host -v /var/run/docker.sock:/var/run/docker.sock -e MCP_GATEWAY_PORT -e MCP_GATEWAY_DOMAIN -e MCP_GATEWAY_API_KEY -e MCP_GATEWAY_PAYLOAD_DIR -e DEBUG -e MCP_GATEWAY_LOG_DIR -e GH_AW_MCP_LOG_DIR -e GH_AW_SAFE_OUTPUTS -e GH_AW_SAFE_OUTPUTS_CONFIG_PATH -e GH_AW_SAFE_OUTPUTS_TOOLS_PATH -e GH_AW_ASSETS_BRANCH -e GH_AW_ASSETS_MAX_SIZE_KB -e GH_AW_ASSETS_ALLOWED_EXTS -e DEFAULT_BRANCH -e GITHUB_MCP_SERVER_TOKEN -e GITHUB_MCP_LOCKDOWN -e GITHUB_REPOSITORY -e GITHUB_SERVER_URL -e GITHUB_SHA -e GITHUB_WORKSPACE -e GITHUB_TOKEN -e GITHUB_RUN_ID -e GITHUB_RUN_NUMBER -e GITHUB_RUN_ATTEMPT -e GITHUB_JOB -e GITHUB_ACTION -e GITHUB_EVENT_NAME -e GITHUB_EVENT_PATH -e GITHUB_ACTOR -e GITHUB_ACTOR_ID -e GITHUB_TRIGGERING_ACTOR -e GITHUB_WORKFLOW -e GITHUB_WORKFLOW_REF -e GITHUB_WORKFLOW_SHA -e GITHUB_REF -e GITHUB_REF_NAME -e GITHUB_REF_TYPE -e GITHUB_HEAD_REF -e GITHUB_BASE_REF -e GH_AW_SAFE_OUTPUTS_PORT -e GH_AW_SAFE_OUTPUTS_API_KEY -v /tmp/gh-aw/mcp-payloads:/tmp/gh-aw/mcp-payloads:rw -v /opt:/opt:ro -v /tmp:/tmp:rw -v '"${GITHUB_WORKSPACE}"':'"${GITHUB_WORKSPACE}"':rw ghcr.io/github/gh-aw-mcpg:v0.1.5'
606
607 mkdir -p /home/runner/.copilot
608 cat << GH_AW_MCP_CONFIG_EOF | bash /opt/gh-aw/actions/start_mcp_gateway.sh
609 {
610 "mcpServers": {
611 "github": {
612 "type": "stdio",
613 "container": "ghcr.io/github/github-mcp-server:v0.31.0",
614 "env": {
615 "GITHUB_LOCKDOWN_MODE": "$GITHUB_MCP_LOCKDOWN",
616 "GITHUB_PERSONAL_ACCESS_TOKEN": "\${GITHUB_MCP_SERVER_TOKEN}",
617 "GITHUB_READ_ONLY": "1",
618 "GITHUB_TOOLSETS": "context,repos,issues,pull_requests"
619 }
620 },
621 "safeoutputs": {
622 "type": "http",
623 "url": "http://host.docker.internal:$GH_AW_SAFE_OUTPUTS_PORT",
624 "headers": {
625 "Authorization": "\${GH_AW_SAFE_OUTPUTS_API_KEY}"
626 }
627 }
628 },
629 "gateway": {
630 "port": $MCP_GATEWAY_PORT,
631 "domain": "${MCP_GATEWAY_DOMAIN}",
632 "apiKey": "${MCP_GATEWAY_API_KEY}",
633 "payloadDir": "${MCP_GATEWAY_PAYLOAD_DIR}"
634 }
635 }
636 GH_AW_MCP_CONFIG_EOF
637 - name: Generate workflow overview
638 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
639 with:
640 script: |
641 const { generateWorkflowOverview } = require('/opt/gh-aw/actions/generate_workflow_overview.cjs');
642 await generateWorkflowOverview(core);
643 - name: Download prompt artifact
644 uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8.0.1
645 with:
646 name: prompt
647 path: /tmp/gh-aw/aw-prompts
648 - name: Clean git credentials
649 run: bash /opt/gh-aw/actions/clean_git_credentials.sh
650 - name: Execute GitHub Copilot CLI
651 id: agentic_execution
652 # Copilot CLI tool arguments (sorted):
653 timeout-minutes: 20
654 run: |
655 set -o pipefail
656 # shellcheck disable=SC1003
657 sudo -E awf --env-all --container-workdir "${GITHUB_WORKSPACE}" --allow-domains "api.business.githubcopilot.com,api.enterprise.githubcopilot.com,api.github.com,api.githubcopilot.com,api.individual.githubcopilot.com,api.snapcraft.io,archive.ubuntu.com,azure.archive.ubuntu.com,crl.geotrust.com,crl.globalsign.com,crl.identrust.com,crl.sectigo.com,crl.thawte.com,crl.usertrust.com,crl.verisign.com,crl3.digicert.com,crl4.digicert.com,crls.ssl.com,github.com,host.docker.internal,json-schema.org,json.schemastore.org,keyserver.ubuntu.com,ocsp.digicert.com,ocsp.geotrust.com,ocsp.globalsign.com,ocsp.identrust.com,ocsp.sectigo.com,ocsp.ssl.com,ocsp.thawte.com,ocsp.usertrust.com,ocsp.verisign.com,packagecloud.io,packages.cloud.google.com,packages.microsoft.com,ppa.launchpad.net,raw.githubusercontent.com,registry.npmjs.org,s.symcb.com,s.symcd.com,security.ubuntu.com,telemetry.enterprise.githubcopilot.com,ts-crl.ws.symantec.com,ts-ocsp.ws.symantec.com" --log-level info --proxy-logs-dir /tmp/gh-aw/sandbox/firewall/logs --enable-host-access --image-tag 0.23.0 --skip-pull --enable-api-proxy \
658 -- /bin/bash -c '/usr/local/bin/copilot --add-dir /tmp/gh-aw/ --log-level all --log-dir /tmp/gh-aw/sandbox/agent/logs/ --add-dir "${GITHUB_WORKSPACE}" --disable-builtin-mcps --allow-all-tools --allow-all-paths --prompt "$(cat /tmp/gh-aw/aw-prompts/prompt.txt)"' 2>&1 | tee -a /tmp/gh-aw/agent-stdio.log
659 env:
660 COPILOT_AGENT_RUNNER_TYPE: STANDALONE
661 COPILOT_GITHUB_TOKEN: ${{ secrets.COPILOT_GITHUB_TOKEN }}
662 COPILOT_MODEL: claude-sonnet-4.5
663 GH_AW_MCP_CONFIG: /home/runner/.copilot/mcp-config.json
664 GH_AW_PROMPT: /tmp/gh-aw/aw-prompts/prompt.txt
665 GH_AW_SAFE_OUTPUTS: ${{ env.GH_AW_SAFE_OUTPUTS }}
666 GITHUB_HEAD_REF: ${{ github.head_ref }}
667 GITHUB_MCP_SERVER_TOKEN: ${{ secrets.GH_AW_GITHUB_MCP_SERVER_TOKEN || secrets.GH_AW_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
668 GITHUB_REF_NAME: ${{ github.ref_name }}
669 GITHUB_STEP_SUMMARY: ${{ env.GITHUB_STEP_SUMMARY }}
670 GITHUB_WORKSPACE: ${{ github.workspace }}
671 XDG_CONFIG_HOME: /home/runner
672 - name: Configure Git credentials
673 env:
674 REPO_NAME: ${{ github.repository }}
675 SERVER_URL: ${{ github.server_url }}
676 run: |
677 git config --global user.email "github-actions[bot]@users.noreply.github.com"
678 git config --global user.name "github-actions[bot]"
679 git config --global am.keepcr true
680 # Re-authenticate git with GitHub token
681 SERVER_URL_STRIPPED="${SERVER_URL#https://}"
682 git remote set-url origin "https://x-access-token:${{ github.token }}@${SERVER_URL_STRIPPED}/${REPO_NAME}.git"
683 echo "Git configured with standard GitHub Actions identity"
684 - name: Copy Copilot session state files to logs
685 if: always()
686 continue-on-error: true
687 run: |
688 # Copy Copilot session state files to logs folder for artifact collection
689 # This ensures they are in /tmp/gh-aw/ where secret redaction can scan them
690 SESSION_STATE_DIR="$HOME/.copilot/session-state"
691 LOGS_DIR="/tmp/gh-aw/sandbox/agent/logs"
692
693 if [ -d "$SESSION_STATE_DIR" ]; then
694 echo "Copying Copilot session state files from $SESSION_STATE_DIR to $LOGS_DIR"
695 mkdir -p "$LOGS_DIR"
696 cp -v "$SESSION_STATE_DIR"/*.jsonl "$LOGS_DIR/" 2>/dev/null || true
697 echo "Session state files copied successfully"
698 else
699 echo "No session-state directory found at $SESSION_STATE_DIR"
700 fi
701 - name: Stop MCP Gateway
702 if: always()
703 continue-on-error: true
704 env:
705 MCP_GATEWAY_PORT: ${{ steps.start-mcp-gateway.outputs.gateway-port }}
706 MCP_GATEWAY_API_KEY: ${{ steps.start-mcp-gateway.outputs.gateway-api-key }}
707 GATEWAY_PID: ${{ steps.start-mcp-gateway.outputs.gateway-pid }}
708 run: |
709 bash /opt/gh-aw/actions/stop_mcp_gateway.sh "$GATEWAY_PID"
710 - name: Redact secrets in logs
711 if: always()
712 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
713 with:
714 script: |
715 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
716 setupGlobals(core, github, context, exec, io);
717 const { main } = require('/opt/gh-aw/actions/redact_secrets.cjs');
718 await main();
719 env:
720 GH_AW_SECRET_NAMES: 'COPILOT_GITHUB_TOKEN,GH_AW_GITHUB_MCP_SERVER_TOKEN,GH_AW_GITHUB_TOKEN,GITHUB_TOKEN'
721 SECRET_COPILOT_GITHUB_TOKEN: ${{ secrets.COPILOT_GITHUB_TOKEN }}
722 SECRET_GH_AW_GITHUB_MCP_SERVER_TOKEN: ${{ secrets.GH_AW_GITHUB_MCP_SERVER_TOKEN }}
723 SECRET_GH_AW_GITHUB_TOKEN: ${{ secrets.GH_AW_GITHUB_TOKEN }}
724 SECRET_GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
725 - name: Upload Safe Outputs
726 if: always()
727 uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
728 with:
729 name: safe-output
730 path: ${{ env.GH_AW_SAFE_OUTPUTS }}
731 if-no-files-found: warn
732 - name: Ingest agent output
733 id: collect_output
734 if: always()
735 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
736 env:
737 GH_AW_SAFE_OUTPUTS: ${{ env.GH_AW_SAFE_OUTPUTS }}
738 GH_AW_ALLOWED_DOMAINS: "api.business.githubcopilot.com,api.enterprise.githubcopilot.com,api.github.com,api.githubcopilot.com,api.individual.githubcopilot.com,api.snapcraft.io,archive.ubuntu.com,azure.archive.ubuntu.com,crl.geotrust.com,crl.globalsign.com,crl.identrust.com,crl.sectigo.com,crl.thawte.com,crl.usertrust.com,crl.verisign.com,crl3.digicert.com,crl4.digicert.com,crls.ssl.com,github.com,host.docker.internal,json-schema.org,json.schemastore.org,keyserver.ubuntu.com,ocsp.digicert.com,ocsp.geotrust.com,ocsp.globalsign.com,ocsp.identrust.com,ocsp.sectigo.com,ocsp.ssl.com,ocsp.thawte.com,ocsp.usertrust.com,ocsp.verisign.com,packagecloud.io,packages.cloud.google.com,packages.microsoft.com,ppa.launchpad.net,raw.githubusercontent.com,registry.npmjs.org,s.symcb.com,s.symcd.com,security.ubuntu.com,telemetry.enterprise.githubcopilot.com,ts-crl.ws.symantec.com,ts-ocsp.ws.symantec.com"
739 GITHUB_SERVER_URL: ${{ github.server_url }}
740 GITHUB_API_URL: ${{ github.api_url }}
741 with:
742 script: |
743 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
744 setupGlobals(core, github, context, exec, io);
745 const { main } = require('/opt/gh-aw/actions/collect_ndjson_output.cjs');
746 await main();
747 - name: Upload sanitized agent output
748 if: always() && env.GH_AW_AGENT_OUTPUT
749 uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
750 with:
751 name: agent-output
752 path: ${{ env.GH_AW_AGENT_OUTPUT }}
753 if-no-files-found: warn
754 - name: Upload engine output files
755 uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
756 with:
757 name: agent_outputs
758 path: |
759 /tmp/gh-aw/sandbox/agent/logs/
760 /tmp/gh-aw/redacted-urls.log
761 if-no-files-found: ignore
762 - name: Parse agent logs for step summary
763 if: always()
764 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
765 env:
766 GH_AW_AGENT_OUTPUT: /tmp/gh-aw/sandbox/agent/logs/
767 with:
768 script: |
769 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
770 setupGlobals(core, github, context, exec, io);
771 const { main } = require('/opt/gh-aw/actions/parse_copilot_log.cjs');
772 await main();
773 - name: Parse MCP Gateway logs for step summary
774 if: always()
775 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
776 with:
777 script: |
778 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
779 setupGlobals(core, github, context, exec, io);
780 const { main } = require('/opt/gh-aw/actions/parse_mcp_gateway_log.cjs');
781 await main();
782 - name: Print firewall logs
783 if: always()
784 continue-on-error: true
785 env:
786 AWF_LOGS_DIR: /tmp/gh-aw/sandbox/firewall/logs
787 run: |
788 # Fix permissions on firewall logs so they can be uploaded as artifacts
789 # AWF runs with sudo, creating files owned by root
790 sudo chmod -R a+r /tmp/gh-aw/sandbox/firewall/logs 2>/dev/null || true
791 # Only run awf logs summary if awf command exists (it may not be installed if workflow failed before install step)
792 if command -v awf &> /dev/null; then
793 awf logs summary | tee -a "$GITHUB_STEP_SUMMARY"
794 else
795 echo 'AWF binary not installed, skipping firewall log summary'
796 fi
797 - name: Upload agent artifacts
798 if: always()
799 continue-on-error: true
800 uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
801 with:
802 name: agent-artifacts
803 path: |
804 /tmp/gh-aw/aw-prompts/prompt.txt
805 /tmp/gh-aw/aw_info.json
806 /tmp/gh-aw/mcp-logs/
807 /tmp/gh-aw/sandbox/firewall/logs/
808 /tmp/gh-aw/agent-stdio.log
809 /tmp/gh-aw/agent/
810 if-no-files-found: ignore
811 # --- Threat Detection (inline) ---
812 - name: Check if detection needed
813 id: detection_guard
814 if: always()
815 env:
816 OUTPUT_TYPES: ${{ steps.collect_output.outputs.output_types }}
817 HAS_PATCH: ${{ steps.collect_output.outputs.has_patch }}
818 run: |
819 if [[ -n "$OUTPUT_TYPES" || "$HAS_PATCH" == "true" ]]; then
820 echo "run_detection=true" >> "$GITHUB_OUTPUT"
821 echo "Detection will run: output_types=$OUTPUT_TYPES, has_patch=$HAS_PATCH"
822 else
823 echo "run_detection=false" >> "$GITHUB_OUTPUT"
824 echo "Detection skipped: no agent outputs or patches to analyze"
825 fi
826 - name: Clear MCP configuration for detection
827 if: always() && steps.detection_guard.outputs.run_detection == 'true'
828 run: |
829 rm -f /tmp/gh-aw/mcp-config/mcp-servers.json
830 rm -f /home/runner/.copilot/mcp-config.json
831 rm -f "$GITHUB_WORKSPACE/.gemini/settings.json"
832 - name: Prepare threat detection files
833 if: always() && steps.detection_guard.outputs.run_detection == 'true'
834 run: |
835 mkdir -p /tmp/gh-aw/threat-detection/aw-prompts
836 cp /tmp/gh-aw/aw-prompts/prompt.txt /tmp/gh-aw/threat-detection/aw-prompts/prompt.txt 2>/dev/null || true
837 cp /tmp/gh-aw/agent_output.json /tmp/gh-aw/threat-detection/agent_output.json 2>/dev/null || true
838 for f in /tmp/gh-aw/aw-*.patch; do
839 [ -f "$f" ] && cp "$f" /tmp/gh-aw/threat-detection/ 2>/dev/null || true
840 done
841 echo "Prepared threat detection files:"
842 ls -la /tmp/gh-aw/threat-detection/ 2>/dev/null || true
843 - name: Setup threat detection
844 if: always() && steps.detection_guard.outputs.run_detection == 'true'
845 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
846 env:
847 WORKFLOW_NAME: "Relevance Check Summary Report"
848 WORKFLOW_DESCRIPTION: "Manually triggered workflow that summarizes all open issues and PRs with a /relevance-check response into a single issue"
849 HAS_PATCH: ${{ steps.collect_output.outputs.has_patch }}
850 with:
851 script: |
852 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
853 setupGlobals(core, github, context, exec, io);
854 const { main } = require('/opt/gh-aw/actions/setup_threat_detection.cjs');
855 await main();
856 - name: Ensure threat-detection directory and log
857 if: always() && steps.detection_guard.outputs.run_detection == 'true'
858 run: |
859 mkdir -p /tmp/gh-aw/threat-detection
860 touch /tmp/gh-aw/threat-detection/detection.log
861 - name: Execute GitHub Copilot CLI
862 if: always() && steps.detection_guard.outputs.run_detection == 'true'
863 id: detection_agentic_execution
864 # Copilot CLI tool arguments (sorted):
865 # --allow-tool shell(cat)
866 # --allow-tool shell(grep)
867 # --allow-tool shell(head)
868 # --allow-tool shell(jq)
869 # --allow-tool shell(ls)
870 # --allow-tool shell(tail)
871 # --allow-tool shell(wc)
872 timeout-minutes: 20
873 run: |
874 set -o pipefail
875 # shellcheck disable=SC1003
876 sudo -E awf --env-all --container-workdir "${GITHUB_WORKSPACE}" --allow-domains "api.business.githubcopilot.com,api.enterprise.githubcopilot.com,api.github.com,api.githubcopilot.com,api.individual.githubcopilot.com,github.com,host.docker.internal,raw.githubusercontent.com,registry.npmjs.org,telemetry.enterprise.githubcopilot.com" --log-level info --proxy-logs-dir /tmp/gh-aw/sandbox/firewall/logs --enable-host-access --image-tag 0.23.0 --skip-pull --enable-api-proxy \
877 -- /bin/bash -c '/usr/local/bin/copilot --add-dir /tmp/gh-aw/ --log-level all --log-dir /tmp/gh-aw/sandbox/agent/logs/ --add-dir "${GITHUB_WORKSPACE}" --disable-builtin-mcps --allow-tool '\''shell(cat)'\'' --allow-tool '\''shell(grep)'\'' --allow-tool '\''shell(head)'\'' --allow-tool '\''shell(jq)'\'' --allow-tool '\''shell(ls)'\'' --allow-tool '\''shell(tail)'\'' --allow-tool '\''shell(wc)'\'' --prompt "$(cat /tmp/gh-aw/aw-prompts/prompt.txt)"' 2>&1 | tee -a /tmp/gh-aw/threat-detection/detection.log
878 env:
879 COPILOT_AGENT_RUNNER_TYPE: STANDALONE
880 COPILOT_GITHUB_TOKEN: ${{ secrets.COPILOT_GITHUB_TOKEN }}
881 COPILOT_MODEL: claude-sonnet-4.5
882 GH_AW_PROMPT: /tmp/gh-aw/aw-prompts/prompt.txt
883 GITHUB_HEAD_REF: ${{ github.head_ref }}
884 GITHUB_REF_NAME: ${{ github.ref_name }}
885 GITHUB_STEP_SUMMARY: ${{ env.GITHUB_STEP_SUMMARY }}
886 GITHUB_WORKSPACE: ${{ github.workspace }}
887 XDG_CONFIG_HOME: /home/runner
888 - name: Parse threat detection results
889 id: parse_detection_results
890 if: always() && steps.detection_guard.outputs.run_detection == 'true'
891 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
892 with:
893 script: |
894 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
895 setupGlobals(core, github, context, exec, io);
896 const { main } = require('/opt/gh-aw/actions/parse_threat_detection_results.cjs');
897 await main();
898 - name: Upload threat detection log
899 if: always() && steps.detection_guard.outputs.run_detection == 'true'
900 uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
901 with:
902 name: threat-detection.log
903 path: /tmp/gh-aw/threat-detection/detection.log
904 if-no-files-found: ignore
905 - name: Set detection conclusion
906 id: detection_conclusion
907 if: always()
908 env:
909 RUN_DETECTION: ${{ steps.detection_guard.outputs.run_detection }}
910 DETECTION_SUCCESS: ${{ steps.parse_detection_results.outputs.success }}
911 run: |
912 if [[ "$RUN_DETECTION" != "true" ]]; then
913 echo "conclusion=skipped" >> "$GITHUB_OUTPUT"
914 echo "success=true" >> "$GITHUB_OUTPUT"
915 echo "Detection was not needed, marking as skipped"
916 elif [[ "$DETECTION_SUCCESS" == "true" ]]; then
917 echo "conclusion=success" >> "$GITHUB_OUTPUT"
918 echo "success=true" >> "$GITHUB_OUTPUT"
919 echo "Detection passed successfully"
920 else
921 echo "conclusion=failure" >> "$GITHUB_OUTPUT"
922 echo "success=false" >> "$GITHUB_OUTPUT"
923 echo "Detection found issues"
924 fi
925
926 conclusion:
927 needs:
928 - activation
929 - agent
930 - safe_outputs
931 if: (always()) && (needs.agent.result != 'skipped')
932 runs-on: ubuntu-slim
933 permissions:
934 contents: read
935 issues: write
936 outputs:
937 noop_message: ${{ steps.noop.outputs.noop_message }}
938 tools_reported: ${{ steps.missing_tool.outputs.tools_reported }}
939 total_count: ${{ steps.missing_tool.outputs.total_count }}
940 steps:
941 - name: Setup Scripts
942 uses: github/gh-aw/actions/setup@80f243ca31e3f6632caaeae6930f5a00018fd24b # v0.65.0
943 with:
944 destination: /opt/gh-aw/actions
945 - name: Download agent output artifact
946 continue-on-error: true
947 uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8.0.1
948 with:
949 name: agent-output
950 path: /tmp/gh-aw/safeoutputs/
951 - name: Setup agent output environment variable
952 run: |
953 mkdir -p /tmp/gh-aw/safeoutputs/
954 find "/tmp/gh-aw/safeoutputs/" -type f -print
955 echo "GH_AW_AGENT_OUTPUT=/tmp/gh-aw/safeoutputs/agent_output.json" >> "$GITHUB_ENV"
956 - name: Process No-Op Messages
957 id: noop
958 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
959 env:
960 GH_AW_AGENT_OUTPUT: ${{ env.GH_AW_AGENT_OUTPUT }}
961 GH_AW_NOOP_MAX: "1"
962 GH_AW_WORKFLOW_NAME: "Relevance Check Summary Report"
963 with:
964 github-token: ${{ secrets.GH_AW_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
965 script: |
966 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
967 setupGlobals(core, github, context, exec, io);
968 const { main } = require('/opt/gh-aw/actions/noop.cjs');
969 await main();
970 - name: Record Missing Tool
971 id: missing_tool
972 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
973 env:
974 GH_AW_AGENT_OUTPUT: ${{ env.GH_AW_AGENT_OUTPUT }}
975 GH_AW_WORKFLOW_NAME: "Relevance Check Summary Report"
976 with:
977 github-token: ${{ secrets.GH_AW_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
978 script: |
979 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
980 setupGlobals(core, github, context, exec, io);
981 const { main } = require('/opt/gh-aw/actions/missing_tool.cjs');
982 await main();
983 - name: Handle Agent Failure
984 id: handle_agent_failure
985 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
986 env:
987 GH_AW_AGENT_OUTPUT: ${{ env.GH_AW_AGENT_OUTPUT }}
988 GH_AW_WORKFLOW_NAME: "Relevance Check Summary Report"
989 GH_AW_RUN_URL: ${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }}
990 GH_AW_AGENT_CONCLUSION: ${{ needs.agent.result }}
991 GH_AW_WORKFLOW_ID: "relevance-summary"
992 GH_AW_SECRET_VERIFICATION_RESULT: ${{ needs.agent.outputs.secret_verification_result }}
993 GH_AW_CHECKOUT_PR_SUCCESS: ${{ needs.agent.outputs.checkout_pr_success }}
994 GH_AW_GROUP_REPORTS: "false"
995 with:
996 github-token: ${{ secrets.GH_AW_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
997 script: |
998 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
999 setupGlobals(core, github, context, exec, io);
1000 const { main } = require('/opt/gh-aw/actions/handle_agent_failure.cjs');
1001 await main();
1002 - name: Handle No-Op Message
1003 id: handle_noop_message
1004 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
1005 env:
1006 GH_AW_AGENT_OUTPUT: ${{ env.GH_AW_AGENT_OUTPUT }}
1007 GH_AW_WORKFLOW_NAME: "Relevance Check Summary Report"
1008 GH_AW_RUN_URL: ${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }}
1009 GH_AW_AGENT_CONCLUSION: ${{ needs.agent.result }}
1010 GH_AW_NOOP_MESSAGE: ${{ steps.noop.outputs.noop_message }}
1011 GH_AW_NOOP_REPORT_AS_ISSUE: "true"
1012 with:
1013 github-token: ${{ secrets.GH_AW_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
1014 script: |
1015 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
1016 setupGlobals(core, github, context, exec, io);
1017 const { main } = require('/opt/gh-aw/actions/handle_noop_message.cjs');
1018 await main();
1019
1020 safe_outputs:
1021 needs: agent
1022 if: ((!cancelled()) && (needs.agent.result != 'skipped')) && (needs.agent.outputs.detection_success == 'true')
1023 runs-on: ubuntu-slim
1024 permissions:
1025 contents: read
1026 issues: write
1027 timeout-minutes: 15
1028 env:
1029 GH_AW_ENGINE_ID: "copilot"
1030 GH_AW_ENGINE_MODEL: "claude-sonnet-4.5"
1031 GH_AW_WORKFLOW_ID: "relevance-summary"
1032 GH_AW_WORKFLOW_NAME: "Relevance Check Summary Report"
1033 outputs:
1034 code_push_failure_count: ${{ steps.process_safe_outputs.outputs.code_push_failure_count }}
1035 code_push_failure_errors: ${{ steps.process_safe_outputs.outputs.code_push_failure_errors }}
1036 create_discussion_error_count: ${{ steps.process_safe_outputs.outputs.create_discussion_error_count }}
1037 create_discussion_errors: ${{ steps.process_safe_outputs.outputs.create_discussion_errors }}
1038 process_safe_outputs_processed_count: ${{ steps.process_safe_outputs.outputs.processed_count }}
1039 process_safe_outputs_temporary_id_map: ${{ steps.process_safe_outputs.outputs.temporary_id_map }}
1040 steps:
1041 - name: Setup Scripts
1042 uses: github/gh-aw/actions/setup@80f243ca31e3f6632caaeae6930f5a00018fd24b # v0.65.0
1043 with:
1044 destination: /opt/gh-aw/actions
1045 - name: Download agent output artifact
1046 continue-on-error: true
1047 uses: actions/download-artifact@3e5f45b2cfb9172054b4087a40e8e0b5a5461e7c # v8.0.1
1048 with:
1049 name: agent-output
1050 path: /tmp/gh-aw/safeoutputs/
1051 - name: Setup agent output environment variable
1052 run: |
1053 mkdir -p /tmp/gh-aw/safeoutputs/
1054 find "/tmp/gh-aw/safeoutputs/" -type f -print
1055 echo "GH_AW_AGENT_OUTPUT=/tmp/gh-aw/safeoutputs/agent_output.json" >> "$GITHUB_ENV"
1056 - name: Process Safe Outputs
1057 id: process_safe_outputs
1058 uses: actions/github-script@3a2844b7e9c422d3c10d287c895573f7108da1b3 # v9.0.0
1059 env:
1060 GH_AW_AGENT_OUTPUT: ${{ env.GH_AW_AGENT_OUTPUT }}
1061 GH_AW_SAFE_OUTPUTS_HANDLER_CONFIG: "{\"create_issue\":{\"close_older_issues\":true,\"labels\":[\"report\"],\"max\":1,\"title_prefix\":\"Relevance Summary:\"},\"missing_data\":{},\"missing_tool\":{}}"
1062 with:
1063 github-token: ${{ secrets.GH_AW_GITHUB_TOKEN || secrets.GITHUB_TOKEN }}
1064 script: |
1065 const { setupGlobals } = require('/opt/gh-aw/actions/setup_globals.cjs');
1066 setupGlobals(core, github, context, exec, io);
1067 const { main } = require('/opt/gh-aw/actions/safe_output_handler_manager.cjs');
1068 await main();
1069 - name: Upload safe output items manifest
1070 if: always()
1071 uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
1072 with:
1073 name: safe-output-items
1074 path: /tmp/safe-output-items.jsonl
1075 if-no-files-found: warn
1076
1077