updates on the miler page and the create order calculations as well
This commit is contained in:
156
tests/integration/milerAccount.test.jsx
Normal file
156
tests/integration/milerAccount.test.jsx
Normal file
@@ -0,0 +1,156 @@
|
||||
import React from 'react';
|
||||
import { configure, render, screen, fireEvent, within } from '@testing-library/react';
|
||||
import { MemoryRouter } from 'react-router-dom';
|
||||
|
||||
configure({ asyncUtilTimeout: 5000 });
|
||||
|
||||
/**
|
||||
* Rider (miler) create and edit forms. The hooks are mocked; the server rules
|
||||
* (duplicate phone, hub in another city, block holding) are covered by
|
||||
* doormile_backend's routes_miler_account_pg_test.go.
|
||||
*/
|
||||
|
||||
beforeAll(() => {
|
||||
global.ResizeObserver = global.ResizeObserver || class { observe() {} unobserve() {} disconnect() {} };
|
||||
// Radix Select needs these in jsdom.
|
||||
window.HTMLElement.prototype.hasPointerCapture = window.HTMLElement.prototype.hasPointerCapture || (() => false);
|
||||
window.HTMLElement.prototype.releasePointerCapture = window.HTMLElement.prototype.releasePointerCapture || (() => {});
|
||||
window.HTMLElement.prototype.scrollIntoView = window.HTMLElement.prototype.scrollIntoView || (() => {});
|
||||
});
|
||||
|
||||
jest.mock('lucide-react', () =>
|
||||
new Proxy({}, { get: (_t, prop) => (prop === '__esModule' ? true : (props) => <span data-testid={`icon-${String(prop)}`} {...props} />) })
|
||||
);
|
||||
|
||||
const mockCreate = jest.fn();
|
||||
const mockUpdate = jest.fn();
|
||||
const HUBS = [
|
||||
{ hubid: 11, hubname: 'Coimbatore Neptune Hub', applocationid: 1 },
|
||||
{ hubid: 21, hubname: 'Hyderabad Mars Hub', applocationid: 2 },
|
||||
];
|
||||
const CITIES = [
|
||||
{ applocationid: 1, locationname: 'Coimbatore' },
|
||||
{ applocationid: 2, locationname: 'Hyderabad' },
|
||||
];
|
||||
let mockRider = null;
|
||||
|
||||
jest.mock('@/lib/doormileHooks', () => ({
|
||||
useTenants: () => ({ data: [{ tenantid: 5, tenantname: "Sai's Kitchen" }] }),
|
||||
useHubs: () => ({ data: HUBS }),
|
||||
useAppLocations: () => ({ data: CITIES }),
|
||||
useCreateMiler: () => ({ mutate: mockCreate, isPending: false }),
|
||||
useUpdateMiler: () => ({ mutate: mockUpdate, isPending: false }),
|
||||
useMiler: () => ({ data: mockRider, isLoading: false }),
|
||||
}));
|
||||
|
||||
import CreateRider from '@/pages/doormile/riders/CreateRider';
|
||||
import EditRider from '@/pages/doormile/riders/EditRider';
|
||||
|
||||
/** Opens a Radix select by its trigger and returns the visible option labels. */
|
||||
const openSelect = (trigger) => {
|
||||
fireEvent.keyDown(trigger, { key: 'Enter' });
|
||||
return screen.getAllByRole('option').map((o) => o.textContent);
|
||||
};
|
||||
const pick = (trigger, label) => {
|
||||
openSelect(trigger);
|
||||
fireEvent.click(screen.getByRole('option', { name: label }));
|
||||
};
|
||||
|
||||
beforeEach(() => {
|
||||
jest.clearAllMocks();
|
||||
localStorage.clear();
|
||||
mockRider = null;
|
||||
});
|
||||
|
||||
describe('Create miler', () => {
|
||||
const fill = () => {
|
||||
fireEvent.change(screen.getByPlaceholderText('9876543210'), { target: { value: '9876500001' } });
|
||||
fireEvent.change(screen.getByPlaceholderText('murali@example.com'), { target: { value: 'ravi@r.test' } });
|
||||
const inputs = screen.getAllByRole('textbox');
|
||||
// Display name and login name are the first two text inputs.
|
||||
fireEvent.change(inputs[0], { target: { value: 'Ravi K' } });
|
||||
fireEvent.change(inputs[1], { target: { value: 'ravi' } });
|
||||
};
|
||||
|
||||
it('asks for no password: the rider sets their own MPIN in the app', () => {
|
||||
render(<MemoryRouter><CreateRider /></MemoryRouter>);
|
||||
expect(screen.queryByText('Initial password')).not.toBeInTheDocument();
|
||||
expect(screen.getByText(/sets their own MPIN/)).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('offers only the hubs of the chosen city', () => {
|
||||
render(<MemoryRouter><CreateRider /></MemoryRouter>);
|
||||
// Staff form: vehicle, client, city, hub.
|
||||
const [, , city, hub] = screen.getAllByRole('combobox');
|
||||
pick(city, 'Coimbatore');
|
||||
const options = openSelect(hub);
|
||||
expect(options).toContain('Coimbatore Neptune Hub');
|
||||
expect(options).not.toContain('Hyderabad Mars Hub');
|
||||
});
|
||||
|
||||
it("creates a rider in Doormile's own pool when no client is chosen", () => {
|
||||
render(<MemoryRouter><CreateRider /></MemoryRouter>);
|
||||
fill();
|
||||
pick(screen.getAllByRole('combobox')[2], 'Coimbatore');
|
||||
fireEvent.click(screen.getByRole('button', { name: /create miler/i }));
|
||||
expect(mockCreate).toHaveBeenCalledTimes(1);
|
||||
const payload = mockCreate.mock.calls[0][0];
|
||||
expect(payload).toMatchObject({ tenantid: 0, applocationid: 1, contactno: '9876500001' });
|
||||
expect(payload).not.toHaveProperty('password');
|
||||
});
|
||||
});
|
||||
|
||||
describe('Edit miler', () => {
|
||||
const RIDER = {
|
||||
milerprofileid: 7, displayname: 'Nagalakshmi', phone: '9876500004', email: 'naga@r.test',
|
||||
tenantid: 5, applocationid: 1, hubid: 11, defaultvehicletype: 'Scooter',
|
||||
};
|
||||
const renderEdit = () =>
|
||||
render(
|
||||
<MemoryRouter initialEntries={[{ pathname: '/doormile/milers/edit', state: { rider: RIDER } }]}>
|
||||
<EditRider />
|
||||
</MemoryRouter>
|
||||
);
|
||||
|
||||
it('saves the changed phone (and not the unchanged hub) — and shows email, client and city read-only', () => {
|
||||
mockRider = RIDER;
|
||||
renderEdit();
|
||||
expect(screen.getByText('naga@r.test')).toBeInTheDocument();
|
||||
expect(screen.getByText("Sai's Kitchen")).toBeInTheDocument();
|
||||
expect(screen.getAllByText(/Can't be changed here/)).toHaveLength(3);
|
||||
|
||||
fireEvent.change(screen.getByDisplayValue('9876500004'), { target: { value: '9876500007' } });
|
||||
fireEvent.click(screen.getByRole('button', { name: /save changes/i }));
|
||||
expect(mockUpdate).toHaveBeenCalledTimes(1);
|
||||
const { id, data } = mockUpdate.mock.calls[0][0];
|
||||
expect(id).toBe(7);
|
||||
// Only what changed: re-sending the old hub could fail a legacy rider's save.
|
||||
expect(data).toEqual({ displayname: 'Nagalakshmi', contactno: '9876500007', defaultvehicletype: 'Scooter' });
|
||||
});
|
||||
|
||||
it('a rename alone does not resend the login phone', () => {
|
||||
mockRider = RIDER;
|
||||
renderEdit();
|
||||
fireEvent.change(screen.getByDisplayValue('Nagalakshmi'), { target: { value: 'Nagalakshmi R' } });
|
||||
fireEvent.click(screen.getByRole('button', { name: /save changes/i }));
|
||||
expect(mockUpdate.mock.calls[0][0].data).toEqual({ displayname: 'Nagalakshmi R', defaultvehicletype: 'Scooter' });
|
||||
});
|
||||
|
||||
it("offers only hubs in the rider's city", () => {
|
||||
mockRider = RIDER;
|
||||
renderEdit();
|
||||
const hubTrigger = screen.getAllByRole('combobox')[1];
|
||||
const options = openSelect(hubTrigger);
|
||||
expect(options).toContain('Coimbatore Neptune Hub');
|
||||
expect(options).not.toContain('Hyderabad Mars Hub');
|
||||
});
|
||||
|
||||
it('refuses a mobile number that is not 10 digits', () => {
|
||||
mockRider = RIDER;
|
||||
renderEdit();
|
||||
fireEvent.change(screen.getByDisplayValue('9876500004'), { target: { value: '98765' } });
|
||||
fireEvent.click(screen.getByRole('button', { name: /save changes/i }));
|
||||
expect(mockUpdate).not.toHaveBeenCalled();
|
||||
expect(within(document.body).getByText('Enter a 10-digit mobile number')).toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user