@burdenoff/microfe-movethewheels 2026.510.105
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +82 -0
- package/dist/AIAssistantPage-hD0VYJdH.js +210 -0
- package/dist/AnalyticsPage-DHTHCUtr.js +201 -0
- package/dist/CreateOrderPage-Cprg4Y9V.js +471 -0
- package/dist/CustomerDetailsPage-DNDEw7IW.js +239 -0
- package/dist/CustomersPage-CDjjeCEL.js +119 -0
- package/dist/DashboardPage-8iTPXRAG.js +374 -0
- package/dist/DataTable-CRIKfdIN.js +239 -0
- package/dist/DriverDetailsPage-CRyRCno7.js +297 -0
- package/dist/DriversPage-16O8fVmf.js +127 -0
- package/dist/FinancePage-BYUxK5dR.js +154 -0
- package/dist/FleetPage-CHYETCWT.js +293 -0
- package/dist/ImportExportPage-C3MKKxfc.js +232 -0
- package/dist/InventoryPage--822AxZM.js +223 -0
- package/dist/LiveTrackingPage-Dp3rTJDr.js +332 -0
- package/dist/MarketplacePage-DjEqudfM.js +192 -0
- package/dist/MetricCard-GTbxAk1a.js +135 -0
- package/dist/OrderDetailsPage-BIuYG0ub.js +398 -0
- package/dist/OrdersListPage-CW5V0Uvh.js +257 -0
- package/dist/PageLayout-B7b0vl0R.js +1894 -0
- package/dist/ProductDetailsPage-Q3X7AT-7.js +168 -0
- package/dist/ProductsPage-CUj9JpnW.js +131 -0
- package/dist/ReportsPage-DblO5CdJ.js +227 -0
- package/dist/RouteDetailsPage-CLctgk6A.js +240 -0
- package/dist/RoutesPage-8hrv6RWT.js +116 -0
- package/dist/SettingsPage-BJ5BQeqn.js +247 -0
- package/dist/StatusBadge-BrrwraIA.js +206 -0
- package/dist/TrackingPage-BGqHDh-w.js +322 -0
- package/dist/VehicleDetailsPage-XnDH4iQR.js +194 -0
- package/dist/VehiclesPage-Cs4XxHkA.js +127 -0
- package/dist/WarehouseDetailsPage-GemdMvr_.js +215 -0
- package/dist/WarehousesPage-QTiuDuXy.js +121 -0
- package/dist/arrow-left-6CiLhqVp.js +11 -0
- package/dist/box-BunB_4UH.js +18 -0
- package/dist/chart-column-DWwVEVQ-.js +22 -0
- package/dist/chevron-right-DhZVf20o.js +8 -0
- package/dist/circle-alert-D5f6RZxt.js +26 -0
- package/dist/circle-check-big-D-JMHcTe.js +11 -0
- package/dist/clock-CvwBKbQP.js +13 -0
- package/dist/dev/main.d.ts +1 -0
- package/dist/dollar-sign-CP9qeU5d.js +14 -0
- package/dist/download-CIuG04pJ.js +21 -0
- package/dist/file-text-Dd_thxkn.js +26 -0
- package/dist/filter-DyRMX9CU.js +8 -0
- package/dist/formatters-_vJlC-47.js +50 -0
- package/dist/generated/global-operations.d.ts +1 -0
- package/dist/generated/global-types.d.ts +20715 -0
- package/dist/generated/wspace-operations.d.ts +3704 -0
- package/dist/generated/wspace-types.d.ts +53362 -0
- package/dist/graphqlClient-CdJyR_ed.js +55 -0
- package/dist/index.d.ts +4 -0
- package/dist/index.js +772 -0
- package/dist/map-BqH1cBJi.js +18 -0
- package/dist/map-pin-CFBOmh-A.js +13 -0
- package/dist/movethewheels/MoveTheWheelsRoot.d.ts +25 -0
- package/dist/movethewheels/MoveTheWheelsRoutes.d.ts +7 -0
- package/dist/movethewheels/components/DataTable.d.ts +32 -0
- package/dist/movethewheels/components/MetricCard.d.ts +43 -0
- package/dist/movethewheels/components/PageLayout.d.ts +68 -0
- package/dist/movethewheels/components/StatusBadge.d.ts +49 -0
- package/dist/movethewheels/components/index.d.ts +10 -0
- package/dist/movethewheels/components/ui.d.ts +22 -0
- package/dist/movethewheels/constants/index.d.ts +24 -0
- package/dist/movethewheels/constants/mockData.d.ts +33 -0
- package/dist/movethewheels/hooks/index.d.ts +12 -0
- package/dist/movethewheels/hooks/useAnalytics.d.ts +118 -0
- package/dist/movethewheels/hooks/useCustomers.d.ts +37 -0
- package/dist/movethewheels/hooks/useFleet.d.ts +71 -0
- package/dist/movethewheels/hooks/useInventory.d.ts +60 -0
- package/dist/movethewheels/hooks/useOrders.d.ts +47 -0
- package/dist/movethewheels/hooks/useRoutes.d.ts +41 -0
- package/dist/movethewheels/hooks/useTracking.d.ts +69 -0
- package/dist/movethewheels/index.d.ts +30 -0
- package/dist/movethewheels/pages/AIAssistantPage.d.ts +4 -0
- package/dist/movethewheels/pages/AnalyticsPage.d.ts +4 -0
- package/dist/movethewheels/pages/CreateOrderPage.d.ts +6 -0
- package/dist/movethewheels/pages/CustomerDetailsPage.d.ts +4 -0
- package/dist/movethewheels/pages/CustomersPage.d.ts +4 -0
- package/dist/movethewheels/pages/DashboardPage.d.ts +6 -0
- package/dist/movethewheels/pages/DriverDetailsPage.d.ts +4 -0
- package/dist/movethewheels/pages/DriversPage.d.ts +4 -0
- package/dist/movethewheels/pages/FinancePage.d.ts +4 -0
- package/dist/movethewheels/pages/FleetPage.d.ts +6 -0
- package/dist/movethewheels/pages/ImportExportPage.d.ts +4 -0
- package/dist/movethewheels/pages/InventoryPage.d.ts +4 -0
- package/dist/movethewheels/pages/LiveTrackingPage.d.ts +6 -0
- package/dist/movethewheels/pages/MarketplacePage.d.ts +4 -0
- package/dist/movethewheels/pages/OrderDetailsPage.d.ts +6 -0
- package/dist/movethewheels/pages/OrdersListPage.d.ts +6 -0
- package/dist/movethewheels/pages/ProductDetailsPage.d.ts +4 -0
- package/dist/movethewheels/pages/ProductsPage.d.ts +4 -0
- package/dist/movethewheels/pages/ReportsPage.d.ts +4 -0
- package/dist/movethewheels/pages/RouteDetailsPage.d.ts +4 -0
- package/dist/movethewheels/pages/RoutesPage.d.ts +4 -0
- package/dist/movethewheels/pages/SettingsPage.d.ts +4 -0
- package/dist/movethewheels/pages/TrackingPage.d.ts +6 -0
- package/dist/movethewheels/pages/VehicleDetailsPage.d.ts +4 -0
- package/dist/movethewheels/pages/VehiclesPage.d.ts +4 -0
- package/dist/movethewheels/pages/WarehouseDetailsPage.d.ts +4 -0
- package/dist/movethewheels/pages/WarehousesPage.d.ts +4 -0
- package/dist/movethewheels/providers/MoveTheWheelsProvider.d.ts +16 -0
- package/dist/movethewheels/store/movethewheelsStore.d.ts +73 -0
- package/dist/movethewheels/types/index.d.ts +655 -0
- package/dist/movethewheels/utils/cn.d.ts +6 -0
- package/dist/movethewheels/utils/formatters.d.ts +60 -0
- package/dist/movethewheels/utils/graphqlClient.d.ts +11 -0
- package/dist/movethewheels/utils/index.d.ts +7 -0
- package/dist/movethewheels/utils/navigation.d.ts +23 -0
- package/dist/navigation-BgnOfsVd.js +6 -0
- package/dist/navigation-C2fY_aS9.js +8 -0
- package/dist/package-DVZbDRcV.js +22 -0
- package/dist/phone-KdwpVmC4.js +18 -0
- package/dist/plus-Bl7uX6Ji.js +11 -0
- package/dist/refresh-cw-BYjl3K-8.js +22 -0
- package/dist/route-Ce_poKFi.js +51 -0
- package/dist/save-C-qDVat-.js +18 -0
- package/dist/search-5pdn5eOO.js +13 -0
- package/dist/settings-C4kIDsYg.js +28 -0
- package/dist/square-pen-BwQ67vLE.js +11 -0
- package/dist/star-BlVsC3Ad.js +8 -0
- package/dist/store-DTmQT5M0.js +26 -0
- package/dist/trending-up-C1faflCI.js +11 -0
- package/dist/triangle-alert-CUoVAA4L.js +18 -0
- package/dist/truck-BmDAzu05.js +30 -0
- package/dist/useAnalytics-ph7eTIK6.js +297 -0
- package/dist/useCustomers-bS3a4ytk.js +186 -0
- package/dist/useFleet-BdETplNE.js +398 -0
- package/dist/useInventory-Dwn18FPz.js +323 -0
- package/dist/useOrders-D_3_hGMp.js +324 -0
- package/dist/useRoutes-v4aBaS-E.js +224 -0
- package/dist/useTracking-De2KIUNu.js +261 -0
- package/dist/user-BplzDrLP.js +13 -0
- package/dist/users-i-igmsP4.js +24 -0
- package/dist/warehouse-DewG0PXh.js +25 -0
- package/dist/wrench-CoSDEIC7.js +31 -0
- package/package.json +107 -0
- package/src/dev/main.tsx +110 -0
- package/src/dev/styles.css +139 -0
- package/src/generated/global-operations.ts +2 -0
- package/src/generated/global-types.ts +24048 -0
- package/src/generated/wspace-operations.ts +3734 -0
- package/src/generated/wspace-types.ts +60715 -0
- package/src/index.ts +4 -0
- package/src/movethewheels/MoveTheWheelsRoot.tsx +258 -0
- package/src/movethewheels/MoveTheWheelsRoutes.tsx +119 -0
- package/src/movethewheels/components/DataTable.tsx +367 -0
- package/src/movethewheels/components/MetricCard.tsx +180 -0
- package/src/movethewheels/components/PageLayout.tsx +234 -0
- package/src/movethewheels/components/StatusBadge.tsx +243 -0
- package/src/movethewheels/components/index.ts +26 -0
- package/src/movethewheels/components/ui.tsx +124 -0
- package/src/movethewheels/constants/index.ts +65 -0
- package/src/movethewheels/constants/mockData.ts +1342 -0
- package/src/movethewheels/hooks/index.ts +55 -0
- package/src/movethewheels/hooks/useAnalytics.ts +476 -0
- package/src/movethewheels/hooks/useCustomers.ts +359 -0
- package/src/movethewheels/hooks/useFleet.ts +778 -0
- package/src/movethewheels/hooks/useInventory.ts +632 -0
- package/src/movethewheels/hooks/useOrders.ts +703 -0
- package/src/movethewheels/hooks/useRoutes.ts +453 -0
- package/src/movethewheels/hooks/useTracking.ts +505 -0
- package/src/movethewheels/index.ts +68 -0
- package/src/movethewheels/pages/AIAssistantPage.tsx +160 -0
- package/src/movethewheels/pages/AnalyticsPage.tsx +190 -0
- package/src/movethewheels/pages/CreateOrderPage.tsx +454 -0
- package/src/movethewheels/pages/CustomerDetailsPage.tsx +207 -0
- package/src/movethewheels/pages/CustomersPage.tsx +115 -0
- package/src/movethewheels/pages/DashboardPage.tsx +414 -0
- package/src/movethewheels/pages/DriverDetailsPage.tsx +261 -0
- package/src/movethewheels/pages/DriversPage.tsx +118 -0
- package/src/movethewheels/pages/FinancePage.tsx +141 -0
- package/src/movethewheels/pages/FleetPage.tsx +289 -0
- package/src/movethewheels/pages/ImportExportPage.tsx +165 -0
- package/src/movethewheels/pages/InventoryPage.tsx +212 -0
- package/src/movethewheels/pages/LiveTrackingPage.tsx +325 -0
- package/src/movethewheels/pages/MarketplacePage.tsx +235 -0
- package/src/movethewheels/pages/OrderDetailsPage.tsx +387 -0
- package/src/movethewheels/pages/OrdersListPage.tsx +241 -0
- package/src/movethewheels/pages/ProductDetailsPage.tsx +155 -0
- package/src/movethewheels/pages/ProductsPage.tsx +124 -0
- package/src/movethewheels/pages/ReportsPage.tsx +164 -0
- package/src/movethewheels/pages/RouteDetailsPage.tsx +245 -0
- package/src/movethewheels/pages/RoutesPage.tsx +104 -0
- package/src/movethewheels/pages/SettingsPage.tsx +242 -0
- package/src/movethewheels/pages/TrackingPage.tsx +419 -0
- package/src/movethewheels/pages/VehicleDetailsPage.tsx +218 -0
- package/src/movethewheels/pages/VehiclesPage.tsx +124 -0
- package/src/movethewheels/pages/WarehouseDetailsPage.tsx +216 -0
- package/src/movethewheels/pages/WarehousesPage.tsx +122 -0
- package/src/movethewheels/providers/MoveTheWheelsProvider.tsx +66 -0
- package/src/movethewheels/store/movethewheelsStore.ts +136 -0
- package/src/movethewheels/types/index.ts +744 -0
- package/src/movethewheels/utils/cn.ts +9 -0
- package/src/movethewheels/utils/formatters.ts +215 -0
- package/src/movethewheels/utils/graphqlClient.ts +63 -0
- package/src/movethewheels/utils/index.ts +8 -0
- package/src/movethewheels/utils/navigation.ts +70 -0
- package/src/operations/global/.gitkeep +0 -0
- package/src/operations/wspace/movethewheels/fragments/core.graphql +191 -0
- package/src/operations/wspace/movethewheels/mutations/entities.graphql +87 -0
- package/src/operations/wspace/movethewheels/mutations/logistics.graphql +86 -0
- package/src/operations/wspace/movethewheels/mutations/marketplace-reports.graphql +81 -0
- package/src/operations/wspace/movethewheels/mutations/orders.graphql +21 -0
- package/src/operations/wspace/movethewheels/queries/dashboard.graphql +61 -0
- package/src/operations/wspace/movethewheels/queries/entities.graphql +83 -0
- package/src/operations/wspace/movethewheels/queries/logistics.graphql +84 -0
- package/src/operations/wspace/movethewheels/queries/marketplace-reports.graphql +40 -0
- package/src/operations/wspace/movethewheels/queries/orders.graphql +43 -0
|
@@ -0,0 +1,234 @@
|
|
|
1
|
+
import type { ReactNode } from 'react';
|
|
2
|
+
import { cn } from '../utils/cn';
|
|
3
|
+
|
|
4
|
+
interface PageLayoutProps {
|
|
5
|
+
children: ReactNode;
|
|
6
|
+
/** Page title */
|
|
7
|
+
title?: string;
|
|
8
|
+
/** Page subtitle/description */
|
|
9
|
+
subtitle?: string;
|
|
10
|
+
/** Icon component to display next to title */
|
|
11
|
+
icon?: ReactNode;
|
|
12
|
+
/** Actions to display in header (buttons, etc.) */
|
|
13
|
+
headerActions?: ReactNode;
|
|
14
|
+
/** Additional header content below title */
|
|
15
|
+
headerContent?: ReactNode;
|
|
16
|
+
/** Maximum width of content: 'sm' | 'md' | 'lg' | 'xl' | '2xl' | '3xl' | 'full' */
|
|
17
|
+
maxWidth?: 'sm' | 'md' | 'lg' | 'xl' | '2xl' | '3xl' | 'full';
|
|
18
|
+
/** Whether to show the header section */
|
|
19
|
+
showHeader?: boolean;
|
|
20
|
+
/** Additional CSS classes for the container */
|
|
21
|
+
className?: string;
|
|
22
|
+
/** Additional CSS classes for the content area */
|
|
23
|
+
contentClassName?: string;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
const maxWidthClasses = {
|
|
27
|
+
sm: 'max-w-screen-sm', // 640px
|
|
28
|
+
md: 'max-w-screen-md', // 768px
|
|
29
|
+
lg: 'max-w-screen-lg', // 1024px
|
|
30
|
+
xl: 'max-w-screen-xl', // 1280px
|
|
31
|
+
'2xl': 'max-w-screen-2xl', // 1536px
|
|
32
|
+
'3xl': 'max-w-[1600px]',
|
|
33
|
+
full: 'max-w-full',
|
|
34
|
+
};
|
|
35
|
+
|
|
36
|
+
/**
|
|
37
|
+
* PageLayout - A consistent page wrapper with responsive design
|
|
38
|
+
*
|
|
39
|
+
* Features:
|
|
40
|
+
* - Proper max-width constraints
|
|
41
|
+
* - Responsive padding
|
|
42
|
+
* - Animated entrance
|
|
43
|
+
* - Consistent header styling
|
|
44
|
+
*/
|
|
45
|
+
export function PageLayout({
|
|
46
|
+
children,
|
|
47
|
+
title,
|
|
48
|
+
subtitle,
|
|
49
|
+
icon,
|
|
50
|
+
headerActions,
|
|
51
|
+
headerContent,
|
|
52
|
+
maxWidth = 'xl',
|
|
53
|
+
showHeader = true,
|
|
54
|
+
className,
|
|
55
|
+
contentClassName,
|
|
56
|
+
}: PageLayoutProps) {
|
|
57
|
+
return (
|
|
58
|
+
<div
|
|
59
|
+
className={cn(
|
|
60
|
+
// Base styles - full width container with padding
|
|
61
|
+
'min-h-full w-full',
|
|
62
|
+
// Responsive horizontal padding
|
|
63
|
+
'px-4 sm:px-6 lg:px-8 xl:px-12',
|
|
64
|
+
// Responsive vertical padding
|
|
65
|
+
'py-6 sm:py-8 lg:py-10',
|
|
66
|
+
// Entrance animation
|
|
67
|
+
'animate-in fade-in-0 slide-in-from-bottom-4 duration-500',
|
|
68
|
+
className
|
|
69
|
+
)}
|
|
70
|
+
>
|
|
71
|
+
{/* Max-width constrained content container */}
|
|
72
|
+
<div className={cn('mx-auto w-full', maxWidthClasses[maxWidth], contentClassName)}>
|
|
73
|
+
{/* Page Header */}
|
|
74
|
+
{showHeader && (title || headerActions) && (
|
|
75
|
+
<header className="mb-6 sm:mb-8">
|
|
76
|
+
<div className="flex flex-col gap-4 sm:flex-row sm:items-start sm:justify-between">
|
|
77
|
+
{/* Title Section */}
|
|
78
|
+
<div className="space-y-1">
|
|
79
|
+
{(title || icon) && (
|
|
80
|
+
<div className="flex items-center gap-3">
|
|
81
|
+
{icon && (
|
|
82
|
+
<div className="flex-shrink-0 p-2.5 rounded-xl bg-primary/10 text-primary">
|
|
83
|
+
{icon}
|
|
84
|
+
</div>
|
|
85
|
+
)}
|
|
86
|
+
{title && (
|
|
87
|
+
<h1 className="text-2xl sm:text-3xl font-bold tracking-tight text-foreground">
|
|
88
|
+
{title}
|
|
89
|
+
</h1>
|
|
90
|
+
)}
|
|
91
|
+
</div>
|
|
92
|
+
)}
|
|
93
|
+
{subtitle && (
|
|
94
|
+
<p className="text-sm sm:text-base text-muted-foreground max-w-2xl">{subtitle}</p>
|
|
95
|
+
)}
|
|
96
|
+
</div>
|
|
97
|
+
|
|
98
|
+
{/* Header Actions */}
|
|
99
|
+
{headerActions && (
|
|
100
|
+
<div className="flex items-center gap-2 flex-shrink-0">{headerActions}</div>
|
|
101
|
+
)}
|
|
102
|
+
</div>
|
|
103
|
+
|
|
104
|
+
{/* Additional Header Content */}
|
|
105
|
+
{headerContent && <div className="mt-4">{headerContent}</div>}
|
|
106
|
+
</header>
|
|
107
|
+
)}
|
|
108
|
+
|
|
109
|
+
{/* Page content — must not use a <main> landmark here because the
|
|
110
|
+
host shell (AppShellLayout) already renders one; nesting <main>
|
|
111
|
+
elements is invalid HTML and an a11y violation. */}
|
|
112
|
+
<div className="space-y-6">{children}</div>
|
|
113
|
+
</div>
|
|
114
|
+
</div>
|
|
115
|
+
);
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
/**
|
|
119
|
+
* PageSection - A section within a page with consistent spacing
|
|
120
|
+
*/
|
|
121
|
+
export function PageSection({
|
|
122
|
+
children,
|
|
123
|
+
title,
|
|
124
|
+
description,
|
|
125
|
+
actions,
|
|
126
|
+
className,
|
|
127
|
+
}: {
|
|
128
|
+
children: ReactNode;
|
|
129
|
+
title?: string;
|
|
130
|
+
description?: string;
|
|
131
|
+
actions?: ReactNode;
|
|
132
|
+
className?: string;
|
|
133
|
+
}) {
|
|
134
|
+
return (
|
|
135
|
+
<section className={cn('space-y-4', className)}>
|
|
136
|
+
{(title || actions) && (
|
|
137
|
+
<div className="flex items-center justify-between">
|
|
138
|
+
<div>
|
|
139
|
+
{title && <h2 className="text-lg font-semibold text-foreground">{title}</h2>}
|
|
140
|
+
{description && <p className="text-sm text-muted-foreground">{description}</p>}
|
|
141
|
+
</div>
|
|
142
|
+
{actions && <div className="flex items-center gap-2">{actions}</div>}
|
|
143
|
+
</div>
|
|
144
|
+
)}
|
|
145
|
+
{children}
|
|
146
|
+
</section>
|
|
147
|
+
);
|
|
148
|
+
}
|
|
149
|
+
|
|
150
|
+
/**
|
|
151
|
+
* EmptyState - A consistent empty state component
|
|
152
|
+
*/
|
|
153
|
+
export function EmptyState({
|
|
154
|
+
icon,
|
|
155
|
+
title,
|
|
156
|
+
description,
|
|
157
|
+
action,
|
|
158
|
+
className,
|
|
159
|
+
}: {
|
|
160
|
+
icon?: ReactNode;
|
|
161
|
+
title: string;
|
|
162
|
+
description?: string;
|
|
163
|
+
action?: ReactNode;
|
|
164
|
+
className?: string;
|
|
165
|
+
}) {
|
|
166
|
+
return (
|
|
167
|
+
<div
|
|
168
|
+
className={cn(
|
|
169
|
+
'flex flex-col items-center justify-center',
|
|
170
|
+
'py-12 sm:py-16 px-4',
|
|
171
|
+
'text-center',
|
|
172
|
+
'animate-in fade-in-0 zoom-in-95 duration-300',
|
|
173
|
+
className
|
|
174
|
+
)}
|
|
175
|
+
>
|
|
176
|
+
{icon && <div className="mb-4 p-4 rounded-2xl bg-muted/50 text-muted-foreground">{icon}</div>}
|
|
177
|
+
<h3 className="text-lg font-semibold text-foreground mb-1">{title}</h3>
|
|
178
|
+
{description && <p className="text-sm text-muted-foreground max-w-sm mb-4">{description}</p>}
|
|
179
|
+
{action}
|
|
180
|
+
</div>
|
|
181
|
+
);
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
/**
|
|
185
|
+
* LoadingState - A consistent loading state component
|
|
186
|
+
*/
|
|
187
|
+
export function LoadingState({ message = 'Loading...' }: { message?: string }) {
|
|
188
|
+
return (
|
|
189
|
+
<div className="flex items-center justify-center min-h-[400px]">
|
|
190
|
+
<div className="flex flex-col items-center gap-3">
|
|
191
|
+
<div className="animate-spin rounded-full h-8 w-8 border-b-2 border-primary"></div>
|
|
192
|
+
<p className="text-sm text-muted-foreground">{message}</p>
|
|
193
|
+
</div>
|
|
194
|
+
</div>
|
|
195
|
+
);
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
/**
|
|
199
|
+
* ErrorState - A consistent error state component
|
|
200
|
+
*/
|
|
201
|
+
export function ErrorState({
|
|
202
|
+
title = 'Something went wrong',
|
|
203
|
+
message,
|
|
204
|
+
onRetry,
|
|
205
|
+
}: {
|
|
206
|
+
title?: string;
|
|
207
|
+
message?: string;
|
|
208
|
+
onRetry?: () => void;
|
|
209
|
+
}) {
|
|
210
|
+
return (
|
|
211
|
+
<div className="flex flex-col items-center justify-center py-12 px-4 text-center">
|
|
212
|
+
<div className="mb-4 p-4 rounded-2xl bg-destructive/10 text-destructive">
|
|
213
|
+
<svg className="h-12 w-12" fill="none" viewBox="0 0 24 24" stroke="currentColor">
|
|
214
|
+
<path
|
|
215
|
+
strokeLinecap="round"
|
|
216
|
+
strokeLinejoin="round"
|
|
217
|
+
strokeWidth={2}
|
|
218
|
+
d="M12 9v2m0 4h.01m-6.938 4h13.856c1.54 0 2.502-1.667 1.732-3L13.732 4c-.77-1.333-2.694-1.333-3.464 0L3.34 16c-.77 1.333.192 3 1.732 3z"
|
|
219
|
+
/>
|
|
220
|
+
</svg>
|
|
221
|
+
</div>
|
|
222
|
+
<h3 className="text-lg font-semibold text-foreground mb-1">{title}</h3>
|
|
223
|
+
{message && <p className="text-sm text-muted-foreground max-w-sm mb-4">{message}</p>}
|
|
224
|
+
{onRetry && (
|
|
225
|
+
<button
|
|
226
|
+
onClick={onRetry}
|
|
227
|
+
className="px-4 py-2 text-sm font-medium text-primary hover:text-primary/80 transition-colors"
|
|
228
|
+
>
|
|
229
|
+
Try again
|
|
230
|
+
</button>
|
|
231
|
+
)}
|
|
232
|
+
</div>
|
|
233
|
+
);
|
|
234
|
+
}
|
|
@@ -0,0 +1,243 @@
|
|
|
1
|
+
import { cn } from '../utils/cn';
|
|
2
|
+
import { Badge } from './ui';
|
|
3
|
+
import type { OrderStatus, VehicleStatus, DriverStatus } from '../types';
|
|
4
|
+
import { ORDER_STATUS_COLORS, VEHICLE_STATUS_COLORS, DRIVER_STATUS_COLORS } from '../constants';
|
|
5
|
+
|
|
6
|
+
type StatusType = 'order' | 'vehicle' | 'driver' | 'custom';
|
|
7
|
+
|
|
8
|
+
interface StatusBadgeProps {
|
|
9
|
+
status: string;
|
|
10
|
+
type?: StatusType;
|
|
11
|
+
customColors?: {
|
|
12
|
+
bg: string;
|
|
13
|
+
text: string;
|
|
14
|
+
};
|
|
15
|
+
size?: 'sm' | 'md' | 'lg';
|
|
16
|
+
showDot?: boolean;
|
|
17
|
+
className?: string;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
const sizeClasses = {
|
|
21
|
+
sm: 'text-xs px-2 py-0.5',
|
|
22
|
+
md: 'text-sm px-2.5 py-1',
|
|
23
|
+
lg: 'text-base px-3 py-1.5',
|
|
24
|
+
};
|
|
25
|
+
|
|
26
|
+
/**
|
|
27
|
+
* StatusBadge - Displays status with appropriate colors
|
|
28
|
+
*/
|
|
29
|
+
export function StatusBadge({
|
|
30
|
+
status,
|
|
31
|
+
type = 'custom',
|
|
32
|
+
customColors,
|
|
33
|
+
size = 'md',
|
|
34
|
+
showDot = true,
|
|
35
|
+
className,
|
|
36
|
+
}: StatusBadgeProps) {
|
|
37
|
+
// Get colors based on type
|
|
38
|
+
let colors = customColors;
|
|
39
|
+
|
|
40
|
+
if (!colors) {
|
|
41
|
+
switch (type) {
|
|
42
|
+
case 'order':
|
|
43
|
+
colors = ORDER_STATUS_COLORS[status as OrderStatus] || {
|
|
44
|
+
bg: 'bg-gray-100',
|
|
45
|
+
text: 'text-gray-700',
|
|
46
|
+
};
|
|
47
|
+
break;
|
|
48
|
+
case 'vehicle':
|
|
49
|
+
colors = VEHICLE_STATUS_COLORS[status as VehicleStatus] || {
|
|
50
|
+
bg: 'bg-gray-100',
|
|
51
|
+
text: 'text-gray-700',
|
|
52
|
+
};
|
|
53
|
+
break;
|
|
54
|
+
case 'driver':
|
|
55
|
+
colors = DRIVER_STATUS_COLORS[status as DriverStatus] || {
|
|
56
|
+
bg: 'bg-gray-100',
|
|
57
|
+
text: 'text-gray-700',
|
|
58
|
+
};
|
|
59
|
+
break;
|
|
60
|
+
default:
|
|
61
|
+
colors = { bg: 'bg-gray-100 dark:bg-gray-800', text: 'text-gray-700 dark:text-gray-300' };
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
// Format status for display
|
|
66
|
+
const displayStatus = status.replace(/_/g, ' ').replace(/\b\w/g, (c) => c.toUpperCase());
|
|
67
|
+
|
|
68
|
+
return (
|
|
69
|
+
<Badge
|
|
70
|
+
variant="outline"
|
|
71
|
+
className={cn(
|
|
72
|
+
'font-medium capitalize border-0 whitespace-nowrap inline-flex items-center',
|
|
73
|
+
colors.bg,
|
|
74
|
+
colors.text,
|
|
75
|
+
sizeClasses[size],
|
|
76
|
+
className
|
|
77
|
+
)}
|
|
78
|
+
>
|
|
79
|
+
{showDot && (
|
|
80
|
+
<span
|
|
81
|
+
className={cn(
|
|
82
|
+
'w-1.5 h-1.5 rounded-full mr-1.5 flex-shrink-0',
|
|
83
|
+
colors.text.replace('text-', 'bg-')
|
|
84
|
+
)}
|
|
85
|
+
/>
|
|
86
|
+
)}
|
|
87
|
+
{displayStatus}
|
|
88
|
+
</Badge>
|
|
89
|
+
);
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
/**
|
|
93
|
+
* Priority Badge - Displays priority level
|
|
94
|
+
*/
|
|
95
|
+
export function PriorityBadge({
|
|
96
|
+
priority,
|
|
97
|
+
size = 'md',
|
|
98
|
+
className,
|
|
99
|
+
}: {
|
|
100
|
+
priority: 'low' | 'normal' | 'high' | 'urgent';
|
|
101
|
+
size?: 'sm' | 'md' | 'lg';
|
|
102
|
+
className?: string;
|
|
103
|
+
}) {
|
|
104
|
+
const priorityColors = {
|
|
105
|
+
low: { bg: 'bg-gray-100 dark:bg-gray-800', text: 'text-gray-600 dark:text-gray-400' },
|
|
106
|
+
normal: { bg: 'bg-blue-100 dark:bg-blue-900/30', text: 'text-blue-700 dark:text-blue-400' },
|
|
107
|
+
high: {
|
|
108
|
+
bg: 'bg-orange-100 dark:bg-orange-900/30',
|
|
109
|
+
text: 'text-orange-700 dark:text-orange-400',
|
|
110
|
+
},
|
|
111
|
+
urgent: { bg: 'bg-red-100 dark:bg-red-900/30', text: 'text-red-700 dark:text-red-400' },
|
|
112
|
+
};
|
|
113
|
+
|
|
114
|
+
const colors = priorityColors[priority];
|
|
115
|
+
|
|
116
|
+
return (
|
|
117
|
+
<Badge
|
|
118
|
+
variant="outline"
|
|
119
|
+
className={cn(
|
|
120
|
+
'font-medium capitalize border-0 whitespace-nowrap',
|
|
121
|
+
colors.bg,
|
|
122
|
+
colors.text,
|
|
123
|
+
sizeClasses[size],
|
|
124
|
+
className
|
|
125
|
+
)}
|
|
126
|
+
>
|
|
127
|
+
{priority}
|
|
128
|
+
</Badge>
|
|
129
|
+
);
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
/**
|
|
133
|
+
* TypeBadge - Displays B2B/B2C type
|
|
134
|
+
*/
|
|
135
|
+
export function TypeBadge({
|
|
136
|
+
type,
|
|
137
|
+
size = 'md',
|
|
138
|
+
className,
|
|
139
|
+
}: {
|
|
140
|
+
type: 'b2b' | 'b2c';
|
|
141
|
+
size?: 'sm' | 'md' | 'lg';
|
|
142
|
+
className?: string;
|
|
143
|
+
}) {
|
|
144
|
+
const typeColors = {
|
|
145
|
+
b2b: {
|
|
146
|
+
bg: 'bg-purple-100 dark:bg-purple-900/30',
|
|
147
|
+
text: 'text-purple-700 dark:text-purple-400',
|
|
148
|
+
},
|
|
149
|
+
b2c: { bg: 'bg-teal-100 dark:bg-teal-900/30', text: 'text-teal-700 dark:text-teal-400' },
|
|
150
|
+
};
|
|
151
|
+
|
|
152
|
+
const colors = typeColors[type];
|
|
153
|
+
|
|
154
|
+
return (
|
|
155
|
+
<Badge
|
|
156
|
+
variant="outline"
|
|
157
|
+
className={cn(
|
|
158
|
+
'font-medium uppercase border-0 whitespace-nowrap',
|
|
159
|
+
colors.bg,
|
|
160
|
+
colors.text,
|
|
161
|
+
sizeClasses[size],
|
|
162
|
+
className
|
|
163
|
+
)}
|
|
164
|
+
>
|
|
165
|
+
{type}
|
|
166
|
+
</Badge>
|
|
167
|
+
);
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
/**
|
|
171
|
+
* PaymentStatusBadge - Displays payment status
|
|
172
|
+
*/
|
|
173
|
+
export function PaymentStatusBadge({
|
|
174
|
+
status,
|
|
175
|
+
size = 'md',
|
|
176
|
+
className,
|
|
177
|
+
}: {
|
|
178
|
+
status: 'pending' | 'paid' | 'failed' | 'refunded';
|
|
179
|
+
size?: 'sm' | 'md' | 'lg';
|
|
180
|
+
className?: string;
|
|
181
|
+
}) {
|
|
182
|
+
const statusColors = {
|
|
183
|
+
pending: {
|
|
184
|
+
bg: 'bg-yellow-100 dark:bg-yellow-900/30',
|
|
185
|
+
text: 'text-yellow-700 dark:text-yellow-400',
|
|
186
|
+
},
|
|
187
|
+
paid: { bg: 'bg-green-100 dark:bg-green-900/30', text: 'text-green-700 dark:text-green-400' },
|
|
188
|
+
failed: { bg: 'bg-red-100 dark:bg-red-900/30', text: 'text-red-700 dark:text-red-400' },
|
|
189
|
+
refunded: { bg: 'bg-gray-100 dark:bg-gray-800', text: 'text-gray-700 dark:text-gray-400' },
|
|
190
|
+
};
|
|
191
|
+
|
|
192
|
+
const colors = statusColors[status];
|
|
193
|
+
|
|
194
|
+
return (
|
|
195
|
+
<Badge
|
|
196
|
+
variant="outline"
|
|
197
|
+
className={cn(
|
|
198
|
+
'font-medium capitalize border-0 whitespace-nowrap',
|
|
199
|
+
colors.bg,
|
|
200
|
+
colors.text,
|
|
201
|
+
sizeClasses[size],
|
|
202
|
+
className
|
|
203
|
+
)}
|
|
204
|
+
>
|
|
205
|
+
{status}
|
|
206
|
+
</Badge>
|
|
207
|
+
);
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
/**
|
|
211
|
+
* VehicleTypeBadge - Displays vehicle type
|
|
212
|
+
*/
|
|
213
|
+
export function VehicleTypeBadge({
|
|
214
|
+
type,
|
|
215
|
+
size = 'md',
|
|
216
|
+
className,
|
|
217
|
+
}: {
|
|
218
|
+
type: 'van' | 'truck' | 'motorcycle' | 'bicycle' | 'car';
|
|
219
|
+
size?: 'sm' | 'md' | 'lg';
|
|
220
|
+
className?: string;
|
|
221
|
+
}) {
|
|
222
|
+
const typeIcons = {
|
|
223
|
+
van: '🚐',
|
|
224
|
+
truck: '🚚',
|
|
225
|
+
motorcycle: '🏍️',
|
|
226
|
+
bicycle: '🚲',
|
|
227
|
+
car: '🚗',
|
|
228
|
+
};
|
|
229
|
+
|
|
230
|
+
return (
|
|
231
|
+
<Badge
|
|
232
|
+
variant="outline"
|
|
233
|
+
className={cn(
|
|
234
|
+
'font-medium capitalize whitespace-nowrap inline-flex items-center',
|
|
235
|
+
sizeClasses[size],
|
|
236
|
+
className
|
|
237
|
+
)}
|
|
238
|
+
>
|
|
239
|
+
<span className="mr-1">{typeIcons[type]}</span>
|
|
240
|
+
{type}
|
|
241
|
+
</Badge>
|
|
242
|
+
);
|
|
243
|
+
}
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* MoveTheWheels Components
|
|
3
|
+
*
|
|
4
|
+
* All shared components for the microfrontend.
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
// UI re-exports
|
|
8
|
+
export * from './ui';
|
|
9
|
+
|
|
10
|
+
// Layout components
|
|
11
|
+
export { PageLayout, PageSection, EmptyState, LoadingState, ErrorState } from './PageLayout';
|
|
12
|
+
|
|
13
|
+
// Metric components
|
|
14
|
+
export { MetricCard, MetricCardSkeleton, MetricGrid } from './MetricCard';
|
|
15
|
+
|
|
16
|
+
// Status components
|
|
17
|
+
export {
|
|
18
|
+
StatusBadge,
|
|
19
|
+
PriorityBadge,
|
|
20
|
+
TypeBadge,
|
|
21
|
+
PaymentStatusBadge,
|
|
22
|
+
VehicleTypeBadge,
|
|
23
|
+
} from './StatusBadge';
|
|
24
|
+
|
|
25
|
+
// Table components
|
|
26
|
+
export { DataTable, type Column } from './DataTable';
|
|
@@ -0,0 +1,124 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* UI Component re-exports from @burdenoff/fe-libs
|
|
3
|
+
* All styled components are imported from the shared fe-libs package
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
// Re-export all UI components from fe-libs
|
|
7
|
+
export {
|
|
8
|
+
Button,
|
|
9
|
+
Badge,
|
|
10
|
+
Card,
|
|
11
|
+
CardContent,
|
|
12
|
+
CardHeader,
|
|
13
|
+
CardTitle,
|
|
14
|
+
CardDescription,
|
|
15
|
+
CardFooter,
|
|
16
|
+
Input,
|
|
17
|
+
Skeleton,
|
|
18
|
+
Separator,
|
|
19
|
+
Select,
|
|
20
|
+
SelectContent,
|
|
21
|
+
SelectItem,
|
|
22
|
+
SelectTrigger,
|
|
23
|
+
SelectValue,
|
|
24
|
+
Tabs,
|
|
25
|
+
TabsList,
|
|
26
|
+
TabsTrigger,
|
|
27
|
+
TabsContent,
|
|
28
|
+
Dialog,
|
|
29
|
+
DialogContent,
|
|
30
|
+
DialogHeader,
|
|
31
|
+
DialogTitle,
|
|
32
|
+
DialogDescription,
|
|
33
|
+
DialogFooter,
|
|
34
|
+
DialogTrigger,
|
|
35
|
+
DropdownMenu,
|
|
36
|
+
DropdownMenuContent,
|
|
37
|
+
DropdownMenuItem,
|
|
38
|
+
DropdownMenuTrigger,
|
|
39
|
+
DropdownMenuSeparator,
|
|
40
|
+
Label,
|
|
41
|
+
Textarea,
|
|
42
|
+
Switch,
|
|
43
|
+
Checkbox,
|
|
44
|
+
Tooltip,
|
|
45
|
+
TooltipContent,
|
|
46
|
+
TooltipProvider,
|
|
47
|
+
TooltipTrigger,
|
|
48
|
+
ScrollArea,
|
|
49
|
+
Table,
|
|
50
|
+
TableBody,
|
|
51
|
+
TableCell,
|
|
52
|
+
TableHead,
|
|
53
|
+
TableHeader,
|
|
54
|
+
TableRow,
|
|
55
|
+
} from '@burdenoff/fe-libs/ui';
|
|
56
|
+
|
|
57
|
+
// Custom Progress component (not in fe-libs)
|
|
58
|
+
import * as React from 'react';
|
|
59
|
+
import { cn } from '../utils/cn';
|
|
60
|
+
|
|
61
|
+
interface ProgressProps extends React.HTMLAttributes<HTMLDivElement> {
|
|
62
|
+
value?: number;
|
|
63
|
+
max?: number;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
const Progress = React.forwardRef<HTMLDivElement, ProgressProps>(
|
|
67
|
+
({ className, value = 0, max = 100, ...props }, ref) => {
|
|
68
|
+
const percentage = Math.min(Math.max((value / max) * 100, 0), 100);
|
|
69
|
+
return (
|
|
70
|
+
<div
|
|
71
|
+
ref={ref}
|
|
72
|
+
className={cn('relative h-2 w-full overflow-hidden rounded-full bg-muted', className)}
|
|
73
|
+
{...props}
|
|
74
|
+
>
|
|
75
|
+
<div
|
|
76
|
+
className="h-full bg-primary transition-all duration-300 ease-in-out"
|
|
77
|
+
style={{ width: `${percentage}%` }}
|
|
78
|
+
/>
|
|
79
|
+
</div>
|
|
80
|
+
);
|
|
81
|
+
}
|
|
82
|
+
);
|
|
83
|
+
Progress.displayName = 'Progress';
|
|
84
|
+
|
|
85
|
+
export { Progress };
|
|
86
|
+
|
|
87
|
+
// Custom Avatar components (not in fe-libs)
|
|
88
|
+
interface AvatarProps extends React.HTMLAttributes<HTMLDivElement> {}
|
|
89
|
+
|
|
90
|
+
const Avatar = React.forwardRef<HTMLDivElement, AvatarProps>(({ className, ...props }, ref) => (
|
|
91
|
+
<div
|
|
92
|
+
ref={ref}
|
|
93
|
+
className={cn('relative flex h-10 w-10 shrink-0 overflow-hidden rounded-full', className)}
|
|
94
|
+
{...props}
|
|
95
|
+
/>
|
|
96
|
+
));
|
|
97
|
+
Avatar.displayName = 'Avatar';
|
|
98
|
+
|
|
99
|
+
interface AvatarImageProps extends React.ImgHTMLAttributes<HTMLImageElement> {}
|
|
100
|
+
|
|
101
|
+
const AvatarImage = React.forwardRef<HTMLImageElement, AvatarImageProps>(
|
|
102
|
+
({ className, ...props }, ref) => (
|
|
103
|
+
<img ref={ref} className={cn('aspect-square h-full w-full', className)} {...props} />
|
|
104
|
+
)
|
|
105
|
+
);
|
|
106
|
+
AvatarImage.displayName = 'AvatarImage';
|
|
107
|
+
|
|
108
|
+
interface AvatarFallbackProps extends React.HTMLAttributes<HTMLDivElement> {}
|
|
109
|
+
|
|
110
|
+
const AvatarFallback = React.forwardRef<HTMLDivElement, AvatarFallbackProps>(
|
|
111
|
+
({ className, ...props }, ref) => (
|
|
112
|
+
<div
|
|
113
|
+
ref={ref}
|
|
114
|
+
className={cn(
|
|
115
|
+
'flex h-full w-full items-center justify-center rounded-full bg-muted',
|
|
116
|
+
className
|
|
117
|
+
)}
|
|
118
|
+
{...props}
|
|
119
|
+
/>
|
|
120
|
+
)
|
|
121
|
+
);
|
|
122
|
+
AvatarFallback.displayName = 'AvatarFallback';
|
|
123
|
+
|
|
124
|
+
export { Avatar, AvatarImage, AvatarFallback };
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Constants barrel export
|
|
3
|
+
*/
|
|
4
|
+
|
|
5
|
+
export * from './mockData';
|
|
6
|
+
|
|
7
|
+
// Order status colors
|
|
8
|
+
export const ORDER_STATUS_COLORS: Record<string, { bg: string; text: string; border: string }> = {
|
|
9
|
+
pending: { bg: 'bg-yellow-100', text: 'text-yellow-800', border: 'border-yellow-200' },
|
|
10
|
+
confirmed: { bg: 'bg-blue-100', text: 'text-blue-800', border: 'border-blue-200' },
|
|
11
|
+
assigned: { bg: 'bg-purple-100', text: 'text-purple-800', border: 'border-purple-200' },
|
|
12
|
+
picked_up: { bg: 'bg-indigo-100', text: 'text-indigo-800', border: 'border-indigo-200' },
|
|
13
|
+
in_transit: { bg: 'bg-cyan-100', text: 'text-cyan-800', border: 'border-cyan-200' },
|
|
14
|
+
out_for_delivery: { bg: 'bg-orange-100', text: 'text-orange-800', border: 'border-orange-200' },
|
|
15
|
+
delivered: { bg: 'bg-green-100', text: 'text-green-800', border: 'border-green-200' },
|
|
16
|
+
cancelled: { bg: 'bg-red-100', text: 'text-red-800', border: 'border-red-200' },
|
|
17
|
+
failed: { bg: 'bg-red-100', text: 'text-red-800', border: 'border-red-200' },
|
|
18
|
+
};
|
|
19
|
+
|
|
20
|
+
// Vehicle status colors
|
|
21
|
+
export const VEHICLE_STATUS_COLORS: Record<string, { bg: string; text: string }> = {
|
|
22
|
+
available: { bg: 'bg-green-100', text: 'text-green-800' },
|
|
23
|
+
assigned: { bg: 'bg-blue-100', text: 'text-blue-800' },
|
|
24
|
+
maintenance: { bg: 'bg-yellow-100', text: 'text-yellow-800' },
|
|
25
|
+
out_of_service: { bg: 'bg-red-100', text: 'text-red-800' },
|
|
26
|
+
};
|
|
27
|
+
|
|
28
|
+
// Driver status colors
|
|
29
|
+
export const DRIVER_STATUS_COLORS: Record<string, { bg: string; text: string }> = {
|
|
30
|
+
available: { bg: 'bg-green-100', text: 'text-green-800' },
|
|
31
|
+
busy: { bg: 'bg-blue-100', text: 'text-blue-800' },
|
|
32
|
+
offline: { bg: 'bg-gray-100', text: 'text-gray-800' },
|
|
33
|
+
on_break: { bg: 'bg-yellow-100', text: 'text-yellow-800' },
|
|
34
|
+
};
|
|
35
|
+
|
|
36
|
+
// Priority colors
|
|
37
|
+
export const PRIORITY_COLORS: Record<string, { bg: string; text: string }> = {
|
|
38
|
+
low: { bg: 'bg-gray-100', text: 'text-gray-600' },
|
|
39
|
+
normal: { bg: 'bg-blue-100', text: 'text-blue-600' },
|
|
40
|
+
high: { bg: 'bg-orange-100', text: 'text-orange-600' },
|
|
41
|
+
urgent: { bg: 'bg-red-100', text: 'text-red-600' },
|
|
42
|
+
};
|
|
43
|
+
|
|
44
|
+
// Customer type labels
|
|
45
|
+
export const CUSTOMER_TYPE_LABELS: Record<string, string> = {
|
|
46
|
+
b2b: 'Business',
|
|
47
|
+
b2c: 'Individual',
|
|
48
|
+
};
|
|
49
|
+
|
|
50
|
+
// Vehicle type labels
|
|
51
|
+
export const VEHICLE_TYPE_LABELS: Record<string, string> = {
|
|
52
|
+
van: 'Van',
|
|
53
|
+
truck: 'Truck',
|
|
54
|
+
motorcycle: 'Motorcycle',
|
|
55
|
+
bicycle: 'Bicycle',
|
|
56
|
+
car: 'Car',
|
|
57
|
+
};
|
|
58
|
+
|
|
59
|
+
// Warehouse type labels
|
|
60
|
+
export const WAREHOUSE_TYPE_LABELS: Record<string, string> = {
|
|
61
|
+
distribution: 'Distribution Center',
|
|
62
|
+
fulfillment: 'Fulfillment Center',
|
|
63
|
+
cold_storage: 'Cold Storage',
|
|
64
|
+
cross_dock: 'Cross Dock',
|
|
65
|
+
};
|