| Rev |
Age |
Author |
Path |
Log message |
Diff |
| 37837 |
3 d 11 h |
amit |
/trunk/profitmandi-dao/src/main/java/com/spice/profitmandi/dao/entity/warehouse/ |
fix(availability): tablets (10010) count as devices in the stock half of BrandRegionMapping.availability and .availabilityVendorWarehouse, matching their reservation half and every other routing query - stock and reservations now go through the same mapping rows |
|
| 37813 |
9 d 4 h |
amit |
/trunk/profitmandi-dao/src/main/java/com/spice/profitmandi/dao/entity/warehouse/ |
revert(samsung-rebilling): restore original PCM filter, drop TODO
Reverts r37811: findByBillingDateBrand goes back to spcm.pcmDate > wsi.invoiceDate
(stores with no samsung_pcm row are no longer listed). File is identical to r37810. |
|
| 37811 |
9 d 6 h |
amit |
/trunk/profitmandi-dao/src/main/java/com/spice/profitmandi/dao/entity/warehouse/ |
fix(samsung-rebilling): list IMEIs of stores with no PCM date
findByBillingDateBrand required spcm.pcmDate > wsi.invoiceDate in the WHERE, so the
left join to SamsungPCM behaved as an inner join and the "PCM date Missing" label in
the cron mail could never appear. No PCM date has been entered since 2025-10-26, so
the query has returned nothing on almost every run and the daily mail went silent.
Stores with no samsung_pcm row now come through with a null PCM date (interim),
alongside the existing PCM-date-after-invoice rows. Internal-movement stock is still
dropped by s.internal=false - TODO(amit.gupta) left on the query.
Deploy with the matching profitmandi-cron commit. |
|
| 37769 |
14 d 4 h |
amit |
/trunk/profitmandi-dao/src/ |
fix(movement): receive a movement invoice only against its own PO, stop auto-closing movements, cancel reduces the PO line
- GRN: movement invoice resolves invoice -> orders -> transaction -> its own movement PO (or a receive-only PO
from the billing warehouse); supplier/warehouse keyed at entry must match; scanned IMEIs must be the billed ones
- Cancelling an unbilled movement order takes its qty off the PO line; PO CLOSED/PRECLOSED once nothing is open
- reopenedAt removed (movements no longer auto-close); PO records createdBy
- SupplierStateResolver: a supplier's state is derived from its GSTIN on save
- sql: add_po_created_by (applied), drop_po_reopened_at (run AFTER fofo/cron/web deploy) |
|
| 37754 |
15 d 3 h |
ranu |
/trunk/profitmandi-dao/src/main/java/com/spice/profitmandi/dao/entity/warehouse/ |
aging po approval process |
|
| 37750 |
15 d 4 h |
ranu |
/trunk/ |
aging sku purchasing need to approval of niranjan kala sir |
|
| 37704 |
20 d 18 h |
amit |
/trunk/ |
Reopen a movement PO whose stock arrived late, and stop stranding GRN price corrections
Internal movements auto-close after four days, which fits 99.6% of them - 5,491 of 5,515 receipts
land inside the window. The remainder leave the PO closed with the stock still in transit and
nowhere to receive it: 998 internal POs closed during 2026 still holding 21,996 unreceived units.
A closed movement PO can now be reopened from the purchase order list. Reopening stamps
reopenedAt, and auto-close measures from WarehousePurchaseOrder.getOpenSince() - reopenedAt when
set, the PO date otherwise - so a reopened PO gets the same fresh window a new one gets instead of
being closed straight back on the next sweep. Only movements between our own warehouses: an
external vendor PO that has closed is settled with that vendor, not reopened unilaterally.
Separately, a GRN price correction now checks that the PO it just raised is one the invoice can
actually be received against. Matching reads POs that are open and approved for the same supplier
and warehouse dated on or before the invoice; it never looks at the PO being corrected, so what
matters is that the new PO is receivable. 54 were not - backdated into INIT by the old approval
gate, hence outside the match - and each stranded silently: original line discarded, GRN completed
without it, the correction left holding a reservation for stock that had already arrived.
isOpen() names the open set - INIT, READY, PARTIALLY_FULFILLED - that the movement and commitment
queries already read.
Migration sql/add_po_reopened_at_20260918.sql adds reopenedAt, nullable and additive. It must run
before this ships: the entity maps the column. |
|
| 37703 |
20 d 18 h |
amit |
/trunk/profitmandi-dao/src/main/java/com/spice/profitmandi/ |
GRN price mismatch: ask for the original PO to be reopened instead of stranding a correction PO
Resolving a price mismatch raised a correction PO dated to the supplier invoice, and stored its id
on the GRN request item to receive against. But by then the stock has already arrived and the PO it
corrects is closed - every one of the 54 raised this way had its mapped PO in CLOSED. The
correction therefore had nowhere to land: the GRN completed against the original, nothing was ever
received against the correction, and it sat holding a reservation for stock that was not coming.
Backdated by nature, it also parked in INIT under the old approval gate, so it could not have been
received even if anyone tried.
Resolving a mismatch against a closed PO now says so and names it, asking for that purchase order
to be reopened first, rather than silently creating a second PO that cannot be used.
WarehousePurchaseOrder.isOpen() names the open set - INIT, READY, PARTIALLY_FULFILLED - that the
movement and commitment queries already read, so it stops being restated per caller. |
|
| 37702 |
20 d 18 h |
amit |
/trunk/profitmandi-dao/src/main/java/com/spice/profitmandi/ |
Internal movement: an unapproved PO no longer dispatches stock
A PO raised on one of our own warehouses also raises the order that moves the stock, and that
order pays and processes immediately - so raising it ships goods. The approval gate never
governed that half. It set the PO to INIT and mailed an approval link, then created and processed
the order anyway, several lines later and without consulting the status it had just set. The gate
held back receiving - PO list, GRN matching, auto-close all skip INIT - while dispatch went ahead
unconditionally.
That is how PO/07-26/52029 was delivered and invoiced while frozen out of GRN. Its goods had to be
received against a second PO raised for the purpose, leaving the first holding a phantom
unfulfilled quantity for two months.
Order creation now waits on approval. WarehousePurchaseOrder.isApproved() names the rule once -
INIT is the only state before approval, every other state is something the order has already been
approved to do - matching how the PO list, GRN matching and the auto-close sweep already read it,
so callers stop restating it.
Backdated POs are approved at creation since r37682, so this holds nothing up today; it is what
keeps the two halves from separating again if any future rule leaves a PO unapproved. Nothing
raises the order later, so such a PO simply does not move stock and has to be raised again once
approved - the safe failure, and it is logged. |
|
| 37694 |
21 d 4 h |
amit |
/trunk/profitmandi-dao/src/main/ |
feat(warehouse): record where stock came from and what it cost; price internal movements at that cost
- inventoryItem.origin_vendor_id / receipt_unit_cost and lineitem.origin_vendor_id (sql/add_inventory_cost_layer_20260917.sql, applied on prod 2026-09-17 in 75s): GRN copies both from the PO line it arrived on, so origin survives any number of hops and non-serialised stock keeps it too. Unknowable origin stays NULL - never a guess, never an internal supplier
- A movement now moves stock at the cost it was received at, not the origin vendor's current catalog TP. Layers are grouped by cost; a quantity spanning two costs is refused with both numbers, since a PO line carries one price
- Stock already promised on open outbound movement orders is no longer offered again (176 item/warehouse pairs on prod are fully promised today)
- Stock on open inbound POs is offered for planning at that order's price and reported as 'on the way in', but cannot be dispatched until received; the PO item picker lists those items too
- Backfill: 4,010 of 4,646 in-stock rows on prod got origin and cost; 636 stay unknown and are priced from the latest approved external catalog price as before |
|
| 37656 |
22 d 5 h |
amit |
/trunk/profitmandi-dao/src/main/java/com/spice/profitmandi/ |
Point dao at the relocated KYC and SD Credit types (r37655)
Imports follow services.mandii -> services.kyc / services.sdcredit, and
RecordingService takes RawHttpResponse in place of MandiiResponse.
Gateway.MANDII is kept, with a comment saying why: it is persisted as a
string on FofoPayment.gateway and CreditAccount.gateway, and 740 historical
fofo.payment rows still carry it - removing the constant would make
Hibernate throw when reading them. |
|
| 37601 |
26 d 8 h |
amit |
/trunk/profitmandi-dao/src/main/ |
Remove dead stock-ageing fields rootInvoiceDate and oldest/newest_invoice_date
rootInvoiceDate on WarehouseInventoryItem had no writer anywhere in the codebase and
was read only by ScheduledTasks.refreshSnapshotAgeing(), which therefore matched zero
rows on every 30-minute run. oldest/newest_invoice_date on SaholicInventorySnapshot
were written only by that task and read by nothing. Verified on prod: null on all
1,528,669 inventoryItem rows and all 11,686 snapshot rows respectively.
Stock ageing that is actually in use resolves the original external supplier at query
time by serialNumber + supplier.internal = false, and does not read these columns.
originalInventoryItemId is deliberately left alone - it is populated on 157,020 rows.
Includes sql/drop_dead_ageing_columns_20260912.sql to drop the columns. Run it only
after web, fofo and cron are all on this build. |
|
| 36910 |
106 d 11 h |
amit |
/trunk/profitmandi-dao/src/main/ |
Internal PO: map created transaction to PO; block warehouse change for PO-mapped orders
- WarehousePurchaseOrder: add transactionId column + selectByTransactionId
- createOrderInternally returns txn id; createPurchaseOrder maps it onto the PO
- Block order.setWarehouseId for PO-mapped orders in changeFulfillmentWarehouse; cron moveOrders skips them
- Migration: add warehouse.purchaseorder.transactionId |
|
| 36581 |
144 d 7 h |
amit |
/trunk/ |
Add rootInvoiceDate to inventoryItem and ageing columns to snapshot, with 30-min cron refresh |
|
| 36568 |
145 d 8 h |
amit |
/trunk/ |
refactor: RTV - add local caching, batch queries, typed DTO, fix documentNumber overwrite and settledAmount validation |
|
| 36559 |
145 d 10 h |
amit |
/trunk/profitmandi-dao/src/main/ |
feat: auto-generate debit notes on RTV with proper DN/{prefix}/{sequence} numbering |
|
| 36318 |
171 d 3 h |
aman |
/trunk/ |
Fix:Migrate legacy Purchase Return flow (Report + Bulk Create + Debit Notes) into FOFO |
|
| 36316 |
171 d 4 h |
aman |
/trunk/ |
Fix:Migrate legacy Purchase Return flow (Report + Bulk Create + Debit Notes) into FOFO |
|
| 36273 |
176 d 11 h |
amit |
/trunk/profitmandi-dao/src/main/java/com/spice/profitmandi/dao/entity/warehouse/ |
Fix app config |
|
| 36272 |
177 d 4 h |
amit |
/trunk/profitmandi-dao/src/main/java/com/spice/profitmandi/ |
Add receiveDate to WarehouseSupplierInvoice
Added receiveDate field to warehouse.invoice entity to track when goods
were physically received. Set from PORowModel.getReceivedDate() during
GRN processing in PurchaseOrderServiceImpl.addPORowModels. |
|