filters
This commit is contained in:
@@ -52,15 +52,23 @@ export function ProductsPanel({
|
||||
const [publishing, setPublishing] = useState<Product[] | null>(null);
|
||||
|
||||
/**
|
||||
* One branch, always.
|
||||
* The branch in scope, or all of them.
|
||||
*
|
||||
* `getlocationproducts` takes a single `locationid` and there is no
|
||||
* tenant-wide product read. Under "All branches" this reads the first.
|
||||
* Publishing is tenant-wide regardless, so the choice affects what is
|
||||
* LISTED, not what is changed.
|
||||
* `current` is undefined under "All branches", and that now means what it
|
||||
* says: `getlocationproducts` answers a tenant-wide read with one row per
|
||||
* product and stock summed across outlets.
|
||||
*
|
||||
* It used to fall back to `scoped[0]` — the FIRST branch — so "All branches"
|
||||
* listed one outlet's products and called them the catalogue. A merchant with
|
||||
* five outlets saw four products instead of six, and picking a single branch
|
||||
* showed MORE than picking all of them.
|
||||
*
|
||||
* Publishing is tenant-wide regardless, so this affects what is LISTED, not
|
||||
* what is changed.
|
||||
*/
|
||||
const branch = current ?? scoped[0];
|
||||
const products = useLocationProducts(tenantid || undefined, branch?.locationid, 0);
|
||||
const products = useLocationProducts(tenantid || undefined, current?.locationid, 0, {
|
||||
allBranches: true,
|
||||
});
|
||||
const categories = useTenantCategories(tenantid || undefined);
|
||||
|
||||
/**
|
||||
@@ -123,7 +131,12 @@ export function ProductsPanel({
|
||||
{isUploading ? (
|
||||
<SheetUploadDrawer
|
||||
tenantid={tenantid || undefined}
|
||||
locationid={branch?.locationid}
|
||||
/* `current`, never a fallback to the first branch. An upload becomes
|
||||
opening stock on ONE shelf, so under "All branches" there is no
|
||||
answer to guess — passing nothing leaves the drawer's own branch
|
||||
picker to ask, and it blocks the upload until it is answered.
|
||||
Defaulting here would load a shelf nobody chose. */
|
||||
locationid={current?.locationid}
|
||||
onClose={onCloseUpload}
|
||||
/>
|
||||
) : null}
|
||||
|
||||
@@ -166,20 +166,48 @@ export function useCatalogueProduct(brand: string | undefined, sku: string | und
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* A tenant's products, at one branch or across all of them.
|
||||
*
|
||||
* `locationid` of 0 or undefined means EVERY branch, and the backend answers it
|
||||
* — one row per product, stock summed across outlets. It did not always: the
|
||||
* read required a single branch, so "All branches" listed the FIRST one and a
|
||||
* merchant with five outlets saw four products at RS Puram instead of the six
|
||||
* they stock. Picking one branch showed more than picking all of them.
|
||||
*
|
||||
* So the tenant alone is enough to run this query now. Gating on `locationid`
|
||||
* is what turned a missing backend feature into a silently wrong list.
|
||||
*/
|
||||
export function useLocationProducts(
|
||||
tenantid: number | undefined,
|
||||
locationid: number | undefined,
|
||||
page = 0,
|
||||
options: {
|
||||
/**
|
||||
* Treat a missing branch as "every branch" rather than as "not ready yet".
|
||||
*
|
||||
* Off by default, and that default is the safe one. A Store user is pinned
|
||||
* to a single outlet and their branch resolves asynchronously — so during
|
||||
* that window an opt-out default would answer tenant-wide and show them
|
||||
* every other branch's stock as if it were their own.
|
||||
*
|
||||
* The admin catalogue opts in, because there "All branches" is a real
|
||||
* selection a merchant made, not a value that has not arrived.
|
||||
*/
|
||||
allBranches?: boolean;
|
||||
} = {},
|
||||
) {
|
||||
const wantsAll = options.allBranches === true;
|
||||
return useQuery({
|
||||
queryKey: queryKeys.products.byLocation(tenantid ?? 0, locationid ?? 0, page),
|
||||
queryFn: () =>
|
||||
productsApi.locationProducts({
|
||||
tenantid: tenantid as number,
|
||||
locationid: locationid as number,
|
||||
// 0 is meaningful to the backend here, not a missing value.
|
||||
locationid: locationid ?? 0,
|
||||
pageno: page,
|
||||
}),
|
||||
enabled: Boolean(tenantid) && Boolean(locationid),
|
||||
enabled: Boolean(tenantid) && (wantsAll || Boolean(locationid)),
|
||||
...live,
|
||||
});
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user