Files
edr-platform/apps/edr-freight-api/src/modules/exports/export.registry.ts
Nathnael 8c941fdf4b feat(exports): add the remaining eight datasets
customers, contracts, invoices, payments, train-schedules, locomotives,
trains and wagons. 319 fields across the nine datasets, all reusing the
existing engine — no change to export.types.ts was needed, which is the
result the bookings-first phase was meant to test.

Per-dataset notes worth keeping:

- trains resolves route, stations and current yard, which the list endpoint
  never loads — the UI shows raw FK uuids there today.
- wagons reads tare/payload/length off wagon_types (they are not on the
  wagon), and reproduces the service's attachStatusDates() as correlated
  subqueries. wagon_status_logs stores from_status/to_status, not status.
- payments applies no soft-delete guard: freight.payments has neither
  deleted_at nor updated_at, so the usual predicate is a 42703. Failure
  columns are failer_code/failer_message. payment_refunds stores MINOR
  units, so refundedTotal divides by 100.
- train-schedules derives freightType from the bookings aboard rather than
  a column, matching the list service.
- customers stays one row per company; profiles, bookings and invoice
  totals aggregate in subqueries. Verified no row multiplication: trains,
  customers and contracts each return exactly their counted row count while
  selecting one-to-many aggregate fields.

EXPLAIN-validated against the database: every dataset's widest query, its
count query, and all 319 fields individually. That run caught five columns
typed varchar rather than timestamp (companies.date_registered,
renewal_date, renewed_from, renewed_to and invoices.eims_ack_date), which
were being pushed through to_char and would have 500'd the moment anyone
ticked them; they now export verbatim.

All nine count endpoints verified equal to SELECT count(*) on their table.
2026-08-20 07:10:36 +00:00

34 lines
1.3 KiB
TypeScript

import { bookingsDataset } from './datasets/bookings.dataset';
import { contractsDataset } from './datasets/contracts.dataset';
import { customersDataset } from './datasets/customers.dataset';
import { invoicesDataset } from './datasets/invoices.dataset';
import { locomotivesDataset } from './datasets/locomotives.dataset';
import { paymentsDataset } from './datasets/payments.dataset';
import { trainSchedulesDataset } from './datasets/train-schedules.dataset';
import { trainsDataset } from './datasets/trains.dataset';
import { wagonsDataset } from './datasets/wagons.dataset';
import { ExportDataset } from './export.types';
/**
* Every exportable dataset.
*
* Adding one = a new file under `datasets/` + an entry here. No frontend edit,
* no route, no permission seed — the dialog is driven entirely by the catalog
* this registry serves, and a dataset reuses its module's existing `view` key.
*/
export const DATASETS: ExportDataset[] = [
bookingsDataset,
contractsDataset,
customersDataset,
invoicesDataset,
paymentsDataset,
trainSchedulesDataset,
locomotivesDataset,
trainsDataset,
wagonsDataset,
];
const BY_KEY = new Map(DATASETS.map((d) => [d.key, d]));
export const getDataset = (key: string): ExportDataset | undefined => BY_KEY.get(key);