@propeller-commerce/propeller-v2-react-ui 0.13.0 → 0.15.0
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/CHANGELOG.md +64 -0
- package/MIGRATION.md +63 -0
- package/dist/index.cjs +153 -61
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +42 -19
- package/dist/index.d.ts +42 -19
- package/dist/index.js +154 -62
- package/dist/index.js.map +1 -1
- package/dist/styles.css +1 -1
- package/package.json +2 -2
package/dist/index.d.cts
CHANGED
|
@@ -1396,11 +1396,13 @@ interface UseProductSearchOptions {
|
|
|
1396
1396
|
/** Upper price bound filter. */
|
|
1397
1397
|
priceFilterMax?: number;
|
|
1398
1398
|
/**
|
|
1399
|
-
* Stock
|
|
1400
|
-
*
|
|
1399
|
+
* Stock selection to filter by. `'all'` or unset sends no stock filter.
|
|
1400
|
+
* Filtering happens server-side, so `itemsFound` and the page count
|
|
1401
1401
|
* describe the filtered set.
|
|
1402
1402
|
*/
|
|
1403
|
-
availability?: Availability
|
|
1403
|
+
availability?: Availability;
|
|
1404
|
+
/** Minimum stock quantity for the `'in-stock'` selection. */
|
|
1405
|
+
minStock?: number;
|
|
1404
1406
|
/** Sort field; overrides the internal sort state when set. */
|
|
1405
1407
|
sortField?: string;
|
|
1406
1408
|
/** Sort direction (`'ASC'` / `'DESC'`); overrides internal state when set. */
|
|
@@ -4635,12 +4637,14 @@ interface GridFiltersProps {
|
|
|
4635
4637
|
*/
|
|
4636
4638
|
showAvailabilityFilter?: boolean;
|
|
4637
4639
|
/**
|
|
4638
|
-
* Currently active availability
|
|
4639
|
-
* on the first render so a restored filtered URL renders
|
|
4640
|
+
* Currently active availability selection (URL-driven). Seeds the toggle
|
|
4641
|
+
* on the first render so a restored filtered URL renders it correctly.
|
|
4640
4642
|
*/
|
|
4641
|
-
activeAvailability?: Availability
|
|
4642
|
-
/**
|
|
4643
|
-
|
|
4643
|
+
activeAvailability?: Availability;
|
|
4644
|
+
/** Currently active minimum stock quantity (URL-driven). Undefined means the minimum. */
|
|
4645
|
+
activeMinStock?: number;
|
|
4646
|
+
/** Called on every toggle or stepper change with both values. */
|
|
4647
|
+
onAvailabilityChange?: (sel: Availability, minStock: number) => void;
|
|
4644
4648
|
/**
|
|
4645
4649
|
* When true, all checkboxes and price inputs are disabled.
|
|
4646
4650
|
* Wire to ProductGrid's `onLoadingChange` to block rapid re-clicks while a fetch is in flight.
|
|
@@ -4826,15 +4830,14 @@ interface GridToolbarProps {
|
|
|
4826
4830
|
*/
|
|
4827
4831
|
onPriceFilterRemove?: () => void;
|
|
4828
4832
|
/**
|
|
4829
|
-
* Currently active availability (stock)
|
|
4830
|
-
* Renders
|
|
4833
|
+
* Currently active availability (stock) selection.
|
|
4834
|
+
* Renders a single removable chip when set to `'in-stock'`.
|
|
4831
4835
|
*/
|
|
4832
|
-
availability?: Availability
|
|
4833
|
-
/**
|
|
4834
|
-
|
|
4835
|
-
|
|
4836
|
-
|
|
4837
|
-
onAvailabilityFilterRemove?: (value: Availability) => void;
|
|
4836
|
+
availability?: Availability;
|
|
4837
|
+
/** Currently active minimum stock quantity, shown on the chip above the default. */
|
|
4838
|
+
minStock?: number;
|
|
4839
|
+
/** Called when the availability filter badge × is clicked. */
|
|
4840
|
+
onAvailabilityFilterRemove?: () => void;
|
|
4838
4841
|
/**
|
|
4839
4842
|
* Called when "Clear All" is clicked.
|
|
4840
4843
|
*/
|
|
@@ -5278,6 +5281,10 @@ interface OrderListProps {
|
|
|
5278
5281
|
showCompanyOrders?: boolean;
|
|
5279
5282
|
/** Hide pagination controls. Defaults to false. */
|
|
5280
5283
|
hidePagination?: boolean;
|
|
5284
|
+
/** Hide the column header row. Defaults to false. */
|
|
5285
|
+
hideHeader?: boolean;
|
|
5286
|
+
/** Drop the results container's card chrome (background/border/shadow). Defaults to false. */
|
|
5287
|
+
flat?: boolean;
|
|
5281
5288
|
/** Filter orders by channel IDs */
|
|
5282
5289
|
channelIds?: number[];
|
|
5283
5290
|
/** Format price */
|
|
@@ -6229,10 +6236,12 @@ interface ProductGridProps {
|
|
|
6229
6236
|
/** * Active price range lower bound from the FiltersSidebar `onPriceChange`. * Triggers a re-fetch when changed. */ priceFilterMin?: number;
|
|
6230
6237
|
/** * Active price range upper bound from the FiltersSidebar `onPriceChange`. * Triggers a re-fetch when changed. */ priceFilterMax?: number;
|
|
6231
6238
|
/**
|
|
6232
|
-
* Active stock
|
|
6233
|
-
* changed.
|
|
6239
|
+
* Active stock selection from the filters sidebar. Triggers a re-fetch when
|
|
6240
|
+
* changed. `'all'` or undefined means no stock filter.
|
|
6234
6241
|
*/
|
|
6235
|
-
availability?: Availability
|
|
6242
|
+
availability?: Availability;
|
|
6243
|
+
/** Minimum stock quantity for the `'in-stock'` selection. Defaults to the minimum threshold. */
|
|
6244
|
+
minStock?: number;
|
|
6236
6245
|
/** * Called when sort state changes internally (for syncing a sibling toolbar). */ onSortChange?: (field: string, order: string) => void;
|
|
6237
6246
|
/** * Called after each internal data fetch with the min/max price of the * current product set — use to populate a price range slider in the parent. */ onPriceBoundsChange?: (min: number, max: number) => void;
|
|
6238
6247
|
/** * Called after each fetch with the total number of products found — * use to display a result count in the parent toolbar. */ onItemsFoundChange?: (count: number) => void;
|
|
@@ -7048,6 +7057,20 @@ interface PurchaseAuthorizationRequestsProps {
|
|
|
7048
7057
|
user?: Contact | Customer;
|
|
7049
7058
|
/** The companyId of the current selected company. Resolved from PropellerProvider when omitted. */
|
|
7050
7059
|
companyId?: number;
|
|
7060
|
+
/** Limit the number of requests shown (e.g. 3 = last 3 modified). undefined = show all */
|
|
7061
|
+
limit?: number;
|
|
7062
|
+
/** Columns to display, in order. Keys: 'date' | 'quantity' | 'total' | 'requestedBy' | 'action'. Defaults to all five. */
|
|
7063
|
+
columns?: string[];
|
|
7064
|
+
/** Label mapping for columns */
|
|
7065
|
+
columnConfig?: Record<string, string>;
|
|
7066
|
+
/** Show the actions column and its buttons. Defaults to true. */
|
|
7067
|
+
showActions?: boolean;
|
|
7068
|
+
/** Hide the column header row. Defaults to false. */
|
|
7069
|
+
hideHeader?: boolean;
|
|
7070
|
+
/** Drop the results container's card chrome (background/border/shadow). Defaults to false. */
|
|
7071
|
+
flat?: boolean;
|
|
7072
|
+
/** Hide the component's own title. Defaults to false. */
|
|
7073
|
+
hideTitle?: boolean;
|
|
7051
7074
|
/**
|
|
7052
7075
|
* Override: fires instead of the default CartService.acceptPurchaseAuthorizationRequest() call.
|
|
7053
7076
|
* Receives the cartId string.
|
package/dist/index.d.ts
CHANGED
|
@@ -1396,11 +1396,13 @@ interface UseProductSearchOptions {
|
|
|
1396
1396
|
/** Upper price bound filter. */
|
|
1397
1397
|
priceFilterMax?: number;
|
|
1398
1398
|
/**
|
|
1399
|
-
* Stock
|
|
1400
|
-
*
|
|
1399
|
+
* Stock selection to filter by. `'all'` or unset sends no stock filter.
|
|
1400
|
+
* Filtering happens server-side, so `itemsFound` and the page count
|
|
1401
1401
|
* describe the filtered set.
|
|
1402
1402
|
*/
|
|
1403
|
-
availability?: Availability
|
|
1403
|
+
availability?: Availability;
|
|
1404
|
+
/** Minimum stock quantity for the `'in-stock'` selection. */
|
|
1405
|
+
minStock?: number;
|
|
1404
1406
|
/** Sort field; overrides the internal sort state when set. */
|
|
1405
1407
|
sortField?: string;
|
|
1406
1408
|
/** Sort direction (`'ASC'` / `'DESC'`); overrides internal state when set. */
|
|
@@ -4635,12 +4637,14 @@ interface GridFiltersProps {
|
|
|
4635
4637
|
*/
|
|
4636
4638
|
showAvailabilityFilter?: boolean;
|
|
4637
4639
|
/**
|
|
4638
|
-
* Currently active availability
|
|
4639
|
-
* on the first render so a restored filtered URL renders
|
|
4640
|
+
* Currently active availability selection (URL-driven). Seeds the toggle
|
|
4641
|
+
* on the first render so a restored filtered URL renders it correctly.
|
|
4640
4642
|
*/
|
|
4641
|
-
activeAvailability?: Availability
|
|
4642
|
-
/**
|
|
4643
|
-
|
|
4643
|
+
activeAvailability?: Availability;
|
|
4644
|
+
/** Currently active minimum stock quantity (URL-driven). Undefined means the minimum. */
|
|
4645
|
+
activeMinStock?: number;
|
|
4646
|
+
/** Called on every toggle or stepper change with both values. */
|
|
4647
|
+
onAvailabilityChange?: (sel: Availability, minStock: number) => void;
|
|
4644
4648
|
/**
|
|
4645
4649
|
* When true, all checkboxes and price inputs are disabled.
|
|
4646
4650
|
* Wire to ProductGrid's `onLoadingChange` to block rapid re-clicks while a fetch is in flight.
|
|
@@ -4826,15 +4830,14 @@ interface GridToolbarProps {
|
|
|
4826
4830
|
*/
|
|
4827
4831
|
onPriceFilterRemove?: () => void;
|
|
4828
4832
|
/**
|
|
4829
|
-
* Currently active availability (stock)
|
|
4830
|
-
* Renders
|
|
4833
|
+
* Currently active availability (stock) selection.
|
|
4834
|
+
* Renders a single removable chip when set to `'in-stock'`.
|
|
4831
4835
|
*/
|
|
4832
|
-
availability?: Availability
|
|
4833
|
-
/**
|
|
4834
|
-
|
|
4835
|
-
|
|
4836
|
-
|
|
4837
|
-
onAvailabilityFilterRemove?: (value: Availability) => void;
|
|
4836
|
+
availability?: Availability;
|
|
4837
|
+
/** Currently active minimum stock quantity, shown on the chip above the default. */
|
|
4838
|
+
minStock?: number;
|
|
4839
|
+
/** Called when the availability filter badge × is clicked. */
|
|
4840
|
+
onAvailabilityFilterRemove?: () => void;
|
|
4838
4841
|
/**
|
|
4839
4842
|
* Called when "Clear All" is clicked.
|
|
4840
4843
|
*/
|
|
@@ -5278,6 +5281,10 @@ interface OrderListProps {
|
|
|
5278
5281
|
showCompanyOrders?: boolean;
|
|
5279
5282
|
/** Hide pagination controls. Defaults to false. */
|
|
5280
5283
|
hidePagination?: boolean;
|
|
5284
|
+
/** Hide the column header row. Defaults to false. */
|
|
5285
|
+
hideHeader?: boolean;
|
|
5286
|
+
/** Drop the results container's card chrome (background/border/shadow). Defaults to false. */
|
|
5287
|
+
flat?: boolean;
|
|
5281
5288
|
/** Filter orders by channel IDs */
|
|
5282
5289
|
channelIds?: number[];
|
|
5283
5290
|
/** Format price */
|
|
@@ -6229,10 +6236,12 @@ interface ProductGridProps {
|
|
|
6229
6236
|
/** * Active price range lower bound from the FiltersSidebar `onPriceChange`. * Triggers a re-fetch when changed. */ priceFilterMin?: number;
|
|
6230
6237
|
/** * Active price range upper bound from the FiltersSidebar `onPriceChange`. * Triggers a re-fetch when changed. */ priceFilterMax?: number;
|
|
6231
6238
|
/**
|
|
6232
|
-
* Active stock
|
|
6233
|
-
* changed.
|
|
6239
|
+
* Active stock selection from the filters sidebar. Triggers a re-fetch when
|
|
6240
|
+
* changed. `'all'` or undefined means no stock filter.
|
|
6234
6241
|
*/
|
|
6235
|
-
availability?: Availability
|
|
6242
|
+
availability?: Availability;
|
|
6243
|
+
/** Minimum stock quantity for the `'in-stock'` selection. Defaults to the minimum threshold. */
|
|
6244
|
+
minStock?: number;
|
|
6236
6245
|
/** * Called when sort state changes internally (for syncing a sibling toolbar). */ onSortChange?: (field: string, order: string) => void;
|
|
6237
6246
|
/** * Called after each internal data fetch with the min/max price of the * current product set — use to populate a price range slider in the parent. */ onPriceBoundsChange?: (min: number, max: number) => void;
|
|
6238
6247
|
/** * Called after each fetch with the total number of products found — * use to display a result count in the parent toolbar. */ onItemsFoundChange?: (count: number) => void;
|
|
@@ -7048,6 +7057,20 @@ interface PurchaseAuthorizationRequestsProps {
|
|
|
7048
7057
|
user?: Contact | Customer;
|
|
7049
7058
|
/** The companyId of the current selected company. Resolved from PropellerProvider when omitted. */
|
|
7050
7059
|
companyId?: number;
|
|
7060
|
+
/** Limit the number of requests shown (e.g. 3 = last 3 modified). undefined = show all */
|
|
7061
|
+
limit?: number;
|
|
7062
|
+
/** Columns to display, in order. Keys: 'date' | 'quantity' | 'total' | 'requestedBy' | 'action'. Defaults to all five. */
|
|
7063
|
+
columns?: string[];
|
|
7064
|
+
/** Label mapping for columns */
|
|
7065
|
+
columnConfig?: Record<string, string>;
|
|
7066
|
+
/** Show the actions column and its buttons. Defaults to true. */
|
|
7067
|
+
showActions?: boolean;
|
|
7068
|
+
/** Hide the column header row. Defaults to false. */
|
|
7069
|
+
hideHeader?: boolean;
|
|
7070
|
+
/** Drop the results container's card chrome (background/border/shadow). Defaults to false. */
|
|
7071
|
+
flat?: boolean;
|
|
7072
|
+
/** Hide the component's own title. Defaults to false. */
|
|
7073
|
+
hideTitle?: boolean;
|
|
7051
7074
|
/**
|
|
7052
7075
|
* Override: fires instead of the default CartService.acceptPurchaseAuthorizationRequest() call.
|
|
7053
7076
|
* Receives the cartId string.
|
package/dist/index.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
"use client";
|
|
2
|
-
import { getLabel, getLocalizedValue, formatPrice, getClusterSku, getClusterImageUrl, isContentHidden, getProductSku, getProductImageUrl, createServices, err, ok, formatSurcharge, deriveUserMode, isContact, isCustomer, getAddresses, attributeNameMatches, getAttributeDisplayName, filterProductsBySelections, extractAttributeValues, buildInventoryFilter, getLanguageString, collectAttributeValues, getCountryName } from '@propeller-commerce/propeller-v2-core-ui';
|
|
2
|
+
import { getLabel, getLocalizedValue, formatPrice, getClusterSku, getClusterImageUrl, isContentHidden, getProductSku, getProductImageUrl, createServices, err, ok, formatSurcharge, deriveUserMode, isContact, isCustomer, getAddresses, attributeNameMatches, getAttributeDisplayName, filterProductsBySelections, extractAttributeValues, buildInventoryFilter, MIN_STOCK_THRESHOLD, getLanguageString, collectAttributeValues, getCountryName } from '@propeller-commerce/propeller-v2-core-ui';
|
|
3
3
|
export * from '@propeller-commerce/propeller-v2-core-ui';
|
|
4
4
|
import * as React6 from 'react';
|
|
5
5
|
import { createContext, useState, useRef, useMemo, useCallback, useContext, useEffect } from 'react';
|
|
@@ -2242,7 +2242,8 @@ function useProductSearch(options) {
|
|
|
2242
2242
|
JSON.stringify(options.textFilters ?? []),
|
|
2243
2243
|
options.priceFilterMin ?? "",
|
|
2244
2244
|
options.priceFilterMax ?? "",
|
|
2245
|
-
|
|
2245
|
+
options.availability ?? "",
|
|
2246
|
+
options.minStock ?? ""
|
|
2246
2247
|
].join("|");
|
|
2247
2248
|
if (inflightFetches2.has(inflightKey)) {
|
|
2248
2249
|
fetchIdRef.current--;
|
|
@@ -2284,7 +2285,7 @@ function useProductSearch(options) {
|
|
|
2284
2285
|
}
|
|
2285
2286
|
] : [];
|
|
2286
2287
|
const priceFilter = options.priceFilterMin !== void 0 || options.priceFilterMax !== void 0 ? { from: options.priceFilterMin ?? 0, to: options.priceFilterMax ?? 999999 } : void 0;
|
|
2287
|
-
const inventoryFilter = buildInventoryFilter(options.availability);
|
|
2288
|
+
const inventoryFilter = buildInventoryFilter(options.availability, options.minStock);
|
|
2288
2289
|
const userId = options.user && "contactId" in options.user ? options.user.contactId : options.user && "customerId" in options.user ? options.user.customerId : void 0;
|
|
2289
2290
|
const contactId = options.user && "contactId" in options.user ? options.user.contactId : void 0;
|
|
2290
2291
|
const customerId = options.user && "customerId" in options.user ? options.user.customerId : void 0;
|
|
@@ -2385,6 +2386,7 @@ function useProductSearch(options) {
|
|
|
2385
2386
|
options.priceFilterMin,
|
|
2386
2387
|
options.priceFilterMax,
|
|
2387
2388
|
options.availability,
|
|
2389
|
+
options.minStock,
|
|
2388
2390
|
options.sortField,
|
|
2389
2391
|
options.sortOrder,
|
|
2390
2392
|
options.companyId,
|
|
@@ -2424,7 +2426,7 @@ function useProductSearch(options) {
|
|
|
2424
2426
|
const userId = options.user && "contactId" in options.user ? options.user.contactId : options.user && "customerId" in options.user ? options.user.customerId : void 0;
|
|
2425
2427
|
const contactId = options.user && "contactId" in options.user ? options.user.contactId : void 0;
|
|
2426
2428
|
const customerId = options.user && "customerId" in options.user ? options.user.customerId : void 0;
|
|
2427
|
-
const inventoryFilter = buildInventoryFilter(options.availability);
|
|
2429
|
+
const inventoryFilter = buildInventoryFilter(options.availability, options.minStock);
|
|
2428
2430
|
const categoryProductSearchInput = {
|
|
2429
2431
|
language,
|
|
2430
2432
|
page: 1,
|
|
@@ -2517,6 +2519,7 @@ function useProductSearch(options) {
|
|
|
2517
2519
|
options.priceFilterMin,
|
|
2518
2520
|
options.priceFilterMax,
|
|
2519
2521
|
options.availability,
|
|
2522
|
+
options.minStock,
|
|
2520
2523
|
options.sortField,
|
|
2521
2524
|
options.sortOrder,
|
|
2522
2525
|
pageSize,
|
|
@@ -9040,6 +9043,7 @@ function ProductGrid(rawProps) {
|
|
|
9040
9043
|
priceFilterMin: props.priceFilterMin,
|
|
9041
9044
|
priceFilterMax: props.priceFilterMax,
|
|
9042
9045
|
availability: props.availability,
|
|
9046
|
+
minStock: props.minStock,
|
|
9043
9047
|
sortField: props.sortField,
|
|
9044
9048
|
sortOrder: props.sortOrder,
|
|
9045
9049
|
pageSize: props.pageSize,
|
|
@@ -9343,7 +9347,13 @@ function GridFilters(rawProps) {
|
|
|
9343
9347
|
const [appliedMin, setAppliedMin] = useState(() => void 0);
|
|
9344
9348
|
const [appliedMax, setAppliedMax] = useState(() => void 0);
|
|
9345
9349
|
const [availability, setAvailability] = useState(
|
|
9346
|
-
() =>
|
|
9350
|
+
() => props.activeAvailability || "all"
|
|
9351
|
+
);
|
|
9352
|
+
const [minStock, setMinStock] = useState(
|
|
9353
|
+
() => props.activeMinStock ?? MIN_STOCK_THRESHOLD
|
|
9354
|
+
);
|
|
9355
|
+
const [minStockInput, setMinStockInput] = useState(
|
|
9356
|
+
() => String(props.activeMinStock ?? MIN_STOCK_THRESHOLD)
|
|
9347
9357
|
);
|
|
9348
9358
|
function showPriceFilter() {
|
|
9349
9359
|
const mode = props.portalMode || "open";
|
|
@@ -9398,13 +9408,28 @@ function GridFilters(rawProps) {
|
|
|
9398
9408
|
props.onFilterChange(filter, value);
|
|
9399
9409
|
if (props.getSelectedFilters) props.getSelectedFilters();
|
|
9400
9410
|
}
|
|
9401
|
-
function
|
|
9402
|
-
const
|
|
9403
|
-
setAvailability(
|
|
9411
|
+
function handleAvailabilityChange(value) {
|
|
9412
|
+
const nextMinStock = value === "all" ? MIN_STOCK_THRESHOLD : minStock;
|
|
9413
|
+
setAvailability(value);
|
|
9414
|
+
setMinStock(nextMinStock);
|
|
9415
|
+
setMinStockInput(String(nextMinStock));
|
|
9416
|
+
setIsPending(true);
|
|
9417
|
+
if (props.onAvailabilityChange) props.onAvailabilityChange(value, nextMinStock);
|
|
9418
|
+
if (props.getSelectedFilters) props.getSelectedFilters();
|
|
9419
|
+
}
|
|
9420
|
+
function handleMinStockChange(value) {
|
|
9421
|
+
const n = Math.max(Math.floor(value) || MIN_STOCK_THRESHOLD, MIN_STOCK_THRESHOLD);
|
|
9422
|
+
setMinStock(n);
|
|
9423
|
+
setMinStockInput(String(n));
|
|
9424
|
+
if (n === minStock) return;
|
|
9404
9425
|
setIsPending(true);
|
|
9405
|
-
if (props.onAvailabilityChange) props.onAvailabilityChange(
|
|
9426
|
+
if (props.onAvailabilityChange) props.onAvailabilityChange(availability, n);
|
|
9406
9427
|
if (props.getSelectedFilters) props.getSelectedFilters();
|
|
9407
9428
|
}
|
|
9429
|
+
function commitMinStockInput() {
|
|
9430
|
+
const parsed = parseInt(minStockInput, 10);
|
|
9431
|
+
handleMinStockChange(isNaN(parsed) ? MIN_STOCK_THRESHOLD : parsed);
|
|
9432
|
+
}
|
|
9408
9433
|
function handleMinChange(value) {
|
|
9409
9434
|
const n = value > currentMax ? currentMax : value;
|
|
9410
9435
|
setCurrentMin(n);
|
|
@@ -9478,7 +9503,9 @@ function GridFilters(rawProps) {
|
|
|
9478
9503
|
setCurrentMin(props.priceMin || 0);
|
|
9479
9504
|
setCurrentMax(props.priceMax || 9999);
|
|
9480
9505
|
setExpandedFilters({});
|
|
9481
|
-
setAvailability(
|
|
9506
|
+
setAvailability("all");
|
|
9507
|
+
setMinStock(MIN_STOCK_THRESHOLD);
|
|
9508
|
+
setMinStockInput(String(MIN_STOCK_THRESHOLD));
|
|
9482
9509
|
}, [props.clearSignal, props.priceMin, props.priceMax]);
|
|
9483
9510
|
useEffect(() => {
|
|
9484
9511
|
if (!props.activeTextFilters) return;
|
|
@@ -9486,8 +9513,10 @@ function GridFilters(rawProps) {
|
|
|
9486
9513
|
}, [props.activeTextFilters]);
|
|
9487
9514
|
useEffect(() => {
|
|
9488
9515
|
if (!props.activeAvailability) return;
|
|
9489
|
-
setAvailability(
|
|
9490
|
-
|
|
9516
|
+
setAvailability(props.activeAvailability);
|
|
9517
|
+
setMinStock(props.activeMinStock ?? MIN_STOCK_THRESHOLD);
|
|
9518
|
+
setMinStockInput(String(props.activeMinStock ?? MIN_STOCK_THRESHOLD));
|
|
9519
|
+
}, [props.activeAvailability, props.activeMinStock]);
|
|
9491
9520
|
useEffect(() => {
|
|
9492
9521
|
if (props.activePriceMin === void 0 && props.activePriceMax === void 0) {
|
|
9493
9522
|
setCurrentMin(props.priceMin || 0);
|
|
@@ -9590,34 +9619,76 @@ function GridFilters(rawProps) {
|
|
|
9590
9619
|
showAvailability() ? /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
9591
9620
|
/* @__PURE__ */ jsxs("div", { className: "propeller-grid-filters__availability space-y-3", children: [
|
|
9592
9621
|
/* @__PURE__ */ jsx("h3", { className: "propeller-grid-filters__availability-title text-xs font-semibold uppercase tracking-wide text-muted-foreground", children: getLabel(props.labels, "availability", "Availability") }),
|
|
9593
|
-
/* @__PURE__ */ jsxs("div", { className: "propeller-grid-filters__availability-
|
|
9594
|
-
/* @__PURE__ */
|
|
9622
|
+
/* @__PURE__ */ jsxs("div", { className: "propeller-grid-filters__availability-toggle inline-flex h-8 w-full rounded-control border border-input overflow-hidden", children: [
|
|
9623
|
+
/* @__PURE__ */ jsx(
|
|
9624
|
+
"button",
|
|
9625
|
+
{
|
|
9626
|
+
type: "button",
|
|
9627
|
+
className: `propeller-grid-filters__availability-option flex-1 text-xs font-medium transition-colors ${availability === "all" ? "bg-secondary text-secondary-foreground" : "bg-transparent text-muted-foreground hover:text-foreground"}`,
|
|
9628
|
+
"aria-pressed": availability === "all",
|
|
9629
|
+
disabled: !!props.isLoading,
|
|
9630
|
+
onClick: () => handleAvailabilityChange("all"),
|
|
9631
|
+
children: getLabel(props.labels, "allProducts", "All products")
|
|
9632
|
+
}
|
|
9633
|
+
),
|
|
9634
|
+
/* @__PURE__ */ jsx(
|
|
9635
|
+
"button",
|
|
9636
|
+
{
|
|
9637
|
+
type: "button",
|
|
9638
|
+
className: `propeller-grid-filters__availability-option flex-1 text-xs font-medium transition-colors ${availability === "in-stock" ? "bg-secondary text-secondary-foreground" : "bg-transparent text-muted-foreground hover:text-foreground"}`,
|
|
9639
|
+
"aria-pressed": availability === "in-stock",
|
|
9640
|
+
disabled: !!props.isLoading,
|
|
9641
|
+
onClick: () => handleAvailabilityChange("in-stock"),
|
|
9642
|
+
children: getLabel(props.labels, "inStock", "In stock")
|
|
9643
|
+
}
|
|
9644
|
+
)
|
|
9645
|
+
] }),
|
|
9646
|
+
availability === "in-stock" ? /* @__PURE__ */ jsxs("div", { className: "propeller-grid-filters__availability-quantity flex items-center gap-2 text-sm text-muted-foreground", children: [
|
|
9647
|
+
/* @__PURE__ */ jsx("span", { children: getLabel(props.labels, "atLeast", "at least") }),
|
|
9648
|
+
/* @__PURE__ */ jsxs("div", { className: "propeller-grid-filters__availability-stepper inline-flex items-center h-8 rounded-control border border-input bg-card overflow-hidden focus-within:ring-1 focus-within:ring-secondary", children: [
|
|
9595
9649
|
/* @__PURE__ */ jsx(
|
|
9596
|
-
"
|
|
9650
|
+
"button",
|
|
9597
9651
|
{
|
|
9598
|
-
type: "
|
|
9599
|
-
className: "propeller-grid-
|
|
9600
|
-
|
|
9601
|
-
disabled: !!props.isLoading,
|
|
9602
|
-
|
|
9652
|
+
type: "button",
|
|
9653
|
+
className: "propeller-grid-filters__quantity-decrease h-full w-8 flex items-center justify-center text-muted-foreground disabled:opacity-40 disabled:cursor-not-allowed hover:bg-accent hover:text-foreground transition-colors",
|
|
9654
|
+
"aria-label": getLabel(props.labels, "quantityDecrease", "Decrease quantity"),
|
|
9655
|
+
disabled: !!props.isLoading || minStock <= MIN_STOCK_THRESHOLD,
|
|
9656
|
+
onClick: () => handleMinStockChange(minStock - 1),
|
|
9657
|
+
children: "\u2212"
|
|
9603
9658
|
}
|
|
9604
9659
|
),
|
|
9605
|
-
/* @__PURE__ */ jsx("span", { className: "propeller-grid-filters__option-label flex-1 text-sm text-muted-foreground leading-none select-none group-hover:text-foreground", children: getLabel(props.labels, "inStock", "In stock") })
|
|
9606
|
-
] }),
|
|
9607
|
-
/* @__PURE__ */ jsxs("label", { className: "propeller-grid-filters__option flex items-center gap-2 cursor-pointer group", children: [
|
|
9608
9660
|
/* @__PURE__ */ jsx(
|
|
9609
9661
|
"input",
|
|
9610
9662
|
{
|
|
9611
|
-
type: "
|
|
9612
|
-
|
|
9613
|
-
|
|
9663
|
+
type: "number",
|
|
9664
|
+
inputMode: "numeric",
|
|
9665
|
+
className: "propeller-grid-filters__availability-quantity-input w-10 h-full px-0 text-center font-medium text-foreground bg-transparent border-0 focus:outline-none focus:ring-0 [appearance:textfield] [&::-webkit-outer-spin-button]:appearance-none [&::-webkit-inner-spin-button]:appearance-none",
|
|
9666
|
+
"aria-label": getLabel(props.labels, "atLeast", "at least"),
|
|
9667
|
+
min: MIN_STOCK_THRESHOLD,
|
|
9668
|
+
step: 1,
|
|
9669
|
+
value: minStockInput,
|
|
9614
9670
|
disabled: !!props.isLoading,
|
|
9615
|
-
onChange: (e) =>
|
|
9671
|
+
onChange: (e) => setMinStockInput(e.target.value),
|
|
9672
|
+
onBlur: () => commitMinStockInput(),
|
|
9673
|
+
onKeyDown: (e) => {
|
|
9674
|
+
if (e.key === "Enter") e.target.blur();
|
|
9675
|
+
}
|
|
9616
9676
|
}
|
|
9617
9677
|
),
|
|
9618
|
-
/* @__PURE__ */ jsx(
|
|
9619
|
-
|
|
9620
|
-
|
|
9678
|
+
/* @__PURE__ */ jsx(
|
|
9679
|
+
"button",
|
|
9680
|
+
{
|
|
9681
|
+
type: "button",
|
|
9682
|
+
className: "propeller-grid-filters__quantity-increase h-full w-8 flex items-center justify-center text-muted-foreground disabled:opacity-40 disabled:cursor-not-allowed hover:bg-accent hover:text-foreground transition-colors",
|
|
9683
|
+
"aria-label": getLabel(props.labels, "quantityIncrease", "Increase quantity"),
|
|
9684
|
+
disabled: !!props.isLoading,
|
|
9685
|
+
onClick: () => handleMinStockChange(minStock + 1),
|
|
9686
|
+
children: "+"
|
|
9687
|
+
}
|
|
9688
|
+
)
|
|
9689
|
+
] }),
|
|
9690
|
+
/* @__PURE__ */ jsx("span", { children: getLabel(props.labels, "pcs", "pcs") })
|
|
9691
|
+
] }) : null
|
|
9621
9692
|
] }),
|
|
9622
9693
|
/* @__PURE__ */ jsx("div", { className: "propeller-grid-filters__divider h-px bg-border-subtle" })
|
|
9623
9694
|
] }) : null,
|
|
@@ -9797,7 +9868,6 @@ var DEFAULT_LABELS = {
|
|
|
9797
9868
|
perPage: " per page",
|
|
9798
9869
|
price: "Price",
|
|
9799
9870
|
inStock: "In stock",
|
|
9800
|
-
outOfStock: "Out of stock",
|
|
9801
9871
|
switchToList: "Switch to list view",
|
|
9802
9872
|
switchToGrid: "Switch to grid view"
|
|
9803
9873
|
};
|
|
@@ -9826,7 +9896,7 @@ function GridToolbar(rawProps) {
|
|
|
9826
9896
|
const text = props.activeTextFilters || {};
|
|
9827
9897
|
const hasText = Object.keys(text).some((k) => (text[k] || []).length > 0);
|
|
9828
9898
|
const hasPrice = props.priceFilterMin !== void 0 || props.priceFilterMax !== void 0;
|
|
9829
|
-
const hasAvailability =
|
|
9899
|
+
const hasAvailability = props.availability === "in-stock";
|
|
9830
9900
|
return hasText || hasPrice || hasAvailability;
|
|
9831
9901
|
}
|
|
9832
9902
|
function getActiveFilterBadges() {
|
|
@@ -9845,8 +9915,10 @@ function GridToolbar(rawProps) {
|
|
|
9845
9915
|
function isPriceSortDisabled() {
|
|
9846
9916
|
return isContentHidden(props.portalMode, props.user);
|
|
9847
9917
|
}
|
|
9848
|
-
function getAvailabilityLabel(
|
|
9849
|
-
|
|
9918
|
+
function getAvailabilityLabel() {
|
|
9919
|
+
const qty = props.minStock;
|
|
9920
|
+
if (qty !== void 0 && qty > MIN_STOCK_THRESHOLD) return `${getLabel56("inStock")}: ${qty}+`;
|
|
9921
|
+
return getLabel56("inStock");
|
|
9850
9922
|
}
|
|
9851
9923
|
function handleSortFieldChange(field) {
|
|
9852
9924
|
setCurrentSortField(field);
|
|
@@ -10021,20 +10093,19 @@ function GridToolbar(rawProps) {
|
|
|
10021
10093
|
]
|
|
10022
10094
|
}
|
|
10023
10095
|
) : null,
|
|
10024
|
-
|
|
10096
|
+
props.availability === "in-stock" ? /* @__PURE__ */ jsxs(
|
|
10025
10097
|
"span",
|
|
10026
10098
|
{
|
|
10027
10099
|
className: "propeller-grid-toolbar__filter-badge propeller-grid-toolbar__filter-badge--availability inline-flex items-center gap-1 cursor-pointer px-2.5 py-0.5 rounded-full text-xs font-semibold border border-input bg-background hover:bg-primary hover:text-primary-foreground hover:border-primary transition-colors",
|
|
10028
10100
|
onClick: (event) => {
|
|
10029
|
-
if (props.onAvailabilityFilterRemove) props.onAvailabilityFilterRemove(
|
|
10101
|
+
if (props.onAvailabilityFilterRemove) props.onAvailabilityFilterRemove();
|
|
10030
10102
|
},
|
|
10031
10103
|
children: [
|
|
10032
|
-
getAvailabilityLabel(
|
|
10104
|
+
getAvailabilityLabel(),
|
|
10033
10105
|
/* @__PURE__ */ jsx("span", { className: "propeller-grid-toolbar__filter-badge-remove", children: "\xD7" })
|
|
10034
10106
|
]
|
|
10035
|
-
}
|
|
10036
|
-
|
|
10037
|
-
)),
|
|
10107
|
+
}
|
|
10108
|
+
) : null,
|
|
10038
10109
|
getActiveFilterBadges()?.map((badge) => /* @__PURE__ */ jsxs(
|
|
10039
10110
|
"span",
|
|
10040
10111
|
{
|
|
@@ -13886,9 +13957,9 @@ function OrderList(rawProps) {
|
|
|
13886
13957
|
)
|
|
13887
13958
|
] })
|
|
13888
13959
|
] }) : null,
|
|
13889
|
-
!loading || orders.length > 0 ? /* @__PURE__ */ jsx(Fragment, { children: orders.length > 0 ? /* @__PURE__ */ jsxs("div", { className:
|
|
13960
|
+
!loading || orders.length > 0 ? /* @__PURE__ */ jsx(Fragment, { children: orders.length > 0 ? /* @__PURE__ */ jsxs("div", { className: `propeller-order-list__results${props.flat ? "" : " bg-card rounded-container shadow"} overflow-hidden`, children: [
|
|
13890
13961
|
/* @__PURE__ */ jsx("div", { className: "overflow-x-auto", children: /* @__PURE__ */ jsxs("table", { className: "propeller-order-list__table min-w-full divide-y divide-border", children: [
|
|
13891
|
-
/* @__PURE__ */ jsx("thead", { className: "propeller-order-list__thead bg-surface-hover", children: /* @__PURE__ */ jsx("tr", { children: columns?.map((col) => /* @__PURE__ */ jsx(
|
|
13962
|
+
!props.hideHeader ? /* @__PURE__ */ jsx("thead", { className: "propeller-order-list__thead bg-surface-hover", children: /* @__PURE__ */ jsx("tr", { children: columns?.map((col) => /* @__PURE__ */ jsx(
|
|
13892
13963
|
"th",
|
|
13893
13964
|
{
|
|
13894
13965
|
"data-column": col,
|
|
@@ -13896,7 +13967,7 @@ function OrderList(rawProps) {
|
|
|
13896
13967
|
children: getColumnLabel(col)
|
|
13897
13968
|
},
|
|
13898
13969
|
col
|
|
13899
|
-
)) }) }),
|
|
13970
|
+
)) }) }) : null,
|
|
13900
13971
|
/* @__PURE__ */ jsx("tbody", { className: "propeller-order-list__tbody bg-card divide-y divide-border", children: orders?.map((order) => /* @__PURE__ */ jsx(
|
|
13901
13972
|
"tr",
|
|
13902
13973
|
{
|
|
@@ -14003,7 +14074,7 @@ function OrderList(rawProps) {
|
|
|
14003
14074
|
) })
|
|
14004
14075
|
] })
|
|
14005
14076
|
] }) : null
|
|
14006
|
-
] }) : /* @__PURE__ */ jsx("div", { className:
|
|
14077
|
+
] }) : /* @__PURE__ */ jsx("div", { className: `propeller-order-list__empty${props.flat ? "" : " bg-card rounded-container shadow"} p-8 text-center`, children: /* @__PURE__ */ jsx("p", { className: "text-muted-foreground mb-4", children: getLabel(props.labels, "noOrders", "No orders found.") }) }) }) : /* @__PURE__ */ jsx("div", { className: "propeller-order-list__loading p-8 text-center text-muted-foreground", children: getLabel(props.labels, "loading", "Loading orders...") })
|
|
14007
14078
|
] });
|
|
14008
14079
|
}
|
|
14009
14080
|
var OrderList_default = OrderList;
|
|
@@ -17170,6 +17241,10 @@ function PurchaseAuthorizationConfigurator(rawProps) {
|
|
|
17170
17241
|
var PurchaseAuthorizationConfigurator_default = PurchaseAuthorizationConfigurator;
|
|
17171
17242
|
function PurchaseAuthorizationRequests(rawProps) {
|
|
17172
17243
|
const props = useInfraProps(rawProps);
|
|
17244
|
+
const showActions = props.showActions !== false;
|
|
17245
|
+
const columns = (props.columns || ["date", "quantity", "total", "requestedBy", "action"]).filter(
|
|
17246
|
+
(col) => showActions || col !== "action"
|
|
17247
|
+
);
|
|
17173
17248
|
const {
|
|
17174
17249
|
carts,
|
|
17175
17250
|
loading,
|
|
@@ -17203,6 +17278,17 @@ function PurchaseAuthorizationRequests(rawProps) {
|
|
|
17203
17278
|
await handleDeleteRequest();
|
|
17204
17279
|
setShowDeleteConfirm(false);
|
|
17205
17280
|
};
|
|
17281
|
+
const displayedCarts = useMemo(() => {
|
|
17282
|
+
if (props.limit && props.limit > 0) {
|
|
17283
|
+
const sorted = [...carts].sort((a, b) => {
|
|
17284
|
+
const dateA = new Date(a.lastModifiedAt || "").getTime();
|
|
17285
|
+
const dateB = new Date(b.lastModifiedAt || "").getTime();
|
|
17286
|
+
return dateB - dateA;
|
|
17287
|
+
});
|
|
17288
|
+
return sorted.slice(0, props.limit);
|
|
17289
|
+
}
|
|
17290
|
+
return carts;
|
|
17291
|
+
}, [carts, props.limit]);
|
|
17206
17292
|
function formatDate(dateStr) {
|
|
17207
17293
|
if (props.formatDate) return props.formatDate(dateStr);
|
|
17208
17294
|
if (!dateStr) return "-";
|
|
@@ -17216,6 +17302,18 @@ function PurchaseAuthorizationRequests(rawProps) {
|
|
|
17216
17302
|
if (props.formatPrice) return props.formatPrice(price);
|
|
17217
17303
|
return formatPrice(price, { symbol: props.currency ?? "\u20AC" });
|
|
17218
17304
|
}
|
|
17305
|
+
const columnLabelKeys = {
|
|
17306
|
+
date: ["colDate", "Date"],
|
|
17307
|
+
quantity: ["colQuantity", "Quantity"],
|
|
17308
|
+
total: ["colTotal", "Total"],
|
|
17309
|
+
requestedBy: ["colRequestedBy", "Requested by"],
|
|
17310
|
+
action: ["colActions", "Actions"]
|
|
17311
|
+
};
|
|
17312
|
+
function getColumnLabel(col) {
|
|
17313
|
+
if (props.columnConfig?.[col]) return props.columnConfig[col];
|
|
17314
|
+
const [key, fallback] = columnLabelKeys[col] || [col, col];
|
|
17315
|
+
return getLabel(props.labels, key, fallback);
|
|
17316
|
+
}
|
|
17219
17317
|
function getProductName5(item) {
|
|
17220
17318
|
const lang = props.language || "NL";
|
|
17221
17319
|
const fromNames = getLanguageString(item?.product?.names, lang, "");
|
|
@@ -17225,27 +17323,21 @@ function PurchaseAuthorizationRequests(rawProps) {
|
|
|
17225
17323
|
return item?.product?.sku || "";
|
|
17226
17324
|
}
|
|
17227
17325
|
return /* @__PURE__ */ jsx("div", { className: `propeller-purchase-authorization-requests ${props.className || ""}`, children: isAuthManager ? /* @__PURE__ */ jsxs("div", { className: "propeller-purchase-authorization-requests__content space-y-4", children: [
|
|
17228
|
-
/* @__PURE__ */ jsx("h2", { className: "propeller-purchase-authorization-requests__title text-xl font-semibold", children: getLabel(props.labels, "title", "Authorization Requests") }),
|
|
17326
|
+
!props.hideTitle ? /* @__PURE__ */ jsx("h2", { className: "propeller-purchase-authorization-requests__title text-xl font-semibold", children: getLabel(props.labels, "title", "Authorization Requests") }) : null,
|
|
17229
17327
|
loading ? /* @__PURE__ */ jsx("div", { className: "flex items-center justify-center py-12", children: /* @__PURE__ */ jsx("div", { className: "w-8 h-8 border-4 border-primary border-t-transparent rounded-full animate-spin" }) }) : null,
|
|
17230
17328
|
!loading ? /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
17231
17329
|
carts.length === 0 ? /* @__PURE__ */ jsx("div", { className: "text-center py-12 text-muted-foreground", children: getLabel(props.labels, "empty", "No pending authorization requests") }) : null,
|
|
17232
|
-
carts.length > 0 ? /* @__PURE__ */ jsx("div", { className:
|
|
17233
|
-
/* @__PURE__ */ jsx("thead", { className: "bg-muted/50 border-b border-border", children: /* @__PURE__ */
|
|
17234
|
-
|
|
17235
|
-
|
|
17236
|
-
|
|
17237
|
-
|
|
17238
|
-
/* @__PURE__ */
|
|
17239
|
-
] }) }),
|
|
17240
|
-
/* @__PURE__ */ jsx("tbody", { className: "divide-y divide-border", children: carts.map((cart, index) => /* @__PURE__ */ jsxs("tr", { className: "hover:bg-muted/30 transition-colors", children: [
|
|
17241
|
-
/* @__PURE__ */ jsx("td", { className: "px-4 py-3 text-muted-foreground", children: formatDate(cart.lastModifiedAt ?? "") }),
|
|
17242
|
-
/* @__PURE__ */ jsx("td", { className: "px-4 py-3", children: getTotalQuantity(cart) }),
|
|
17243
|
-
/* @__PURE__ */ jsx("td", { className: "px-4 py-3 font-medium", children: formatPrice17(cart.total?.totalNet ?? 0) }),
|
|
17244
|
-
/* @__PURE__ */ jsxs("td", { className: "px-4 py-3", children: [
|
|
17330
|
+
carts.length > 0 ? /* @__PURE__ */ jsx("div", { className: `propeller-purchase-authorization-requests__results overflow-x-auto${props.flat ? "" : " rounded-lg border border-border bg-card shadow-sm"}`, children: /* @__PURE__ */ jsxs("table", { className: "w-full text-sm", children: [
|
|
17331
|
+
!props.hideHeader ? /* @__PURE__ */ jsx("thead", { className: "bg-muted/50 border-b border-border", children: /* @__PURE__ */ jsx("tr", { children: columns.map((col) => /* @__PURE__ */ jsx("th", { className: "text-left px-4 py-3 font-medium text-muted-foreground", children: getColumnLabel(col) }, col)) }) }) : null,
|
|
17332
|
+
/* @__PURE__ */ jsx("tbody", { className: "divide-y divide-border", children: displayedCarts.map((cart, index) => /* @__PURE__ */ jsx("tr", { className: "hover:bg-muted/30 transition-colors", children: columns.map((col) => /* @__PURE__ */ jsxs("td", { className: `px-4 py-3${col === "date" ? " text-muted-foreground" : ""}${col === "total" ? " font-medium" : ""}`, children: [
|
|
17333
|
+
col === "date" ? formatDate(cart.lastModifiedAt ?? "") : null,
|
|
17334
|
+
col === "quantity" ? getTotalQuantity(cart) : null,
|
|
17335
|
+
col === "total" ? formatPrice17(cart.total?.totalNet ?? 0) : null,
|
|
17336
|
+
col === "requestedBy" ? /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
17245
17337
|
/* @__PURE__ */ jsx("div", { className: "font-medium", children: getContactName(cart.contact) }),
|
|
17246
17338
|
/* @__PURE__ */ jsx("div", { className: "text-xs text-muted-foreground mt-0.5", children: cart.contact?.email })
|
|
17247
|
-
] }),
|
|
17248
|
-
|
|
17339
|
+
] }) : null,
|
|
17340
|
+
col === "action" ? /* @__PURE__ */ jsx(
|
|
17249
17341
|
"button",
|
|
17250
17342
|
{
|
|
17251
17343
|
type: "button",
|
|
@@ -17253,8 +17345,8 @@ function PurchaseAuthorizationRequests(rawProps) {
|
|
|
17253
17345
|
onClick: () => handleViewCart(cart),
|
|
17254
17346
|
children: getLabel(props.labels, "view", "View")
|
|
17255
17347
|
}
|
|
17256
|
-
)
|
|
17257
|
-
] }, index)) })
|
|
17348
|
+
) : null
|
|
17349
|
+
] }, col)) }, index)) })
|
|
17258
17350
|
] }) }) : null
|
|
17259
17351
|
] }) : null,
|
|
17260
17352
|
selectedCart ? /* @__PURE__ */ jsxs("div", { className: "propeller-purchase-authorization-requests__modal fixed inset-0 z-50 flex items-center justify-center px-4", children: [
|