package plugin import "context" // RemoveContainerByName is a best-effort cleanup of a name conflict before a // CreateContainer retry: enumerate the managed containers and stop+remove the // one whose name matches. Docker enforces unique container names per daemon, // so at most one managed container can match — the loop returns after the // first hit. // // Shared by the source plugins (dockerfile, static) that previously each kept // their own copy. Those copies had diverged: the dockerfile copy removed every // match (defending against a since-debunked "a partial deploy can leave more // than one matching artifact" case), while the static copy stopped at the // first. We deliberately converge on stop-at-first: ManagedContainer.Name is // the primary Docker name (Names[0]), which the daemon keeps globally unique // across every container state, so the remove-all loop could never actually // match more than one container — the two behaviours are equivalent for every // reachable state. // // Failures are intentionally swallowed: the caller treats this as opportunistic // and re-attempts CreateContainer regardless. func RemoveContainerByName(ctx context.Context, deps Deps, name string) { containers, err := deps.Docker.ListContainers(ctx, nil) if err != nil { return } for _, c := range containers { if c.Name == name { deps.Docker.StopContainer(ctx, c.ID, 10) deps.Docker.RemoveContainer(ctx, c.ID, true) return } } }