]>
Commit | Line | Data |
---|---|---|
11fdf7f2 TL |
1 | import { HttpClientTestingModule } from '@angular/common/http/testing'; |
2 | import { ComponentFixture, TestBed } from '@angular/core/testing'; | |
3 | import { ReactiveFormsModule } from '@angular/forms'; | |
4 | import { RouterTestingModule } from '@angular/router/testing'; | |
5 | ||
f67539c2 TL |
6 | import { NgbActiveModal } from '@ng-bootstrap/ng-bootstrap'; |
7 | import _ from 'lodash'; | |
494da23a | 8 | import { ToastrModule } from 'ngx-toastr'; |
81eedcae | 9 | import { of as observableOf } from 'rxjs'; |
11fdf7f2 | 10 | |
f67539c2 TL |
11 | import { ConfigurationService } from '~/app/shared/api/configuration.service'; |
12 | import { SharedModule } from '~/app/shared/shared.module'; | |
13 | import { configureTestBed } from '~/testing/unit-test-helper'; | |
11fdf7f2 TL |
14 | import { OsdRecvSpeedModalComponent } from './osd-recv-speed-modal.component'; |
15 | ||
16 | describe('OsdRecvSpeedModalComponent', () => { | |
17 | let component: OsdRecvSpeedModalComponent; | |
18 | let fixture: ComponentFixture<OsdRecvSpeedModalComponent>; | |
81eedcae | 19 | let configurationService: ConfigurationService; |
11fdf7f2 TL |
20 | |
21 | configureTestBed({ | |
22 | imports: [ | |
23 | HttpClientTestingModule, | |
11fdf7f2 TL |
24 | ReactiveFormsModule, |
25 | RouterTestingModule, | |
26 | SharedModule, | |
494da23a | 27 | ToastrModule.forRoot() |
11fdf7f2 TL |
28 | ], |
29 | declarations: [OsdRecvSpeedModalComponent], | |
f67539c2 | 30 | providers: [NgbActiveModal] |
11fdf7f2 TL |
31 | }); |
32 | ||
9f95a23c | 33 | let configOptions: any[] = []; |
11fdf7f2 TL |
34 | |
35 | beforeEach(() => { | |
36 | fixture = TestBed.createComponent(OsdRecvSpeedModalComponent); | |
37 | component = fixture.componentInstance; | |
38 | fixture.detectChanges(); | |
f67539c2 | 39 | configurationService = TestBed.inject(ConfigurationService); |
11fdf7f2 TL |
40 | configOptions = [ |
41 | { | |
42 | name: 'osd_max_backfills', | |
43 | desc: '', | |
44 | type: 'uint', | |
45 | default: 1 | |
46 | }, | |
47 | { | |
48 | name: 'osd_recovery_max_active', | |
49 | desc: '', | |
50 | type: 'uint', | |
51 | default: 3 | |
52 | }, | |
53 | { | |
54 | name: 'osd_recovery_max_single_start', | |
55 | desc: '', | |
56 | type: 'uint', | |
57 | default: 1 | |
58 | }, | |
59 | { | |
60 | name: 'osd_recovery_sleep', | |
61 | desc: 'Time in seconds to sleep before next recovery or backfill op', | |
62 | type: 'float', | |
63 | default: 0 | |
64 | } | |
65 | ]; | |
81eedcae | 66 | spyOn(configurationService, 'filter').and.returnValue(observableOf(configOptions)); |
11fdf7f2 TL |
67 | }); |
68 | ||
69 | it('should create', () => { | |
70 | expect(component).toBeTruthy(); | |
71 | }); | |
72 | ||
81eedcae | 73 | describe('ngOnInit', () => { |
9f95a23c TL |
74 | let setPriority: jasmine.Spy; |
75 | let setValidators: jasmine.Spy; | |
81eedcae TL |
76 | |
77 | beforeEach(() => { | |
78 | setPriority = spyOn(component, 'setPriority').and.callThrough(); | |
79 | setValidators = spyOn(component, 'setValidators').and.callThrough(); | |
80 | component.ngOnInit(); | |
81 | }); | |
82 | ||
83 | it('should call setValidators', () => { | |
84 | expect(setValidators).toHaveBeenCalled(); | |
85 | }); | |
86 | ||
87 | it('should get and set priority correctly', () => { | |
88 | const defaultPriority = _.find(component.priorities, (p) => { | |
89 | return _.isEqual(p.name, 'default'); | |
90 | }); | |
91 | expect(setPriority).toHaveBeenCalledWith(defaultPriority); | |
92 | }); | |
93 | ||
94 | it('should set descriptions correctly', () => { | |
95 | expect(component.priorityAttrs['osd_max_backfills'].desc).toBe(''); | |
96 | expect(component.priorityAttrs['osd_recovery_max_active'].desc).toBe(''); | |
97 | expect(component.priorityAttrs['osd_recovery_max_single_start'].desc).toBe(''); | |
98 | expect(component.priorityAttrs['osd_recovery_sleep'].desc).toBe( | |
99 | 'Time in seconds to sleep before next recovery or backfill op' | |
100 | ); | |
101 | }); | |
102 | }); | |
103 | ||
11fdf7f2 TL |
104 | describe('setPriority', () => { |
105 | it('should prepare the form for a custom priority', () => { | |
106 | const customPriority = { | |
107 | name: 'custom', | |
108 | text: 'Custom', | |
109 | values: { | |
110 | osd_max_backfills: 1, | |
111 | osd_recovery_max_active: 4, | |
112 | osd_recovery_max_single_start: 1, | |
113 | osd_recovery_sleep: 1 | |
114 | } | |
115 | }; | |
116 | ||
117 | component.setPriority(customPriority); | |
118 | ||
119 | const customInPriorities = _.find(component.priorities, (p) => { | |
120 | return p.name === 'custom'; | |
121 | }); | |
122 | ||
123 | expect(customInPriorities).not.toBeNull(); | |
124 | expect(component.osdRecvSpeedForm.getValue('priority')).toBe('custom'); | |
125 | expect(component.osdRecvSpeedForm.getValue('osd_max_backfills')).toBe(1); | |
126 | expect(component.osdRecvSpeedForm.getValue('osd_recovery_max_active')).toBe(4); | |
127 | expect(component.osdRecvSpeedForm.getValue('osd_recovery_max_single_start')).toBe(1); | |
128 | expect(component.osdRecvSpeedForm.getValue('osd_recovery_sleep')).toBe(1); | |
129 | }); | |
130 | ||
131 | it('should prepare the form for a none custom priority', () => { | |
132 | const lowPriority = { | |
133 | name: 'low', | |
134 | text: 'Low', | |
135 | values: { | |
136 | osd_max_backfills: 1, | |
137 | osd_recovery_max_active: 1, | |
138 | osd_recovery_max_single_start: 1, | |
139 | osd_recovery_sleep: 0.5 | |
140 | } | |
141 | }; | |
142 | ||
143 | component.setPriority(lowPriority); | |
144 | ||
145 | const customInPriorities = _.find(component.priorities, (p) => { | |
146 | return p.name === 'custom'; | |
147 | }); | |
148 | ||
149 | expect(customInPriorities).toBeUndefined(); | |
150 | expect(component.osdRecvSpeedForm.getValue('priority')).toBe('low'); | |
151 | expect(component.osdRecvSpeedForm.getValue('osd_max_backfills')).toBe(1); | |
152 | expect(component.osdRecvSpeedForm.getValue('osd_recovery_max_active')).toBe(1); | |
153 | expect(component.osdRecvSpeedForm.getValue('osd_recovery_max_single_start')).toBe(1); | |
154 | expect(component.osdRecvSpeedForm.getValue('osd_recovery_sleep')).toBe(0.5); | |
155 | }); | |
156 | }); | |
157 | ||
158 | describe('detectPriority', () => { | |
159 | const configOptionsLow = { | |
160 | osd_max_backfills: 1, | |
161 | osd_recovery_max_active: 1, | |
162 | osd_recovery_max_single_start: 1, | |
163 | osd_recovery_sleep: 0.5 | |
164 | }; | |
165 | ||
166 | const configOptionsDefault = { | |
167 | osd_max_backfills: 1, | |
168 | osd_recovery_max_active: 3, | |
169 | osd_recovery_max_single_start: 1, | |
170 | osd_recovery_sleep: 0 | |
171 | }; | |
172 | ||
173 | const configOptionsHigh = { | |
174 | osd_max_backfills: 4, | |
175 | osd_recovery_max_active: 4, | |
176 | osd_recovery_max_single_start: 4, | |
177 | osd_recovery_sleep: 0 | |
178 | }; | |
179 | ||
180 | const configOptionsCustom = { | |
181 | osd_max_backfills: 1, | |
182 | osd_recovery_max_active: 2, | |
183 | osd_recovery_max_single_start: 1, | |
184 | osd_recovery_sleep: 0 | |
185 | }; | |
186 | ||
187 | const configOptionsIncomplete = { | |
188 | osd_max_backfills: 1, | |
189 | osd_recovery_max_single_start: 1, | |
190 | osd_recovery_sleep: 0 | |
191 | }; | |
192 | ||
193 | it('should return priority "low" if the config option values have been set accordingly', () => { | |
9f95a23c | 194 | component.detectPriority(configOptionsLow, (priority: Record<string, any>) => { |
11fdf7f2 TL |
195 | expect(priority.name).toBe('low'); |
196 | }); | |
197 | expect(component.osdRecvSpeedForm.getValue('customizePriority')).toBeFalsy(); | |
198 | }); | |
199 | ||
200 | it('should return priority "default" if the config option values have been set accordingly', () => { | |
9f95a23c | 201 | component.detectPriority(configOptionsDefault, (priority: Record<string, any>) => { |
11fdf7f2 TL |
202 | expect(priority.name).toBe('default'); |
203 | }); | |
204 | expect(component.osdRecvSpeedForm.getValue('customizePriority')).toBeFalsy(); | |
205 | }); | |
206 | ||
207 | it('should return priority "high" if the config option values have been set accordingly', () => { | |
9f95a23c | 208 | component.detectPriority(configOptionsHigh, (priority: Record<string, any>) => { |
11fdf7f2 TL |
209 | expect(priority.name).toBe('high'); |
210 | }); | |
211 | expect(component.osdRecvSpeedForm.getValue('customizePriority')).toBeFalsy(); | |
212 | }); | |
213 | ||
214 | it('should return priority "custom" if the config option values do not match any priority', () => { | |
9f95a23c | 215 | component.detectPriority(configOptionsCustom, (priority: Record<string, any>) => { |
11fdf7f2 TL |
216 | expect(priority.name).toBe('custom'); |
217 | }); | |
218 | expect(component.osdRecvSpeedForm.getValue('customizePriority')).toBeTruthy(); | |
219 | }); | |
220 | ||
221 | it('should return no priority if the config option values are incomplete', () => { | |
9f95a23c | 222 | component.detectPriority(configOptionsIncomplete, (priority: Record<string, any>) => { |
11fdf7f2 TL |
223 | expect(priority.name).toBeNull(); |
224 | }); | |
225 | expect(component.osdRecvSpeedForm.getValue('customizePriority')).toBeFalsy(); | |
226 | }); | |
227 | }); | |
228 | ||
229 | describe('getCurrentValues', () => { | |
230 | it('should return default values if no value has been set by the user', () => { | |
231 | const currentValues = component.getCurrentValues(configOptions); | |
232 | configOptions.forEach((configOption) => { | |
233 | const configOptionValue = currentValues.values[configOption.name]; | |
234 | expect(configOptionValue).toBe(configOption.default); | |
235 | }); | |
236 | }); | |
237 | ||
238 | it('should return the values set by the user if they exist', () => { | |
239 | configOptions.forEach((configOption) => { | |
240 | configOption['value'] = [{ section: 'osd', value: 7 }]; | |
241 | }); | |
242 | ||
243 | const currentValues = component.getCurrentValues(configOptions); | |
244 | Object.values(currentValues.values).forEach((configValue) => { | |
245 | expect(configValue).toBe(7); | |
246 | }); | |
247 | }); | |
248 | ||
249 | it('should return the default value if one is missing', () => { | |
250 | for (let i = 1; i < configOptions.length; i++) { | |
251 | configOptions[i]['value'] = [{ section: 'osd', value: 7 }]; | |
252 | } | |
253 | ||
254 | const currentValues = component.getCurrentValues(configOptions); | |
255 | Object.entries(currentValues.values).forEach(([configName, configValue]) => { | |
256 | if (configName === 'osd_max_backfills') { | |
257 | expect(configValue).toBe(1); | |
258 | } else { | |
259 | expect(configValue).toBe(7); | |
260 | } | |
261 | }); | |
262 | }); | |
263 | ||
264 | it('should return nothing if neither value nor default value is given', () => { | |
265 | configOptions[0].default = null; | |
266 | const currentValues = component.getCurrentValues(configOptions); | |
267 | expect(currentValues.values).not.toContain('osd_max_backfills'); | |
268 | }); | |
269 | }); | |
270 | ||
271 | describe('setDescription', () => { | |
272 | it('should set the description if one is given', () => { | |
273 | component.setDescription(configOptions); | |
274 | Object.keys(component.priorityAttrs).forEach((configOptionName) => { | |
275 | if (configOptionName === 'osd_recovery_sleep') { | |
276 | expect(component.priorityAttrs[configOptionName].desc).toBe( | |
277 | 'Time in seconds to sleep before next recovery or backfill op' | |
278 | ); | |
279 | } else { | |
280 | expect(component.priorityAttrs[configOptionName].desc).toBe(''); | |
281 | } | |
282 | }); | |
283 | }); | |
284 | }); | |
285 | ||
286 | describe('setValidators', () => { | |
287 | it('should set needed validators for config option', () => { | |
288 | component.setValidators(configOptions); | |
289 | configOptions.forEach((configOption) => { | |
290 | const control = component.osdRecvSpeedForm.controls[configOption.name]; | |
291 | ||
292 | if (configOption.type === 'float') { | |
293 | expect(component.priorityAttrs[configOption.name].patternHelpText).toBe( | |
294 | 'The entered value needs to be a number or decimal.' | |
295 | ); | |
296 | } else { | |
297 | expect(component.priorityAttrs[configOption.name].minValue).toBe(0); | |
298 | expect(component.priorityAttrs[configOption.name].patternHelpText).toBe( | |
299 | 'The entered value needs to be an unsigned number.' | |
300 | ); | |
301 | ||
302 | control.setValue(-1); | |
303 | expect(control.hasError('min')).toBeTruthy(); | |
304 | } | |
305 | ||
306 | control.setValue(null); | |
307 | expect(control.hasError('required')).toBeTruthy(); | |
308 | control.setValue('E'); | |
309 | expect(control.hasError('pattern')).toBeTruthy(); | |
310 | control.setValue(3); | |
311 | expect(control.hasError('required')).toBeFalsy(); | |
312 | expect(control.hasError('min')).toBeFalsy(); | |
313 | expect(control.hasError('pattern')).toBeFalsy(); | |
314 | }); | |
315 | }); | |
316 | }); | |
317 | }); |