Skip to content

Commit

Permalink
Merge pull request #1916 from dnephin/fix-pull-after-failure
Browse files Browse the repository at this point in the history
Fix image pull after a failure
  • Loading branch information
estesp committed Dec 14, 2017
2 parents 10ef7f3 + 9184908 commit 5971d36
Show file tree
Hide file tree
Showing 3 changed files with 45 additions and 1 deletion.
2 changes: 1 addition & 1 deletion content/helpers.go
Expand Up @@ -77,7 +77,7 @@ func Copy(ctx context.Context, cw Writer, r io.Reader, size int64, expected dige
r, err = seekReader(r, ws.Offset, size)
if err != nil {
if !isUnseekable(err) {
return errors.Wrapf(err, "unabled to resume write to %v", ws.Ref)
return errors.Wrapf(err, "unable to resume write to %v", ws.Ref)
}

// reader is unseekable, try to move the writer back to the start.
Expand Down
40 changes: 40 additions & 0 deletions content/local/store_test.go
Expand Up @@ -22,6 +22,7 @@ import (
"github.com/containerd/containerd/content/testsuite"
"github.com/containerd/containerd/testutil"
"github.com/opencontainers/go-digest"
"github.com/stretchr/testify/require"
)

type memoryLabelStore struct {
Expand Down Expand Up @@ -335,3 +336,42 @@ func checkWrite(ctx context.Context, t checker, cs content.Store, dgst digest.Di

return dgst
}

func TestWriterTruncateRecoversFromIncompleteWrite(t *testing.T) {
tmpdir, err := ioutil.TempDir("", "test-local-content-store-recover")
require.NoError(t, err)
defer os.RemoveAll(tmpdir)

cs, err := NewStore(tmpdir)
require.NoError(t, err)

ctx, cancel := context.WithCancel(context.Background())
defer cancel()

ref := "ref"
content := []byte("this is the content")
total := int64(len(content))
setupIncompleteWrite(ctx, t, cs, ref, total)

writer, err := cs.Writer(ctx, ref, total, "")
require.NoError(t, err)

require.NoError(t, writer.Truncate(0))

_, err = writer.Write(content)
require.NoError(t, err)

dgst := digest.FromBytes(content)
err = writer.Commit(ctx, total, dgst)
require.NoError(t, err)
}

func setupIncompleteWrite(ctx context.Context, t *testing.T, cs content.Store, ref string, total int64) {
writer, err := cs.Writer(ctx, ref, total, "")
require.NoError(t, err)

_, err = writer.Write([]byte("bad data"))
require.NoError(t, err)

require.NoError(t, writer.Close())
}
4 changes: 4 additions & 0 deletions content/local/writer.go
Expand Up @@ -2,6 +2,7 @@ package local

import (
"context"
"io"
"os"
"path/filepath"
"runtime"
Expand Down Expand Up @@ -167,5 +168,8 @@ func (w *writer) Truncate(size int64) error {
}
w.offset = 0
w.digester.Hash().Reset()
if _, err := w.fp.Seek(0, io.SeekStart); err != nil {
return err
}
return w.fp.Truncate(0)
}

0 comments on commit 5971d36

Please sign in to comment.