diff --git a/src/app/core/layout/store-layout/store-layout.component.html b/src/app/core/layout/store-layout/store-layout.component.html index 6a4aa73..1262c77 100644 --- a/src/app/core/layout/store-layout/store-layout.component.html +++ b/src/app/core/layout/store-layout/store-layout.component.html @@ -74,7 +74,7 @@ [backgroundImageUrl]="tenant()?.footer_bg_image ?? null" [storeName]="tenant()?.nombre ?? null" [address]="tenant()?.main_address?.address_text ?? null" - [phone]="tenant()?.phone ?? null" + [phone]="tenant()?.main_phone_number?.number ?? null" (logoutClick)="onLogoutClick()" /> diff --git a/src/app/core/layout/store-layout/store-layout.component.spec.ts b/src/app/core/layout/store-layout/store-layout.component.spec.ts index 6dace09..9f2daf9 100644 --- a/src/app/core/layout/store-layout/store-layout.component.spec.ts +++ b/src/app/core/layout/store-layout/store-layout.component.spec.ts @@ -37,6 +37,7 @@ const tenant: Tenant = { address: 'Calle Test 123, Rosario', main_address: { id: 1, label: 'Principal', address_text: 'Calle Test 123, Rosario', latitude: null, longitude: null }, phone: '+54 341 555 1234', + main_phone_number: { id: 1, label: 'Principal', number: '+54 341 555 1234', tel_url: 'tel:+543415551234' }, primary_color: '#6376F3', secondary_color: '#A0A0A0', danger_color: '#FF8888', @@ -579,6 +580,21 @@ describe('StoreLayoutComponent', () => { expect(footer.textContent).not.toContain(tenant.address); }); + it('uses only the main phone number in the footer', () => { + tenantState.set({ ...tenant, main_phone_number: { + id: 10, label: 'Principal', number: '3411234567', tel_url: 'tel:3411234567', + } }); + const fixture = TestBed.createComponent(StoreLayoutComponent); + fixture.detectChanges(); + const footer = fixture.nativeElement.querySelector('app-store-footer') as HTMLElement; + expect(footer.textContent).toContain('3411234567'); + expect(footer.textContent).not.toContain(tenant.phone); + tenantState.set({ ...tenant, main_phone_number: null }); + fixture.detectChanges(); + expect(footer.textContent).not.toContain('3411234567'); + expect(footer.textContent).not.toContain(tenant.phone); + }); + it('navigates to search results when the search button is clicked', () => { const router = TestBed.inject(Router); vi.spyOn(router, 'navigate'); diff --git a/src/app/core/services/phone-number.interface.ts b/src/app/core/services/phone-number.interface.ts new file mode 100644 index 0000000..f437bb2 --- /dev/null +++ b/src/app/core/services/phone-number.interface.ts @@ -0,0 +1,10 @@ +export interface PhoneNumber { + id: number; + label: string; + number: string; + tel_url: string; +} + +export interface TenantPhoneNumber extends PhoneNumber { + is_main: boolean; +} diff --git a/src/app/core/services/tenant.interface.ts b/src/app/core/services/tenant.interface.ts index 0ba6c3e..eb07024 100644 --- a/src/app/core/services/tenant.interface.ts +++ b/src/app/core/services/tenant.interface.ts @@ -1,5 +1,6 @@ import { ApiResponse } from './api-response.interface'; import { Address, TenantAddress } from './address.interface'; +import { PhoneNumber, TenantPhoneNumber } from './phone-number.interface'; export type CartEditingPolicyCode = 'disabled' | 'quantity_and_remove' | 'full'; @@ -126,6 +127,8 @@ export interface Tenant { addresses?: TenantAddress[]; main_address?: Address | null; phone?: string | null; + phone_numbers?: TenantPhoneNumber[]; + main_phone_number?: PhoneNumber | null; favicon?: string | null; primary_color: string; secondary_color: string; diff --git a/src/app/features/store/pages/help-page/pages/contact-page/contact-page.html b/src/app/features/store/pages/help-page/pages/contact-page/contact-page.html index 39f84e1..ab7afcd 100644 --- a/src/app/features/store/pages/help-page/pages/contact-page/contact-page.html +++ b/src/app/features/store/pages/help-page/pages/contact-page/contact-page.html @@ -13,10 +13,10 @@ } - @if (contact().phone; as phone) { - + @for (phone of contact().phones; track phone.id) { + - {{ phone }} + {{ phone.label }}: {{ phone.number }} } @@ -35,7 +35,7 @@ } - @if (!contact().whatsappUrl && !contact().phone && contact().locations.length === 0) { + @if (!contact().whatsappUrl && contact().phones.length === 0 && contact().locations.length === 0) {
No hay datos de contacto disponibles.
} diff --git a/src/app/features/store/pages/help-page/pages/contact-page/contact-page.spec.ts b/src/app/features/store/pages/help-page/pages/contact-page/contact-page.spec.ts index 11ee362..9eef25e 100644 --- a/src/app/features/store/pages/help-page/pages/contact-page/contact-page.spec.ts +++ b/src/app/features/store/pages/help-page/pages/contact-page/contact-page.spec.ts @@ -19,6 +19,10 @@ const tenant: Tenant = { header_logo: '', footer_logo: '', categories: [], + phone_numbers: [ + { id: 1, label: 'Principal', number: '+54 9 (0341) 6658247', tel_url: 'tel:+54903416658247', is_main: true }, + { id: 2, label: 'Ventas', number: '3411234567', tel_url: 'tel:3411234567', is_main: false }, + ], addresses: [ { id: 1, label: 'Gigante de Arroyito', address_text: 'Av. Génova 640, Rosario', latitude: -32.913997, longitude: -60.674567, is_main: true }, { id: 2, label: 'Telepagos', address_text: 'Rioja 1150, piso 12, dpto. 3, Rosario', latitude: -32.94682, longitude: -60.63932, is_main: false }, @@ -145,6 +149,17 @@ describe('ContactPage', () => { expect(map?.textContent).toContain('San Martín 2450'); }); + it('renders canonical numbers with the main first and never restores legacy numbers', () => { + const element = fixture.nativeElement as HTMLElement; + expect(element.querySelectorAll('a[href^="tel:"]')).toHaveLength(2); + expect(element.querySelector('a[href^="tel:"]')?.textContent).toContain('Principal'); + tenantState.set({ ...tenant, phone: '999999', phone_numbers: [] }); + fixture.detectChanges(); + expect(element.querySelectorAll('a[href^="tel:"]')).toHaveLength(0); + expect(element.textContent).not.toContain('999999'); + expect(element.textContent).not.toContain('+54 9 (0341) 6658247'); + }); + it('shows every canonical address and maps only addresses with coordinates', () => { tenantState.set({ ...tenant, addresses: [ { id: 10, label: 'Principal', address_text: 'Nueva sede 123', latitude: 0, longitude: 0, is_main: true }, diff --git a/src/app/features/store/pages/help-page/pages/contact-page/contact-page.ts b/src/app/features/store/pages/help-page/pages/contact-page/contact-page.ts index e388bec..3587cb5 100644 --- a/src/app/features/store/pages/help-page/pages/contact-page/contact-page.ts +++ b/src/app/features/store/pages/help-page/pages/contact-page/contact-page.ts @@ -2,6 +2,7 @@ import { Component, computed, inject } from '@angular/core'; import { findMenu } from '../../../../../../core/services/menu.utils'; import { TenantService } from '../../../../../../core/services/tenant.service'; +import { TenantPhoneNumber } from '../../../../../../core/services/phone-number.interface'; import { MenuContentSectionComponent } from '../../../../components/menu-content-section/menu-content-section.component'; import { LocationMapComponent, @@ -24,7 +25,7 @@ type ContactAddress = { type ContactContent = { whatsappUrl: string | null; whatsappLabel: string | null; - phone: string | null; + phones: TenantPhoneNumber[]; locations: ContactLocation[]; mapLocations: MapLocation[]; }; @@ -48,11 +49,6 @@ export class ContactPage { ), ); - protected phoneUrl(phone: string): string { - const normalizedPhone = phone.replace(/[^\d+]/g, ''); - return `tel:${normalizedPhone}`; - } - private parseContactContent(value: unknown): ContactContent { const content = this.isRecord(value) ? value : {}; const whatsapp = this.isRecord(content['whatsapp']) ? content['whatsapp'] : null; @@ -72,7 +68,8 @@ export class ContactPage { return { whatsappUrl: whatsapp ? this.stringValue(whatsapp['whatsapp_url']) : null, whatsappLabel: whatsapp ? this.stringValue(whatsapp['whatsapp_label']) : null, - phone: this.stringValue(content['phone']) ?? this.tenantService.tenant()?.phone ?? null, + phones: [...(this.tenantService.tenant()?.phone_numbers ?? [])] + .sort((a, b) => Number(b.is_main) - Number(a.is_main)), locations, mapLocations: locations.flatMap((location) => location.addresses.flatMap(