summaryrefslogtreecommitdiffstats
path: root/src/pybind/mgr/dashboard/frontend/src/app/core/navigation/navigation/navigation.component.spec.ts
diff options
context:
space:
mode:
Diffstat (limited to 'src/pybind/mgr/dashboard/frontend/src/app/core/navigation/navigation/navigation.component.spec.ts')
-rw-r--r--src/pybind/mgr/dashboard/frontend/src/app/core/navigation/navigation/navigation.component.spec.ts237
1 files changed, 237 insertions, 0 deletions
diff --git a/src/pybind/mgr/dashboard/frontend/src/app/core/navigation/navigation/navigation.component.spec.ts b/src/pybind/mgr/dashboard/frontend/src/app/core/navigation/navigation/navigation.component.spec.ts
new file mode 100644
index 000000000..241910f2b
--- /dev/null
+++ b/src/pybind/mgr/dashboard/frontend/src/app/core/navigation/navigation/navigation.component.spec.ts
@@ -0,0 +1,237 @@
+import { HttpClientTestingModule } from '@angular/common/http/testing';
+import { ComponentFixture, TestBed } from '@angular/core/testing';
+import { By } from '@angular/platform-browser';
+
+import { MockModule } from 'ng-mocks';
+import { of } from 'rxjs';
+
+import { Permission, Permissions } from '~/app/shared/models/permissions';
+import { AuthStorageService } from '~/app/shared/services/auth-storage.service';
+import {
+ Features,
+ FeatureTogglesMap,
+ FeatureTogglesService
+} from '~/app/shared/services/feature-toggles.service';
+import { PrometheusAlertService } from '~/app/shared/services/prometheus-alert.service';
+import { SummaryService } from '~/app/shared/services/summary.service';
+import { configureTestBed } from '~/testing/unit-test-helper';
+import { NavigationModule } from '../navigation.module';
+import { NavigationComponent } from './navigation.component';
+
+function everythingPermittedExcept(disabledPermissions: string[] = []): any {
+ const permissions: Permissions = new Permissions({});
+ Object.keys(permissions).forEach(
+ (key) => (permissions[key] = new Permission(disabledPermissions.includes(key) ? [] : ['read']))
+ );
+ return permissions;
+}
+
+function onlyPermitted(enabledPermissions: string[] = []): any {
+ const permissions: Permissions = new Permissions({});
+ enabledPermissions.forEach((key) => (permissions[key] = new Permission(['read'])));
+ return permissions;
+}
+
+function everythingEnabledExcept(features: Features[] = []): FeatureTogglesMap {
+ const featureTogglesMap: FeatureTogglesMap = new FeatureTogglesMap();
+ features.forEach((key) => (featureTogglesMap[key] = false));
+ return featureTogglesMap;
+}
+
+function onlyEnabled(features: Features[] = []): FeatureTogglesMap {
+ const featureTogglesMap: FeatureTogglesMap = new FeatureTogglesMap();
+ Object.keys(featureTogglesMap).forEach(
+ (key) => (featureTogglesMap[key] = features.includes(<Features>key))
+ );
+ return featureTogglesMap;
+}
+
+describe('NavigationComponent', () => {
+ let component: NavigationComponent;
+ let fixture: ComponentFixture<NavigationComponent>;
+
+ configureTestBed({
+ declarations: [NavigationComponent],
+ imports: [HttpClientTestingModule, MockModule(NavigationModule)],
+ providers: [
+ {
+ provide: AuthStorageService,
+ useValue: {
+ getPermissions: jest.fn(),
+ isPwdDisplayed$: { subscribe: jest.fn() },
+ telemetryNotification$: { subscribe: jest.fn() }
+ }
+ },
+ { provide: SummaryService, useValue: { subscribe: jest.fn() } },
+ { provide: FeatureTogglesService, useValue: { get: jest.fn() } },
+ { provide: PrometheusAlertService, useValue: { alerts: [] } }
+ ]
+ });
+
+ beforeEach(() => {
+ fixture = TestBed.createComponent(NavigationComponent);
+ component = fixture.componentInstance;
+ });
+
+ describe('Test Permissions', () => {
+ const testCases: [string[], string[]][] = [
+ [
+ ['hosts'],
+ [
+ '.tc_submenuitem_hosts',
+ '.tc_submenuitem_cluster_inventory',
+ '.tc_submenuitem_cluster_services'
+ ]
+ ],
+ [['monitor'], ['.tc_submenuitem_cluster_monitor']],
+ [['osd'], ['.tc_submenuitem_osds', '.tc_submenuitem_crush']],
+ [['configOpt'], ['.tc_submenuitem_configuration', '.tc_submenuitem_modules']],
+ [['log'], ['.tc_submenuitem_log']],
+ [['prometheus'], ['.tc_submenuitem_monitoring']],
+ [['pool'], ['.tc_menuitem_pool']],
+ [['rbdImage'], ['.tc_submenuitem_block_images']],
+ [['rbdMirroring'], ['.tc_submenuitem_block_mirroring']],
+ [['iscsi'], ['.tc_submenuitem_block_iscsi']],
+ [['rbdImage', 'rbdMirroring', 'iscsi'], ['.tc_menuitem_block']],
+ [['nfs'], ['.tc_menuitem_nfs']],
+ [['cephfs'], ['.tc_menuitem_cephfs']],
+ [
+ ['rgw'],
+ [
+ '.tc_menuitem_rgw',
+ '.tc_submenuitem_rgw_daemons',
+ '.tc_submenuitem_rgw_buckets',
+ '.tc_submenuitem_rgw_users'
+ ]
+ ]
+ ];
+
+ for (const [disabledPermissions, selectors] of testCases) {
+ it(`When disabled permissions: ${JSON.stringify(
+ disabledPermissions
+ )} => hidden: "${selectors}"`, () => {
+ component.permissions = everythingPermittedExcept(disabledPermissions);
+ component.enabledFeature$ = of(everythingEnabledExcept());
+
+ fixture.detectChanges();
+ for (const selector of selectors) {
+ expect(fixture.debugElement.query(By.css(selector))).toBeFalsy();
+ }
+ });
+ }
+
+ for (const [enabledPermissions, selectors] of testCases) {
+ it(`When enabled permissions: ${JSON.stringify(
+ enabledPermissions
+ )} => visible: "${selectors}"`, () => {
+ component.permissions = onlyPermitted(enabledPermissions);
+ component.enabledFeature$ = of(everythingEnabledExcept());
+
+ fixture.detectChanges();
+ for (const selector of selectors) {
+ expect(fixture.debugElement.query(By.css(selector))).toBeTruthy();
+ }
+ });
+ }
+ });
+
+ describe('Test FeatureToggles', () => {
+ const testCases: [Features[], string[]][] = [
+ [['rbd'], ['.tc_submenuitem_block_images']],
+ [['mirroring'], ['.tc_submenuitem_block_mirroring']],
+ [['iscsi'], ['.tc_submenuitem_block_iscsi']],
+ [['rbd', 'mirroring', 'iscsi'], ['.tc_menuitem_block']],
+ [['nfs'], ['.tc_menuitem_nfs']],
+ [['cephfs'], ['.tc_menuitem_cephfs']],
+ [
+ ['rgw'],
+ [
+ '.tc_menuitem_rgw',
+ '.tc_submenuitem_rgw_daemons',
+ '.tc_submenuitem_rgw_buckets',
+ '.tc_submenuitem_rgw_users'
+ ]
+ ]
+ ];
+
+ for (const [disabledFeatures, selectors] of testCases) {
+ it(`When disabled features: ${JSON.stringify(
+ disabledFeatures
+ )} => hidden: "${selectors}"`, () => {
+ component.enabledFeature$ = of(everythingEnabledExcept(disabledFeatures));
+ component.permissions = everythingPermittedExcept();
+
+ fixture.detectChanges();
+ for (const selector of selectors) {
+ expect(fixture.debugElement.query(By.css(selector))).toBeFalsy();
+ }
+ });
+ }
+
+ for (const [enabledFeatures, selectors] of testCases) {
+ it(`When enabled features: ${JSON.stringify(
+ enabledFeatures
+ )} => visible: "${selectors}"`, () => {
+ component.enabledFeature$ = of(onlyEnabled(enabledFeatures));
+ component.permissions = everythingPermittedExcept();
+
+ fixture.detectChanges();
+ for (const selector of selectors) {
+ expect(fixture.debugElement.query(By.css(selector))).toBeTruthy();
+ }
+ });
+ }
+ });
+
+ describe('showTopNotification', () => {
+ const notification1 = 'notificationName1';
+ const notification2 = 'notificationName2';
+
+ beforeEach(() => {
+ component.notifications = [];
+ });
+
+ it('should show notification', () => {
+ component.showTopNotification(notification1, true);
+ expect(component.notifications.includes(notification1)).toBeTruthy();
+ expect(component.notifications.length).toBe(1);
+ });
+
+ it('should not add a second notification if it is already shown', () => {
+ component.showTopNotification(notification1, true);
+ component.showTopNotification(notification1, true);
+ expect(component.notifications.includes(notification1)).toBeTruthy();
+ expect(component.notifications.length).toBe(1);
+ });
+
+ it('should add a second notification if the first one is different', () => {
+ component.showTopNotification(notification1, true);
+ component.showTopNotification(notification2, true);
+ expect(component.notifications.includes(notification1)).toBeTruthy();
+ expect(component.notifications.includes(notification2)).toBeTruthy();
+ expect(component.notifications.length).toBe(2);
+ });
+
+ it('should hide an active notification', () => {
+ component.showTopNotification(notification1, true);
+ expect(component.notifications.includes(notification1)).toBeTruthy();
+ expect(component.notifications.length).toBe(1);
+ component.showTopNotification(notification1, false);
+ expect(component.notifications.length).toBe(0);
+ });
+
+ it('should not fail if it tries to hide an inactive notification', () => {
+ expect(() => component.showTopNotification(notification1, false)).not.toThrow();
+ expect(component.notifications.length).toBe(0);
+ });
+
+ it('should keep other notifications if it hides one', () => {
+ component.showTopNotification(notification1, true);
+ component.showTopNotification(notification2, true);
+ expect(component.notifications.length).toBe(2);
+ component.showTopNotification(notification2, false);
+ expect(component.notifications.length).toBe(1);
+ expect(component.notifications.includes(notification1)).toBeTruthy();
+ });
+ });
+});