import { QUERY_KEYS } from "@/constants/QUERY_KEYS";
import type { FleetResourceSlug } from "@/pages/fleet/config/resources";
import type { BookingDetail } from "@/types/booking";
import type {
  Company,
  CompanyListFilter,
  CompanyProfile,
  CompanyStats,
  CustomerBooking,
  CustomerDocument,
  CustomerPayment,
  PaginatedCompanies,
  ProfileStatus,
} from "@/types/customer";
import {
  CreateDropdownOptionDto,
  CreateDropdownSettingDto,
  DropdownOption,
  DropdownSetting,
  UpdateDropdownOptionDto,
  UpdateDropdownSettingDto,
} from "@/types/dropdownSettings";
import type {
  CreateFileUploadFieldDto,
  CreateFileUploadSettingDto,
  FileUploadField,
  FileUploadSetting,
  UpdateFileUploadFieldDto,
  UpdateFileUploadSettingDto,
} from "@/types/fileUploadSettings";
import type { IOverviewDashboard, OverviewRange } from "@/types/overview";
import {
  RuleEngineListResult,
  RuleEngineRecord,
  RuleEngineResourceSlug,
} from "@/types/rule-engine";
import type {
  AssignBookingsPayload,
  BatchBoardSchedule,
  BatchBoardScheduleDetail,
  BookableSchedule,
  CompositionRemovalEntry,
  CreateTrainSchedulePayload,
  EligibleContainerBookingsResponse,
  FreightType,
  LocomotiveRecord,
  PinWagonsPayload,
  RecordCheckpointPayload,
  TrainScheduleDetail,
  TrainScheduleFilters,
  TrainScheduleListItem,
  TrainSchedulePreviewPayload,
  TrainSchedulePreviewResponse,
  TrainTrackResponse,
  UnassignedBookingsResponse,
  WagonAllocationAttemptResult,
  YardOption,
} from "@/types/trainScheduling";
import type {
  AllocationCriteria,
  AllocationPreviewResult,
  AllocationRule,
  ArrivalQueueItem,
  AutoLoadResult,
  AutoUnloadArrivedResult,
  AutoUnloadResult,
  BookingScheduleView,
  BulkDispatchResult,
  BulkInspectPayload,
  BulkInspectResult,
  BulkReceivePayload,
  BulkReceiveResult,
  DeliverInventoryPayload,
  EligibleBooking,
  FeePreview,
  FeeRule,
  ImportTrain,
  ImportTrainItem,
  ImportUnloadedItem,
  InspectionAttachment,
  InspectionReport,
  InspectionReportPayload,
  InventoryFilter,
  InventoryInquiryFilter,
  InventoryInquiryResult,
  InventoryMovement,
  LoadableWagon,
  LoadInventoryPayload,
  LoadPassedExportResult,
  MoveInventoryPayload,
  PayInvoicePayload,
  ReadyToLoadRow,
  ReceiveInventoryPayload,
  ReleaseOrderPayload,
  ReserveInventoryPayload,
  SaveAllocationRulePayload,
  SaveFeeRulePayload,
  SaveWarehousePayload,
  SaveYardPayload,
  SaveZonePayload,
  Warehouse,
  WarehouseActivityLog,
  WarehouseDashboard,
  WarehouseFeeInvoice,
  WarehouseFilter,
  WarehouseInventoryItem,
  WarehouseInvoiceFilter,
  WarehouseLoading,
  WarehouseYard,
  WarehouseZone,
} from "@/types/warehouse";
import { endpoint } from "@/utils/endpoint";
import {
  BookingListFilter,
  bookingsService,
  type ApproveStepPayload,
  type PaginatedBookings,
  type RejectStepPayload,
} from "./bookings.service";
import { cargoTypesService } from "./cargo-types.service";
import {
  cargoService,
  type Cargo,
  type DeliverCargoPayload,
} from "./cargoService";
import { containerTypesService } from "./container-types.service";
import { containerService, type Container } from "./containerService";
import { customersService } from "./customers.service";
import { dropdownSettingsService } from "./dropdownSettings.service";
import { fileUploadSettingsService } from "./fileUploadSettings.service";
import {
  fleetService,
  type FleetListFilters,
  type FleetRecord,
} from "./fleet/fleet.service";
import {
  locomotivesService,
  type Locomotive,
  type SaveLocomotivePayload,
} from "./locomotives.service";
import { overviewService } from "./overview.service";
import {
  paymentsService,
  type PaginatedPayments,
  type PaymentListFilter,
  type PaymentSummary,
} from "./payments.service";
import {
  routesService,
  type RouteRecord,
  type SaveRoutePayload,
  type YardRef,
} from "./routes.service";
import {
  RuleEngineListParams,
  ruleEngineService,
} from "./ruleEngine/ruleEngine.service";
import {
  signaturesService,
  type SavedSignature,
  type SaveSignaturePayload,
} from "./signatures.service";
import { trainService, type Train } from "./trains.service";
import { trainSchedulingService } from "./trainScheduling.service";
import { wagonTypesService, type WagonType } from "./wagon-types.service";
import {
  wagonService,
  type Wagon,
  type WagonListFilters,
} from "./wagon.service";
import { warehouseService } from "./warehouse.service";

/** Query keys for inventory-lifecycle mutations that ripple across views. */
const INVENTORY_INVALIDATIONS: ReadonlyArray<readonly unknown[]> = [
  ["warehouse-inventory"],
  ["warehouse-loadings"],
  ["warehouses"],
  // Singular `"warehouse"` root covers loadableWagons / bookingSchedule, which
  // change when inventory is loaded/dispatched. Distinct from the `warehouse-*`
  // roots above (prefix matching is element-exact, not string-prefix).
  ["warehouse"],
];

/**
 * Train-scheduling mutations broadly affect the schedule board and bookings.
 * The grouped hooks invalidated TRAIN_SCHEDULING.ROOT + BOOKINGS.ROOT; since
 * every train-scheduling key is prefixed with `"train-scheduling"`, the two
 * roots below cover all of them via React Query's prefix matching.
 */
const TRAIN_SCHEDULING_INVALIDATIONS: ReadonlyArray<readonly unknown[]> = [
  QUERY_KEYS.TRAIN_SCHEDULING.ROOT,
  QUERY_KEYS.BOOKINGS.ROOT,
];

export const api = {
  trainScheduling: {
    // ── Queries ────────────────────────────────────────────────────────────
    scheduleList: endpoint<{ freightType?: FreightType }, TrainScheduleListItem[]>(
      "train-scheduling",
      "schedules",
      ({ freightType }) => trainSchedulingService.listSchedules(freightType),
      () => QUERY_KEYS.TRAIN_SCHEDULING.schedules(),
    ),

    batchBoard: endpoint<void, BatchBoardSchedule[]>(
      "train-scheduling",
      "batch-board",
      () => trainSchedulingService.getBatchBoard(),
      () => QUERY_KEYS.TRAIN_SCHEDULING.batchBoard(),
    ),

    batchBoardDetail: endpoint<{ scheduleId: string }, BatchBoardScheduleDetail>(
      "train-scheduling",
      "batch-board-detail",
      ({ scheduleId }) => trainSchedulingService.getBatchBoardDetail(scheduleId),
      ({ scheduleId }) => QUERY_KEYS.TRAIN_SCHEDULING.batchBoardDetail(scheduleId),
    ),

    scheduleDetail: endpoint<
      { id: string; freightType?: FreightType },
      TrainScheduleDetail
    >(
      "train-scheduling",
      "schedule-detail",
      ({ id, freightType }) =>
        trainSchedulingService.getScheduleById(id, freightType),
      ({ id }) => QUERY_KEYS.TRAIN_SCHEDULING.scheduleById(id),
    ),

    eligibleBookings: endpoint<
      { filters?: TrainScheduleFilters; freightType?: FreightType },
      EligibleContainerBookingsResponse
    >(
      "train-scheduling",
      "eligible-bookings",
      ({ filters, freightType }) =>
        trainSchedulingService.getEligibleBookings(filters, freightType),
      ({ filters, freightType }) =>
        QUERY_KEYS.TRAIN_SCHEDULING.eligible(freightType, filters),
    ),

    availableLocomotives: endpoint<{ routeId?: string }, LocomotiveRecord[]>(
      "train-scheduling",
      "locomotives",
      ({ routeId }) => trainSchedulingService.getAvailableLocomotives(routeId),
      ({ routeId }) => QUERY_KEYS.TRAIN_SCHEDULING.locomotives(routeId),
    ),

    bookableSchedules: endpoint<
      { originYardId?: string | null; destinationYardId?: string | null },
      BookableSchedule[]
    >(
      "train-scheduling",
      "bookable",
      ({ originYardId, destinationYardId }) =>
        trainSchedulingService.getBookableSchedules(
          originYardId ?? undefined,
          destinationYardId ?? undefined,
        ),
      ({ originYardId, destinationYardId }) => [
        ...QUERY_KEYS.TRAIN_SCHEDULING.ROOT,
        "bookable",
        originYardId ?? "",
        destinationYardId ?? "",
      ],
    ),

    availableDays: endpoint<
      { originYardId?: string | null; destinationYardId?: string | null },
      string[]
    >(
      "train-scheduling",
      "available-days",
      ({ originYardId, destinationYardId }) =>
        trainSchedulingService.getAvailableDays(
          originYardId ?? undefined,
          destinationYardId ?? undefined,
        ),
      ({ originYardId, destinationYardId }) => [
        ...QUERY_KEYS.TRAIN_SCHEDULING.ROOT,
        "available-days",
        originYardId ?? "",
        destinationYardId ?? "",
      ],
    ),

    trainTrack: endpoint<{ id: string }, TrainTrackResponse>(
      "train-scheduling",
      "track",
      ({ id }) => trainSchedulingService.getTrack(id),
      ({ id }) => QUERY_KEYS.TRAIN_SCHEDULING.track(id),
    ),

    unassignedBookings: endpoint<
      { scheduleId: string },
      UnassignedBookingsResponse
    >(
      "train-scheduling",
      "unassigned-bookings",
      ({ scheduleId }) =>
        trainSchedulingService.getUnassignedBookings(scheduleId),
      ({ scheduleId }) =>
        QUERY_KEYS.TRAIN_SCHEDULING.unassignedBookings(scheduleId),
    ),

    compositionRemovals: endpoint<
      { scheduleId: string },
      CompositionRemovalEntry[]
    >(
      "train-scheduling",
      "composition-removals",
      ({ scheduleId }) =>
        trainSchedulingService.getCompositionRemovals(scheduleId),
      ({ scheduleId }) =>
        QUERY_KEYS.TRAIN_SCHEDULING.compositionRemovals(scheduleId),
    ),

    // ── Mutations ──────────────────────────────────────────────────────────
    runAllocation: endpoint<{ scheduleId: string }, WagonAllocationAttemptResult>(
      "train-scheduling",
      "run-allocation",
      ({ scheduleId }) => trainSchedulingService.runAllocation(scheduleId),
      undefined,
      () => [QUERY_KEYS.TRAIN_SCHEDULING.ROOT],
    ),

    runBatch: endpoint<string, BatchBoardScheduleDetail>(
      "train-scheduling",
      "run-batch",
      (id) => trainSchedulingService.runBatch(id),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    setBookingWindow: endpoint<
      { id: string; status: "OPEN" | "CLOSED" },
      TrainScheduleDetail
    >(
      "train-scheduling",
      "set-booking-window",
      ({ id, status }) => trainSchedulingService.setBookingWindow(id, status),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    markBookingPaid: endpoint<string, void>(
      "train-scheduling",
      "mark-booking-paid",
      (bookingId) => trainSchedulingService.markBookingPaid(bookingId),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    expireBooking: endpoint<string, void>(
      "train-scheduling",
      "expire-booking",
      (bookingId) => trainSchedulingService.expireBooking(bookingId),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    moveBookingSchedule: endpoint<
      { bookingId: string; trainScheduleId: string },
      void
    >(
      "train-scheduling",
      "move-booking-schedule",
      ({ bookingId, trainScheduleId }) =>
        trainSchedulingService.moveBookingSchedule(bookingId, trainScheduleId),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    createSchedule: endpoint<
      { freightType?: FreightType; payload: CreateTrainSchedulePayload },
      TrainScheduleDetail
    >(
      "train-scheduling",
      "create-schedule",
      ({ freightType, payload }) =>
        trainSchedulingService.createSchedule(payload, freightType),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    preview: endpoint<
      { freightType?: FreightType; payload: TrainSchedulePreviewPayload },
      TrainSchedulePreviewResponse
    >("train-scheduling", "preview", ({ freightType, payload }) =>
      trainSchedulingService.preview(payload, freightType),
    ),

    assignBookings: endpoint<
      { id: string; freightType?: FreightType; payload: AssignBookingsPayload },
      TrainScheduleDetail
    >(
      "train-scheduling",
      "assign-bookings",
      ({ id, freightType, payload }) =>
        trainSchedulingService.assignBookings(id, payload, freightType),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    assignUnassignedBooking: endpoint<
      { id: string; bookingId: string },
      TrainScheduleDetail
    >(
      "train-scheduling",
      "assign-unassigned-booking",
      ({ id, bookingId }) =>
        trainSchedulingService.assignUnassignedBooking(id, bookingId),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    unassignBooking: endpoint<
      { id: string; bookingId: string },
      TrainScheduleDetail
    >(
      "train-scheduling",
      "unassign-booking",
      ({ id, bookingId }) =>
        trainSchedulingService.unassignBooking(id, bookingId),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    pinWagons: endpoint<{ id: string; payload: PinWagonsPayload }, TrainScheduleDetail>(
      "train-scheduling",
      "pin-wagons",
      ({ id, payload }) => trainSchedulingService.pinWagons(id, payload),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    finalizeSchedule: endpoint<string, TrainScheduleDetail>(
      "train-scheduling",
      "finalize-schedule",
      (id) => trainSchedulingService.finalizeSchedule(id),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    dispatchSchedule: endpoint<string, TrainScheduleDetail>(
      "train-scheduling",
      "dispatch-schedule",
      (id) => trainSchedulingService.dispatchSchedule(id),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    cancelSchedule: endpoint<
      { id: string; freightType?: FreightType },
      TrainScheduleDetail
    >(
      "train-scheduling",
      "cancel-schedule",
      ({ id, freightType }) =>
        trainSchedulingService.cancelSchedule(id, freightType ?? "CONTAINER"),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    recordCheckpoint: endpoint<
      { id: string; payload: RecordCheckpointPayload },
      TrainTrackResponse
    >(
      "train-scheduling",
      "record-checkpoint",
      ({ id, payload }) => trainSchedulingService.recordCheckpoint(id, payload),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    arriveSchedule: endpoint<string, TrainScheduleDetail>(
      "train-scheduling",
      "arrive-schedule",
      (id) => trainSchedulingService.arriveSchedule(id),
      undefined,
      () => TRAIN_SCHEDULING_INVALIDATIONS,
    ),

    removeWagonSlot: endpoint<
      { scheduleId: string; wagonId: string },
      TrainScheduleDetail
    >(
      "train-scheduling",
      "remove-wagon-slot",
      ({ scheduleId, wagonId }) =>
        trainSchedulingService.removeWagonSlot(scheduleId, wagonId),
      undefined,
      () => [QUERY_KEYS.TRAIN_SCHEDULING.ROOT],
    ),

    updateContainerItem: endpoint<
      { scheduleId: string; itemId: string; containerNumber: string | null },
      { id: string; containerNumber: string | null }
    >(
      "train-scheduling",
      "update-container-item",
      ({ scheduleId, itemId, containerNumber }) =>
        trainSchedulingService.updateContainerItem(scheduleId, itemId, {
          containerNumber,
        }),
      undefined,
      () => [QUERY_KEYS.TRAIN_SCHEDULING.ROOT],
    ),
  },

  warehouses: {
    // ── Warehouses ─────────────────────────────────────────────────────────
    list: endpoint<{ filter?: WarehouseFilter }, Warehouse[]>(
      "warehouses",
      "list",
      ({ filter }) => warehouseService.list(filter).then((r) => r.data),
    ),

    getById: endpoint<{ id: string }, Warehouse>(
      "warehouses",
      "getById",
      ({ id }) => warehouseService.getById(id).then((r) => r.data),
    ),

    dashboard: endpoint<void, WarehouseDashboard>("warehouses", "dashboard", () =>
      warehouseService.dashboard().then((r) => r.data),
    ),

    create: endpoint<SaveWarehousePayload, Warehouse>(
      "warehouses",
      "create",
      (payload) => warehouseService.create(payload).then((r) => r.data),
      undefined,
      () => [["warehouses"]],
    ),

    update: endpoint<
      { id: string; payload: Partial<SaveWarehousePayload> },
      Warehouse
    >(
      "warehouses",
      "update",
      ({ id, payload }) =>
        warehouseService.update(id, payload).then((r) => r.data),
      undefined,
      () => [["warehouses"]],
    ),

    // ── Yards ──────────────────────────────────────────────────────────────
    listYards: endpoint<{ warehouseId: string }, WarehouseYard[]>(
      "warehouses",
      "listYards",
      ({ warehouseId }) =>
        warehouseService.listYards(warehouseId).then((r) => r.data),
    ),

    createYard: endpoint<
      { warehouseId: string; payload: SaveYardPayload },
      WarehouseYard
    >(
      "warehouses",
      "createYard",
      ({ warehouseId, payload }) =>
        warehouseService.createYard(warehouseId, payload).then((r) => r.data),
      undefined,
      () => [["warehouses"]],
    ),

    updateYard: endpoint<
      { id: string; payload: Partial<SaveYardPayload> },
      WarehouseYard
    >(
      "warehouses",
      "updateYard",
      ({ id, payload }) =>
        warehouseService.updateYard(id, payload).then((r) => r.data),
      undefined,
      () => [["warehouses"], ["warehouse-yards"]],
    ),

    // ── Zones ──────────────────────────────────────────────────────────────
    listZones: endpoint<{ yardId: string }, WarehouseZone[]>(
      "warehouses",
      "listZones",
      ({ yardId }) => warehouseService.listZones(yardId).then((r) => r.data),
      ({ yardId }) => ["warehouse-yards", yardId, "zones"],
    ),

    createZone: endpoint<
      { yardId: string; payload: SaveZonePayload },
      WarehouseZone
    >(
      "warehouses",
      "createZone",
      ({ yardId, payload }) =>
        warehouseService.createZone(yardId, payload).then((r) => r.data),
      undefined,
      ({ yardId }) => [["warehouse-yards", yardId, "zones"]],
    ),

    updateZone: endpoint<
      { id: string; payload: Partial<SaveZonePayload> },
      WarehouseZone
    >(
      "warehouses",
      "updateZone",
      ({ id, payload }) =>
        warehouseService.updateZone(id, payload).then((r) => r.data),
      undefined,
      () => [["warehouse-yards"]],
    ),

    // ── Inventory (queries) ────────────────────────────────────────────────
    listInventory: endpoint<
      { filter?: InventoryFilter },
      WarehouseInventoryItem[]
    >(
      "warehouse-inventory",
      "list",
      ({ filter }) => warehouseService.listInventory(filter).then((r) => r.data),
    ),

    inquiry: endpoint<
      { filter: InventoryInquiryFilter },
      InventoryInquiryResult[]
    >(
      "warehouse-inventory",
      "inquiry",
      ({ filter }) => warehouseService.inquiry(filter).then((r) => r.data),
      ({ filter }) => ["warehouse-inventory", "inquiry", filter],
    ),

    eligibleBookings: endpoint<void, EligibleBooking[]>(
      "warehouse-inventory",
      "eligible-bookings",
      () => warehouseService.eligibleBookings().then((r) => r.data),
      () => ["warehouse-inventory", "eligible-bookings"],
    ),

    readyToLoadExport: endpoint<void, ReadyToLoadRow[]>(
      "warehouse-inventory",
      "ready-to-load-export",
      () => warehouseService.readyToLoadExport().then((r) => r.data),
      () => ["warehouse-inventory", "ready-to-load-export"],
    ),

    loadedExport: endpoint<void, ReadyToLoadRow[]>(
      "warehouse-inventory",
      "loaded-export",
      () => warehouseService.loadedExport().then((r) => r.data),
      () => ["warehouse-inventory", "loaded-export"],
    ),

    importArriveQueue: endpoint<void, ImportTrain[]>(
      "warehouse-inventory",
      "import-arrive-queue",
      () => warehouseService.importArriveQueue().then((r) => r.data),
      () => ["warehouse-inventory", "import-arrive-queue"],
    ),

    importTrainItems: endpoint<{ scheduleId: string }, ImportTrainItem[]>(
      "warehouse-inventory",
      "import-train-items",
      ({ scheduleId }) =>
        warehouseService.importTrainItems(scheduleId).then((r) => r.data),
      ({ scheduleId }) => ["warehouse-inventory", "import-train-items", scheduleId],
    ),

    importUnloadedQueue: endpoint<void, ImportUnloadedItem[]>(
      "warehouse-inventory",
      "import-unloaded-queue",
      () => warehouseService.importUnloadedQueue().then((r) => r.data),
      () => ["warehouse-inventory", "import-unloaded-queue"],
    ),

    importPickupReadyQueue: endpoint<void, ImportUnloadedItem[]>(
      "warehouse-inventory",
      "import-pickup-ready-queue",
      () => warehouseService.importPickupReadyQueue().then((r) => r.data),
      () => ["warehouse-inventory", "import-pickup-ready-queue"],
    ),

    loadableWagons: endpoint<void, LoadableWagon[]>(
      "warehouse",
      "loadable-wagons",
      () => warehouseService.loadableWagons().then((r) => r.data),
      () => ["warehouse", "loadable-wagons"],
    ),

    loadings: endpoint<
      { params?: { bookingId?: string; wagonId?: string } },
      WarehouseLoading[]
    >(
      "warehouse-loadings",
      "list",
      ({ params }) => warehouseService.loadings(params).then((r) => r.data),
      ({ params }) => ["warehouse-loadings", params ?? {}],
    ),

    bookingSchedule: endpoint<{ bookingId: string }, BookingScheduleView>(
      "warehouse",
      "booking-schedule",
      ({ bookingId }) =>
        warehouseService.bookingSchedule(bookingId).then((r) => r.data),
      ({ bookingId }) => ["warehouse", "booking-schedule", bookingId],
    ),

    movements: endpoint<{ id: string }, InventoryMovement[]>(
      "warehouse-inventory",
      "movements",
      ({ id }) => warehouseService.movements(id).then((r) => r.data),
      ({ id }) => ["warehouse-inventory", id, "movements"],
    ),

    activity: endpoint<{ id: string }, WarehouseActivityLog[]>(
      "warehouse-inventory",
      "activity",
      ({ id }) => warehouseService.activity(id).then((r) => r.data),
      ({ id }) => ["warehouse-inventory", id, "activity"],
    ),

    arrivalQueue: endpoint<void, ArrivalQueueItem[]>(
      "warehouse-inventory",
      "arrival-queue",
      () => warehouseService.arrivalQueue().then((r) => r.data),
      () => ["warehouse-inventory", "arrival-queue"],
    ),

    inspectionReports: endpoint<{ inventoryId: string }, InspectionReport[]>(
      "warehouse-inventory",
      "inspection-reports",
      ({ inventoryId }) =>
        warehouseService.listInspectionReports(inventoryId).then((r) => r.data),
      ({ inventoryId }) =>
        ["warehouse-inventory", inventoryId, "inspection-reports"],
    ),

    allocationRules: endpoint<void, AllocationRule[]>(
      "warehouse-allocation-rules",
      "list",
      () => warehouseService.listAllocationRules().then((r) => r.data),
      () => ["warehouse-allocation-rules"],
    ),

    feeRules: endpoint<void, FeeRule[]>(
      "warehouse-fee-rules",
      "list",
      () => warehouseService.listFeeRules().then((r) => r.data),
      () => ["warehouse-fee-rules"],
    ),

    feePreview: endpoint<{ inventoryId: string }, FeePreview[]>(
      "warehouse-inventory",
      "fee-preview",
      ({ inventoryId }) =>
        warehouseService.feePreview(inventoryId).then((r) => r.data),
      ({ inventoryId }) => ["warehouse-inventory", inventoryId, "fee-preview"],
    ),

    invoices: endpoint<{ filter?: WarehouseInvoiceFilter }, WarehouseFeeInvoice[]>(
      "warehouse-fee-invoices",
      "list",
      ({ filter }) => warehouseService.listInvoices(filter).then((r) => r.data),
      ({ filter }) => ["warehouse-fee-invoices", filter ?? {}],
    ),

    invoice: endpoint<{ id: string }, WarehouseFeeInvoice>(
      "warehouse-fee-invoices",
      "detail",
      ({ id }) => warehouseService.getInvoice(id).then((r) => r.data),
      ({ id }) => ["warehouse-fee-invoices", "detail", id],
    ),

    invoicesForInventory: endpoint<
      { inventoryId: string },
      WarehouseFeeInvoice[]
    >(
      "warehouse-inventory",
      "fee-invoices",
      ({ inventoryId }) =>
        warehouseService.invoicesForInventory(inventoryId).then((r) => r.data),
      ({ inventoryId }) => ["warehouse-inventory", inventoryId, "fee-invoices"],
    ),

    // ── Inventory (mutations) ──────────────────────────────────────────────
    receiveInventory: endpoint<ReceiveInventoryPayload, WarehouseInventoryItem>(
      "warehouse-inventory",
      "receive",
      (payload) => warehouseService.receiveInventory(payload).then((r) => r.data),
      undefined,
      () => [["warehouse-inventory"], ["warehouses"]],
    ),

    store: endpoint<string, WarehouseInventoryItem>(
      "warehouse-inventory",
      "store",
      (id) => warehouseService.store(id).then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    reserve: endpoint<ReserveInventoryPayload, WarehouseInventoryItem>(
      "warehouse-inventory",
      "reserve",
      (payload) => warehouseService.reserve(payload).then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    markReadyForLoading: endpoint<string, WarehouseInventoryItem>(
      "warehouse-inventory",
      "mark-ready-for-loading",
      (id) => warehouseService.markReadyForLoading(id).then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    load: endpoint<
      { id: string; payload: LoadInventoryPayload },
      WarehouseInventoryItem
    >(
      "warehouse-inventory",
      "load",
      ({ id, payload }) => warehouseService.load(id, payload).then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    dispatch: endpoint<string, WarehouseInventoryItem>(
      "warehouse-inventory",
      "dispatch",
      (id) => warehouseService.dispatch(id).then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    move: endpoint<
      { id: string; payload: MoveInventoryPayload },
      WarehouseInventoryItem
    >(
      "warehouse-inventory",
      "move",
      ({ id, payload }) => warehouseService.move(id, payload).then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    markReadyForPickup: endpoint<string, WarehouseInventoryItem>(
      "warehouse-inventory",
      "mark-ready-for-pickup",
      (id) => warehouseService.markReadyForPickup(id).then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    release: endpoint<
      { id: string; payload: ReleaseOrderPayload },
      WarehouseInventoryItem
    >(
      "warehouse-inventory",
      "release",
      ({ id, payload }) =>
        warehouseService.release(id, payload).then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    deliver: endpoint<
      { id: string; payload: DeliverInventoryPayload },
      WarehouseInventoryItem
    >(
      "warehouse-inventory",
      "deliver",
      ({ id, payload }) =>
        warehouseService.deliver(id, payload).then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    bulkReceive: endpoint<BulkReceivePayload, BulkReceiveResult>(
      "warehouse-inventory",
      "bulk-receive",
      (payload) => warehouseService.receiveBulk(payload).then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    loadPassedExport: endpoint<void, LoadPassedExportResult>(
      "warehouse-inventory",
      "load-passed-export",
      () => warehouseService.loadPassedExport().then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    bulkMarkInspected: endpoint<BulkInspectPayload, BulkInspectResult>(
      "warehouse-inventory",
      "bulk-mark-inspected",
      (payload) => warehouseService.bulkMarkInspected(payload).then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    bulkDispatchExport: endpoint<string[], BulkDispatchResult>(
      "warehouse-inventory",
      "bulk-dispatch-export",
      (inventoryIds) =>
        warehouseService.bulkDispatchExport(inventoryIds).then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    autoUnloadArrivedBookings: endpoint<string, AutoUnloadArrivedResult>(
      "warehouse-inventory",
      "auto-unload-arrived-bookings",
      (scheduleId) =>
        warehouseService
          .autoUnloadArrivedBookings(scheduleId)
          .then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    autoUnloadArrived: endpoint<void, AutoUnloadResult>(
      "warehouse-inventory",
      "auto-unload-arrived",
      () => warehouseService.autoUnloadArrived().then((r) => r.data),
      undefined,
      () => [["warehouse-inventory"], ["warehouses"]],
    ),

    autoLoadReady: endpoint<void, AutoLoadResult>(
      "warehouse-inventory",
      "auto-load-ready",
      () => warehouseService.autoLoadReady().then((r) => r.data),
      undefined,
      () => INVENTORY_INVALIDATIONS,
    ),

    unloadBooking: endpoint<
      { bookingId: string; payload?: Record<string, unknown> },
      WarehouseInventoryItem
    >(
      "warehouse-inventory",
      "unload-booking",
      ({ bookingId, payload }) =>
        warehouseService.unloadBooking(bookingId, payload).then((r) => r.data),
      undefined,
      () => [["warehouse-inventory"], ["warehouses"]],
    ),

    createInspectionReport: endpoint<
      { inventoryId: string; payload: InspectionReportPayload },
      InspectionReport
    >(
      "warehouse-inventory",
      "create-inspection-report",
      ({ inventoryId, payload }) =>
        warehouseService
          .createInspectionReport(inventoryId, payload)
          .then((r) => r.data),
      undefined,
      ({ inventoryId }) => [
        ["warehouse-inventory", inventoryId, "inspection-reports"],
        ["warehouse-inventory"],
      ],
    ),

    uploadInspectionAttachments: endpoint<
      { reportId: string; files: File[] },
      InspectionAttachment[]
    >(
      "warehouse-inventory",
      "upload-inspection-attachments",
      ({ reportId, files }) =>
        warehouseService
          .uploadInspectionAttachments(reportId, files)
          .then((r) => r.data),
    ),

    // ── Allocation + fee rules ─────────────────────────────────────────────
    previewAllocation: endpoint<AllocationCriteria, AllocationPreviewResult | null>(
      "warehouse-allocation-rules",
      "preview",
      (criteria) =>
        warehouseService.previewAllocation(criteria).then((r) => r.data),
    ),

    createAllocationRule: endpoint<SaveAllocationRulePayload, AllocationRule>(
      "warehouse-allocation-rules",
      "create",
      (payload) =>
        warehouseService.createAllocationRule(payload).then((r) => r.data),
      undefined,
      () => [["warehouse-allocation-rules"]],
    ),

    updateAllocationRule: endpoint<
      { id: string; payload: Partial<SaveAllocationRulePayload> },
      AllocationRule
    >(
      "warehouse-allocation-rules",
      "update",
      ({ id, payload }) =>
        warehouseService.updateAllocationRule(id, payload).then((r) => r.data),
      undefined,
      () => [["warehouse-allocation-rules"]],
    ),

    deleteAllocationRule: endpoint<string, void>(
      "warehouse-allocation-rules",
      "delete",
      (id) => warehouseService.deleteAllocationRule(id).then(() => undefined),
      undefined,
      () => [["warehouse-allocation-rules"]],
    ),

    createFeeRule: endpoint<SaveFeeRulePayload, FeeRule>(
      "warehouse-fee-rules",
      "create",
      (payload) => warehouseService.createFeeRule(payload).then((r) => r.data),
      undefined,
      () => [["warehouse-fee-rules"]],
    ),

    updateFeeRule: endpoint<
      { id: string; payload: Partial<SaveFeeRulePayload> },
      FeeRule
    >(
      "warehouse-fee-rules",
      "update",
      ({ id, payload }) =>
        warehouseService.updateFeeRule(id, payload).then((r) => r.data),
      undefined,
      () => [["warehouse-fee-rules"]],
    ),

    deleteFeeRule: endpoint<string, void>(
      "warehouse-fee-rules",
      "delete",
      (id) => warehouseService.deleteFeeRule(id).then(() => undefined),
      undefined,
      () => [["warehouse-fee-rules"]],
    ),

    // ── Invoices ───────────────────────────────────────────────────────────
    generateInvoice: endpoint<
      { inventoryId: string; confirmZero?: boolean },
      WarehouseFeeInvoice
    >(
      "warehouse-fee-invoices",
      "generate",
      ({ inventoryId, confirmZero }) =>
        warehouseService
          .generateInvoice(inventoryId, confirmZero)
          .then((r) => r.data),
      undefined,
      () => [["warehouse-fee-invoices"], ["warehouse-inventory"]],
    ),

    cancelInvoice: endpoint<string, WarehouseFeeInvoice>(
      "warehouse-fee-invoices",
      "cancel",
      (id) => warehouseService.cancelInvoice(id).then((r) => r.data),
      undefined,
      () => [["warehouse-fee-invoices"], ["warehouse-inventory"]],
    ),

    payInvoice: endpoint<
      { id: string; payload: PayInvoicePayload },
      WarehouseFeeInvoice
    >(
      "warehouse-fee-invoices",
      "pay",
      ({ id, payload }) =>
        warehouseService.payInvoice(id, payload).then((r) => r.data),
      undefined,
      () => [["warehouse-fee-invoices"], ["warehouse-inventory"]],
    ),

    gateClearance: endpoint<string, WarehouseInventoryItem>(
      "warehouse-fee-invoices",
      "gate-clearance",
      (inventoryId) =>
        warehouseService.gateClearance(inventoryId).then((r) => r.data),
      undefined,
      () => [["warehouse-fee-invoices"], ["warehouse-inventory"]],
    ),
  },

  routes: {
    list: endpoint<void, RouteRecord[]>("routes", "list", () =>
      routesService.getAll().then((r) => r.data),
    ),

    yards: endpoint<void, YardRef[]>(
      "routes",
      "yards",
      () => routesService.getYards().then((r) => r.data.data),
      () => ["routes", "yards"],
    ),

    create: endpoint<SaveRoutePayload, RouteRecord>(
      "routes",
      "create",
      (payload) => routesService.create(payload).then((r) => r.data),
      undefined,
      () => [["routes"]],
    ),

    update: endpoint<{ id: string; data: Partial<SaveRoutePayload> }, RouteRecord>(
      "routes",
      "update",
      ({ id, data }) => routesService.update(id, data).then((r) => r.data),
      undefined,
      () => [["routes"]],
    ),

    deactivate: endpoint<string, void>(
      "routes",
      "deactivate",
      (id) => routesService.deactivate(id).then(() => undefined),
      undefined,
      () => [["routes"]],
    ),
  },

  stations: {
    list: endpoint<void, YardOption[]>(
      "train-scheduling",
      "stations",
      () => trainSchedulingService.getStations(),
      () => QUERY_KEYS.TRAIN_SCHEDULING.stations(),
    ),
  },

  containers: {
    list: endpoint<void, Container[]>("containers", "list", () =>
      containerService.getAll().then((r) => r.data),
    ),

    listByWagon: endpoint<{ wagonId: string }, Container[]>(
      "containers",
      "listByWagon",
      ({ wagonId }) => containerService.getByWagon(wagonId).then((r) => r.data),
      ({ wagonId }) => ["containers", "wagon", wagonId],
    ),

    getById: endpoint<{ id: string }, Container>(
      "containers",
      "getById",
      ({ id }) => containerService.getById(id).then((r) => r.data),
    ),

    create: endpoint<Partial<Container>, Container>(
      "containers",
      "create",
      (payload) => containerService.create(payload).then((r) => r.data),
      undefined,
      () => [["containers"]],
    ),

    update: endpoint<{ id: string; data: Partial<Container> }, Container>(
      "containers",
      "update",
      ({ id, data }) => containerService.update(id, data).then((r) => r.data),
      undefined,
      () => [["containers"]],
    ),

    remove: endpoint<string, void>(
      "containers",
      "remove",
      (id) => containerService.delete(id).then(() => undefined),
      undefined,
      () => [["containers"]],
    ),

    assignToWagon: endpoint<
      { containerId: string; wagonId: string; position?: number },
      Container
    >(
      "containers",
      "assignToWagon",
      ({ containerId, wagonId, position }) =>
        containerService
          .assignToWagon(containerId, wagonId, position)
          .then((r) => r.data),
      undefined,
      () => [["containers"]],
    ),

    unassign: endpoint<string, void>(
      "containers",
      "unassign",
      (containerId) =>
        containerService.unassign(containerId).then(() => undefined),
      undefined,
      () => [["containers"]],
    ),
  },

  containerTypes: {
    list: endpoint<void, unknown[]>("container-types", "list", () =>
      containerTypesService.getContainerTypes(),
    ),
  },

  wagons: {
    list: endpoint<{ filters?: WagonListFilters }, Wagon[]>(
      "wagons",
      "list",
      ({ filters }) => wagonService.getAll(filters ?? {}).then((r) => r.data),
      ({ filters }) => ["wagons", "list", filters ?? {}],
    ),

    listByTrain: endpoint<{ trainId: string }, Wagon[]>(
      "wagons",
      "listByTrain",
      ({ trainId }) => wagonService.getByTrain(trainId).then((r) => r.data),
      ({ trainId }) => ["wagons", "train", trainId],
    ),

    getById: endpoint<{ id: string }, Wagon>(
      "wagons",
      "getById",
      ({ id }) => wagonService.getById(id).then((r) => r.data),
    ),

    assignToTrain: endpoint<
      { wagonId: string; trainId: string; sequenceNumber?: number },
      Wagon
    >(
      "wagons",
      "assignToTrain",
      ({ wagonId, trainId, sequenceNumber }) =>
        wagonService
          .assignToTrain(wagonId, trainId, sequenceNumber)
          .then((r) => r.data),
      undefined,
      () => [["wagons"]],
    ),

    unassign: endpoint<string, void>(
      "wagons",
      "unassign",
      (wagonId) => wagonService.unassign(wagonId).then(() => undefined),
      undefined,
      () => [["wagons"]],
    ),

    reorder: endpoint<{ trainId: string; wagonIds: string[] }, Wagon[]>(
      "wagons",
      "reorder",
      ({ trainId, wagonIds }) =>
        wagonService.reorder(trainId, wagonIds).then((r) => r.data),
      undefined,
      () => [["wagons"]],
    ),

    create: endpoint<Partial<Wagon>, Wagon>(
      "wagons",
      "create",
      (payload) => wagonService.create(payload).then((r) => r.data),
      undefined,
      () => [["wagons"]],
    ),

    update: endpoint<{ id: string; data: Partial<Wagon> }, Wagon>(
      "wagons",
      "update",
      ({ id, data }) => wagonService.update(id, data).then((r) => r.data),
      undefined,
      () => [["wagons"]],
    ),

    remove: endpoint<string, void>(
      "wagons",
      "remove",
      (id) => wagonService.delete(id).then(() => undefined),
      undefined,
      () => [["wagons"]],
    ),
  },

  trains: {
    list: endpoint<void, Train[]>(
      "trains",
      "list",
      () => trainService.getAll().then((r) => r.data),
      () => ["trains", "list"],
    ),

    getById: endpoint<{ id: string }, Train>(
      "trains",
      "getById",
      ({ id }) => trainService.getById(id).then((r) => r.data),
      ({ id }) => ["trains", "detail", id],
    ),

    create: endpoint<Partial<Train>, Train>(
      "trains",
      "create",
      (payload) => trainService.create(payload).then((r) => r.data),
      undefined,
      () => [["trains"]],
    ),

    update: endpoint<{ id: string; data: Partial<Train> }, Train>(
      "trains",
      "update",
      ({ id, data }) => trainService.update(id, data).then((r) => r.data),
      undefined,
      () => [["trains"]],
    ),

    remove: endpoint<string, void>(
      "trains",
      "remove",
      (id) => trainService.delete(id).then(() => undefined),
      undefined,
      () => [["trains"]],
    ),
  },

  locomotives: {
    list: endpoint<void, Locomotive[]>(
      "locomotives",
      "list",
      () => locomotivesService.getAll().then((r) => r.data),
      () => ["locomotives"],
    ),

    create: endpoint<Partial<SaveLocomotivePayload>, Locomotive>(
      "locomotives",
      "create",
      (payload) => locomotivesService.create(payload).then((r) => r.data),
      undefined,
      () => [["locomotives"]],
    ),

    update: endpoint<
      { id: string; data: Partial<SaveLocomotivePayload> },
      Locomotive
    >(
      "locomotives",
      "update",
      ({ id, data }) => locomotivesService.update(id, data).then((r) => r.data),
      undefined,
      () => [["locomotives"]],
    ),

    decommission: endpoint<string, void>(
      "locomotives",
      "decommission",
      (id) => locomotivesService.decommission(id).then(() => undefined),
      undefined,
      () => [["locomotives"]],
    ),
  },

  cargoTypes: {
    list: endpoint<void, unknown[]>("cargo-types", "list", () =>
      cargoTypesService.getCargoTypes(),
    ),
  },

  payments: {
    list: endpoint<{ filter?: PaymentListFilter }, PaginatedPayments>(
      "payments",
      "list",
      ({ filter }) => paymentsService.list(filter),
      ({ filter }) => ["payments", "list", filter ?? {}],
    ),

    summary: endpoint<void, PaymentSummary>(
      "payments",
      "summary",
      () => paymentsService.getSummary(),
      () => ["payments", "summary"],
    ),
  },

  signatures: {
    mySignature: endpoint<void, SavedSignature | null>(
      "me",
      "signature",
      () => signaturesService.getMySignature(),
      () => ["me", "signature"],
    ),

    save: endpoint<SaveSignaturePayload, SavedSignature | null>(
      "me",
      "save-signature",
      (payload) => signaturesService.saveMySignature(payload),
      undefined,
      () => [["me", "signature"]],
    ),
  },

  fleet: {
    list: endpoint<
      { slug: FleetResourceSlug; filters?: FleetListFilters },
      FleetRecord[]
    >(
      "fleet",
      "list",
      ({ slug, filters }) => fleetService.list(slug, filters),
      ({ slug, filters }) => [...QUERY_KEYS.FLEET.list(slug), filters ?? {}],
    ),

    create: endpoint<
      { slug: FleetResourceSlug; data: Record<string, unknown> },
      unknown
    >(
      "fleet",
      "create",
      ({ slug, data }) => fleetService.create(slug, data),
      undefined,
      ({ slug }) => [QUERY_KEYS.FLEET.list(slug)],
    ),

    update: endpoint<
      { slug: FleetResourceSlug; id: string; data: Record<string, unknown> },
      unknown
    >(
      "fleet",
      "update",
      ({ slug, id, data }) => fleetService.update(slug, id, data),
      undefined,
      ({ slug }) => [QUERY_KEYS.FLEET.list(slug)],
    ),

    remove: endpoint<{ slug: FleetResourceSlug; id: string }, unknown>(
      "fleet",
      "remove",
      ({ slug, id }) => fleetService.remove(slug, id),
      undefined,
      ({ slug }) => [QUERY_KEYS.FLEET.list(slug)],
    ),
  },

  wagonTypes: {
    list: endpoint<void, WagonType[]>("wagon-types", "list", () =>
      wagonTypesService.getWagonTypes(),
    ),

    create: endpoint<Partial<WagonType>, WagonType>(
      "wagon-types",
      "create",
      (payload) => wagonTypesService.create(payload).then((r) => r.data),
      undefined,
      () => [["wagon-types"]],
    ),

    update: endpoint<{ id: string; data: Partial<WagonType> }, WagonType>(
      "wagon-types",
      "update",
      ({ id, data }) => wagonTypesService.update(id, data).then((r) => r.data),
      undefined,
      () => [["wagon-types"]],
    ),

    remove: endpoint<string, void>(
      "wagon-types",
      "remove",
      (id) => wagonTypesService.delete(id).then(() => undefined),
      undefined,
      () => [["wagon-types"]],
    ),
  },

  cargoes: {
    list: endpoint<void, Cargo[]>("cargoes", "list", () =>
      cargoService.getAll().then((r) => r.data),
    ),

    listByContainer: endpoint<{ containerId: string }, Cargo[]>(
      "cargoes",
      "listByContainer",
      ({ containerId }) =>
        cargoService.getByContainer(containerId).then((r) => r.data),
    ),

    getById: endpoint<{ id: string }, Cargo>("cargoes", "getById", ({ id }) =>
      cargoService.getById(id).then((r) => r.data),
    ),

    create: endpoint<Partial<Cargo>, Cargo>(
      "cargoes",
      "create",
      (payload) => cargoService.create(payload).then((r) => r.data),
      undefined,
      () => [["cargoes"]],
    ),

    update: endpoint<{ id: string; data: Partial<Cargo> }, Cargo>(
      "cargoes",
      "update",
      ({ id, data }) => cargoService.update(id, data).then((r) => r.data),
      undefined,
      () => [["cargoes"]],
    ),

    remove: endpoint<string, void>(
      "cargoes",
      "remove",
      (id) => cargoService.delete(id).then(() => undefined),
      undefined,
      () => [["cargoes"]],
    ),

    load: endpoint<
      { id: string; quantity: number; weight: number; volume?: number },
      Cargo
    >(
      "cargoes",
      "load",
      ({ id, quantity, weight, volume }) =>
        cargoService.load(id, quantity, weight, volume).then((r) => r.data),
      undefined,
      () => [["cargoes"]],
    ),

    deliver: endpoint<{ id: string; payload?: DeliverCargoPayload }, Cargo>(
      "cargoes",
      "deliver",
      ({ id, payload }) =>
        cargoService.deliver(id, payload).then((r) => r.data),
      undefined,
      () => [["cargoes"]],
    ),

    unload: endpoint<{ id: string }, Cargo>(
      "cargoes",
      "unload",
      ({ id }) => cargoService.unload(id).then((r) => r.data),
      undefined,
      () => [["cargoes"]],
    ),
  },

  fileUploadSettings: {
    list: endpoint<void, FileUploadSetting[]>(
      "file-upload-settings",
      "list",
      fileUploadSettingsService.list,
    ),

    getById: endpoint<{ id: string }, FileUploadSetting>(
      "file-upload-settings",
      "getById",
      ({ id }) => fileUploadSettingsService.getById(id),
    ),

    getByCode: endpoint<{ code: string }, FileUploadSetting>(
      "file-upload-settings",
      "getByCode",
      ({ code }) => fileUploadSettingsService.getByCode(code),
    ),

    create: endpoint<CreateFileUploadSettingDto, FileUploadSetting>(
      "file-upload-settings",
      "create",
      (payload) => fileUploadSettingsService.create(payload),
      undefined,
      () => [["file-upload-settings"]],
    ),

    update: endpoint<
      { id: string; dto: UpdateFileUploadSettingDto },
      FileUploadSetting
    >(
      "file-upload-settings",
      "update",
      ({ id, dto }) => fileUploadSettingsService.update(id, dto),
      undefined,
      () => [["file-upload-settings"]],
    ),

    remove: endpoint<{ id: string }, void>(
      "file-upload-settings",
      "remove",
      ({ id }) => fileUploadSettingsService.remove(id),
      undefined,
      () => [["file-upload-settings"]],
    ),

    replaceFields: endpoint<
      { id: string; fields: CreateFileUploadFieldDto[] },
      FileUploadField[]
    >(
      "file-upload-settings",
      "replaceFields",
      ({ id, fields }) => fileUploadSettingsService.replaceFields(id, fields),
      undefined,
      () => [["file-upload-settings"]],
    ),

    addField: endpoint<
      { settingId: string; dto: CreateFileUploadFieldDto },
      FileUploadField
    >(
      "file-upload-settings",
      "addField",
      ({ settingId, dto }) => fileUploadSettingsService.addField(settingId, dto),
      undefined,
      () => [["file-upload-settings"]],
    ),

    updateField: endpoint<
      { fieldId: string; dto: UpdateFileUploadFieldDto },
      FileUploadField
    >(
      "file-upload-settings",
      "updateField",
      ({ fieldId, dto }) => fileUploadSettingsService.updateField(fieldId, dto),
      undefined,
      () => [["file-upload-settings"]],
    ),

    removeField: endpoint<{ fieldId: string }, void>(
      "file-upload-settings",
      "removeField",
      ({ fieldId }) => fileUploadSettingsService.removeField(fieldId),
      undefined,
      () => [["file-upload-settings"]],
    ),
  },

  dropdownSettings: {
    list: endpoint<void, DropdownSetting[]>(
      "dropdown-settings",
      "list",
      dropdownSettingsService.list,
    ),

    getById: endpoint<{ id: string }, DropdownSetting>(
      "dropdown-settings",
      "getById",
      ({ id }) => dropdownSettingsService.getById(id),
    ),

    getByCode: endpoint<{ code: string }, DropdownSetting>(
      "dropdown-settings",
      "getByCode",
      ({ code }) => dropdownSettingsService.getByCode(code),
    ),

    create: endpoint<CreateDropdownSettingDto, DropdownSetting>(
      "dropdown-settings",
      "create",
      (payload) => dropdownSettingsService.create(payload),
      undefined,
      () => [["dropdown-settings"]],
    ),

    update: endpoint<
      { id: string; dto: UpdateDropdownSettingDto },
      DropdownSetting
    >(
      "dropdown-settings",
      "update",
      ({ id, dto }) => dropdownSettingsService.update(id, dto),
      undefined,
      () => [["dropdown-settings"]],
    ),

    remove: endpoint<{ id: string }, void>(
      "dropdown-settings",
      "remove",
      ({ id }) => dropdownSettingsService.remove(id),
      undefined,
      () => [["dropdown-settings"]],
    ),

    replaceOptions: endpoint<
      { id: string; options: CreateDropdownOptionDto[] },
      DropdownOption[]
    >(
      "dropdown-settings",
      "replaceOptions",
      ({ id, options }) => dropdownSettingsService.replaceOptions(id, options),
      undefined,
      () => [["dropdown-settings"]],
    ),

    addOption: endpoint<
      { id: string; dto: CreateDropdownOptionDto },
      DropdownOption
    >(
      "dropdown-settings",
      "addOption",
      ({ id, dto }) => dropdownSettingsService.addOption(id, dto),
      undefined,
      () => [["dropdown-settings"]],
    ),

    updateOption: endpoint<
      { optionId: string; dto: UpdateDropdownOptionDto },
      DropdownOption
    >(
      "dropdown-settings",
      "updateOption",
      ({ optionId, dto }) => dropdownSettingsService.updateOption(optionId, dto),
      undefined,
      () => [["dropdown-settings"]],
    ),

    removeOption: endpoint<{ optionId: string }, void>(
      "dropdown-settings",
      "removeOption",
      ({ optionId }) => dropdownSettingsService.removeOption(optionId),
      undefined,
      () => [["dropdown-settings"]],
    ),
  },

  ruleEngine: {
    list: endpoint<
      { resource: RuleEngineResourceSlug; params?: RuleEngineListParams },
      RuleEngineListResult<RuleEngineRecord>
    >(
      "rule-engine",
      "list",
      ({ resource, params }) => ruleEngineService.list(resource, params),
      ({ resource, params }) => QUERY_KEYS.RULE_ENGINE.list(resource, params),
    ),

    getById: endpoint<
      { resource: RuleEngineResourceSlug; id: string },
      RuleEngineRecord
    >(
      "rule-engine",
      "getById",
      ({ resource, id }) => ruleEngineService.getById(resource, id),
      ({ resource, id }) => QUERY_KEYS.RULE_ENGINE.detail(resource, id),
    ),

    create: endpoint<
      { resource: RuleEngineResourceSlug; payload: Record<string, unknown> },
      RuleEngineRecord
    >("rule-engine", "create", ({ resource, payload }) =>
      ruleEngineService.create(resource, payload),
    ),

    update: endpoint<
      {
        resource: RuleEngineResourceSlug;
        id: string;
        payload: Record<string, unknown>;
      },
      RuleEngineRecord
    >("rule-engine", "update", ({ resource, id, payload }) =>
      ruleEngineService.update(resource, id, payload),
    ),

    remove: endpoint<
      { resource: RuleEngineResourceSlug; id: string },
      void
    >("rule-engine", "remove", ({ resource, id }) =>
      ruleEngineService.remove(resource, id),
    ),

    submitRate: endpoint<{ id: string }, RuleEngineRecord>(
      "rule-engine",
      "submitRate",
      ({ id }) => ruleEngineService.submitRate(id),
    ),

    approveRate: endpoint<{ id: string }, RuleEngineRecord>(
      "rule-engine",
      "approveRate",
      ({ id }) => ruleEngineService.approveRate(id),
    ),

    getApprovalChain: endpoint<void, RuleEngineRecord[]>(
      "rule-engine",
      "getApprovalChain",
      () => ruleEngineService.getApprovalChain(),
      () => QUERY_KEYS.RULE_ENGINE.chain,
    ),

    reorder: endpoint<
      { resource: RuleEngineResourceSlug; payload: { ids: string[]; requiresDirectorApproval?: boolean } },
      void
    >("rule-engine", "reorder", ({ resource, payload }) =>
      ruleEngineService.reorder(resource, payload),
    ),

    moveOrder: endpoint<
      { resource: RuleEngineResourceSlug; id: string; direction: "up" | "down" },
      void
    >("rule-engine", "moveOrder", ({ resource, id, direction }) =>
      ruleEngineService.moveOrder(resource, id, direction),
    ),
  },

  bookings: {
    list: endpoint<{ filter?: BookingListFilter }, PaginatedBookings>(
      "bookings",
      "list",
      ({ filter }) => bookingsService.list(filter),
      ({ filter }) => QUERY_KEYS.BOOKINGS.list(filter),
    ),

    getById: endpoint<{ id: string }, BookingDetail>(
      "bookings",
      "getById",
      ({ id }) => bookingsService.getById(id),
      ({ id }) => QUERY_KEYS.BOOKINGS.byId(id),
    ),

    remove: endpoint<{ id: string }, void>(
      "bookings",
      "remove",
      ({ id }) => bookingsService.remove(id),
    ),

    staffAccept: endpoint<{ id: string; validityDays: number }, BookingDetail>(
      "bookings",
      "staffAccept",
      ({ id, validityDays }) => bookingsService.staffAccept(id, validityDays),
    ),

    requestChanges: endpoint<{ id: string; note: string }, BookingDetail>(
      "bookings",
      "requestChanges",
      ({ id, note }) => bookingsService.requestChanges(id, note),
    ),

    staffReject: endpoint<{ id: string; reason: string }, BookingDetail>(
      "bookings",
      "staffReject",
      ({ id, reason }) => bookingsService.staffReject(id, reason),
    ),

    reviewOperation: endpoint<
      {
        id: string;
        decision: "ACCEPT" | "REQUEST_CHANGES" | "ADJUST_PRICE";
        note?: string;
        amount?: number;
      },
      BookingDetail
    >("bookings", "reviewOperation", ({ id, decision, note, amount }) =>
      bookingsService.reviewOperation(id, decision, { note, amount }),
    ),

    approveStep: endpoint<ApproveStepPayload, BookingDetail>(
      "bookings",
      "approveStep",
      (payload) => bookingsService.approveStep(payload),
    ),

    rejectStep: endpoint<RejectStepPayload, BookingDetail>(
      "bookings",
      "rejectStep",
      (payload) => bookingsService.rejectStep(payload),
    ),

    generateContract: endpoint<{ id: string }, BookingDetail>(
      "bookings",
      "generateContract",
      ({ id }) => bookingsService.generateContract(id),
    ),

    getContractView: endpoint<{ id: string }, import("./bookings.service").ContractView>(
      "bookings",
      "getContractView",
      ({ id }) => bookingsService.getContractView(id),
    ),

    signContract: endpoint<
      { id: string } & import("./bookings.service").SignContractPayload,
      BookingDetail
    >("bookings", "signContract", ({ id, ...payload }) =>
      bookingsService.signContract(id, payload),
    ),

    payBooking: endpoint<{ id: string }, BookingDetail>(
      "bookings",
      "payBooking",
      ({ id }) => bookingsService.payBooking(id),
    ),

    startTransit: endpoint<{ id: string }, BookingDetail>(
      "bookings",
      "startTransit",
      ({ id }) => bookingsService.startTransit(id),
    ),

    complete: endpoint<{ id: string }, BookingDetail>(
      "bookings",
      "complete",
      ({ id }) => bookingsService.complete(id),
    ),

    cancel: endpoint<{ id: string; reason: string }, BookingDetail>(
      "bookings",
      "cancel",
      ({ id, reason }) => bookingsService.cancel(id, reason),
    ),
  },

  customers: {
    stats: endpoint<Record<string, never>, CompanyStats>(
      "customers",
      "stats",
      () => customersService.stats(),
      () => QUERY_KEYS.CUSTOMERS.stats,
    ),

    list: endpoint<{ filter: CompanyListFilter }, PaginatedCompanies>(
      "customers",
      "list",
      ({ filter }) => customersService.list(filter),
      ({ filter }) => QUERY_KEYS.CUSTOMERS.list(filter),
    ),

    getById: endpoint<{ id: string }, Company | undefined>(
      "customers",
      "getById",
      ({ id }) => customersService.getById(id),
      ({ id }) => QUERY_KEYS.CUSTOMERS.byId(id),
    ),

    bookings: endpoint<{ id: string }, CustomerBooking[]>(
      "customers",
      "bookings",
      ({ id }) => customersService.bookingsFor(id),
      ({ id }) => QUERY_KEYS.CUSTOMERS.bookings(id),
    ),

    documents: endpoint<{ id: string }, CustomerDocument[]>(
      "customers",
      "documents",
      ({ id }) => customersService.documentsFor(id),
      ({ id }) => QUERY_KEYS.CUSTOMERS.documents(id),
    ),

    payments: endpoint<{ id: string }, CustomerPayment[]>(
      "customers",
      "payments",
      ({ id }) => customersService.paymentsFor(id),
      ({ id }) => QUERY_KEYS.CUSTOMERS.payments(id),
    ),

    setProfileStatus: endpoint<
      { profileId: string; status: ProfileStatus },
      CompanyProfile
    >(
      "customers",
      "setProfileStatus",
      ({ profileId, status }) => customersService.setProfileStatus(profileId, status),
      undefined,
      (_input, data) => [
        QUERY_KEYS.CUSTOMERS.byId(data.companyId),
        QUERY_KEYS.CUSTOMERS.ROOT,
      ],
    ),

    setCompanyStatus: endpoint<{ companyId: string; status: string }, unknown>(
      "customers",
      "setCompanyStatus",
      ({ companyId, status }) =>
        customersService.setCompanyStatus(companyId, status),
      undefined,
      (input) => [
        QUERY_KEYS.CUSTOMERS.byId(input.companyId),
        QUERY_KEYS.CUSTOMERS.ROOT,
      ],
    ),
  },

  overview: {
    get: endpoint<{ range?: OverviewRange }, IOverviewDashboard>(
      "overview",
      "get",
      ({ range }) => overviewService.getDashboard(range),
    ),
  },
};