summaryrefslogtreecommitdiffstats
path: root/src/pybind/mgr/dashboard/frontend/src/app/shared/services/task-message.service.spec.ts
blob: a529656a0a022e28a955de9cb78d4bfdd8594807 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
import { HttpClientTestingModule } from '@angular/common/http/testing';
import { TestBed } from '@angular/core/testing';

import _ from 'lodash';

import { configureTestBed } from '~/testing/unit-test-helper';
import { RbdService } from '../api/rbd.service';
import { FinishedTask } from '../models/finished-task';
import { TaskException } from '../models/task-exception';
import { TaskMessageOperation, TaskMessageService } from './task-message.service';

describe('TaskManagerMessageService', () => {
  let service: TaskMessageService;
  let finishedTask: FinishedTask;

  configureTestBed({
    providers: [TaskMessageService, RbdService],
    imports: [HttpClientTestingModule]
  });

  beforeEach(() => {
    service = TestBed.inject(TaskMessageService);
    finishedTask = new FinishedTask();
    finishedTask.duration = 30;
  });

  it('should be created', () => {
    expect(service).toBeTruthy();
  });

  it('should get default description', () => {
    expect(service.getErrorTitle(finishedTask)).toBe('Failed to execute unknown task');
  });

  it('should get default running message', () => {
    expect(service.getRunningTitle(finishedTask)).toBe('Executing unknown task');
  });

  it('should get default running message with a set component', () => {
    finishedTask.metadata = { component: 'rbd' };
    expect(service.getRunningTitle(finishedTask)).toBe('Executing RBD');
  });

  it('should getSuccessMessage', () => {
    expect(service.getSuccessTitle(finishedTask)).toBe('Executed unknown task');
  });

  describe('defined tasks messages', () => {
    let defaultMsg: string;
    const testMessages = (operation: TaskMessageOperation, involves: string) => {
      expect(service.getRunningTitle(finishedTask)).toBe(operation.running + ' ' + involves);
      expect(service.getErrorTitle(finishedTask)).toBe(
        'Failed to ' + operation.failure + ' ' + involves
      );
      expect(service.getSuccessTitle(finishedTask)).toBe(`${operation.success} ${involves}`);
    };

    const testCreate = (involves: string) => {
      testMessages(new TaskMessageOperation('Creating', 'create', 'Created'), involves);
    };

    const testUpdate = (involves: string) => {
      testMessages(new TaskMessageOperation('Updating', 'update', 'Updated'), involves);
    };

    const testDelete = (involves: string) => {
      testMessages(new TaskMessageOperation('Deleting', 'delete', 'Deleted'), involves);
    };

    const testImport = (involves: string) => {
      testMessages(new TaskMessageOperation('Importing', 'import', 'Imported'), involves);
    };

    const testErrorCode = (code: number, msg: string) => {
      finishedTask.exception = _.assign(new TaskException(), {
        code: code
      });
      expect(service.getErrorMessage(finishedTask)).toBe(msg);
    };

    describe('pool tasks', () => {
      beforeEach(() => {
        const metadata = {
          pool_name: 'somePool'
        };
        defaultMsg = `pool '${metadata.pool_name}'`;
        finishedTask.metadata = metadata;
      });

      it('tests pool/create messages', () => {
        finishedTask.name = 'pool/create';
        testCreate(defaultMsg);
        testErrorCode(17, `Name is already used by ${defaultMsg}.`);
      });

      it('tests pool/edit messages', () => {
        finishedTask.name = 'pool/edit';
        testUpdate(defaultMsg);
        testErrorCode(17, `Name is already used by ${defaultMsg}.`);
      });

      it('tests pool/delete messages', () => {
        finishedTask.name = 'pool/delete';
        testDelete(defaultMsg);
      });
    });

    describe('erasure code profile tasks', () => {
      beforeEach(() => {
        const metadata = {
          name: 'someEcpName'
        };
        defaultMsg = `erasure code profile '${metadata.name}'`;
        finishedTask.metadata = metadata;
      });

      it('tests ecp/create messages', () => {
        finishedTask.name = 'ecp/create';
        testCreate(defaultMsg);
        testErrorCode(17, `Name is already used by ${defaultMsg}.`);
      });

      it('tests ecp/delete messages', () => {
        finishedTask.name = 'ecp/delete';
        testDelete(defaultMsg);
      });
    });

    describe('crush rule tasks', () => {
      beforeEach(() => {
        const metadata = {
          name: 'someRuleName'
        };
        defaultMsg = `crush rule '${metadata.name}'`;
        finishedTask.metadata = metadata;
      });

      it('tests crushRule/create messages', () => {
        finishedTask.name = 'crushRule/create';
        testCreate(defaultMsg);
        testErrorCode(17, `Name is already used by ${defaultMsg}.`);
      });

      it('tests crushRule/delete messages', () => {
        finishedTask.name = 'crushRule/delete';
        testDelete(defaultMsg);
      });
    });

    describe('rbd tasks', () => {
      let metadata: Record<string, any>;
      let childMsg: string;
      let destinationMsg: string;
      let snapMsg: string;

      beforeEach(() => {
        metadata = {
          pool_name: 'somePool',
          image_name: 'someImage',
          image_id: '12345',
          image_spec: 'somePool/someImage',
          image_id_spec: 'somePool/12345',
          snapshot_name: 'someSnapShot',
          dest_pool_name: 'someDestinationPool',
          dest_image_name: 'someDestinationImage',
          child_pool_name: 'someChildPool',
          child_image_name: 'someChildImage',
          new_image_name: 'someImage2'
        };
        defaultMsg = `RBD '${metadata.pool_name}/${metadata.image_name}'`;
        childMsg = `RBD '${metadata.child_pool_name}/${metadata.child_image_name}'`;
        destinationMsg = `RBD '${metadata.dest_pool_name}/${metadata.dest_image_name}'`;
        snapMsg = `RBD snapshot '${metadata.pool_name}/${metadata.image_name}@${metadata.snapshot_name}'`;
        finishedTask.metadata = metadata;
      });

      it('tests rbd/create messages', () => {
        finishedTask.name = 'rbd/create';
        testCreate(defaultMsg);
        testErrorCode(17, `Name is already used by ${defaultMsg}.`);
      });

      it('tests rbd/edit messages', () => {
        finishedTask.name = 'rbd/edit';
        testUpdate(defaultMsg);
        testErrorCode(17, `Name is already used by ${defaultMsg}.`);
      });

      it('tests rbd/delete messages', () => {
        finishedTask.name = 'rbd/delete';
        testDelete(defaultMsg);
        testErrorCode(16, `${defaultMsg} is busy.`);
        testErrorCode(39, `${defaultMsg} contains snapshots.`);
      });

      it('tests rbd/clone messages', () => {
        finishedTask.name = 'rbd/clone';
        testMessages(new TaskMessageOperation('Cloning', 'clone', 'Cloned'), childMsg);
        testErrorCode(17, `Name is already used by ${childMsg}.`);
        testErrorCode(22, `Snapshot of ${childMsg} must be protected.`);
      });

      it('tests rbd/copy messages', () => {
        finishedTask.name = 'rbd/copy';
        testMessages(new TaskMessageOperation('Copying', 'copy', 'Copied'), destinationMsg);
        testErrorCode(17, `Name is already used by ${destinationMsg}.`);
      });

      it('tests rbd/flatten messages', () => {
        finishedTask.name = 'rbd/flatten';
        testMessages(new TaskMessageOperation('Flattening', 'flatten', 'Flattened'), defaultMsg);
      });

      it('tests rbd/snap/create messages', () => {
        finishedTask.name = 'rbd/snap/create';
        testCreate(snapMsg);
        testErrorCode(17, `Name is already used by ${snapMsg}.`);
      });

      it('tests rbd/snap/edit messages', () => {
        finishedTask.name = 'rbd/snap/edit';
        testUpdate(snapMsg);
        testErrorCode(16, `Cannot unprotect ${snapMsg} because it contains child images.`);
      });

      it('tests rbd/snap/delete messages', () => {
        finishedTask.name = 'rbd/snap/delete';
        testDelete(snapMsg);
        testErrorCode(16, `Cannot delete ${snapMsg} because it's protected.`);
      });

      it('tests rbd/snap/rollback messages', () => {
        finishedTask.name = 'rbd/snap/rollback';
        testMessages(new TaskMessageOperation('Rolling back', 'rollback', 'Rolled back'), snapMsg);
      });

      it('tests rbd/trash/move messages', () => {
        finishedTask.name = 'rbd/trash/move';
        testMessages(
          new TaskMessageOperation('Moving', 'move', 'Moved'),
          `image '${metadata.image_spec}' to trash`
        );
        testErrorCode(2, `Could not find image.`);
      });

      it('tests rbd/trash/restore messages', () => {
        finishedTask.name = 'rbd/trash/restore';
        testMessages(
          new TaskMessageOperation('Restoring', 'restore', 'Restored'),
          `image '${metadata.image_id_spec}' into '${metadata.new_image_name}'`
        );
        testErrorCode(17, `Image name '${metadata.new_image_name}' is already in use.`);
      });

      it('tests rbd/trash/remove messages', () => {
        finishedTask.name = 'rbd/trash/remove';
        testDelete(`image '${metadata.image_id_spec}'`);
      });

      it('tests rbd/trash/purge messages', () => {
        finishedTask.name = 'rbd/trash/purge';
        testMessages(
          new TaskMessageOperation('Purging', 'purge', 'Purged'),
          `images from '${metadata.pool_name}'`
        );
      });
    });
    describe('rbd tasks', () => {
      let metadata;
      let modeMsg: string;
      let peerMsg: string;

      beforeEach(() => {
        metadata = {
          pool_name: 'somePool'
        };
        modeMsg = `mirror mode for pool '${metadata.pool_name}'`;
        peerMsg = `mirror peer for pool '${metadata.pool_name}'`;
        finishedTask.metadata = metadata;
      });
      it('tests rbd/mirroring/site_name/edit messages', () => {
        finishedTask.name = 'rbd/mirroring/site_name/edit';
        testUpdate('mirroring site name');
      });
      it('tests rbd/mirroring/bootstrap/create messages', () => {
        finishedTask.name = 'rbd/mirroring/bootstrap/create';
        testCreate('bootstrap token');
      });
      it('tests rbd/mirroring/bootstrap/import messages', () => {
        finishedTask.name = 'rbd/mirroring/bootstrap/import';
        testImport('bootstrap token');
      });
      it('tests rbd/mirroring/pool/edit messages', () => {
        finishedTask.name = 'rbd/mirroring/pool/edit';
        testUpdate(modeMsg);
        testErrorCode(16, 'Cannot disable mirroring because it contains a peer.');
      });
      it('tests rbd/mirroring/peer/edit messages', () => {
        finishedTask.name = 'rbd/mirroring/peer/edit';
        testUpdate(peerMsg);
      });
      it('tests rbd/mirroring/peer/add messages', () => {
        finishedTask.name = 'rbd/mirroring/peer/add';
        testCreate(peerMsg);
      });
      it('tests rbd/mirroring/peer/delete messages', () => {
        finishedTask.name = 'rbd/mirroring/peer/delete';
        testDelete(peerMsg);
      });
    });
  });
});