]> git.proxmox.com Git - ceph.git/blame - ceph/src/pybind/mgr/dashboard/frontend/src/app/core/auth/role-form/role-form.component.spec.ts
import 15.2.5
[ceph.git] / ceph / src / pybind / mgr / dashboard / frontend / src / app / core / auth / role-form / role-form.component.spec.ts
CommitLineData
11fdf7f2
TL
1import { HttpClientTestingModule, HttpTestingController } from '@angular/common/http/testing';
2import { Component } from '@angular/core';
3import { ComponentFixture, TestBed } from '@angular/core/testing';
4import { ReactiveFormsModule } from '@angular/forms';
5import { Router, Routes } from '@angular/router';
6import { RouterTestingModule } from '@angular/router/testing';
7
494da23a 8import { ToastrModule } from 'ngx-toastr';
11fdf7f2
TL
9import { of } from 'rxjs';
10
11import { configureTestBed, FormHelper, i18nProviders } from '../../../../testing/unit-test-helper';
12import { RoleService } from '../../../shared/api/role.service';
13import { ScopeService } from '../../../shared/api/scope.service';
14import { CdFormGroup } from '../../../shared/forms/cd-form-group';
15import { NotificationService } from '../../../shared/services/notification.service';
16import { SharedModule } from '../../../shared/shared.module';
17import { RoleFormComponent } from './role-form.component';
18import { RoleFormModel } from './role-form.model';
19
20describe('RoleFormComponent', () => {
21 let component: RoleFormComponent;
22 let form: CdFormGroup;
23 let fixture: ComponentFixture<RoleFormComponent>;
24 let httpTesting: HttpTestingController;
25 let roleService: RoleService;
26 let router: Router;
9f95a23c 27 const setUrl = (url: string) => Object.defineProperty(router, 'url', { value: url });
11fdf7f2
TL
28
29 @Component({ selector: 'cd-fake', template: '' })
30 class FakeComponent {}
31
32 const routes: Routes = [{ path: 'roles', component: FakeComponent }];
33
f6b5b4d7
TL
34 configureTestBed({
35 imports: [
36 RouterTestingModule.withRoutes(routes),
37 HttpClientTestingModule,
38 ReactiveFormsModule,
39 ToastrModule.forRoot(),
40 SharedModule
41 ],
42 declarations: [RoleFormComponent, FakeComponent],
43 providers: i18nProviders
44 });
11fdf7f2
TL
45
46 beforeEach(() => {
47 fixture = TestBed.createComponent(RoleFormComponent);
48 component = fixture.componentInstance;
49 form = component.roleForm;
50 httpTesting = TestBed.get(HttpTestingController);
51 roleService = TestBed.get(RoleService);
52 router = TestBed.get(Router);
53 spyOn(router, 'navigate');
54 fixture.detectChanges();
55 const notify = TestBed.get(NotificationService);
56 spyOn(notify, 'show');
57 });
58
59 it('should create', () => {
60 expect(component).toBeTruthy();
61 expect(form).toBeTruthy();
62 });
63
64 describe('create mode', () => {
65 let formHelper: FormHelper;
66
67 beforeEach(() => {
68 setUrl('/user-management/roles/add');
69 component.ngOnInit();
70 formHelper = new FormHelper(form);
71 });
72
73 it('should not disable fields', () => {
74 ['name', 'description', 'scopes_permissions'].forEach((key) =>
75 expect(form.get(key).disabled).toBeFalsy()
76 );
77 });
78
79 it('should validate name required', () => {
80 formHelper.expectErrorChange('name', '', 'required');
81 });
82
83 it('should set mode', () => {
84 expect(component.mode).toBeUndefined();
85 });
86
87 it('should submit', () => {
88 const role: RoleFormModel = {
89 name: 'role1',
90 description: 'Role 1',
91 scopes_permissions: { osd: ['read'] }
92 };
93 formHelper.setMultipleValues(role);
94 component.submit();
95 const roleReq = httpTesting.expectOne('api/role');
96 expect(roleReq.request.method).toBe('POST');
97 expect(roleReq.request.body).toEqual(role);
98 roleReq.flush({});
99 expect(router.navigate).toHaveBeenCalledWith(['/user-management/roles']);
100 });
101
102 it('should check all perms for a scope', () => {
103 formHelper.setValue('scopes_permissions', { cephfs: ['read'] });
104 component.onClickCellCheckbox('grafana', 'scope');
105 const scopes_permissions = form.getValue('scopes_permissions');
106 expect(Object.keys(scopes_permissions)).toContain('grafana');
107 expect(scopes_permissions['grafana']).toEqual(['create', 'delete', 'read', 'update']);
108 });
109
110 it('should uncheck all perms for a scope', () => {
111 formHelper.setValue('scopes_permissions', { cephfs: ['read', 'create', 'update', 'delete'] });
112 component.onClickCellCheckbox('cephfs', 'scope');
113 const scopes_permissions = form.getValue('scopes_permissions');
114 expect(Object.keys(scopes_permissions)).not.toContain('cephfs');
115 });
116
117 it('should uncheck all scopes and perms', () => {
118 component.scopes = ['cephfs', 'grafana'];
119 formHelper.setValue('scopes_permissions', {
120 cephfs: ['read', 'delete'],
121 grafana: ['update']
122 });
123 component.onClickHeaderCheckbox('scope', ({
124 target: { checked: false }
125 } as unknown) as Event);
126 const scopes_permissions = form.getValue('scopes_permissions');
127 expect(scopes_permissions).toEqual({});
128 });
129
130 it('should check all scopes and perms', () => {
131 component.scopes = ['cephfs', 'grafana'];
132 formHelper.setValue('scopes_permissions', {
133 cephfs: ['create', 'update'],
134 grafana: ['delete']
135 });
136 component.onClickHeaderCheckbox('scope', ({ target: { checked: true } } as unknown) as Event);
137 const scopes_permissions = form.getValue('scopes_permissions');
138 const keys = Object.keys(scopes_permissions);
139 expect(keys).toEqual(['cephfs', 'grafana']);
140 keys.forEach((key) => {
141 expect(scopes_permissions[key].sort()).toEqual(['create', 'delete', 'read', 'update']);
142 });
143 });
144
145 it('should check if column is checked', () => {
146 component.scopes_permissions = [
147 { scope: 'a', read: true, create: true, update: true, delete: true },
148 { scope: 'b', read: false, create: true, update: false, delete: true }
149 ];
150 expect(component.isRowChecked('a')).toBeTruthy();
151 expect(component.isRowChecked('b')).toBeFalsy();
152 expect(component.isRowChecked('c')).toBeFalsy();
153 });
154
155 it('should check if header is checked', () => {
156 component.scopes_permissions = [
157 { scope: 'a', read: true, create: true, update: false, delete: true },
158 { scope: 'b', read: false, create: true, update: false, delete: true }
159 ];
160 expect(component.isHeaderChecked('read')).toBeFalsy();
161 expect(component.isHeaderChecked('create')).toBeTruthy();
162 expect(component.isHeaderChecked('update')).toBeFalsy();
163 });
164 });
165
166 describe('edit mode', () => {
167 const role: RoleFormModel = {
168 name: 'role1',
169 description: 'Role 1',
170 scopes_permissions: { osd: ['read', 'create'] }
171 };
172 const scopes = ['osd', 'user'];
173 beforeEach(() => {
174 spyOn(roleService, 'get').and.callFake(() => of(role));
175 spyOn(TestBed.get(ScopeService), 'list').and.callFake(() => of(scopes));
176 setUrl('/user-management/roles/edit/role1');
177 component.ngOnInit();
178 const reqScopes = httpTesting.expectOne('ui-api/scope');
179 expect(reqScopes.request.method).toBe('GET');
180 });
181
182 afterEach(() => {
183 httpTesting.verify();
184 });
185
186 it('should disable fields if editing', () => {
187 expect(form.get('name').disabled).toBeTruthy();
188 ['description', 'scopes_permissions'].forEach((key) =>
189 expect(form.get(key).disabled).toBeFalsy()
190 );
191 });
192
193 it('should set control values', () => {
194 ['name', 'description', 'scopes_permissions'].forEach((key) =>
195 expect(form.getValue(key)).toBe(role[key])
196 );
197 });
198
199 it('should set mode', () => {
200 expect(component.mode).toBe('editing');
201 });
202
203 it('should submit', () => {
204 component.onClickCellCheckbox('osd', 'update');
205 component.onClickCellCheckbox('osd', 'create');
206 component.onClickCellCheckbox('user', 'read');
207 component.submit();
208 const roleReq = httpTesting.expectOne(`api/role/${role.name}`);
209 expect(roleReq.request.method).toBe('PUT');
210 expect(roleReq.request.body).toEqual({
211 name: 'role1',
212 description: 'Role 1',
213 scopes_permissions: { osd: ['read', 'update'], user: ['read'] }
214 });
215 roleReq.flush({});
216 expect(router.navigate).toHaveBeenCalledWith(['/user-management/roles']);
217 });
218 });
219});