test(ticket-selector): cover compact option responses

This commit is contained in:
2026-08-14 10:15:01 -03:00
parent f7983b109f
commit 46dcb84985
2 changed files with 69 additions and 33 deletions

View File

@@ -1,6 +1,7 @@
import { TestBed, getTestBed } from '@angular/core/testing';
import { BrowserTestingModule, platformBrowserTesting } from '@angular/platform-browser/testing';
import { afterEach, beforeAll, describe, expect, it, vi } from 'vitest';
import { of } from 'rxjs';
import { ApiPaginatedResponse } from '../../../core/services/api-paginated-response.interface';
import { CartService } from '../../../core/services/cart/cart.service';
@@ -53,10 +54,26 @@ describe('ProductListComponent', () => {
productItems: CatalogFeaturedItems = paginatedItems(),
groupLayout: CatalogGroupLayout = 'paginated',
) {
const getVariantOptions = vi.fn().mockReturnValue(
of({
selectors: ['tipo', 'sector', 'fila', 'asiento'].map((key, index) => ({
key,
label: key,
options: [{ value: String(index + 1), label: String(index + 1) }],
enabled: index === 0,
})),
selected_values: {},
resolved_variant: null,
valid: true,
available_variant_count: 2,
matching_variant_count: 2,
price_range: { minimum: '10000.00', maximum: '12000.00' },
}),
);
await TestBed.configureTestingModule({
imports: [ProductListComponent],
providers: [
{ provide: CatalogService, useValue: {} },
{ provide: CatalogService, useValue: { getVariantOptions } },
{ provide: CartService, useValue: {} },
],
}).compileComponents();
@@ -307,23 +324,20 @@ describe('ProductListComponent', () => {
});
});
it('removes unavailable variants from the ticket selector', async () => {
it('loads ticket selector availability without requiring catalog variants', async () => {
const ticket: ProductListItem = {
...items[0],
variants: [
{ id: 401, stock_tecnico: 1, values: { asiento: { value: '1', label: '1' } } },
{ id: 402, stock_tecnico: 1, values: { asiento: { value: '2', label: '2' } } },
],
variants: undefined,
};
const fixture = await render('ticket_selector', [ticket], 'single');
fixture.componentRef.setInput('unavailableVariantIds', new Set([401]));
await fixture.whenStable();
fixture.detectChanges();
const selector = fixture.debugElement.query(By.directive(ProductTicketSelectorComponent))
.componentInstance as ProductTicketSelectorComponent;
expect(selector['selectableVariants']().map((variant) => variant.id)).toEqual([402]);
expect(selector['availableVariantCount']()).toBe(2);
expect(fixture.nativeElement.querySelectorAll('.variant-selector__select')).toHaveLength(4);
});
it('renders carousel groups with the reusable carousel', async () => {

View File

@@ -20,33 +20,59 @@ describe('ProductTicketSelectorComponent', () => {
afterEach(() => TestBed.resetTestingModule());
it('checks partial selections and reserves the resolved variant in the cart', async () => {
const variants = [
{
id: 401,
precio: '10000.00',
stock_tecnico: 1,
values: { sector: { value: 'a', label: 'Sector A' }, seat: '1' },
},
];
const resolvedVariant = {
id: 401,
precio: '10000.00',
stock_tecnico: 1,
values: { sector: { value: 'a', label: 'Sector A' }, seat: '1' },
};
const summary = {
valid: true,
available_variant_count: 1,
matching_variant_count: 1,
price_range: { minimum: '10000.00', maximum: '10000.00' },
};
const catalogService = {
getVariantOptions: vi
.fn()
.mockReturnValueOnce(
of({
variants,
options: { seat: ['1'] },
selected_values: { sector: 'a' },
resolved_variant_id: null,
valid: true,
...summary,
selectors: [
{
key: 'sector',
label: 'Sector',
options: [{ value: 'a', label: 'Sector A' }],
enabled: true,
},
{ key: 'seat', label: 'Seat', options: ['1'], enabled: false },
],
selected_values: {},
resolved_variant: null,
}),
)
.mockReturnValueOnce(
of({
variants,
options: { seat: ['1'] },
...summary,
selectors: [
{
key: 'sector',
label: 'Sector',
options: [{ value: 'a', label: 'Sector A' }],
enabled: true,
},
{ key: 'seat', label: 'Seat', options: ['1'], enabled: true },
],
selected_values: { sector: 'a' },
resolved_variant: null,
}),
)
.mockReturnValueOnce(
of({
...summary,
selectors: [],
selected_values: { sector: 'a', seat: '1' },
resolved_variant_id: 401,
valid: true,
resolved_variant: resolvedVariant,
}),
),
};
@@ -82,12 +108,11 @@ describe('ProductTicketSelectorComponent', () => {
const fixture = TestBed.createComponent(ProductTicketSelectorComponent);
fixture.componentRef.setInput('productId', 7);
fixture.componentRef.setInput('title', 'Entrada');
fixture.componentRef.setInput('variants', variants);
fixture.detectChanges();
fixture.componentInstance['onSelectionChange'](1, {
values: { sector: { value: 'a', label: 'Sector A' } },
selectedVariant: null,
fixture.componentInstance['onSelectionChange'](1, 'sector', {
value: 'a',
label: 'Sector A',
});
expect(catalogService.getVariantOptions).toHaveBeenLastCalledWith(7, {
@@ -96,10 +121,7 @@ describe('ProductTicketSelectorComponent', () => {
});
expect(fixture.componentInstance['rows']()[0].status).toBe('selecting');
fixture.componentInstance['onSelectionChange'](1, {
values: { sector: { value: 'a', label: 'Sector A' }, seat: '1' },
selectedVariant: 401,
});
fixture.componentInstance['onSelectionChange'](1, 'seat', '1');
expect(cartService.addItem).toHaveBeenCalledWith(7, 401, 1);
expect(fixture.componentInstance['rows']()[0]).toMatchObject({