github.com/fawick/restic@v0.1.1-0.20171126184616-c02923fbfc79/internal/backend/test/benchmarks.go (about) 1 package test 2 3 import ( 4 "bytes" 5 "context" 6 "io" 7 "testing" 8 9 "github.com/restic/restic/internal/restic" 10 "github.com/restic/restic/internal/test" 11 ) 12 13 func saveRandomFile(t testing.TB, be restic.Backend, length int) ([]byte, restic.Handle) { 14 data := test.Random(23, length) 15 id := restic.Hash(data) 16 handle := restic.Handle{Type: restic.DataFile, Name: id.String()} 17 if err := be.Save(context.TODO(), handle, bytes.NewReader(data)); err != nil { 18 t.Fatalf("Save() error: %+v", err) 19 } 20 return data, handle 21 } 22 23 func remove(t testing.TB, be restic.Backend, h restic.Handle) { 24 if err := be.Remove(context.TODO(), h); err != nil { 25 t.Fatalf("Remove() returned error: %v", err) 26 } 27 } 28 29 // BenchmarkLoadFile benchmarks the Load() method of a backend by 30 // loading a complete file. 31 func (s *Suite) BenchmarkLoadFile(t *testing.B) { 32 be := s.open(t) 33 defer s.close(t, be) 34 35 length := 1<<24 + 2123 36 data, handle := saveRandomFile(t, be, length) 37 defer remove(t, be, handle) 38 39 buf := make([]byte, length) 40 41 t.SetBytes(int64(length)) 42 t.ResetTimer() 43 44 for i := 0; i < t.N; i++ { 45 rd, err := be.Load(context.TODO(), handle, 0, 0) 46 if err != nil { 47 t.Fatal(err) 48 } 49 50 n, err := io.ReadFull(rd, buf) 51 if err != nil { 52 t.Fatal(err) 53 } 54 55 if err = rd.Close(); err != nil { 56 t.Fatalf("Close() returned error: %v", err) 57 } 58 59 if n != length { 60 t.Fatalf("wrong number of bytes read: want %v, got %v", length, n) 61 } 62 63 if !bytes.Equal(data, buf) { 64 t.Fatalf("wrong bytes returned") 65 } 66 } 67 } 68 69 // BenchmarkLoadPartialFile benchmarks the Load() method of a backend by 70 // loading the remainder of a file starting at a given offset. 71 func (s *Suite) BenchmarkLoadPartialFile(t *testing.B) { 72 be := s.open(t) 73 defer s.close(t, be) 74 75 datalength := 1<<24 + 2123 76 data, handle := saveRandomFile(t, be, datalength) 77 defer remove(t, be, handle) 78 79 testLength := datalength/4 + 555 80 81 buf := make([]byte, testLength) 82 83 t.SetBytes(int64(testLength)) 84 t.ResetTimer() 85 86 for i := 0; i < t.N; i++ { 87 rd, err := be.Load(context.TODO(), handle, testLength, 0) 88 if err != nil { 89 t.Fatal(err) 90 } 91 92 n, err := io.ReadFull(rd, buf) 93 if err != nil { 94 t.Fatal(err) 95 } 96 97 if err = rd.Close(); err != nil { 98 t.Fatalf("Close() returned error: %v", err) 99 } 100 101 if n != testLength { 102 t.Fatalf("wrong number of bytes read: want %v, got %v", testLength, n) 103 } 104 105 if !bytes.Equal(data[:testLength], buf) { 106 t.Fatalf("wrong bytes returned") 107 } 108 109 } 110 } 111 112 // BenchmarkLoadPartialFileOffset benchmarks the Load() method of a 113 // backend by loading a number of bytes of a file starting at a given offset. 114 func (s *Suite) BenchmarkLoadPartialFileOffset(t *testing.B) { 115 be := s.open(t) 116 defer s.close(t, be) 117 118 datalength := 1<<24 + 2123 119 data, handle := saveRandomFile(t, be, datalength) 120 defer remove(t, be, handle) 121 122 testLength := datalength/4 + 555 123 testOffset := 8273 124 125 buf := make([]byte, testLength) 126 127 t.SetBytes(int64(testLength)) 128 t.ResetTimer() 129 130 for i := 0; i < t.N; i++ { 131 rd, err := be.Load(context.TODO(), handle, testLength, int64(testOffset)) 132 if err != nil { 133 t.Fatal(err) 134 } 135 136 n, err := io.ReadFull(rd, buf) 137 if err != nil { 138 t.Fatal(err) 139 } 140 141 if err = rd.Close(); err != nil { 142 t.Fatalf("Close() returned error: %v", err) 143 } 144 145 if n != testLength { 146 t.Fatalf("wrong number of bytes read: want %v, got %v", testLength, n) 147 } 148 149 if !bytes.Equal(data[testOffset:testOffset+testLength], buf) { 150 t.Fatalf("wrong bytes returned") 151 } 152 153 } 154 } 155 156 // BenchmarkSave benchmarks the Save() method of a backend. 157 func (s *Suite) BenchmarkSave(t *testing.B) { 158 be := s.open(t) 159 defer s.close(t, be) 160 161 length := 1<<24 + 2123 162 data := test.Random(23, length) 163 id := restic.Hash(data) 164 handle := restic.Handle{Type: restic.DataFile, Name: id.String()} 165 166 rd := bytes.NewReader(data) 167 168 t.SetBytes(int64(length)) 169 t.ResetTimer() 170 171 for i := 0; i < t.N; i++ { 172 if _, err := rd.Seek(0, 0); err != nil { 173 t.Fatal(err) 174 } 175 176 if err := be.Save(context.TODO(), handle, rd); err != nil { 177 t.Fatal(err) 178 } 179 180 if err := be.Remove(context.TODO(), handle); err != nil { 181 t.Fatal(err) 182 } 183 } 184 }