diff --git a/web/src/components/ProductDetail.tsx b/web/src/components/ProductDetail.tsx index 19a4cc8..ef37061 100644 --- a/web/src/components/ProductDetail.tsx +++ b/web/src/components/ProductDetail.tsx @@ -180,7 +180,31 @@ export function ProductDetail({ > {( [ - ["Price", fmt.money(product.price)], + [ + "Price", + product.kind === "discrete" && product.countOriginal > 0 ? ( + <> + {fmt.money(product.price / product.countOriginal)} + + /unit + +
+ {fmt.money(product.price)} total +
+ + ) : ( + fmt.money(product.price) + ), + ], [ product.kind === "discrete" ? "Quantity" : "Size", product.kind === "discrete" @@ -189,9 +213,9 @@ export function ProductDetail({ ], ["THC", `${product.thc.toFixed(1)}%`], ["CBD", `${product.cbd.toFixed(1)}%`], - ] as [string, string][] - ).map(([l, v]) => ( -
+ ] as [string, React.ReactNode][] + ).map(([l, v], i) => ( +
{l}
{v}
diff --git a/web/src/components/modals/AddProductFlow.tsx b/web/src/components/modals/AddProductFlow.tsx index f722ebb..e8a42c1 100644 --- a/web/src/components/modals/AddProductFlow.tsx +++ b/web/src/components/modals/AddProductFlow.tsx @@ -48,6 +48,8 @@ export function AddProductFlow({ data, onClose }: { data: Bootstrap; onClose: () const cfg = TYPES.find((t) => t.id === form.type); const isDiscrete = cfg?.kind === "discrete"; + // form.price is total for bulk, per-unit for discrete. + const totalPrice = isDiscrete ? form.price * form.countOriginal : form.price; const cpg = !isDiscrete && form.weight > 0 ? form.price / form.weight : 0; // Find an existing strain matching the current name + brand + type. @@ -107,6 +109,7 @@ export function AddProductFlow({ data, onClose }: { data: Bootstrap; onClose: () shopId, binId, kind: isDiscrete ? "discrete" : "bulk", + price: totalPrice, }); }, onSuccess: () => { @@ -274,7 +277,7 @@ export function AddProductFlow({ data, onClose }: { data: Bootstrap; onClose: () /> )} - + {fmt.money(cpg)}
)} + {isDiscrete && form.price > 0 && form.countOriginal > 0 && ( +
+ Total:{" "} + {fmt.money(totalPrice)} + + ({form.countOriginal} × {fmt.money(form.price)}) + +
+ )}
Cannabinoid profile
diff --git a/web/src/components/modals/EditProductFlow.tsx b/web/src/components/modals/EditProductFlow.tsx index eff36c9..c33b2eb 100644 --- a/web/src/components/modals/EditProductFlow.tsx +++ b/web/src/components/modals/EditProductFlow.tsx @@ -22,6 +22,13 @@ export function EditProductFlow({ }) { const qc = useQueryClient(); + const isDiscrete = product.kind === "discrete"; + // form.price is total for bulk, per-unit for discrete. Convert at I/O boundaries. + const initialPrice = + isDiscrete && product.countOriginal > 0 + ? product.price / product.countOriginal + : product.price; + const [form, setForm] = useState({ name: product.name, brandId: product.brandId ?? NEW_BRAND, @@ -30,7 +37,7 @@ export function EditProductFlow({ weight: product.weight, countOriginal: product.countOriginal, unitWeight: product.unitWeight, - price: product.price, + price: initialPrice, thc: product.thc, cbd: product.cbd, totalCannabinoids: product.totalCannabinoids, @@ -49,7 +56,7 @@ export function EditProductFlow({ setForm((f) => ({ ...f, [k]: v })); const cfg = TYPES.find((t) => t.id === product.type); - const isDiscrete = product.kind === "discrete"; + const totalPrice = isDiscrete ? form.price * form.countOriginal : form.price; const cpg = !isDiscrete && form.weight > 0 ? form.price / form.weight : 0; const save = useMutation({ @@ -86,7 +93,7 @@ export function EditProductFlow({ weight: isDiscrete ? undefined : form.weight, countOriginal: isDiscrete ? form.countOriginal : undefined, unitWeight: isDiscrete ? form.unitWeight : undefined, - price: form.price, + price: totalPrice, thc: form.thc, cbd: form.cbd, totalCannabinoids: form.totalCannabinoids, @@ -262,7 +269,7 @@ export function EditProductFlow({ /> )} - + {fmt.money(cpg)}
)} + {isDiscrete && form.price > 0 && form.countOriginal > 0 && ( +
+ Total:{" "} + {fmt.money(totalPrice)} + + ({form.countOriginal} × {fmt.money(form.price)}) + +
+ )}
Cannabinoid profile