Files
portal/app/tests/Frontend/dealsApiMapper.spec.ts
T
2026-06-19 11:29:35 +03:00

110 lines
4.2 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { describe, expect, it } from 'vitest';
import { mapApiDeal } from '../../resources/js/composables/dealsApiMapper';
import type { ApiDeal } from '../../resources/js/api/deals';
describe('mapApiDeal', () => {
const baseApi: ApiDeal = {
id: 42,
tenant_id: 1,
project_id: 7,
project_name: 'Окна Москва',
phone: '+7 (999) 111-11-11',
contact_name: 'Анна С.',
status: 'new',
manager_id: 3,
manager_name: 'Иван П.',
manager_initials: 'ИП',
received_at: '2026-05-09T10:00:00Z',
comment: null,
city: null,
project_signal_type: null,
};
it('маппит обязательные поля 1:1', () => {
const m = mapApiDeal(baseApi, new Date('2026-05-09T10:30:00Z'));
expect(m.id).toBe(42);
expect(m.phone).toBe('+7 (999) 111-11-11');
expect(m.statusSlug).toBe('new');
expect(m.project).toBe('Окна Москва');
expect(m.manager.name).toBe('Иван П.');
expect(m.manager.initials).toBe('ИП');
});
it('name берёт contact_name; fallback на phone когда contact_name = null', () => {
const m1 = mapApiDeal(baseApi);
expect(m1.name).toBe('Анна С.');
const m2 = mapApiDeal({ ...baseApi, contact_name: null });
expect(m2.name).toBe('+7 (999) 111-11-11');
});
it('manager.name = «Не назначен» / initials = «—» если manager null', () => {
const m = mapApiDeal({ ...baseApi, manager_id: null, manager_name: null, manager_initials: null });
expect(m.manager.name).toBe('Не назначен');
expect(m.manager.initials).toBe('—');
});
it('project = «—» если project_name null', () => {
const m = mapApiDeal({ ...baseApi, project_name: null });
expect(m.project).toBe('—');
});
it("cost всегда 0 (отдельного endpoint'а пока нет)", () => {
const m = mapApiDeal(baseApi);
expect(m.cost).toBe(0);
});
it('receivedMinutesAgo вычисляется из received_at', () => {
const m = mapApiDeal(baseApi, new Date('2026-05-09T10:30:00Z'));
expect(m.receivedMinutesAgo).toBe(30);
});
it('receivedMinutesAgo не уходит в отрицательные числа при future timestamp', () => {
const m = mapApiDeal(baseApi, new Date('2026-05-09T09:00:00Z'));
expect(m.receivedMinutesAgo).toBe(0);
});
it('received_at = null → 0 минут (используем "сейчас")', () => {
const m = mapApiDeal({ ...baseApi, received_at: null }, new Date('2026-05-09T10:30:00Z'));
expect(m.receivedMinutesAgo).toBe(0);
});
it('mapApiDeal переносит city/comment/signalType/receivedAt', () => {
const iso = '2026-05-15T09:00:00+00:00';
const result = mapApiDeal({
id: 7,
tenant_id: 1,
project_id: 2,
project_name: 'Окна',
phone: '+7 999 000-00-00',
contact_name: null,
status: 'new',
manager_id: null,
manager_name: null,
manager_initials: null,
received_at: iso,
comment: 'звонил клиент',
city: 'Москва',
project_signal_type: 'call',
});
expect(result.city).toBe('Москва');
expect(result.comment).toBe('звонил клиент');
expect(result.signalType).toBe('call');
expect(result.receivedAt).toBe(iso);
});
// F2 (17.06.2026): costKopecks — снимок rub-списания из cost_kopecks API.
it('costKopecks берётся из cost_kopecks (rub-списание)', () => {
const m = mapApiDeal({ ...baseApi, cost_kopecks: 50000 });
expect(m.costKopecks).toBe(50000);
});
it('costKopecks = null если cost_kopecks null/отсутствует', () => {
const m1 = mapApiDeal({ ...baseApi, cost_kopecks: null });
expect(m1.costKopecks).toBeNull();
const m2 = mapApiDeal(baseApi);
expect(m2.costKopecks).toBeNull();
});
});