Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -61,13 +61,17 @@ USAGE:
OPTIONS:
--commit-info-file value Path to a file which the commit info will be written. The file will be overwritten if it already exists.
--exclude value, -x value [ --exclude value, -x value ] Exclude the status of a specific CI check from failing the wait. By default, a failed status check will exit the pr wait command. [$GITHUB_CI_EXCLUDE]
--ignore-failed-ci Continue waiting for PR merge/close even if CI checks fail. Defaults to false. [$GITHUB_IGNORE_FAILED_CI]
--help, -h show help
```

This command will wait for the given PR (URL or owner/repo/number) to be merged
or closed. If merged, it will exit with code `0` (success) and if closed without
being merged it will exit with code `1` (failure).

By default, the command will also exit with code `1` if the CI checks on the PR
fail. This behavior can be disabled by setting `--ignore-failed-ci=true`.

#### `ci`

```
Expand Down Expand Up @@ -155,6 +159,10 @@ which are not added immediately.
Recheck interval (i.e. poll this often) in golang duration format. Optional.
Default is `30s`.

#### `ignore-failed-ci`

Ignore failed CI checks and continue waiting for PR to be closed or merged. Only used when `wait-for` is set to `"pr"`. Optional. Default is `false`.

#### `owner`

GitHub repo owner. Optional. Default is the current repository's owner,
Expand Down
5 changes: 5 additions & 0 deletions action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,10 @@ inputs:
checks-to-wait-for:
description: 'The comma-separated names of the checks to wait for. Only used when wait-for is "ci"'
required: false
ignore-failed-ci:
description: 'Ignore failed CI checks and continue waiting. Only used when wait-for is "pr". Defaults to false'
required: false
default: "false"

runs:
using: composite
Expand All @@ -68,6 +72,7 @@ runs:
GITHUB_TOKEN: ${{ inputs.token }}
GITHUB_CI_CHECKS: ${{ inputs.checks-to-wait-for }}
GITHUB_CI_EXCLUDE: ${{ inputs.exclude-checks }}
GITHUB_IGNORE_FAILED_CI: ${{ inputs.ignore-failed-ci }}
GITHUB_APP_ID: ${{ inputs.app-id }}
GITHUB_APP_INSTALLATION_ID: ${{ inputs.app-installation-id }}
GITHUB_APP_PRIVATE_KEY: ${{ inputs.app-private-key }}
Expand Down
14 changes: 14 additions & 0 deletions cmd/wait-for-github/pr.go
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@ type prConfig struct {

commitInfoFile string
excludes []string
ignoreFailedCI bool
writer fileWriter
}

Expand Down Expand Up @@ -122,6 +123,7 @@ func parsePRArguments(ctx context.Context, cmd *cli.Command, logger *slog.Logger
pr: n,
commitInfoFile: cmd.String("commit-info-file"),
excludes: cmd.StringSlice("exclude"),
ignoreFailedCI: cmd.Bool("ignore-failed-ci"),
writer: osFileWriter{},
}, nil
}
Expand Down Expand Up @@ -178,6 +180,10 @@ func (pr prCheck) Check(ctx context.Context) error {
return cli.Exit("PR is closed", 1)
}

if pr.ignoreFailedCI {
return nil
}

// not merged, not closed, let's see what the CI status is. If that's bad,
// we can exit early.
sha, err := pr.githubClient.GetPRHeadSHA(ctx, pr.owner, pr.repo, pr.pr)
Expand Down Expand Up @@ -233,6 +239,14 @@ func prCommand(cfg *config) *cli.Command {
cli.EnvVar("GITHUB_CI_EXCLUDE"),
),
},
&cli.BoolFlag{
Name: "ignore-failed-ci",
Usage: "Ignore failed CI checks and continue waiting. Defaults to false.",
Value: false,
Sources: cli.NewValueSourceChain(
cli.EnvVar("GITHUB_IGNORE_FAILED_CI"),
),
},
},
Before: func(ctx context.Context, cmd *cli.Command) (context.Context, error) {
var err error
Expand Down
52 changes: 40 additions & 12 deletions cmd/wait-for-github/pr_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,7 @@ func TestPRCheck(t *testing.T) {
name string
fakeClient fakeGithubClientPRCheck
expectedExitCode *int
ignoreFailedCI bool
}{
{
name: "PR is merged",
Expand Down Expand Up @@ -90,12 +91,30 @@ func TestPRCheck(t *testing.T) {
},
},
{
name: "Not merged, but CI failed",
name: "Not merged, but CI failed (ignore-failed-ci disabled)",
fakeClient: fakeGithubClientPRCheck{
CIStatus: github.CIStatusFailed,
},
expectedExitCode: &one,
},
{
name: "Merged, CI failed",
fakeClient: fakeGithubClientPRCheck{
CIStatus: github.CIStatusFailed,
MergedCommit: "abc123",
MergedAt: 1234567890,
},
expectedExitCode: &zero,
},
{
name: "Closed, CI failed (ignore-failed-ci enabled)",
fakeClient: fakeGithubClientPRCheck{
Closed: true,
CIStatus: github.CIStatusFailed,
},
ignoreFailedCI: true,
expectedExitCode: &one,
},
{
name: "Not merged, getting PR head SHA failed",
fakeClient: fakeGithubClientPRCheck{
Expand All @@ -122,9 +141,10 @@ func TestPRCheck(t *testing.T) {
cancel()

prConfig := prConfig{
owner: "owner",
repo: "repo",
pr: 1,
owner: "owner",
repo: "repo",
pr: 1,
ignoreFailedCI: tt.ignoreFailedCI,
}

err := checkPRMerged(ctx, fakePRStatusChecker, cfg, &prConfig)
Expand Down Expand Up @@ -237,20 +257,22 @@ func TestParsePRArguments(t *testing.T) {
name: "Valid pull request URL",
args: []string{"https://github.com/owner/repo/pull/1"},
want: prConfig{
owner: "owner",
repo: "repo",
pr: 1,
writer: osFileWriter{},
owner: "owner",
repo: "repo",
pr: 1,
ignoreFailedCI: false,
writer: osFileWriter{},
},
},
{
name: "Valid arguments owner, repo, pr",
args: []string{"owner", "repo", "1"},
want: prConfig{
owner: "owner",
repo: "repo",
pr: 1,
writer: osFileWriter{},
owner: "owner",
repo: "repo",
pr: 1,
ignoreFailedCI: false,
writer: osFileWriter{},
},
},
{
Expand Down Expand Up @@ -278,6 +300,12 @@ func TestParsePRArguments(t *testing.T) {
rootCmd := &cli.Command{}
prCmd := &cli.Command{
Name: "pr",
Flags: []cli.Flag{
&cli.BoolFlag{
Name: "ignore-failed-ci",
Value: false,
},
},
Action: func(ctx context.Context, cmd *cli.Command) error {
got, err := parsePRArguments(ctx, cmd, testLogger)
if tt.wantErr != nil {
Expand Down
Loading