changes fixed in the catalogue

This commit is contained in:
2026-08-11 17:10:21 +05:30
parent fba42259ea
commit ff72af9a8a
4 changed files with 65 additions and 14 deletions

View File

@@ -30,13 +30,20 @@ import (
// Idempotent: publishing an already-published product re-prices it and leaves
// the original `publishedat` alone, so "when did this go live" survives a
// second click.
func (r *productRepository) PublishProduct(tenantID, productID int, price float64) (int, error) {
func (r *productRepository) PublishProduct(tenantID, productID int, price, taxPercent float64) (int, error) {
if tenantID <= 0 || productID <= 0 {
return 0, fmt.Errorf("tenantid and productid are required")
}
if price <= 0 {
return 0, fmt.Errorf("set a price before publishing — a product with no price cannot be sold at a till")
}
// Zero is a legitimate rate — plenty of staples are zero-rated — so it
// cannot double as "not specified". Negative is refused rather than stored:
// three products already carry taxpercent -1, which yields negative tax
// under either convention.
if taxPercent < 0 {
return 0, fmt.Errorf("tax percentage cannot be negative")
}
var affected int
err := r.db.Transaction(func(tx *gorm.DB) error {
@@ -93,9 +100,9 @@ func (r *productRepository) PublishProduct(tenantID, productID int, price float6
// The master price follows, so an outlet that has no row of its own
// still reads the right figure through the COALESCE fallback in
// GetProducts.
return tx.Exec(`UPDATE products SET retailprice = ?, updated = NOW()
return tx.Exec(`UPDATE products SET retailprice = ?, taxpercent = ?, updated = NOW()
WHERE productid = ? AND tenantid = ?`,
price, productID, tenantID).Error
price, taxPercent, productID, tenantID).Error
})
return affected, err

View File

@@ -42,7 +42,7 @@ type ProductRepository interface {
// Releasing a product from the admin catalogue to every outlet, and pulling
// it back. See productPublishRepository.go.
PublishProduct(tenantID, productID int, price float64) (int, error)
PublishProduct(tenantID, productID int, price, taxPercent float64) (int, error)
UnpublishProduct(tenantID, productID int) (int, error)
FindTenantProductByCatalogueRef(tenantid int, brand string, catalogueid int64) (*models.Products, error)
CreateProductReturningID(product models.Products) (int, error)
@@ -400,7 +400,7 @@ func (r *productRepository) GetStockStatement(tenantID, locationID, subcategoryI
// arithmetically identical to closing — the Inventory ledger then showed
// the same number in both columns and looked like stock never moved, even
// on days with sales.
query := `SELECT a.productid,a.productname,a.productimage,a.categoryid,a.subcategoryid,a.productunit,a.unitvalue,a.productcost,a.taxpercent,a.taxamount,a.retailprice,b.tenantid,b.locationid,b.publishedat,
query := `SELECT a.productid,a.productname,a.productimage,a.categoryid,a.subcategoryid,a.productunit,a.unitvalue,a.productcost,a.taxpercent,a.taxamount,a.retailprice,b.tenantid,b.locationid,
COALESCE( SUM(CASE WHEN UPPER(c.stocktype) = 'IN' AND c.stockdate::date < CURRENT_DATE THEN c.quantity ELSE 0 END) -
SUM(CASE WHEN UPPER(c.stocktype) = 'OUT' AND c.stockdate::date < CURRENT_DATE THEN c.quantity ELSE 0 END),0 )
AS opening,
@@ -435,7 +435,7 @@ func (r *productRepository) GetStockStatement(tenantID, locationID, subcategoryI
a.productid, a.productname, a.productimage,
a.categoryid, a.subcategoryid, a.productunit,
a.productcost, a.taxpercent, a.taxamount,
a.retailprice, b.tenantid, b.locationid, b.publishedat
a.retailprice, b.tenantid, b.locationid
ORDER BY a.productid DESC LIMIT ` + strconv.Itoa(pagesize) + ` OFFSET ` + strconv.Itoa(offset)
if err := r.db.Raw(query, params...).Scan(&data).Error; err != nil {
@@ -475,7 +475,13 @@ func (r *productRepository) GetLocationProducts(tenantID, locationID, subcategor
// retailprice when the store hasn't set its own. Returning a bare b.price
// reported 0 for any product priced only at tenant level, which the store
// catalogue then rendered as "—".
query := `SELECT a.*, b.productlocationid, b.status,
// b.publishedat decides whether a store user may see this row at all, so it
// has to be selected explicitly for the same reason b.price does: `a.*`
// covers products, and publication is a per-outlet fact on
// productlocations. Without it the column came back null for every row —
// including ones that had just been published — and the store catalogue,
// which filters on it, showed nothing.
query := `SELECT a.*, b.productlocationid, b.status, b.publishedat,
COALESCE(NULLIF(b.price, 0), a.retailprice, 0) AS price,
COALESCE(SUM(CASE WHEN UPPER(c.stocktype) = 'IN' THEN c.quantity ELSE 0 END), 0) AS total_in,
COALESCE(SUM(CASE WHEN UPPER(c.stocktype) = 'OUT' THEN c.quantity ELSE 0 END), 0) AS total_out,
@@ -500,7 +506,7 @@ func (r *productRepository) GetLocationProducts(tenantID, locationID, subcategor
query += ` GROUP BY a.productid, a.productname, a.productimage, a.categoryid, a.subcategoryid,
a.productunit, a.productcost, a.taxpercent, a.taxamount, a.retailprice,
b.tenantid, b.locationid, b.productlocationid, b.status, b.price
b.tenantid, b.locationid, b.productlocationid, b.status, b.price, b.publishedat
ORDER BY a.productid DESC LIMIT ? OFFSET ?`
params = append(params, pagesize, offset)