From b36ae8849243514dd56161da67e71f19a7ef67df Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Wed, 11 Feb 2026 22:27:08 +0000 Subject: [PATCH 1/4] Initial plan From 8f09609c49091869c1b65c8a392efb7433bdb564 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Wed, 11 Feb 2026 22:32:22 +0000 Subject: [PATCH 2/4] Initial plan: Sort GH_AW_RATE_LIMIT_EVENTS alphabetically Co-authored-by: pelikhan <4175913+pelikhan@users.noreply.github.com> --- .github/workflows/ai-moderator.lock.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/ai-moderator.lock.yml b/.github/workflows/ai-moderator.lock.yml index 08cc0136f31..682f246dc43 100644 --- a/.github/workflows/ai-moderator.lock.yml +++ b/.github/workflows/ai-moderator.lock.yml @@ -1025,7 +1025,7 @@ jobs: env: GH_AW_RATE_LIMIT_MAX: "5" GH_AW_RATE_LIMIT_WINDOW: "60" - GH_AW_RATE_LIMIT_EVENTS: "workflow_dispatch,issues,issue_comment" + GH_AW_RATE_LIMIT_EVENTS: "issue_comment,workflow_dispatch,issues" with: github-token: ${{ secrets.GITHUB_TOKEN }} script: | From f26ac6535a31e27c79609ba496997b9815cf587d Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Wed, 11 Feb 2026 22:33:52 +0000 Subject: [PATCH 3/4] Sort GH_AW_RATE_LIMIT_EVENTS alphabetically Co-authored-by: pelikhan <4175913+pelikhan@users.noreply.github.com> --- pkg/workflow/role_checks.go | 10 +++++----- pkg/workflow/role_checks_test.go | 10 +++++----- 2 files changed, 10 insertions(+), 10 deletions(-) diff --git a/pkg/workflow/role_checks.go b/pkg/workflow/role_checks.go index 2446f1e9b27..43e57d838ae 100644 --- a/pkg/workflow/role_checks.go +++ b/pkg/workflow/role_checks.go @@ -211,15 +211,15 @@ func (c *Compiler) inferEventsFromTriggers(frontmatter map[string]any) []string var events []string programmaticTriggers := map[string]string{ - "workflow_dispatch": "workflow_dispatch", - "repository_dispatch": "repository_dispatch", - "issues": "issues", + "discussion": "discussion", + "discussion_comment": "discussion_comment", "issue_comment": "issue_comment", + "issues": "issues", "pull_request": "pull_request", "pull_request_review": "pull_request_review", "pull_request_review_comment": "pull_request_review_comment", - "discussion": "discussion", - "discussion_comment": "discussion_comment", + "repository_dispatch": "repository_dispatch", + "workflow_dispatch": "workflow_dispatch", } switch on := onValue.(type) { diff --git a/pkg/workflow/role_checks_test.go b/pkg/workflow/role_checks_test.go index 2065f13dd68..b854b184e80 100644 --- a/pkg/workflow/role_checks_test.go +++ b/pkg/workflow/role_checks_test.go @@ -206,15 +206,15 @@ func TestInferEventsFromTriggers(t *testing.T) { }, }, expected: []string{ - "workflow_dispatch", - "repository_dispatch", - "issues", + "discussion", + "discussion_comment", "issue_comment", + "issues", "pull_request", "pull_request_review", "pull_request_review_comment", - "discussion", - "discussion_comment", + "repository_dispatch", + "workflow_dispatch", }, }, } From 73b227553c5b28c6c94954ed08827e6fe0f7190a Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Wed, 11 Feb 2026 22:42:20 +0000 Subject: [PATCH 4/4] Add sorting for GH_AW_RATE_LIMIT_EVENTS in generated workflows Co-authored-by: pelikhan <4175913+pelikhan@users.noreply.github.com> --- .github/workflows/ai-moderator.lock.yml | 2 +- docs/src/content/docs/agent-factory-status.mdx | 2 +- docs/src/content/docs/reference/frontmatter-full.md | 6 +++--- pkg/workflow/role_checks.go | 9 ++++++++- pkg/workflow/role_checks_test.go | 10 +++------- 5 files changed, 16 insertions(+), 13 deletions(-) diff --git a/.github/workflows/ai-moderator.lock.yml b/.github/workflows/ai-moderator.lock.yml index 682f246dc43..b43a4b3a0c3 100644 --- a/.github/workflows/ai-moderator.lock.yml +++ b/.github/workflows/ai-moderator.lock.yml @@ -1025,7 +1025,7 @@ jobs: env: GH_AW_RATE_LIMIT_MAX: "5" GH_AW_RATE_LIMIT_WINDOW: "60" - GH_AW_RATE_LIMIT_EVENTS: "issue_comment,workflow_dispatch,issues" + GH_AW_RATE_LIMIT_EVENTS: "issue_comment,issues,workflow_dispatch" with: github-token: ${{ secrets.GITHUB_TOKEN }} script: | diff --git a/docs/src/content/docs/agent-factory-status.mdx b/docs/src/content/docs/agent-factory-status.mdx index da81e579323..398f7ce7020 100644 --- a/docs/src/content/docs/agent-factory-status.mdx +++ b/docs/src/content/docs/agent-factory-status.mdx @@ -22,6 +22,7 @@ These are experimental agentic workflows used by the GitHub Next team to learn, | [Automated Portfolio Analyst](https://github.com/github/gh-aw/blob/main/.github/workflows/portfolio-analyst.md) | copilot | [![Automated Portfolio Analyst](https://github.com/github/gh-aw/actions/workflows/portfolio-analyst.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/portfolio-analyst.lock.yml) | - | - | | [Basic Research Agent](https://github.com/github/gh-aw/blob/main/.github/workflows/research.md) | copilot | [![Basic Research Agent](https://github.com/github/gh-aw/actions/workflows/research.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/research.lock.yml) | - | - | | [Blog Auditor](https://github.com/github/gh-aw/blob/main/.github/workflows/blog-auditor.md) | claude | [![Blog Auditor](https://github.com/github/gh-aw/actions/workflows/blog-auditor.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/blog-auditor.lock.yml) | - | - | +| [Bot Detection Agent 🔍🤖](https://github.com/github/gh-aw/blob/main/.github/workflows/bot-detection.md) | copilot | [![Bot Detection Agent 🔍🤖](https://github.com/github/gh-aw/actions/workflows/bot-detection.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/bot-detection.lock.yml) | - | - | | [Brave Web Search Agent](https://github.com/github/gh-aw/blob/main/.github/workflows/brave.md) | copilot | [![Brave Web Search Agent](https://github.com/github/gh-aw/actions/workflows/brave.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/brave.lock.yml) | - | `/brave` | | [Breaking Change Checker](https://github.com/github/gh-aw/blob/main/.github/workflows/breaking-change-checker.md) | copilot | [![Breaking Change Checker](https://github.com/github/gh-aw/actions/workflows/breaking-change-checker.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/breaking-change-checker.lock.yml) | - | - | | [Changeset Generator](https://github.com/github/gh-aw/blob/main/.github/workflows/changeset.md) | codex | [![Changeset Generator](https://github.com/github/gh-aw/actions/workflows/changeset.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/changeset.lock.yml) | - | - | @@ -143,7 +144,6 @@ These are experimental agentic workflows used by the GitHub Next team to learn, | [Test Create PR Error Handling](https://github.com/github/gh-aw/blob/main/.github/workflows/test-create-pr-error-handling.md) | claude | [![Test Create PR Error Handling](https://github.com/github/gh-aw/actions/workflows/test-create-pr-error-handling.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/test-create-pr-error-handling.lock.yml) | - | - | | [Test Dispatcher Workflow](https://github.com/github/gh-aw/blob/main/.github/workflows/test-dispatcher.md) | copilot | [![Test Dispatcher Workflow](https://github.com/github/gh-aw/actions/workflows/test-dispatcher.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/test-dispatcher.lock.yml) | - | - | | [Test Project URL Explicit Requirement](https://github.com/github/gh-aw/blob/main/.github/workflows/test-project-url-default.md) | copilot | [![Test Project URL Explicit Requirement](https://github.com/github/gh-aw/actions/workflows/test-project-url-default.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/test-project-url-default.lock.yml) | - | - | -| [Test Rate Limiting](https://github.com/github/gh-aw/blob/main/.github/workflows/test-rate-limit.md) | copilot | [![Test Rate Limiting](https://github.com/github/gh-aw/actions/workflows/test-rate-limit.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/test-rate-limit.lock.yml) | - | - | | [Test Workflow](https://github.com/github/gh-aw/blob/main/.github/workflows/test-workflow.md) | copilot | [![Test Workflow](https://github.com/github/gh-aw/actions/workflows/test-workflow.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/test-workflow.lock.yml) | - | - | | [The Daily Repository Chronicle](https://github.com/github/gh-aw/blob/main/.github/workflows/daily-repo-chronicle.md) | copilot | [![The Daily Repository Chronicle](https://github.com/github/gh-aw/actions/workflows/daily-repo-chronicle.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/daily-repo-chronicle.lock.yml) | `0 16 * * 1-5` | - | | [The Great Escapi](https://github.com/github/gh-aw/blob/main/.github/workflows/firewall-escape.md) | copilot | [![The Great Escapi](https://github.com/github/gh-aw/actions/workflows/firewall-escape.lock.yml/badge.svg)](https://github.com/github/gh-aw/actions/workflows/firewall-escape.lock.yml) | - | - | diff --git a/docs/src/content/docs/reference/frontmatter-full.md b/docs/src/content/docs/reference/frontmatter-full.md index 1bce7bc39bb..9d0d3c5851b 100644 --- a/docs/src/content/docs/reference/frontmatter-full.md +++ b/docs/src/content/docs/reference/frontmatter-full.md @@ -3513,11 +3513,11 @@ bots: [] # (optional) rate-limit: # Maximum number of workflow runs allowed per user within the time window. - # Defaults to 5. - # (optional) + # Required field. max: 1 - # Time window in minutes for rate limiting. Defaults to 60 (1 hour). + # Time window in minutes for rate limiting. Defaults to 60 (1 hour). Maximum: 180 + # (3 hours). # (optional) window: 1 diff --git a/pkg/workflow/role_checks.go b/pkg/workflow/role_checks.go index 43e57d838ae..b0de86a1745 100644 --- a/pkg/workflow/role_checks.go +++ b/pkg/workflow/role_checks.go @@ -2,6 +2,7 @@ package workflow import ( "fmt" + "sort" "strings" "github.com/github/gh-aw/pkg/constants" @@ -62,7 +63,11 @@ func (c *Compiler) generateRateLimitCheck(data *WorkflowData, steps []string) [] // Set events to check (if specified) if len(data.RateLimit.Events) > 0 { - steps = append(steps, fmt.Sprintf(" GH_AW_RATE_LIMIT_EVENTS: %q\n", strings.Join(data.RateLimit.Events, ","))) + // Sort events alphabetically for consistent output + events := make([]string, len(data.RateLimit.Events)) + copy(events, data.RateLimit.Events) + sort.Strings(events) + steps = append(steps, fmt.Sprintf(" GH_AW_RATE_LIMIT_EVENTS: %q\n", strings.Join(events, ","))) } steps = append(steps, " with:\n") @@ -243,6 +248,8 @@ func (c *Compiler) inferEventsFromTriggers(frontmatter map[string]any) []string } } + // Sort events alphabetically for consistent output + sort.Strings(events) return events } diff --git a/pkg/workflow/role_checks_test.go b/pkg/workflow/role_checks_test.go index b854b184e80..0d58b362dd5 100644 --- a/pkg/workflow/role_checks_test.go +++ b/pkg/workflow/role_checks_test.go @@ -165,7 +165,7 @@ func TestInferEventsFromTriggers(t *testing.T) { "workflow_dispatch": nil, }, }, - expected: []string{"issues", "issue_comment", "workflow_dispatch"}, + expected: []string{"issue_comment", "issues", "workflow_dispatch"}, }, { name: "infer only programmatic triggers", @@ -222,12 +222,8 @@ func TestInferEventsFromTriggers(t *testing.T) { for _, tt := range tests { t.Run(tt.name, func(t *testing.T) { result := c.inferEventsFromTriggers(tt.frontmatter) - // Use ElementsMatch since map iteration order is non-deterministic - if len(tt.expected) > 0 && len(result) > 0 { - assert.ElementsMatch(t, tt.expected, result, "Inferred events should match expected") - } else { - assert.Equal(t, tt.expected, result, "Inferred events should match expected") - } + // Events should be sorted alphabetically + assert.Equal(t, tt.expected, result, "Inferred events should match expected (in sorted order)") }) } }