diff --git a/pkg/registry/generic/etcd/etcd.go b/pkg/registry/generic/etcd/etcd.go index a976d61af91..2c09a34ad33 100644 --- a/pkg/registry/generic/etcd/etcd.go +++ b/pkg/registry/generic/etcd/etcd.go @@ -464,7 +464,7 @@ func (e *Etcd) DeleteCollection(ctx api.Context, options *api.DeleteOptions, lis if err != nil { return nil, err } - if _, err := e.Delete(ctx, accessor.GetName(), options); err != nil { + if _, err := e.Delete(ctx, accessor.GetName(), options); err != nil && !kubeerr.IsNotFound(err) { return nil, err } } diff --git a/pkg/registry/generic/etcd/etcd_test.go b/pkg/registry/generic/etcd/etcd_test.go index a0d09dd987e..16c7324348a 100644 --- a/pkg/registry/generic/etcd/etcd_test.go +++ b/pkg/registry/generic/etcd/etcd_test.go @@ -23,6 +23,8 @@ import ( "strconv" "testing" + "sync" + "k8s.io/kubernetes/pkg/api" "k8s.io/kubernetes/pkg/api/errors" "k8s.io/kubernetes/pkg/api/meta" @@ -576,6 +578,47 @@ func TestEtcdDeleteCollection(t *testing.T) { } } +func TestEtcdDeleteCollectionNotFound(t *testing.T) { + server, registry := NewTestGenericEtcdRegistry(t) + defer server.Terminate(t) + + testContext := api.WithNamespace(api.NewContext(), "test") + + podA := &api.Pod{ObjectMeta: api.ObjectMeta{Name: "foo"}} + podB := &api.Pod{ObjectMeta: api.ObjectMeta{Name: "bar"}} + + for i := 0; i < 10; i++ { + // Setup + if _, err := registry.Create(testContext, podA); err != nil { + t.Errorf("Unexpected error: %v", err) + } + if _, err := registry.Create(testContext, podB); err != nil { + t.Errorf("Unexpected error: %v", err) + } + + // Kick off multiple delete collection calls to test notfound behavior + wg := &sync.WaitGroup{} + for j := 0; j < 5; j++ { + wg.Add(1) + go func() { + defer wg.Done() + _, err := registry.DeleteCollection(testContext, nil, &api.ListOptions{}) + if err != nil { + t.Fatalf("Unexpected error: %v", err) + } + }() + } + wg.Wait() + + if _, err := registry.Get(testContext, podA.Name); !errors.IsNotFound(err) { + t.Errorf("Unexpected error: %v", err) + } + if _, err := registry.Get(testContext, podB.Name); !errors.IsNotFound(err) { + t.Errorf("Unexpected error: %v", err) + } + } +} + // Test whether objects deleted with DeleteCollection are correctly delivered // to watchers. func TestEtcdDeleteCollectionWithWatch(t *testing.T) {