package repositories import ( "context" "errors" "gitlab.com/mbugroup/lti-api.git/internal/common/repository" entity "gitlab.com/mbugroup/lti-api.git/internal/entities" "gorm.io/gorm" ) type PurchaseRepository interface { repository.BaseRepository[entity.Purchase] CreateWithItems(ctx context.Context, purchase *entity.Purchase, items []*entity.PurchaseItem) error GetByIDWithRelations(ctx context.Context, id uint64) (*entity.Purchase, error) UpdatePricing(ctx context.Context, purchaseID uint64, updates []PurchasePricingUpdate, grandTotal float64) error } type PurchaseRepositoryImpl struct { *repository.BaseRepositoryImpl[entity.Purchase] } func NewPurchaseRepository(db *gorm.DB) PurchaseRepository { return &PurchaseRepositoryImpl{ BaseRepositoryImpl: repository.NewBaseRepository[entity.Purchase](db), } } func (r *PurchaseRepositoryImpl) CreateWithItems(ctx context.Context, purchase *entity.Purchase, items []*entity.PurchaseItem) error { db := r.DB().WithContext(ctx) if err := db.Create(purchase).Error; err != nil { return err } if len(items) == 0 { return nil } for _, item := range items { item.PurchaseId = purchase.Id } if err := db.Create(&items).Error; err != nil { return err } return nil } func (r *PurchaseRepositoryImpl) GetByIDWithRelations(ctx context.Context, id uint64) (*entity.Purchase, error) { var purchase entity.Purchase err := r.DB().WithContext(ctx). Preload("Supplier"). Preload("Items", func(db *gorm.DB) *gorm.DB { return db.Order("id ASC") }). Preload("Items.Product"). Preload("Items.Warehouse"). Preload("Items.Warehouse.Area"). Preload("Items.Warehouse.Location"). Preload("Items.ProductWarehouse"). First(&purchase, id).Error if err != nil { return nil, err } return &purchase, nil } type PurchasePricingUpdate struct { ItemID uint64 Price float64 TotalPrice float64 } func (r *PurchaseRepositoryImpl) UpdatePricing( ctx context.Context, purchaseID uint64, updates []PurchasePricingUpdate, grandTotal float64, ) error { if len(updates) == 0 { return errors.New("pricing updates cannot be empty") } db := r.DB().WithContext(ctx) for _, upd := range updates { result := db.Model(&entity.PurchaseItem{}). Where("purchase_id = ? AND id = ?", purchaseID, upd.ItemID). Updates(map[string]interface{}{ "price": upd.Price, "total_price": upd.TotalPrice, "updated_at": gorm.Expr("NOW()"), }) if result.Error != nil { return result.Error } if result.RowsAffected == 0 { return gorm.ErrRecordNotFound } } if err := db.Model(&entity.Purchase{}). Where("id = ?", purchaseID). Updates(map[string]interface{}{ "grand_total": grandTotal, "updated_at": gorm.Expr("NOW()"), }).Error; err != nil { return err } return nil }