enhance(actions): only create filtered-out workflow commit status for required contexts (#38371)

Follow #38237

#38237 posts "skipped" commit statuses for every workflow that is not
triggered due to a filter (e.g. `paths` or `branches`) mismatch.
However, for non-required workflows, creating "skipped" commit statuses
for them would generate a lot of noise.

To address this issue, this PR adds a check before creating commit
status:

- For the context that matches any required status check patterns, a
"skipped" commit status will be created. The `Required` label can inform
users that this status check is required, but has been skipped because
of a filter mismatch.
- For a non-required context, nothing will be created.

NOTE: Reducing noise is a best-effort approach and isn't entirely
accurate. When creating commit statuses, it is impossible to predict
which branch protection rule will take effect. Therefore, we have to
compare the commit status context against the required patterns from all
rules. If any rule matches, the context is considered "required".
This commit is contained in:
Zettat123
2026-07-09 15:34:56 +00:00
committed by GitHub
parent c0bbd82cd4
commit 761470c01d
6 changed files with 181 additions and 37 deletions
+24 -6
View File
@@ -396,10 +396,22 @@ func buildApproveAndInsertRun(
return nil
}
// handleFilteredWorkflows posts a skipped commit status for each workflow that matched the event but was excluded by a branch/paths filter.
// handleFilteredWorkflows posts a skipped commit status for each filtered-out workflow whose context is a required status check;
// a non-required one posts nothing, so it cannot leak into a pull request.
func handleFilteredWorkflows(ctx context.Context, input *notifyInput, filteredWorkflows []*actions_module.DetectedWorkflow) {
if len(filteredWorkflows) == 0 {
return
}
requiredGlobs, err := getAllRequiredStatusContextGlobs(ctx, input.Repo)
if err != nil {
log.Error("repo %s: required status contexts: %v", input.Repo.RelativePath(), err)
return
}
if len(requiredGlobs) == 0 {
return
}
for _, dwf := range filteredWorkflows {
if err := CreateSkippedCommitStatusForFilteredWorkflow(ctx, input.Repo, input.Event, dwf.TriggerEvent.Name, dwf.EntryName, dwf.Content, input.Payload, ""); err != nil {
if err := CreateSkippedCommitStatusForFilteredWorkflow(ctx, input.Repo, input.Event, dwf.TriggerEvent.Name, dwf.EntryName, dwf.Content, input.Payload, "", requiredGlobs); err != nil {
log.Error("repo %s: skipped commit status for workflow %s: %v", input.Repo.RelativePath(), dwf.EntryName, err)
continue
}
@@ -653,6 +665,12 @@ func detectAndHandleScopedWorkflows(
isForkPullRequest := isForkPullRequestInput(input)
actionsConfig := input.Repo.MustGetUnit(ctx, unit_model.TypeActions).ActionsConfig()
// A filtered-out scoped workflow only posts a skipped status when its context is a required check.
requiredGlobs, err := getAllRequiredStatusContextGlobs(ctx, input.Repo)
if err != nil {
log.Error("scoped workflows: required status contexts for %s: %v", input.Repo.RelativePath(), err)
}
// The same source repo may be registered at both the owner and instance level; dedup
// the IDs and batch-load them in one query instead of one round-trip per source.
seen := make(container.Set[int64], len(sources))
@@ -696,14 +714,14 @@ func detectAndHandleScopedWorkflows(
}
}
// A filtered-out scoped workflow posts a skipped commit status.
if len(filtered) > 0 {
// A filtered-out scoped workflow posts a skipped commit status for its required-check contexts.
if len(filtered) > 0 && len(requiredGlobs) > 0 {
scopedPrefix := actions_model.ScopedStatusContextPrefix(ctx, sourceRepo.ID)
for _, dwf := range filtered {
if actions_model.ScopedWorkflowOptedOut(actionsConfig, sources, sourceRepo.ID, dwf.EntryName) {
continue
}
if err := CreateSkippedCommitStatusForFilteredWorkflow(ctx, input.Repo, input.Event, dwf.TriggerEvent.Name, dwf.EntryName, dwf.Content, input.Payload, scopedPrefix); err != nil {
if err := CreateSkippedCommitStatusForFilteredWorkflow(ctx, input.Repo, input.Event, dwf.TriggerEvent.Name, dwf.EntryName, dwf.Content, input.Payload, scopedPrefix, requiredGlobs); err != nil {
log.Error("scoped workflows: skipped commit status for source %s workflow %s: %v", sourceRepo.RelativePath(), dwf.EntryName, err)
continue
}
@@ -716,7 +734,7 @@ func detectAndHandleScopedWorkflows(
// detectScopedWorkflowsForSource detects the scoped workflows from the source repo at its default branch.
// detected are the workflows to run; filtered matched the event but were excluded by a branch/paths
// filter and post a skipped commit status.
// filter, and later post a skipped commit status only for a required-check context.
func detectScopedWorkflowsForSource(
ctx context.Context,
input *notifyInput,