186 lines
8.5 KiB
TypeScript
186 lines
8.5 KiB
TypeScript
import { ComponentFixture, TestBed } from '@angular/core/testing';
|
|
import { By } from '@angular/platform-browser';
|
|
import { RouterTestingModule } from '@angular/router/testing';
|
|
import { CUSTOM_ELEMENTS_SCHEMA } from '@angular/core';
|
|
import { MatDialogModule } from '@angular/material/dialog';
|
|
import { TranslateModule } from '@ngx-translate/core';
|
|
import { SidebarComponent } from './sidebar.component';
|
|
import { AuthService, UserCategory } from '@services/auth.service';
|
|
|
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
// Rutas con condiciones de visibilidad (según sidebar.component.html)
|
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
|
|
/** Siempre visibles para todos los roles autenticados */
|
|
const ALWAYS_VISIBLE = ['/groups'];
|
|
|
|
/** Solo visibles para super-admin y ou-admin (ocultos para operator y minimal) */
|
|
const ADMIN_ONLY_ROUTES = [
|
|
'/dhcp-servers',
|
|
'/boot-servers',
|
|
'/calendars',
|
|
'/repositories',
|
|
'/menus',
|
|
];
|
|
|
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
// Helper: cuenta mat-list-item visibles en el DOM
|
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
function countVisibleListItems(fixture: ComponentFixture<SidebarComponent>): number {
|
|
return fixture.debugElement.queryAll(By.css('mat-list-item')).length;
|
|
}
|
|
|
|
/** Devuelve true si existe algún mat-list-item con [routerLink] apuntando a la ruta dada */
|
|
function hasRouteLink(fixture: ComponentFixture<SidebarComponent>, route: string): boolean {
|
|
const items = fixture.debugElement.queryAll(By.css(`[routerLink="${route}"]`));
|
|
return items.length > 0;
|
|
}
|
|
|
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
// Mock de AuthService
|
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
function mockAuthService(category: UserCategory) {
|
|
return {
|
|
userCategory: category,
|
|
username: 'test-user',
|
|
isSuperAdmin: category === 'super-admin',
|
|
isOUAdmin: category === 'ou-admin',
|
|
isOUOperator: category === 'ou-operator',
|
|
isOUMinimal: category === 'ou-minimal',
|
|
getCurrentRole: () => category,
|
|
};
|
|
}
|
|
|
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
// Suite principal
|
|
// ─────────────────────────────────────────────────────────────────────────────
|
|
|
|
describe('SidebarComponent — visibilidad de elementos por rol', () => {
|
|
let fixture: ComponentFixture<SidebarComponent>;
|
|
let component: SidebarComponent;
|
|
|
|
async function createComponent(category: UserCategory) {
|
|
await TestBed.configureTestingModule({
|
|
declarations: [SidebarComponent],
|
|
imports: [
|
|
RouterTestingModule,
|
|
MatDialogModule,
|
|
TranslateModule.forRoot(),
|
|
],
|
|
providers: [
|
|
{ provide: AuthService, useValue: mockAuthService(category) },
|
|
],
|
|
schemas: [CUSTOM_ELEMENTS_SCHEMA], // ignora mat-* desconocidos
|
|
}).compileComponents();
|
|
|
|
fixture = TestBed.createComponent(SidebarComponent);
|
|
component = fixture.componentInstance;
|
|
fixture.detectChanges();
|
|
}
|
|
|
|
// ── Grupos — siempre visible ───────────────────────────────────────────────
|
|
describe('/groups — siempre visible para cualquier rol', () => {
|
|
(['super-admin', 'ou-admin', 'ou-operator', 'ou-minimal'] as UserCategory[]).forEach(role => {
|
|
it(`${role} ve el enlace a /groups`, async () => {
|
|
await createComponent(role);
|
|
expect(hasRouteLink(fixture, '/groups')).toBeTrue();
|
|
});
|
|
});
|
|
});
|
|
|
|
// ── Super-admin ve todo ────────────────────────────────────────────────────
|
|
describe('super-admin — ve todos los elementos del sidebar', () => {
|
|
beforeEach(async () => createComponent('super-admin'));
|
|
|
|
ADMIN_ONLY_ROUTES.forEach(route => {
|
|
it(`ve el enlace a ${route}`, () => {
|
|
expect(hasRouteLink(fixture, route)).toBeTrue();
|
|
});
|
|
});
|
|
|
|
it('ve el menú de acciones (commands)', () => {
|
|
// El parent de commands es un mat-list-item sin routerLink pero con el ngIf
|
|
const items = fixture.debugElement.queryAll(By.css('mat-list-item'));
|
|
expect(items.length).toBeGreaterThan(1);
|
|
});
|
|
});
|
|
|
|
// ── Ou-admin ve todo ───────────────────────────────────────────────────────
|
|
describe('ou-admin — ve todos los elementos del sidebar', () => {
|
|
beforeEach(async () => createComponent('ou-admin'));
|
|
|
|
ADMIN_ONLY_ROUTES.forEach(route => {
|
|
it(`ve el enlace a ${route}`, () => {
|
|
expect(hasRouteLink(fixture, route)).toBeTrue();
|
|
});
|
|
});
|
|
});
|
|
|
|
// ── Ou-operator: /groups y las trazas de sus acciones ──────────────────────
|
|
describe('ou-operator — ve /groups y /commands-logs', () => {
|
|
beforeEach(async () => createComponent('ou-operator'));
|
|
|
|
it('ve /groups', () => {
|
|
expect(hasRouteLink(fixture, '/groups')).toBeTrue();
|
|
});
|
|
|
|
ADMIN_ONLY_ROUTES.forEach(route => {
|
|
it(`NO ve el enlace a ${route}`, () => {
|
|
expect(hasRouteLink(fixture, route)).toBeFalse();
|
|
});
|
|
});
|
|
|
|
it('ve el menú de acciones (commands) para acceder a las trazas', () => {
|
|
// /groups + el desplegable de acciones
|
|
expect(countVisibleListItems(fixture)).toBe(2);
|
|
});
|
|
|
|
it('ve el enlace a /commands-logs al desplegar el menú de acciones', () => {
|
|
component.toggleCommandSub();
|
|
fixture.detectChanges();
|
|
expect(hasRouteLink(fixture, '/commands-logs')).toBeTrue();
|
|
});
|
|
|
|
it('NO ve los enlaces de gestión de comandos ni tareas', () => {
|
|
component.toggleCommandSub();
|
|
fixture.detectChanges();
|
|
expect(hasRouteLink(fixture, '/commands')).toBeFalse();
|
|
expect(hasRouteLink(fixture, '/commands-task')).toBeFalse();
|
|
});
|
|
});
|
|
|
|
// ── Ou-minimal: solo /groups ───────────────────────────────────────────────
|
|
describe('ou-minimal — solo ve /groups', () => {
|
|
beforeEach(async () => createComponent('ou-minimal'));
|
|
|
|
it('ve /groups', () => {
|
|
expect(hasRouteLink(fixture, '/groups')).toBeTrue();
|
|
});
|
|
|
|
ADMIN_ONLY_ROUTES.forEach(route => {
|
|
it(`NO ve el enlace a ${route}`, () => {
|
|
expect(hasRouteLink(fixture, route)).toBeFalse();
|
|
});
|
|
});
|
|
|
|
it('NO ve el menú de acciones (commands)', () => {
|
|
expect(countVisibleListItems(fixture)).toBe(1);
|
|
});
|
|
});
|
|
|
|
// ── Comparativa admin vs operator ─────────────────────────────────────────
|
|
describe('comparativa: ou-admin ve más items que ou-operator', () => {
|
|
it('ou-admin tiene más mat-list-items visibles que ou-operator', async () => {
|
|
await createComponent('ou-admin');
|
|
const adminCount = countVisibleListItems(fixture);
|
|
|
|
TestBed.resetTestingModule();
|
|
|
|
await createComponent('ou-operator');
|
|
const operatorCount = countVisibleListItems(fixture);
|
|
|
|
expect(adminCount).toBeGreaterThan(operatorCount);
|
|
});
|
|
});
|
|
});
|