3
3
package restapi_test
4
4
5
5
import (
6
+ "encoding/json"
6
7
"fmt"
7
8
"net/http"
8
9
"net/http/httptest"
9
10
"net/url"
10
11
"testing"
12
+ "time"
11
13
12
14
"github.com/golang/mock/gomock"
13
15
"github.com/scylladb/go-log"
14
16
"github.com/scylladb/scylla-manager/v3/pkg/restapi"
15
17
"github.com/scylladb/scylla-manager/v3/pkg/service/backup"
16
18
"github.com/scylladb/scylla-manager/v3/pkg/service/backup/backupspec"
19
+ "github.com/scylladb/scylla-manager/v3/pkg/service/scheduler"
17
20
"github.com/scylladb/scylla-manager/v3/pkg/util/timeutc"
18
21
"github.com/scylladb/scylla-manager/v3/pkg/util/uuid"
19
22
)
20
23
21
24
//go:generate mockgen -destination mock_backupservice_test.go -mock_names BackupService=MockBackupService -package restapi github.com/scylladb/scylla-manager/v3/pkg/restapi BackupService
25
+ //go:generate mockgen -destination mock_schedservice_test.go -mock_names SchedService=MockSchedService -package restapi github.com/scylladb/scylla-manager/v3/pkg/restapi SchedService
22
26
23
27
func listBackupsRequest (clusterID uuid.UUID ) * http.Request {
24
28
return httptest .NewRequest (http .MethodGet , fmt .Sprintf ("/api/v1/cluster/%s/backups" , clusterID .String ()), nil )
25
29
}
26
30
31
+ func listBackupsPurgeRequest (clusterID uuid.UUID ) * http.Request {
32
+ return httptest .NewRequest (http .MethodDelete , fmt .Sprintf ("/api/v1/cluster/%s/backups/purge" , clusterID .String ()), nil )
33
+ }
34
+
27
35
func listBackupFilesRequest (clusterID uuid.UUID ) * http.Request {
28
36
return httptest .NewRequest (http .MethodGet , fmt .Sprintf ("/api/v1/cluster/%s/backups/files" , clusterID .String ()), nil )
29
37
}
30
38
31
- func withForm (r * http.Request , locations []backupspec.Location , filter backup.ListFilter , query string ) * http.Request {
39
+ func withForm (r * http.Request , dryRun bool , locations []backupspec.Location , filter backup.ListFilter , query string ) * http.Request {
32
40
r .Form = url.Values {}
33
41
for _ , l := range locations {
34
42
r .Form .Add ("locations" , l .String ())
@@ -41,6 +49,7 @@ func withForm(r *http.Request, locations []backupspec.Location, filter backup.Li
41
49
r .Form .Add ("min_date" , string (a ))
42
50
b , _ := filter .MaxDate .MarshalText ()
43
51
r .Form .Add ("max_date" , string (b ))
52
+ r .Form .Add ("dry_run" , fmt .Sprintf ("%v" , dryRun ))
44
53
45
54
return r
46
55
}
@@ -91,15 +100,115 @@ func TestBackupList(t *testing.T) {
91
100
cm .EXPECT ().GetCluster (gomock .Any (), cluster .ID .String ()).Return (cluster , nil )
92
101
bm .EXPECT ().List (gomock .Any (), cluster .ID , locations , filter ).Return (golden , nil )
93
102
94
- r := withForm (listBackupsRequest (cluster .ID ), locations , filter , cluster .Name )
103
+ r := withForm (listBackupsRequest (cluster .ID ), false , locations , filter , cluster .Name )
95
104
w := httptest .NewRecorder ()
96
105
h .ServeHTTP (w , r )
97
106
assertJsonBody (t , w , golden )
98
107
}
99
108
100
- func TestBackupListAllClusters (t * testing.T ) {
109
+ func TestBackupPurge (t * testing.T ) {
101
110
t .Parallel ()
102
111
112
+ ctrl := gomock .NewController (t )
113
+ defer ctrl .Finish ()
114
+ cm := restapi .NewMockClusterService (ctrl )
115
+ bm := restapi .NewMockBackupService (ctrl )
116
+ sm := restapi .NewMockSchedService (ctrl )
117
+
118
+ services := restapi.Services {
119
+ Cluster : cm ,
120
+ Backup : bm ,
121
+ Scheduler : sm ,
122
+ }
123
+
124
+ h := restapi .New (services , log .NewDevelopment ())
125
+
126
+ var (
127
+ cluster = givenCluster ()
128
+
129
+ locations = backupspec.Locations {
130
+ {Provider : backupspec .S3 , Path : "foo" },
131
+ {Provider : backupspec .S3 , Path : "bar" },
132
+ }
133
+
134
+ taskID1 = uuid .MustRandom ()
135
+ taskID2 = uuid .MustRandom ()
136
+
137
+ snapshotNow1 = backupspec .SnapshotTagAt (time .Now ())
138
+ snapshotNow2 = backupspec .SnapshotTagAt (time .Now ().Add (time .Minute ))
139
+
140
+ filter = backup.ListFilter {
141
+ ClusterID : cluster .ID ,
142
+ }
143
+
144
+ manifests = backupspec.Manifests {
145
+ {
146
+ Location : locations [0 ],
147
+ DC : "" ,
148
+ ClusterID : cluster .ID ,
149
+ NodeID : "" ,
150
+ TaskID : taskID1 ,
151
+ SnapshotTag : snapshotNow1 ,
152
+ Temporary : false ,
153
+ },
154
+ {
155
+ Location : locations [1 ],
156
+ DC : "" ,
157
+ ClusterID : cluster .ID ,
158
+ NodeID : "" ,
159
+ TaskID : taskID2 ,
160
+ SnapshotTag : snapshotNow2 ,
161
+ Temporary : false ,
162
+ },
163
+ }
164
+ )
165
+
166
+ task1 := makeTaskItem (cluster .ID , taskID1 , locations , 3 , 30 )
167
+ task2 := makeTaskItem (cluster .ID , taskID2 , locations , 3 , 30 )
168
+ tasks := []* scheduler.TaskListItem {
169
+ task1 , task2 ,
170
+ }
171
+ cm .EXPECT ().GetCluster (gomock .Any (), cluster .ID .String ()).Return (cluster , nil )
172
+ sm .EXPECT ().ListTasks (gomock .Any (), cluster .ID , scheduler.ListFilter {TaskType : []scheduler.TaskType {scheduler .BackupTask }}).Return (tasks , nil )
173
+ bm .EXPECT ().PurgeBackups (gomock .Any (), cluster .ID , locations , gomock .Any (), gomock .Any ()).Return (manifests , nil )
174
+
175
+ itemList := restapi .ConvertManifestsToListItems (manifests )
176
+ r := withForm (listBackupsPurgeRequest (cluster .ID ), true , locations , filter , cluster .Name )
177
+ w := httptest .NewRecorder ()
178
+ h .ServeHTTP (w , r )
179
+ assertJsonBody (t , w , itemList )
180
+ }
181
+
182
+ func makeTaskItem (clusterID , taskID uuid.UUID , locations backupspec.Locations , retention , day int ) * scheduler.TaskListItem {
183
+ taskProp := backup.TaskProperties {
184
+ Location : locations ,
185
+ RetentionMap : make (backup.RetentionMap , 0 ),
186
+ }
187
+ taskProp .RetentionMap .Add (taskID , retention , day )
188
+
189
+ prop , err := json .Marshal (taskProp )
190
+ if err != nil {
191
+ return nil
192
+ }
193
+
194
+ return & scheduler.TaskListItem {
195
+ Task : scheduler.Task {
196
+ ClusterID : clusterID ,
197
+ ID : taskID ,
198
+ Type : scheduler .BackupTask ,
199
+ Enabled : true ,
200
+ Sched : scheduler.Schedule {StartDate : time .Now ()},
201
+ Properties : prop ,
202
+ },
203
+ Suspended : false ,
204
+ NextActivation : nil ,
205
+ Retry : 0 ,
206
+ }
207
+
208
+ }
209
+
210
+ func TestBackupListAllClusters (t * testing.T ) {
211
+
103
212
ctrl := gomock .NewController (t )
104
213
defer ctrl .Finish ()
105
214
cm := restapi .NewMockClusterService (ctrl )
@@ -142,7 +251,7 @@ func TestBackupListAllClusters(t *testing.T) {
142
251
cm .EXPECT ().GetCluster (gomock .Any (), cluster .ID .String ()).Return (cluster , nil )
143
252
bm .EXPECT ().List (gomock .Any (), cluster .ID , locations , filter ).Return (golden , nil )
144
253
145
- r := withForm (listBackupsRequest (cluster .ID ), locations , filter , "" )
254
+ r := withForm (listBackupsRequest (cluster .ID ), false , locations , filter , "" )
146
255
w := httptest .NewRecorder ()
147
256
h .ServeHTTP (w , r )
148
257
assertJsonBody (t , w , golden )
@@ -191,7 +300,7 @@ func TestBackupListFiles(t *testing.T) {
191
300
cm .EXPECT ().GetCluster (gomock .Any (), cluster .ID .String ()).Return (cluster , nil )
192
301
bm .EXPECT ().ListFiles (gomock .Any (), cluster .ID , locations , filter ).Return (golden , nil )
193
302
194
- r := withForm (listBackupFilesRequest (cluster .ID ), locations , filter , cluster .ID .String ())
303
+ r := withForm (listBackupFilesRequest (cluster .ID ), false , locations , filter , cluster .ID .String ())
195
304
w := httptest .NewRecorder ()
196
305
h .ServeHTTP (w , r )
197
306
assertJsonBody (t , w , golden )
0 commit comments