apskel-pos-backend/internal/service/inventory_movement_service.go
Aditya Siregar ebe9999793 Update users
2025-08-03 22:44:27 +07:00

97 lines
3.5 KiB
Go

package service
import (
"apskel-pos-be/internal/entities"
"apskel-pos-be/internal/repository"
"context"
"time"
"github.com/google/uuid"
)
type InventoryMovementService interface {
CreateIngredientMovement(ctx context.Context, ingredientID, organizationID, outletID, userID uuid.UUID, movementType entities.InventoryMovementType, quantity float64, unitCost float64, reason string, referenceType *entities.InventoryMovementReferenceType, referenceID *uuid.UUID) error
CreateProductMovement(ctx context.Context, productID, organizationID, outletID, userID uuid.UUID, movementType entities.InventoryMovementType, quantity float64, unitCost float64, reason string, referenceType *entities.InventoryMovementReferenceType, referenceID *uuid.UUID) error
}
type InventoryMovementServiceImpl struct {
inventoryMovementRepo repository.InventoryMovementRepository
ingredientRepo *repository.IngredientRepository
}
func NewInventoryMovementService(inventoryMovementRepo repository.InventoryMovementRepository, ingredientRepo *repository.IngredientRepository) InventoryMovementService {
return &InventoryMovementServiceImpl{
inventoryMovementRepo: inventoryMovementRepo,
ingredientRepo: ingredientRepo,
}
}
func (s *InventoryMovementServiceImpl) CreateIngredientMovement(ctx context.Context, ingredientID, organizationID, outletID, userID uuid.UUID, movementType entities.InventoryMovementType, quantity float64, unitCost float64, reason string, referenceType *entities.InventoryMovementReferenceType, referenceID *uuid.UUID) error {
ingredient, err := s.ingredientRepo.GetByID(ctx, ingredientID, organizationID)
if err != nil {
return err
}
previousQuantity := ingredient.Stock
newQuantity := previousQuantity + quantity
movement := &entities.InventoryMovement{
ID: uuid.New(),
OrganizationID: organizationID,
OutletID: outletID,
ItemID: ingredientID,
ItemType: "INGREDIENT",
MovementType: movementType,
Quantity: quantity,
PreviousQuantity: previousQuantity,
NewQuantity: newQuantity,
UnitCost: unitCost,
TotalCost: unitCost * quantity,
ReferenceType: referenceType,
ReferenceID: referenceID,
UserID: userID,
Reason: &reason,
CreatedAt: time.Now(),
}
err = s.inventoryMovementRepo.Create(ctx, movement)
if err != nil {
return err
}
err = s.ingredientRepo.UpdateStock(ctx, ingredientID, quantity, organizationID)
if err != nil {
return err
}
return nil
}
func (s *InventoryMovementServiceImpl) CreateProductMovement(ctx context.Context, productID, organizationID, outletID, userID uuid.UUID, movementType entities.InventoryMovementType, quantity float64, unitCost float64, reason string, referenceType *entities.InventoryMovementReferenceType, referenceID *uuid.UUID) error {
movement := &entities.InventoryMovement{
ID: uuid.New(),
OrganizationID: organizationID,
OutletID: outletID,
ItemID: productID,
ItemType: "PRODUCT",
MovementType: movementType,
Quantity: quantity,
PreviousQuantity: 0, // TODO This would be fetched from product inventory
NewQuantity: 0, // TODO This would be calculated
UnitCost: unitCost,
TotalCost: unitCost * quantity,
ReferenceType: referenceType,
ReferenceID: referenceID,
UserID: userID,
Reason: &reason,
CreatedAt: time.Now(),
}
err := s.inventoryMovementRepo.Create(ctx, movement)
if err != nil {
return err
}
return nil
}