chore: build
Backend - Build & Lint / build (push) Failing after 29m22s

This commit is contained in:
Xor290
2026-08-20 21:46:16 +02:00
parent 12cc14eb2b
commit 06abfee274
2 changed files with 62 additions and 6 deletions
+13 -6
View File
@@ -19,12 +19,19 @@ type Product struct {
func (Product) TableName() string { return "products" }
type ProductPrice struct {
ID int `json:"id" gorm:"primaryKey;autoIncrement"`
ProductID int `json:"product_id" gorm:"column:product_id;index"`
Quantity float64 `json:"quantity" gorm:"column:quantity" binding:"required"`
Price float64 `json:"price" gorm:"column:price" binding:"required"`
CreatedAt time.Time `json:"created_at" gorm:"autoCreateTime"`
ActivePrice bool `json:"active_price" gorm:"column:active_price;default:true"`
ID int `json:"id" gorm:"primaryKey;autoIncrement"`
ProductID int `json:"product_id" gorm:"column:product_id;index"`
Quantity float64 `json:"quantity" gorm:"column:quantity" binding:"required"`
Price float64 `json:"price" gorm:"column:price" binding:"required"`
CreatedAt time.Time `json:"created_at" gorm:"autoCreateTime"`
// Pas de tag gorm "default:true" ici : GORM omet de l'INSERT tout champ
// dont la valeur Go est la valeur zéro (false) s'il porte un tag
// "default", laissant Postgres appliquer sa propre valeur par défaut
// (TRUE) à la place — un prix explicitement désactivé (false) revenait
// donc toujours actif après un Create(). La colonne a déjà son défaut
// TRUE posé au niveau SQL (db_init.go), ce tag Go était redondant et
// seulement source du bug.
ActivePrice bool `json:"active_price" gorm:"column:active_price"`
}
func (ProductPrice) TableName() string { return "product_prices" }
@@ -278,6 +278,55 @@ func TestUpdateProduct_UpdatesStockWhenProvided(t *testing.T) {
}
}
// productPriceActiveFlags relit active_price par palier de quantité pour un
// produit, directement en base.
func productPriceActiveFlags(t *testing.T, productID int) map[float64]bool {
t.Helper()
var rows []struct {
Quantity float64 `gorm:"column:quantity"`
ActivePrice bool `gorm:"column:active_price"`
}
if err := testDB.GDB.Raw(
`SELECT quantity, active_price FROM product_prices WHERE product_id = ?`, productID,
).Scan(&rows).Error; err != nil {
t.Fatalf("lecture active_price: %v", err)
}
out := make(map[float64]bool, len(rows))
for _, r := range rows {
out[r.Quantity] = r.ActivePrice
}
return out
}
// Un prix explicitement désactivé (active_price=false) doit rester désactivé
// après UpdateProduct — piège classique de GORM : un champ bool à sa valeur
// zéro (false) avec un tag gorm "default" est omis de l'INSERT, laissant la
// base appliquer son propre défaut (TRUE) à la place. Voir le commentaire sur
// ProductPrice.ActivePrice dans models/product.go.
func TestUpdateProduct_PersistsInactivePriceFlag(t *testing.T) {
cleanupStockTestData(t)
cat := newTestCategory(t, "CatInactive")
productID := newTestProduct(t, "UPInactive", 5)
body := []byte(fmt.Sprintf(
`{"name":"UPInactive","category":%q,"description":"d2","unit":"g","stock":10,"prices":[{"quantity":1,"price":5,"active_price":false},{"quantity":5,"price":20,"active_price":true}]}`,
cat,
))
c, rec := updateProductJSONContext("admin", body, productID)
handlers.UpdateProduct(c)
if rec.Code != http.StatusOK {
t.Fatalf("UpdateProduct valide doit réussir: got=%d body=%s", rec.Code, rec.Body.String())
}
flags := productPriceActiveFlags(t, productID)
if flags[1] != false {
t.Errorf("palier qty=1 doit rester désactivé après UpdateProduct: got active_price=%v", flags[1])
}
if flags[5] != true {
t.Errorf("palier qty=5 doit rester actif après UpdateProduct: got active_price=%v", flags[5])
}
}
// ── DeleteProduct ────────────────────────────────────────────────────────
func TestDeleteProduct_RemovesProductWithoutMedia(t *testing.T) {