Triggers
The on: section uses standard GitHub Actions syntax to define workflow triggers. For example:
on: issues: types: [opened]Trigger Types
Section titled “Trigger Types”GitHub Agentic Workflows supports all standard GitHub Actions triggers plus additional enhancements for reactions, cost control, and advanced filtering.
Dispatch Triggers (workflow_dispatch:)
Section titled “Dispatch Triggers (workflow_dispatch:)”Run workflows manually from the GitHub UI, API, or via gh aw run/gh aw trial. Full syntax reference.
Basic trigger:
on: workflow_dispatch:With input parameters:
on: workflow_dispatch: inputs: topic: description: 'Research topic' required: true type: string priority: description: 'Task priority' required: false type: choice options: - low - medium - high default: medium deploy_env: description: 'Target environment' required: false type: environment default: stagingAccessing Inputs in Markdown
Section titled “Accessing Inputs in Markdown”Use ${{ github.event.inputs.INPUT_NAME }} expressions to access workflow_dispatch inputs in your markdown content:
---on: workflow_dispatch: inputs: topic: description: 'Research topic' required: true type: stringpermissions: contents: readsafe-outputs: create-discussion:---
# Research Assistant
Research the following topic: "${{ github.event.inputs.topic }}"
Provide a comprehensive summary with key findings and recommendations.Supported input types:
string- Free-form text inputboolean- True/false checkboxchoice- Dropdown selection with predefined optionsenvironment- Dropdown selection of GitHub environments configured in the repository
The environment input type automatically populates a dropdown with environments configured in repository Settings → Environments. It returns the environment name as a string and supports a default value. Unlike the manual-approval: field, using an environment input does not enforce environment protection rules—it only provides the environment name as a string value for use in your workflow logic.
Scheduled Triggers (schedule:)
Section titled “Scheduled Triggers (schedule:)”Run workflows on a recurring schedule using human-friendly expressions or cron syntax.
Fuzzy Scheduling (Recommended):
Use fuzzy schedules to automatically scatter execution times and avoid load spikes:
on: schedule: daily # Compiler assigns a unique scattered time per workflowUse the around constraint for a preferred time with flexibility:
on: schedule: daily around 14:00 # Scatters within ±1 hour (13:00-15:00)For workflows that should only run during specific hours (like business hours), use the between constraint:
on: schedule: daily between 9:00 and 17:00 # Scatters within 9am-5pm rangeThe compiler assigns each workflow a unique, deterministic execution time based on the file path, ensuring load distribution and consistency across recompiles. UTC offsets are supported on any time expression (e.g., daily between 9am and 5pm utc-5).
For a fixed time, use standard cron syntax:
on: schedule: - cron: "30 6 * * 1" # Monday at 06:30 UTC - cron: "0 9 15 * *" # 15th of month at 09:00 UTC| Format | Example | Result | Notes |
|---|---|---|---|
| Hourly (Fuzzy) | hourly | 58 */1 * * * | Compiler assigns scattered minute |
| Daily (Fuzzy) | daily | 43 5 * * * | Compiler assigns scattered time |
daily around 14:00 | 20 14 * * * | Scattered within ±1 hour (13:00-15:00) | |
daily between 9:00 and 17:00 | 37 13 * * * | Scattered within range (9:00-17:00) | |
daily between 9am and 5pm utc-5 | 12 18 * * * | With UTC offset (9am-5pm EST → 2pm-10pm UTC) | |
daily around 3pm utc-5 | 33 19 * * * | With UTC offset (3 PM EST → 8 PM UTC) | |
| Weekly (Fuzzy) | weekly or weekly on monday | 43 5 * * 1 | Compiler assigns scattered time |
weekly on friday around 5pm | 18 16 * * 5 | Scattered within ±1 hour | |
| Intervals | every 10 minutes | */10 * * * * | Minimum 5 minutes |
every 2h | 53 */2 * * * | Fuzzy: scattered minute offset | |
0 */2 * * * | 0 */2 * * * | Cron syntax for fixed times |
Time formats: HH:MM (24-hour), midnight, noon, 1pm-12pm, 1am-12am
UTC offsets: Add utc+N or utc-N to any time (e.g., daily around 14:00 utc-5)
Human-friendly formats are automatically converted to standard cron expressions, with the original format preserved as a comment in the generated workflow file.
Issue Triggers (issues:)
Section titled “Issue Triggers (issues:)”Trigger on issue events. Full event reference.
on: issues: types: [opened, edited, labeled]Issue Locking (lock-for-agent:)
Section titled “Issue Locking (lock-for-agent:)”Prevent concurrent modifications to an issue during workflow execution by setting lock-for-agent: true:
on: issues: types: [opened, edited] lock-for-agent: trueWhen enabled, the issue is locked at workflow start and unlocked after completion (or before safe-output processing). The unlock step uses always() to ensure cleanup even on failure. Useful for workflows that make multiple sequential updates to an issue or need to prevent race conditions.
Requirements:
- Requires
issues: writepermission (automatically added to activation and conclusion jobs) - Pull requests are silently skipped (they cannot be locked via the issues API)
- Already-locked issues are skipped without error
Example workflow:
---on: issues: types: [opened] lock-for-agent: truepermissions: contents: read issues: writesafe-outputs: add-comment: max: 3---
# Issue Processor with Locking
Process the issue and make multiple updates without interferencefrom concurrent modifications.
Context: "${{ needs.activation.outputs.text }}"Pull Request Triggers (pull_request:)
Section titled “Pull Request Triggers (pull_request:)”Trigger on pull request events. Full event reference.
Code availability: When triggered by a pull request event, the coding agent has access to both the PR branch and the default branch.
on: pull_request: types: [opened, synchronize, labeled] names: [ready-for-review, needs-review] reaction: "rocket"Fork Filtering (forks:)
Section titled “Fork Filtering (forks:)”Pull request workflows block forks by default for security. Use the forks: field to allow specific fork patterns:
on: pull_request: types: [opened, synchronize] forks: ["trusted-org/*"] # Allow forks from trusted-orgAvailable patterns:
["*"]- Allow all forks (use with caution)["owner/*"]- Allow forks from specific organization or user["owner/repo"]- Allow specific repository- Omit
forksfield - Default behavior (same-repository PRs only)
The compiler uses repository ID comparison for reliable fork detection that is not affected by repository renames.
Comment Triggers
Section titled “Comment Triggers”Note: issue_comment events also fire for comments on pull requests (GitHub models PR comments as issue comments). When a comment is on a pull request, the coding agent has access to both the PR branch and the default branch.
on: issue_comment: types: [created] pull_request_review_comment: types: [created] discussion_comment: types: [created] reaction: "eyes"Comment Locking (lock-for-agent:)
Section titled “Comment Locking (lock-for-agent:)”For issue_comment events, you can lock the parent issue during workflow execution:
on: issue_comment: types: [created, edited] lock-for-agent: trueThis prevents concurrent modifications to the issue while processing the comment. The locking behavior is identical to the issues: trigger (see Issue Locking above for full details).
Note: Pull request comments are silently skipped as pull requests cannot be locked via the issues API.
Workflow Run Triggers (workflow_run:)
Section titled “Workflow Run Triggers (workflow_run:)”Trigger workflows after another workflow completes. Full event reference.
on: workflow_run: workflows: ["CI"] types: [completed] branches: - main - developWorkflows with workflow_run triggers include automatic security protections:
- Repository/fork validation: The compiler injects repository ID and fork checks, rejecting cross-repository or fork-triggered runs.
- Branch restrictions required: Include
branchesto limit triggering branches; without them the compiler warns (or errors in strict mode).
See the Security Architecture for details.
Command Triggers (slash_command:)
Section titled “Command Triggers (slash_command:)”The slash_command: trigger creates workflows that respond to /command-name mentions in issues, pull requests, and comments. See Command Triggers for complete documentation including event filtering, context text, reactions, and examples.
Label Filtering (names:)
Section titled “Label Filtering (names:)”Filter issue and pull request triggers by label names using the names: field:
on: issues: types: [labeled, unlabeled] names: [bug, critical, security]Use convenient shorthand for label-based triggers:
on: issue labeled bugon: issue labeled bug, enhancement, priority-high # Multiple labelson: pull_request labeled needs-review, ready-to-mergeAll shorthand formats compile to standard GitHub Actions syntax and automatically include the workflow_dispatch trigger. Supported for issue, pull_request, and discussion events. See LabelOps workflows for automation examples.
Reactions (reaction:)
Section titled “Reactions (reaction:)”Enable emoji reactions on triggering items (issues, PRs, comments, discussions) to provide visual workflow status feedback:
on: issues: types: [opened] reaction: "eyes"The reaction is added to the triggering item. For issues/PRs, a comment with the workflow run link is created. For comment events in command workflows, the comment is edited to include the run link.
Available reactions: +1 , -1 , laugh , confused , heart , hooray , rocket , eyes
Activation Token (on.github-token:, on.github-app:)
Section titled “Activation Token (on.github-token:, on.github-app:)”Configure a custom GitHub token or GitHub App for the activation job and all skip-if search checks. The activation job posts the initial reaction and status comment on the triggering item, and skip-if checks use the same token to query the GitHub Search API. By default all of these operations use the workflow’s GITHUB_TOKEN.
Use github-token: to supply a PAT or custom token:
on: issues: types: [opened] reaction: "eyes" github-token: ${{ secrets.MY_TOKEN }}Use github-app: to mint a short-lived installation token instead:
on: issues: types: [opened] reaction: "rocket" github-app: app-id: ${{ vars.APP_ID }} private-key: ${{ secrets.APP_KEY }}The github-app object accepts the same fields as the GitHub App configuration used elsewhere in the framework (app-id, private-key, and optionally owner and repositories). The token is minted once in the pre-activation job and is shared across the reaction step, the status comment step, and any skip-if search steps.
Both github-token and github-app can be defined in a shared agentic workflow and will be automatically inherited by any workflow that imports it (first-wins strategy). This means a central CentralRepoOps shared workflow can define the app config once and all importing workflows benefit automatically:
# shared-ops.md - define app config onceon: workflow_call: github-app: app-id: ${{ secrets.ORG_APP_ID }} private-key: ${{ secrets.ORG_APP_PRIVATE_KEY }} owner: myorg# any-workflow.md - inherits github-app from the importimports: - .github/workflows/shared/shared-ops.mdon: schedule: - cron: "*/30 * * * *" skip-if-no-match: query: "org:myorg label:agent-fix is:issue is:open" scope: noneStop After Configuration (stop-after:)
Section titled “Stop After Configuration (stop-after:)”Automatically disable workflow triggering after a deadline to control costs.
on: weekly on monday stop-after: "+25h" # 25 hours from compilation timeAccepts absolute dates (YYYY-MM-DD, MM/DD/YYYY, DD/MM/YYYY, January 2 2006, 1st June 2025, ISO 8601) or relative deltas (+7d, +25h, +1d12h30m) calculated from compilation time. The minimum granularity is hours - minute-only units (e.g., +30m) are not allowed. Recompiling the workflow resets the stop time.
Manual Approval Gates (manual-approval:)
Section titled “Manual Approval Gates (manual-approval:)”Require manual approval before workflow execution using GitHub environment protection rules:
on: workflow_dispatch: manual-approval: productionSets the environment on the activation job for human-in-the-loop approval before execution. The value must match a configured environment in repository Settings → Environments (approval rules, required reviewers, wait timers). See GitHub’s environment documentation for configuration details.
Skip-If-Match Condition (skip-if-match:)
Section titled “Skip-If-Match Condition (skip-if-match:)”Conditionally skip workflow execution when a GitHub search query has matches. Useful for preventing duplicate scheduled runs or waiting for prerequisites.
on: daily skip-if-match: 'is:issue is:open in:title "[daily-report]"' # Skip if any matchon: weekly on monday skip-if-match: query: "is:pr is:open label:urgent" max: 3 # Skip if 3 or more PRs matchA pre-activation check runs the search query against the current repository. If matches reach or exceed the threshold (default max: 1), the workflow is skipped. The query is automatically scoped to the current repository and supports all standard GitHub search qualifiers (is:, label:, in:title, author:, etc.).
Cross-Repo and Org-Wide Queries
Section titled “Cross-Repo and Org-Wide Queries”By default the query is scoped to the current repository. Use scope: none to disable this and search across an entire org. For cross-repo or org-wide searches that require elevated permissions, configure github-token or github-app at the top-level on: section — the same token is shared across all skip-if checks and the activation job:
on: schedule: - cron: "*/15 * * * *" skip-if-match: query: "org:myorg label:ops:in-progress is:issue is:open" scope: none github-app: app-id: ${{ secrets.WORKFLOW_APP_ID }} private-key: ${{ secrets.WORKFLOW_APP_PRIVATE_KEY }} owner: myorg| Field | Location | Description |
|---|---|---|
scope: none | inside skip-if-match | Disables the automatic repo:owner/repo qualifier |
github-token | top-level on: | Custom PAT or token for all skip-if searches (e.g. ${{ secrets.CROSS_ORG_TOKEN }}) |
github-app | top-level on: | Mints a short-lived installation token shared across all skip-if steps; requires app-id and private-key |
github-token and github-app are mutually exclusive. String shorthand always uses the default GITHUB_TOKEN scoped to the current repository.
Skip-If-No-Match Condition (skip-if-no-match:)
Section titled “Skip-If-No-Match Condition (skip-if-no-match:)”Conditionally skip workflow execution when a GitHub search query has no matches (or fewer than the minimum required). This is the opposite of skip-if-match.
on: weekly on monday skip-if-no-match: 'is:pr is:open label:ready-to-deploy' # Skip if no matcheson: workflow_dispatch: skip-if-no-match: query: "is:issue is:open label:urgent" min: 3 # Only run if 3 or more issues matchA pre-activation check runs the search query against the current repository. If matches are below the threshold (default min: 1), the workflow is skipped. Can be combined with skip-if-match for complex conditions.
The same scope: none field available on skip-if-match works identically here. Authentication (github-token / github-app) is configured at the top-level on: section and is shared across all skip-if checks — a single mint step is emitted for both:
on: schedule: - cron: "*/15 * * * *" skip-if-no-match: query: "org:myorg label:agent-fix -label:ops:agentic is:issue is:open" scope: none github-app: app-id: ${{ secrets.WORKFLOW_APP_ID }} private-key: ${{ secrets.WORKFLOW_APP_PRIVATE_KEY }} owner: myorgTrigger Shorthands
Section titled “Trigger Shorthands”Instead of writing full YAML trigger configurations, you can use natural-language shorthand strings with on:. The compiler expands these into standard GitHub Actions trigger syntax and automatically includes workflow_dispatch so the workflow can also be run manually.
For label-based shorthands (on: issue labeled bug, on: pull_request labeled needs-review), see Label Filtering above.
Push and Pull Request
Section titled “Push and Pull Request”on: push to main # Push to specific branchon: push tags v* # Push tags matching patternon: pull_request opened # PR with activity typeon: pull_request merged # PR merged (maps to closed + merge condition)on: pull_request affecting src/** # PR touching paths (opened, synchronize, reopened)on: pull_request opened affecting docs/** # Activity type + path filterpull is an alias for pull_request. Valid activity types: opened, edited, closed, reopened, synchronize, assigned, unassigned, labeled, unlabeled, review_requested, merged.
Issues and Discussions
Section titled “Issues and Discussions”on: issue opened # Issue with activity typeon: issue opened labeled bug # Issue opened with specific label (adds job condition)on: discussion created # Discussion with activity typeValid issue types: opened, edited, closed, reopened, assigned, unassigned, labeled, unlabeled, deleted, transferred. Valid discussion types: created, edited, deleted, transferred, pinned, unpinned, labeled, unlabeled, locked, unlocked, category_changed, answered, unanswered.
Other Shorthands
Section titled “Other Shorthands”on: manual # workflow_dispatch (run manually)on: manual with input version # workflow_dispatch with a string inputon: workflow completed ci-test # Trigger after another workflow completeson: comment created # Issue or PR comment createdon: release published # Release event (published, created, prereleased, etc.)on: repository starred # Repository starred (maps to watch event)on: repository forked # Repository forkedon: dependabot pull request # PR from Dependabot (adds actor condition)on: security alert # Code scanning alerton: code scanning alert # Alias for security alert (code scanning alert)on: api dispatch custom-event # Repository dispatch with custom event typeRelated Documentation
Section titled “Related Documentation”- Schedule Syntax - Complete schedule format reference
- Command Triggers - Special @mention triggers and context text
- Frontmatter - Complete frontmatter configuration
- LabelOps - Label-based automation workflows
- Workflow Structure - Directory layout and organization