@burdenoff/microfe-movethewheels 2026.924.2 → 2026.925.1
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/dist/components/OrderItemRow.js +195 -109
- package/dist/constants/index.js +1 -0
- package/dist/generated/wspace-operations.d.ts +7 -0
- package/dist/hooks/useOrders.js +8 -4
- package/dist/hooks/useTracking.js +127 -66
- package/dist/movethewheels/components/OrderItemRow.d.ts +1 -2
- package/dist/movethewheels/hooks/useOrders.d.ts +1 -0
- package/dist/movethewheels/hooks/useTracking.d.ts +2 -2
- package/dist/movethewheels/types/index.d.ts +1 -1
- package/dist/pages/CreateOrderPage.js +597 -420
- package/dist/pages/OrderDetailsPage.js +289 -266
- package/dist/pages/OrdersListPage.js +4 -0
- package/dist/pages/TrackingPage.js +205 -195
- package/dist/utils/mapMarkers.js +2 -1
- package/package.json +1 -1
- package/src/generated/wspace-operations.ts +10 -3
- package/src/movethewheels/components/OrderItemRow.tsx +162 -99
- package/src/movethewheels/constants/index.ts +1 -0
- package/src/movethewheels/hooks/useOrders.ts +17 -3
- package/src/movethewheels/hooks/useTracking.ts +208 -27
- package/src/movethewheels/pages/CreateOrderPage.tsx +372 -263
- package/src/movethewheels/pages/OrderDetailsPage.tsx +55 -23
- package/src/movethewheels/pages/OrdersListPage.tsx +1 -0
- package/src/movethewheels/pages/TrackingPage.tsx +44 -14
- package/src/movethewheels/types/index.ts +1 -0
- package/src/movethewheels/utils/mapMarkers.ts +1 -0
- package/src/operations/wspace/movethewheels/queries/dashboard.graphql +5 -0
- package/src/operations/wspace/movethewheels/queries/logistics.graphql +2 -2
|
@@ -292,7 +292,7 @@ export type DeleteMovethewheelsOrderMutation = { __typename?: 'Mutation', delete
|
|
|
292
292
|
export type GetMovethewheelsDashboardQueryVariables = Types.Exact<{ [key: string]: never; }>;
|
|
293
293
|
|
|
294
294
|
|
|
295
|
-
export type GetMovethewheelsDashboardQuery = { __typename?: 'Query', dashboardMetrics: { __typename?: 'MtwDashboardMetrics', totalDeliveryJobs: number, activeDeliveries: number, availableDrivers: number, activeVehicles: number, lowStockItems: number, totalRevenue: number, recentDeliveryJobs: Array<{ __typename?: 'MtwDeliveryJob', id: string, deliveryJobNumber: string, status: Types.DeliveryJobStatus, priority: Types.DeliveryPriority, customerId: string, trackingNumber?: string | null, pickupAddress: Record<string, unknown>, deliveryAddress: Record<string, unknown>, cargoItems: Record<string, unknown>, pricing?: Record<string, unknown> | null, scheduledDelivery?: string | null, vehicleId?: string | null, driverId?: string | null, createdAt: string, updatedAt: string }> }, deliveryJobStats: { __typename?: 'MtwDeliveryJobStats', total: number, pending: number, inTransit: number, delivered: number, cancelled: number, failed: number }, fleetStats: { __typename?: 'MtwFleetStats', totalVehicles: number, activeVehicles: number, inTransitVehicles: number, maintenanceVehicles: number, totalDrivers: number, availableDrivers: number, onDeliveryDrivers: number }, financeMetrics: { __typename?: 'MtwFinanceMetrics', fuelCost: number, openInvoices: number, revenue: { __typename?: 'MtwRevenueMetrics', totalRevenue: number, averageOrderValue: number, deliveredRevenue: number } }, analytics: { __typename?: 'MtwAnalyticsSeries', deliveryTrend: Array<{ __typename?: 'MtwAnalyticsPoint', label: string, value: number }>, orderTrend: Array<{ __typename?: 'MtwAnalyticsPoint', label: string, value: number }>, revenueTrend: Array<{ __typename?: 'MtwAnalyticsPoint', label: string, value: number }> } };
|
|
295
|
+
export type GetMovethewheelsDashboardQuery = { __typename?: 'Query', dashboardMetrics: { __typename?: 'MtwDashboardMetrics', totalDeliveryJobs: number, activeDeliveries: number, availableDrivers: number, activeVehicles: number, lowStockItems: number, totalRevenue: number, recentDeliveryJobs: Array<{ __typename?: 'MtwDeliveryJob', id: string, deliveryJobNumber: string, status: Types.DeliveryJobStatus, priority: Types.DeliveryPriority, customerId: string, trackingNumber?: string | null, pickupAddress: Record<string, unknown>, deliveryAddress: Record<string, unknown>, cargoItems: Record<string, unknown>, pricing?: Record<string, unknown> | null, scheduledDelivery?: string | null, vehicleId?: string | null, driverId?: string | null, createdAt: string, updatedAt: string }> }, deliveryJobStats: { __typename?: 'MtwDeliveryJobStats', total: number, pending: number, confirmed: number, assigned: number, pickedUp: number, inTransit: number, outForDelivery: number, delivered: number, cancelled: number, failed: number, returned: number }, fleetStats: { __typename?: 'MtwFleetStats', totalVehicles: number, activeVehicles: number, inTransitVehicles: number, maintenanceVehicles: number, totalDrivers: number, availableDrivers: number, onDeliveryDrivers: number }, financeMetrics: { __typename?: 'MtwFinanceMetrics', fuelCost: number, openInvoices: number, revenue: { __typename?: 'MtwRevenueMetrics', totalRevenue: number, averageOrderValue: number, deliveredRevenue: number } }, analytics: { __typename?: 'MtwAnalyticsSeries', deliveryTrend: Array<{ __typename?: 'MtwAnalyticsPoint', label: string, value: number }>, orderTrend: Array<{ __typename?: 'MtwAnalyticsPoint', label: string, value: number }>, revenueTrend: Array<{ __typename?: 'MtwAnalyticsPoint', label: string, value: number }> } };
|
|
296
296
|
|
|
297
297
|
export type ListCustomersQueryVariables = Types.Exact<{
|
|
298
298
|
filter?: Types.InputMaybe<Types.CustomerFilterInput>;
|
|
@@ -436,6 +436,7 @@ export type GetShipmentQuery = { __typename?: 'Query', shipment?: { __typename?:
|
|
|
436
436
|
|
|
437
437
|
export type GetDeliveryJobTrackingQueryVariables = Types.Exact<{
|
|
438
438
|
deliveryJobId: Types.Scalars['ID']['input'];
|
|
439
|
+
pagination?: Types.InputMaybe<Types.PaginationInput>;
|
|
439
440
|
}>;
|
|
440
441
|
|
|
441
442
|
|
|
@@ -1837,10 +1838,15 @@ export const GetMovethewheelsDashboardDocument = gql`
|
|
|
1837
1838
|
deliveryJobStats {
|
|
1838
1839
|
total
|
|
1839
1840
|
pending
|
|
1841
|
+
confirmed
|
|
1842
|
+
assigned
|
|
1843
|
+
pickedUp
|
|
1840
1844
|
inTransit
|
|
1845
|
+
outForDelivery
|
|
1841
1846
|
delivered
|
|
1842
1847
|
cancelled
|
|
1843
1848
|
failed
|
|
1849
|
+
returned
|
|
1844
1850
|
}
|
|
1845
1851
|
fleetStats {
|
|
1846
1852
|
totalVehicles
|
|
@@ -2809,8 +2815,8 @@ export type GetShipmentLazyQueryHookResult = ReturnType<typeof useGetShipmentLaz
|
|
|
2809
2815
|
export type GetShipmentSuspenseQueryHookResult = ReturnType<typeof useGetShipmentSuspenseQuery>;
|
|
2810
2816
|
export type GetShipmentQueryResult = Apollo.QueryResult<Types.GetShipmentQuery, Types.GetShipmentQueryVariables>;
|
|
2811
2817
|
export const GetDeliveryJobTrackingDocument = gql`
|
|
2812
|
-
query GetDeliveryJobTracking($deliveryJobId: ID
|
|
2813
|
-
deliveryJobTracking(deliveryJobId: $deliveryJobId) {
|
|
2818
|
+
query GetDeliveryJobTracking($deliveryJobId: ID!, $pagination: PaginationInput) {
|
|
2819
|
+
deliveryJobTracking(deliveryJobId: $deliveryJobId, pagination: $pagination) {
|
|
2814
2820
|
id
|
|
2815
2821
|
shipmentId
|
|
2816
2822
|
eventType
|
|
@@ -2834,6 +2840,7 @@ export const GetDeliveryJobTrackingDocument = gql`
|
|
|
2834
2840
|
* const { data, loading, error } = useGetDeliveryJobTrackingQuery({
|
|
2835
2841
|
* variables: {
|
|
2836
2842
|
* deliveryJobId: // value for 'deliveryJobId'
|
|
2843
|
+
* pagination: // value for 'pagination'
|
|
2837
2844
|
* },
|
|
2838
2845
|
* });
|
|
2839
2846
|
*/
|
|
@@ -1,23 +1,21 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* OrderItemRow — one order-item line in CreateOrderPage's "
|
|
2
|
+
* OrderItemRow — one order-item line in CreateOrderPage's "Shipment contents" section.
|
|
3
3
|
*
|
|
4
4
|
* Its own component (not inlined in a `.map()`) because it needs one
|
|
5
|
-
* `useProduct`/`useProductStockLevels` hook call per row to resolve the
|
|
6
|
-
*
|
|
7
|
-
*
|
|
8
|
-
* Hooks don't allow that from inside a loop in the parent.
|
|
5
|
+
* `useProduct`/`useProductStockLevels` hook call per row to resolve the selected
|
|
6
|
+
* catalog item's label and stock hint independently of the shared, search-filtered
|
|
7
|
+
* products list passed down from the page.
|
|
9
8
|
*/
|
|
10
9
|
import type { ChangeEvent } from 'react';
|
|
11
10
|
import { Trash2 } from 'lucide-react';
|
|
12
|
-
import { Button, Input, Label
|
|
11
|
+
import { Button, Input, Label } from './ui';
|
|
13
12
|
import { EntityCombobox } from './EntityCombobox';
|
|
14
13
|
import { useProduct, useProductStockLevels } from '../hooks/useInventory';
|
|
15
|
-
import type { OrderItem, Product } from '../types';
|
|
14
|
+
import type { Dimensions, OrderItem, Product } from '../types';
|
|
16
15
|
|
|
17
16
|
interface OrderItemRowProps {
|
|
18
17
|
item: OrderItem;
|
|
19
18
|
index: number;
|
|
20
|
-
isFirst: boolean;
|
|
21
19
|
products: Product[];
|
|
22
20
|
productsLoading: boolean;
|
|
23
21
|
onUpdate: (index: number, field: string, value: unknown) => void;
|
|
@@ -37,7 +35,6 @@ function stockHintText(totalAvailable: number, levels: { warehouseName: string }
|
|
|
37
35
|
export function OrderItemRow({
|
|
38
36
|
item,
|
|
39
37
|
index,
|
|
40
|
-
isFirst,
|
|
41
38
|
products,
|
|
42
39
|
productsLoading,
|
|
43
40
|
onUpdate,
|
|
@@ -55,6 +52,9 @@ export function OrderItemRow({
|
|
|
55
52
|
isLoading: stockLoading,
|
|
56
53
|
} = useProductStockLevels(item.productId || undefined);
|
|
57
54
|
|
|
55
|
+
const dimensions =
|
|
56
|
+
item.dimensions ?? ({ length: 0, width: 0, height: 0, unit: 'cm' } satisfies Dimensions);
|
|
57
|
+
|
|
58
58
|
const selectProduct = (productId: string) => {
|
|
59
59
|
if (!productId) {
|
|
60
60
|
onUpdate(index, 'productId', '');
|
|
@@ -69,103 +69,166 @@ export function OrderItemRow({
|
|
|
69
69
|
onUpdate(index, 'weight', product.weight);
|
|
70
70
|
onUpdate(index, 'value', product.value);
|
|
71
71
|
onUpdate(index, 'dimensions', product.dimensions);
|
|
72
|
-
// Quantity is never set from the catalog — there
|
|
73
|
-
// quantity on a cargo item
|
|
72
|
+
// Quantity is never set from the catalog — there is no per-unit default
|
|
73
|
+
// quantity on a cargo item; it belongs to this specific order line.
|
|
74
|
+
};
|
|
75
|
+
|
|
76
|
+
const updateDimension = (field: keyof Omit<Dimensions, 'unit'>, value: string) => {
|
|
77
|
+
onUpdate(index, 'dimensions', {
|
|
78
|
+
...dimensions,
|
|
79
|
+
[field]: Number.parseFloat(value) || 0,
|
|
80
|
+
});
|
|
74
81
|
};
|
|
75
82
|
|
|
76
83
|
return (
|
|
77
|
-
<div
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
</>
|
|
93
|
-
)}
|
|
94
|
-
selectedOption={selectedProduct}
|
|
95
|
-
selectedLoading={selectedProductLoading}
|
|
96
|
-
placeholder="Pick from your product catalog"
|
|
97
|
-
emptyText="No products found."
|
|
98
|
-
noneLabel="Enter details manually"
|
|
99
|
-
// Search is driven by the shared "Search product catalog" box above
|
|
100
|
-
// this list — no second input inside the popover.
|
|
101
|
-
/>
|
|
102
|
-
{item.productId && !stockLoading && (
|
|
103
|
-
<p className="text-xs text-text-secondary">{stockHintText(totalAvailable, levels)}</p>
|
|
104
|
-
)}
|
|
105
|
-
</div>
|
|
106
|
-
<div className="grid grid-cols-1 gap-4 md:grid-cols-7">
|
|
107
|
-
<div className="space-y-2 md:col-span-2">
|
|
108
|
-
<Label>Item Name</Label>
|
|
109
|
-
<Input
|
|
110
|
-
value={item.name}
|
|
111
|
-
onChange={(e: ChangeEvent<HTMLInputElement>) => onUpdate(index, 'name', e.target.value)}
|
|
112
|
-
placeholder="Product name"
|
|
113
|
-
/>
|
|
114
|
-
</div>
|
|
115
|
-
<div className="space-y-2">
|
|
116
|
-
<Label>SKU</Label>
|
|
117
|
-
<Input
|
|
118
|
-
value={item.sku}
|
|
119
|
-
onChange={(e: ChangeEvent<HTMLInputElement>) => onUpdate(index, 'sku', e.target.value)}
|
|
120
|
-
placeholder="SKU-001"
|
|
121
|
-
/>
|
|
122
|
-
</div>
|
|
123
|
-
<div className="space-y-2">
|
|
124
|
-
<Label>Quantity</Label>
|
|
125
|
-
<Input
|
|
126
|
-
type="number"
|
|
127
|
-
min="1"
|
|
128
|
-
value={item.quantity}
|
|
129
|
-
onChange={(e: ChangeEvent<HTMLInputElement>) =>
|
|
130
|
-
onUpdate(index, 'quantity', parseInt(e.target.value) || 1)
|
|
131
|
-
}
|
|
132
|
-
/>
|
|
133
|
-
</div>
|
|
134
|
-
<div className="space-y-2">
|
|
135
|
-
<Label>Weight (kg)</Label>
|
|
136
|
-
<Input
|
|
137
|
-
type="number"
|
|
138
|
-
min="0"
|
|
139
|
-
step="0.1"
|
|
140
|
-
value={item.weight}
|
|
141
|
-
onChange={(e: ChangeEvent<HTMLInputElement>) =>
|
|
142
|
-
onUpdate(index, 'weight', parseFloat(e.target.value) || 0)
|
|
143
|
-
}
|
|
144
|
-
/>
|
|
84
|
+
<div
|
|
85
|
+
className="rounded-card border border-border-subtle bg-bg-surface p-4 shadow-elevation-1 sm:p-5"
|
|
86
|
+
aria-labelledby={`order-item-${item.id}-title`}
|
|
87
|
+
>
|
|
88
|
+
<div className="mb-4 flex items-start justify-between gap-4">
|
|
89
|
+
<div>
|
|
90
|
+
<h3
|
|
91
|
+
id={`order-item-${item.id}-title`}
|
|
92
|
+
className="text-sm font-semibold text-text-primary"
|
|
93
|
+
>
|
|
94
|
+
Item {index + 1}
|
|
95
|
+
</h3>
|
|
96
|
+
<p className="mt-1 text-xs text-text-secondary">
|
|
97
|
+
Select a catalog item to prefill details, or enter a one-off shipment manually.
|
|
98
|
+
</p>
|
|
145
99
|
</div>
|
|
146
|
-
<
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
100
|
+
<Button
|
|
101
|
+
type="button"
|
|
102
|
+
variant="ghost"
|
|
103
|
+
size="icon"
|
|
104
|
+
className="shrink-0 text-status-error-text"
|
|
105
|
+
onClick={() => onRemove(index)}
|
|
106
|
+
aria-label={`Remove item ${index + 1}`}
|
|
107
|
+
title={`Remove item ${index + 1}`}
|
|
108
|
+
>
|
|
109
|
+
<Trash2 size={16} aria-hidden="true" />
|
|
110
|
+
</Button>
|
|
111
|
+
</div>
|
|
112
|
+
|
|
113
|
+
<div className="space-y-4">
|
|
114
|
+
<div className="rounded-card border border-border-subtle bg-bg-sunken/40 p-3 sm:p-4">
|
|
115
|
+
<Label htmlFor={`item-product-${item.id}`}>Catalog item (optional)</Label>
|
|
116
|
+
<EntityCombobox
|
|
117
|
+
id={`item-product-${item.id}`}
|
|
118
|
+
value={item.productId}
|
|
119
|
+
onChange={selectProduct}
|
|
120
|
+
options={products}
|
|
121
|
+
loading={productsLoading}
|
|
122
|
+
getId={(product) => product.id}
|
|
123
|
+
getLabel={(product) => `${product.name} (${product.sku})`}
|
|
124
|
+
renderOption={(product) => (
|
|
125
|
+
<>
|
|
126
|
+
{product.name} <span className="text-text-tertiary">({product.sku})</span>
|
|
127
|
+
</>
|
|
128
|
+
)}
|
|
129
|
+
selectedOption={selectedProduct}
|
|
130
|
+
selectedLoading={selectedProductLoading}
|
|
131
|
+
placeholder="Pick from your product catalog"
|
|
132
|
+
emptyText="No products found."
|
|
133
|
+
noneLabel="Enter details manually"
|
|
156
134
|
/>
|
|
135
|
+
{item.productId && !stockLoading && (
|
|
136
|
+
<p className="mt-2 text-xs text-text-secondary" role="status">
|
|
137
|
+
{stockHintText(totalAvailable, levels)}
|
|
138
|
+
</p>
|
|
139
|
+
)}
|
|
157
140
|
</div>
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
141
|
+
|
|
142
|
+
<div className="grid grid-cols-1 gap-4 sm:grid-cols-2 lg:grid-cols-12">
|
|
143
|
+
<div className="space-y-2 lg:col-span-4">
|
|
144
|
+
<Label htmlFor={`item-name-${item.id}`}>Item name</Label>
|
|
145
|
+
<Input
|
|
146
|
+
id={`item-name-${item.id}`}
|
|
147
|
+
value={item.name}
|
|
148
|
+
onChange={(e: ChangeEvent<HTMLInputElement>) =>
|
|
149
|
+
onUpdate(index, 'name', e.target.value)
|
|
150
|
+
}
|
|
151
|
+
placeholder="Product name"
|
|
152
|
+
/>
|
|
153
|
+
</div>
|
|
154
|
+
<div className="space-y-2 lg:col-span-3">
|
|
155
|
+
<Label htmlFor={`item-sku-${item.id}`}>SKU</Label>
|
|
156
|
+
<Input
|
|
157
|
+
id={`item-sku-${item.id}`}
|
|
158
|
+
value={item.sku}
|
|
159
|
+
onChange={(e: ChangeEvent<HTMLInputElement>) =>
|
|
160
|
+
onUpdate(index, 'sku', e.target.value)
|
|
161
|
+
}
|
|
162
|
+
placeholder="SKU-001"
|
|
163
|
+
/>
|
|
164
|
+
</div>
|
|
165
|
+
<div className="space-y-2 lg:col-span-2">
|
|
166
|
+
<Label htmlFor={`item-quantity-${item.id}`}>Quantity</Label>
|
|
167
|
+
<Input
|
|
168
|
+
id={`item-quantity-${item.id}`}
|
|
169
|
+
type="number"
|
|
170
|
+
min="1"
|
|
171
|
+
value={item.quantity}
|
|
172
|
+
onChange={(e: ChangeEvent<HTMLInputElement>) =>
|
|
173
|
+
onUpdate(index, 'quantity', parseInt(e.target.value, 10) || 1)
|
|
174
|
+
}
|
|
175
|
+
/>
|
|
176
|
+
</div>
|
|
177
|
+
<div className="space-y-2 lg:col-span-2">
|
|
178
|
+
<Label htmlFor={`item-weight-${item.id}`}>Weight (kg)</Label>
|
|
179
|
+
<Input
|
|
180
|
+
id={`item-weight-${item.id}`}
|
|
181
|
+
type="number"
|
|
182
|
+
min="0"
|
|
183
|
+
step="0.1"
|
|
184
|
+
value={item.weight}
|
|
185
|
+
onChange={(e: ChangeEvent<HTMLInputElement>) =>
|
|
186
|
+
onUpdate(index, 'weight', parseFloat(e.target.value) || 0)
|
|
187
|
+
}
|
|
188
|
+
/>
|
|
189
|
+
</div>
|
|
190
|
+
<div className="space-y-2 lg:col-span-1">
|
|
191
|
+
<Label htmlFor={`item-value-${item.id}`}>Value ($)</Label>
|
|
192
|
+
<Input
|
|
193
|
+
id={`item-value-${item.id}`}
|
|
194
|
+
type="number"
|
|
195
|
+
min="0"
|
|
196
|
+
step="0.01"
|
|
197
|
+
value={item.value}
|
|
198
|
+
onChange={(e: ChangeEvent<HTMLInputElement>) =>
|
|
199
|
+
onUpdate(index, 'value', parseFloat(e.target.value) || 0)
|
|
200
|
+
}
|
|
201
|
+
/>
|
|
202
|
+
</div>
|
|
168
203
|
</div>
|
|
204
|
+
|
|
205
|
+
<fieldset className="rounded-card border border-border-subtle bg-bg-sunken/40 p-3 sm:p-4">
|
|
206
|
+
<legend className="px-1 text-xs font-medium text-text-secondary">
|
|
207
|
+
Dimensions ({dimensions.unit})
|
|
208
|
+
</legend>
|
|
209
|
+
<div className="grid grid-cols-1 gap-4 sm:grid-cols-3">
|
|
210
|
+
{(['length', 'width', 'height'] as const).map((field) => (
|
|
211
|
+
<div key={field} className="space-y-2">
|
|
212
|
+
<Label htmlFor={`item-${field}-${item.id}`}>
|
|
213
|
+
{field.charAt(0).toUpperCase() + field.slice(1)}
|
|
214
|
+
</Label>
|
|
215
|
+
<Input
|
|
216
|
+
id={`item-${field}-${item.id}`}
|
|
217
|
+
type="number"
|
|
218
|
+
min="0"
|
|
219
|
+
step="0.1"
|
|
220
|
+
value={dimensions[field]}
|
|
221
|
+
onChange={(e: ChangeEvent<HTMLInputElement>) =>
|
|
222
|
+
updateDimension(field, e.target.value)
|
|
223
|
+
}
|
|
224
|
+
/>
|
|
225
|
+
</div>
|
|
226
|
+
))}
|
|
227
|
+
</div>
|
|
228
|
+
<p className="mt-2 text-xs text-text-secondary">
|
|
229
|
+
Catalog selections prefill these measurements, and you can adjust them for this order.
|
|
230
|
+
</p>
|
|
231
|
+
</fieldset>
|
|
169
232
|
</div>
|
|
170
233
|
</div>
|
|
171
234
|
);
|
|
@@ -155,10 +155,14 @@ const ORDER_STATS_QUERY = `
|
|
|
155
155
|
deliveryJobStats {
|
|
156
156
|
total
|
|
157
157
|
pending
|
|
158
|
+
confirmed
|
|
159
|
+
assigned
|
|
158
160
|
inTransit
|
|
161
|
+
outForDelivery
|
|
159
162
|
delivered
|
|
160
163
|
cancelled
|
|
161
164
|
failed
|
|
165
|
+
returned
|
|
162
166
|
}
|
|
163
167
|
financeMetrics {
|
|
164
168
|
revenue {
|
|
@@ -221,6 +225,8 @@ export function mapOrderStatus(status: string): OrderStatus {
|
|
|
221
225
|
return 'out_for_delivery';
|
|
222
226
|
case 'DELIVERED':
|
|
223
227
|
return 'delivered';
|
|
228
|
+
case 'RETURNED':
|
|
229
|
+
return 'returned';
|
|
224
230
|
case 'CANCELLED':
|
|
225
231
|
return 'cancelled';
|
|
226
232
|
default:
|
|
@@ -263,6 +269,8 @@ function toApiStatus(status: OrderStatus): string {
|
|
|
263
269
|
return 'OUT_FOR_DELIVERY';
|
|
264
270
|
case 'delivered':
|
|
265
271
|
return 'DELIVERED';
|
|
272
|
+
case 'returned':
|
|
273
|
+
return 'RETURNED';
|
|
266
274
|
case 'cancelled':
|
|
267
275
|
return 'CANCELLED';
|
|
268
276
|
default:
|
|
@@ -593,6 +601,7 @@ export function useOrderStats() {
|
|
|
593
601
|
in_transit: 0,
|
|
594
602
|
out_for_delivery: 0,
|
|
595
603
|
delivered: 0,
|
|
604
|
+
returned: 0,
|
|
596
605
|
cancelled: 0,
|
|
597
606
|
failed: 0,
|
|
598
607
|
},
|
|
@@ -621,10 +630,14 @@ export function useOrderStats() {
|
|
|
621
630
|
deliveryJobStats: {
|
|
622
631
|
total: number;
|
|
623
632
|
pending: number;
|
|
633
|
+
confirmed: number;
|
|
634
|
+
assigned: number;
|
|
624
635
|
inTransit: number;
|
|
636
|
+
outForDelivery: number;
|
|
625
637
|
delivered: number;
|
|
626
638
|
cancelled: number;
|
|
627
639
|
failed: number;
|
|
640
|
+
returned: number;
|
|
628
641
|
};
|
|
629
642
|
financeMetrics: {
|
|
630
643
|
revenue: {
|
|
@@ -638,12 +651,13 @@ export function useOrderStats() {
|
|
|
638
651
|
total: data.deliveryJobStats.total,
|
|
639
652
|
byStatus: {
|
|
640
653
|
pending: data.deliveryJobStats.pending,
|
|
641
|
-
confirmed:
|
|
642
|
-
assigned:
|
|
654
|
+
confirmed: data.deliveryJobStats.confirmed,
|
|
655
|
+
assigned: data.deliveryJobStats.assigned,
|
|
643
656
|
picked_up: 0,
|
|
644
657
|
in_transit: data.deliveryJobStats.inTransit,
|
|
645
|
-
out_for_delivery:
|
|
658
|
+
out_for_delivery: data.deliveryJobStats.outForDelivery,
|
|
646
659
|
delivered: data.deliveryJobStats.delivered,
|
|
660
|
+
returned: data.deliveryJobStats.returned,
|
|
647
661
|
cancelled: data.deliveryJobStats.cancelled,
|
|
648
662
|
failed: data.deliveryJobStats.failed,
|
|
649
663
|
},
|