feat: improve container conflict detection#3574
feat: improve container conflict detection#3574mdelapenya merged 1 commit intotestcontainers:mainfrom
Conversation
✅ Deploy Preview for testcontainers-go ready!
To edit notification comments on pull requests, go to your Netlify project configuration. |
|
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configurationConfiguration used: Organization UI Review profile: CHILL Plan: Pro Run ID: 📒 Files selected for processing (2)
Summary by CodeRabbit
WalkthroughBroadened container-name conflict detection regex to match Docker and Podman messages; added table-driven tests for spawner.retryError covering multiple error types and verifying permanent vs. non-permanent classification. Changes
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~20 minutes Poem
🚥 Pre-merge checks | ✅ 3 | ❌ 2❌ Failed checks (2 warnings)
✅ Passed checks (3 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
🧹 Nitpick comments (1)
reaper_test.go (1)
544-613: Add coverage for theTimeout() boolretry path.This table still misses the retryable branch for errors that only satisfy the timeout interface in
reaperSpawner.retryError, so that path can regress unnoticed.Suggested addition
var errExpected = errors.New("expected") + +type timeoutErr struct{} + +func (timeoutErr) Error() string { return "timeout" } +func (timeoutErr) Timeout() bool { return true }tests := []struct { name string err error permanent bool }{ + { + name: "timeout interface error", + err: fmt.Errorf("foo: %w", timeoutErr{}), + permanent: false, + }, { name: "random error", err: errors.New("some random error"), permanent: true, },🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@reaper_test.go` around lines 544 - 613, Add a test case that exercises the retry path for errors implementing the timeout interface (Timeout() bool) in reaperSpawner.retryError: create a small error type that implements error and Timeout() bool returning true (or wrap a net.Error-like timeout), add it to the tests table in reaper_test.go alongside the other cases, assert that retryError returns a non-nil error and that it is not a *backoff.PermanentError; place the new case with name like "timeout interface error" and permanent: false so the timeout-only branch is covered.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Nitpick comments:
In `@reaper_test.go`:
- Around line 544-613: Add a test case that exercises the retry path for errors
implementing the timeout interface (Timeout() bool) in reaperSpawner.retryError:
create a small error type that implements error and Timeout() bool returning
true (or wrap a net.Error-like timeout), add it to the tests table in
reaper_test.go alongside the other cases, assert that retryError returns a
non-nil error and that it is not a *backoff.PermanentError; place the new case
with name like "timeout interface error" and permanent: false so the
timeout-only branch is covered.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: CHILL
Plan: Pro
Run ID: 8354bc0d-025a-4a45-8cba-75900218670a
📒 Files selected for processing (2)
docker.goreaper_test.go
bdb6d18 to
c0e8ab1
Compare
There was a problem hiding this comment.
🧹 Nitpick comments (1)
reaper_test.go (1)
554-614: Add a cleanup-safe case to this table.
retryErrorshort-circuits onisCleanupSafe(err)before the name-conflict and timeout checks, but this matrix never exercises that branch. A regression in the cleanup-safe unwrapping logic would still pass this test, so I’d add at least one retryable case for a cleanup-safe error (for example a containerd not-found/already-in-progress error).🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@reaper_test.go` around lines 554 - 614, The test matrix for retryError doesn't include a case exercising the isCleanupSafe(err) branch, so add a test entry in the tests slice that supplies an error which isCleanupSafe should detect (e.g., a containerd "not found" or "already in progress" diagnostic wrapped via fmt.Errorf) and assert permanent: false; update the table near the other cases so retryError and isCleanupSafe are exercised together and prevent regressions in the cleanup-safe unwrapping logic.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Nitpick comments:
In `@reaper_test.go`:
- Around line 554-614: The test matrix for retryError doesn't include a case
exercising the isCleanupSafe(err) branch, so add a test entry in the tests slice
that supplies an error which isCleanupSafe should detect (e.g., a containerd
"not found" or "already in progress" diagnostic wrapped via fmt.Errorf) and
assert permanent: false; update the table near the other cases so retryError and
isCleanupSafe are exercised together and prevent regressions in the cleanup-safe
unwrapping logic.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Organization UI
Review profile: CHILL
Plan: Pro
Run ID: fe2266f8-98ef-4966-b6ba-052204227507
📒 Files selected for processing (2)
docker.goreaper_test.go
🚧 Files skipped from review as they are similar to previous changes (1)
- docker.go
Modify the container conflict detection regex for improved Podman compatibility.
c0e8ab1 to
a60fd7e
Compare
| var ( | ||
| // createContainerFailDueToNameConflictRegex is a regular expression that matches the container is already in use error. | ||
| createContainerFailDueToNameConflictRegex = regexp.MustCompile("Conflict. The container name .* is already in use by container .*") | ||
| createContainerFailDueToNameConflictRegex = regexp.MustCompile("[Tt]he container name .* is already in use by .*") |
There was a problem hiding this comment.
LGTM, although we should look for another way to detect the conflicts, logs are fragile. cc/ @stevenh
…m-v2 * upstream/main: (269 commits) chore(deps): bump actions/checkout from 6.0.1 to 6.0.2 (#3560) chore(deps): bump go.opentelemetry.io/otel/sdk to v1.41.0 (#3589) feat: add TiDB module (#3575) feat: add Forgejo module (#3556) feat: improve container conflict detection (#3574) chore(deps): bump go to 1.25 everywhere (#3572) chore(pulsar): bump base image to 4.x, replacing the wait for log strategy with wait for listening port (deterministic) (#3573) chore(deps): bump github.com/sigstore/sigstore in /modules/compose (#3571) chore(compose): update to compose-v5 (#3568) chore(deps): bump github.com/modelcontextprotocol/go-sdk (#3557) chore(deps): bump mkdocs-codeinclude-plugin from 0.2.1 to 0.3.1 (#3561) chore: update usage metrics (2026-03-02) (#3565) chore(deps): bump mkdocs-include-markdown-plugin from 7.2.0 to 7.2.1 (#3562) chore(deps): bump go.opentelemetry.io/otel/sdk in /modules/grafana-lgtm (#3563) chore(deps): bump go.opentelemetry.io/otel/sdk in /modules/toxiproxy (#3564) feat(azure): add lowkey vault container (#3542) feat(chroma): update to chroma 1.x (#3552) chore(deps): bump mkdocs-include-markdown-plugin from 7.2.0 to 7.2.1 (#3547) chore(deps): bump tj-actions/changed-files from 47.0.0 to 47.0.1 (#3546) chore(deps): bump actions/upload-artifact from 4.6.2 to 6.0.0 (#3545) ...
…archive-temp * upstream/main: chore(deps): bump actions/checkout from 6.0.1 to 6.0.2 (#3560) chore(deps): bump go.opentelemetry.io/otel/sdk to v1.41.0 (#3589) feat: add TiDB module (#3575) feat: add Forgejo module (#3556) feat: improve container conflict detection (#3574) chore(deps): bump go to 1.25 everywhere (#3572) chore(pulsar): bump base image to 4.x, replacing the wait for log strategy with wait for listening port (deterministic) (#3573) chore(deps): bump github.com/sigstore/sigstore in /modules/compose (#3571) chore(compose): update to compose-v5 (#3568) chore(deps): bump github.com/modelcontextprotocol/go-sdk (#3557) chore(deps): bump mkdocs-codeinclude-plugin from 0.2.1 to 0.3.1 (#3561) chore: update usage metrics (2026-03-02) (#3565) chore(deps): bump mkdocs-include-markdown-plugin from 7.2.0 to 7.2.1 (#3562) chore(deps): bump go.opentelemetry.io/otel/sdk in /modules/grafana-lgtm (#3563) chore(deps): bump go.opentelemetry.io/otel/sdk in /modules/toxiproxy (#3564)
…-action * upstream/main: (22 commits) chore(deps): bump golang.org/x/mod in /modules/localstack (#3587) chore(deps): bump golang.org/x/mod in /modules/elasticsearch (#3585) chore(deps): bump golang.org/x/mod in /modules/redpanda (#3588) chore(deps): bump golang.org/x/mod in /modules/kafka (#3586) chore(deps): bump github.com/shirou/gopsutil/v4 from 4.25.12 to 4.26.2 (#3576) chore(deps): bump github.com/moby/go-archive from 0.1.0 to 0.2.0 (#3548) chore(deps): bump github.com/moby/term from 0.5.0 to 0.5.2 (#3081) chore(deps): bump actions/checkout from 6.0.1 to 6.0.2 (#3560) chore(deps): bump go.opentelemetry.io/otel/sdk to v1.41.0 (#3589) feat: add TiDB module (#3575) feat: add Forgejo module (#3556) feat: improve container conflict detection (#3574) chore(deps): bump go to 1.25 everywhere (#3572) chore(pulsar): bump base image to 4.x, replacing the wait for log strategy with wait for listening port (deterministic) (#3573) chore(deps): bump github.com/sigstore/sigstore in /modules/compose (#3571) chore(compose): update to compose-v5 (#3568) chore(deps): bump github.com/modelcontextprotocol/go-sdk (#3557) chore(deps): bump mkdocs-codeinclude-plugin from 0.2.1 to 0.3.1 (#3561) chore: update usage metrics (2026-03-02) (#3565) chore(deps): bump mkdocs-include-markdown-plugin from 7.2.0 to 7.2.1 (#3562) ...
What does this PR do?
Modify the container conflict detection regex for improved Podman compatibility.
The shape of the conflict error comes from Podman's test suite.
Why is it important?
Container creation conflicts happen fairly often when creating the reaper container in parallel tests. Making the retry logic work with the Podman provider can prevent some of these errors from happening.
Related issues