mirror of https://github.com/restic/restic.git
180 lines
4.9 KiB
Go
180 lines
4.9 KiB
Go
|
package storage
|
||
|
|
||
|
import (
|
||
|
"bytes"
|
||
|
"io/ioutil"
|
||
|
|
||
|
chk "gopkg.in/check.v1"
|
||
|
)
|
||
|
|
||
|
type PageBlobSuite struct{}
|
||
|
|
||
|
var _ = chk.Suite(&PageBlobSuite{})
|
||
|
|
||
|
func (s *PageBlobSuite) TestPutPageBlob(c *chk.C) {
|
||
|
cli := getBlobClient(c)
|
||
|
rec := cli.client.appendRecorder(c)
|
||
|
defer rec.Stop()
|
||
|
|
||
|
cnt := cli.GetContainerReference(containerName(c))
|
||
|
b := cnt.GetBlobReference(blobName(c))
|
||
|
c.Assert(cnt.Create(nil), chk.IsNil)
|
||
|
defer cnt.Delete(nil)
|
||
|
|
||
|
size := int64(10 * 1024 * 1024)
|
||
|
b.Properties.ContentLength = size
|
||
|
c.Assert(b.PutPageBlob(nil), chk.IsNil)
|
||
|
|
||
|
// Verify
|
||
|
err := b.GetProperties(nil)
|
||
|
c.Assert(err, chk.IsNil)
|
||
|
c.Assert(b.Properties.ContentLength, chk.Equals, size)
|
||
|
c.Assert(b.Properties.BlobType, chk.Equals, BlobTypePage)
|
||
|
}
|
||
|
|
||
|
func (s *PageBlobSuite) TestPutPagesUpdate(c *chk.C) {
|
||
|
cli := getBlobClient(c)
|
||
|
rec := cli.client.appendRecorder(c)
|
||
|
defer rec.Stop()
|
||
|
|
||
|
cnt := cli.GetContainerReference(containerName(c))
|
||
|
b := cnt.GetBlobReference(blobName(c))
|
||
|
c.Assert(cnt.Create(nil), chk.IsNil)
|
||
|
defer cnt.Delete(nil)
|
||
|
|
||
|
size := int64(10 * 1024 * 1024) // larger than we'll use
|
||
|
b.Properties.ContentLength = size
|
||
|
c.Assert(b.PutPageBlob(nil), chk.IsNil)
|
||
|
|
||
|
chunk1 := content(1024)
|
||
|
chunk2 := content(512)
|
||
|
|
||
|
// Append chunks
|
||
|
blobRange := BlobRange{
|
||
|
End: uint64(len(chunk1) - 1),
|
||
|
}
|
||
|
c.Assert(b.WriteRange(blobRange, bytes.NewReader(chunk1), nil), chk.IsNil)
|
||
|
blobRange.Start = uint64(len(chunk1))
|
||
|
blobRange.End = uint64(len(chunk1) + len(chunk2) - 1)
|
||
|
c.Assert(b.WriteRange(blobRange, bytes.NewReader(chunk2), nil), chk.IsNil)
|
||
|
|
||
|
// Verify contents
|
||
|
options := GetBlobRangeOptions{
|
||
|
Range: &BlobRange{
|
||
|
End: uint64(len(chunk1) + len(chunk2) - 1),
|
||
|
},
|
||
|
}
|
||
|
out, err := b.GetRange(&options)
|
||
|
c.Assert(err, chk.IsNil)
|
||
|
defer out.Close()
|
||
|
blobContents, err := ioutil.ReadAll(out)
|
||
|
c.Assert(err, chk.IsNil)
|
||
|
c.Assert(blobContents, chk.DeepEquals, append(chunk1, chunk2...))
|
||
|
|
||
|
// Overwrite first half of chunk1
|
||
|
chunk0 := content(512)
|
||
|
blobRange.Start = 0
|
||
|
blobRange.End = uint64(len(chunk0) - 1)
|
||
|
c.Assert(b.WriteRange(blobRange, bytes.NewReader(chunk0), nil), chk.IsNil)
|
||
|
|
||
|
// Verify contents
|
||
|
out, err = b.GetRange(&options)
|
||
|
c.Assert(err, chk.IsNil)
|
||
|
defer out.Close()
|
||
|
blobContents, err = ioutil.ReadAll(out)
|
||
|
c.Assert(err, chk.IsNil)
|
||
|
c.Assert(blobContents, chk.DeepEquals, append(append(chunk0, chunk1[512:]...), chunk2...))
|
||
|
}
|
||
|
|
||
|
func (s *PageBlobSuite) TestPutPagesClear(c *chk.C) {
|
||
|
cli := getBlobClient(c)
|
||
|
rec := cli.client.appendRecorder(c)
|
||
|
defer rec.Stop()
|
||
|
|
||
|
cnt := cli.GetContainerReference(containerName(c))
|
||
|
b := cnt.GetBlobReference(blobName(c))
|
||
|
c.Assert(cnt.Create(nil), chk.IsNil)
|
||
|
defer cnt.Delete(nil)
|
||
|
|
||
|
size := int64(10 * 1024 * 1024) // larger than we'll use
|
||
|
b.Properties.ContentLength = size
|
||
|
c.Assert(b.PutPageBlob(nil), chk.IsNil)
|
||
|
|
||
|
// Put 0-2047
|
||
|
chunk := content(2048)
|
||
|
blobRange := BlobRange{
|
||
|
End: 2047,
|
||
|
}
|
||
|
c.Assert(b.WriteRange(blobRange, bytes.NewReader(chunk), nil), chk.IsNil)
|
||
|
|
||
|
// Clear 512-1023
|
||
|
blobRange.Start = 512
|
||
|
blobRange.End = 1023
|
||
|
c.Assert(b.ClearRange(blobRange, nil), chk.IsNil)
|
||
|
|
||
|
// Verify contents
|
||
|
options := GetBlobRangeOptions{
|
||
|
Range: &BlobRange{
|
||
|
Start: 0,
|
||
|
End: 2047,
|
||
|
},
|
||
|
}
|
||
|
out, err := b.GetRange(&options)
|
||
|
c.Assert(err, chk.IsNil)
|
||
|
contents, err := ioutil.ReadAll(out)
|
||
|
c.Assert(err, chk.IsNil)
|
||
|
defer out.Close()
|
||
|
c.Assert(contents, chk.DeepEquals, append(append(chunk[:512], make([]byte, 512)...), chunk[1024:]...))
|
||
|
}
|
||
|
|
||
|
func (s *PageBlobSuite) TestGetPageRanges(c *chk.C) {
|
||
|
cli := getBlobClient(c)
|
||
|
rec := cli.client.appendRecorder(c)
|
||
|
defer rec.Stop()
|
||
|
|
||
|
cnt := cli.GetContainerReference(containerName(c))
|
||
|
c.Assert(cnt.Create(nil), chk.IsNil)
|
||
|
defer cnt.Delete(nil)
|
||
|
|
||
|
size := int64(10 * 1024) // larger than we'll use
|
||
|
|
||
|
// Get page ranges on empty blob
|
||
|
blob1 := cnt.GetBlobReference(blobName(c, "1"))
|
||
|
blob1.Properties.ContentLength = size
|
||
|
c.Assert(blob1.PutPageBlob(nil), chk.IsNil)
|
||
|
out, err := blob1.GetPageRanges(nil)
|
||
|
c.Assert(err, chk.IsNil)
|
||
|
c.Assert(len(out.PageList), chk.Equals, 0)
|
||
|
|
||
|
// Get page ranges with just one range
|
||
|
blob2 := cnt.GetBlobReference(blobName(c, "2"))
|
||
|
blob2.Properties.ContentLength = size
|
||
|
c.Assert(blob2.PutPageBlob(nil), chk.IsNil)
|
||
|
blobRange := []BlobRange{
|
||
|
{End: 511},
|
||
|
{Start: 1024, End: 2047},
|
||
|
}
|
||
|
c.Assert(blob2.WriteRange(blobRange[0], bytes.NewReader(content(512)), nil), chk.IsNil)
|
||
|
|
||
|
out, err = blob2.GetPageRanges(nil)
|
||
|
c.Assert(err, chk.IsNil)
|
||
|
c.Assert(len(out.PageList), chk.Equals, 1)
|
||
|
expected := []PageRange{
|
||
|
{End: 511},
|
||
|
{Start: 1024, End: 2047},
|
||
|
}
|
||
|
c.Assert(out.PageList[0], chk.Equals, expected[0])
|
||
|
|
||
|
// Get page ranges with just two range
|
||
|
blob3 := cnt.GetBlobReference(blobName(c, "3"))
|
||
|
blob3.Properties.ContentLength = size
|
||
|
c.Assert(blob3.PutPageBlob(nil), chk.IsNil)
|
||
|
for _, br := range blobRange {
|
||
|
c.Assert(blob3.WriteRange(br, bytes.NewReader(content(int(br.End-br.Start+1))), nil), chk.IsNil)
|
||
|
}
|
||
|
out, err = blob3.GetPageRanges(nil)
|
||
|
c.Assert(err, chk.IsNil)
|
||
|
c.Assert(len(out.PageList), chk.Equals, 2)
|
||
|
c.Assert(out.PageList, chk.DeepEquals, expected)
|
||
|
}
|