aditya.siregar 67f1dbc850 init project
2024-05-28 14:14:55 +07:00

148 lines
4.0 KiB
Go

package order
import (
"context"
"fmt"
"furtuna-be/internal/common/logger"
"furtuna-be/internal/common/mycontext"
"furtuna-be/internal/constants/order"
"furtuna-be/internal/constants/transaction"
"furtuna-be/internal/entity"
"furtuna-be/internal/repository"
"go.uber.org/zap"
)
type OrderService struct {
repo repository.Order
prodRepo repository.Product
studioRepo repository.Studio
}
func NewOrderService(repo repository.Order, prodRepo repository.Product, studioRepo repository.Studio) *OrderService {
return &OrderService{
repo: repo,
prodRepo: prodRepo,
studioRepo: studioRepo,
}
}
func (o *OrderService) Create(ctx mycontext.Context, req *entity.Order) error {
for i, oi := range req.OrderItem {
if oi.ItemType.IsProduct() {
item, err := o.prodRepo.GetProductByID(ctx, oi.ItemID)
if err != nil {
logger.ContextLogger(ctx).Error("error when get product item", zap.Error(err))
return err
}
req.OrderItem[i].Price = item.Price
req.OrderItem[i].CreatedBy = ctx.RequestedBy()
} else if oi.ItemType.IsStudio() {
//get data studio
item, err := o.studioRepo.GetStudioByID(ctx, oi.ItemID)
if err != nil {
logger.ContextLogger(ctx).Error("error when get studio item", zap.Error(err))
return err
}
req.OrderItem[i].Price = item.Price
req.OrderItem[i].CreatedBy = ctx.RequestedBy()
}
}
orderDB := req.ToOrderDB()
orderDB.CreatedBy = ctx.RequestedBy()
orderDB.Transaction.CreatedBy = ctx.RequestedBy()
//set status
orderDB.Status = order.Paid
orderDB.Transaction.Status = transaction.Paid
orderDB, err := o.repo.CreateOrder(ctx, orderDB)
if err != nil {
logger.ContextLogger(ctx).Error("error when create order", zap.Error(err))
return err
}
return nil
}
func (s *OrderService) GetByID(ctx context.Context, id int64) (*entity.Order, error) {
orderDB, err := s.repo.GetOrderByID(ctx, id)
if err != nil {
logger.ContextLogger(ctx).Error("error when get order by id", zap.Error(err))
return nil, err
}
return orderDB.ToOrder(), nil
}
func (s *OrderService) GetAll(ctx context.Context, search entity.OrderSearch) ([]*entity.Order, int, error) {
orders, total, err := s.repo.GetAllOrders(ctx, search)
if err != nil {
logger.ContextLogger(ctx).Error("error when get all orders", zap.Error(err))
return nil, 0, err
}
return orders.ToOrderList(), total, nil
}
func (s *OrderService) GetTotalRevenue(ctx context.Context, search entity.OrderTotalRevenueSearch) (float64, int64, error) {
rev, trans, err := s.repo.GetTotalRevenue(ctx, search)
if err != nil {
logger.ContextLogger(ctx).Error("error when get total revenue orders", zap.Error(err))
return 0, 0, err
}
return rev, trans, nil
}
func (s *OrderService) GetYearlyRevenue(ctx context.Context, year int) (entity.OrderYearlyRevenueList, error) {
result, err := s.repo.GetYearlyRevenue(ctx, year)
if err != nil {
logger.ContextLogger(ctx).Error("error when get yearly revenue orders", zap.Error(err))
return nil, err
}
return result, nil
}
func (s *OrderService) GetBranchRevenue(ctx context.Context, req entity.OrderBranchRevenueSearch) (entity.OrderBranchRevenueList, error) {
result, err := s.repo.GetBranchRevenue(ctx, req)
if err != nil {
logger.ContextLogger(ctx).Error("error when get branch revenue orders", zap.Error(err))
return nil, err
}
return result, nil
}
func (s *OrderService) UpdateStatus(ctx mycontext.Context, id int64, orderReq *entity.Order) (*entity.Order, error) {
existingOrder, err := s.repo.GetOrderByID(ctx, id)
if err != nil {
return nil, err
}
//validate state
if !existingOrder.Status.IsNew() {
return nil, fmt.Errorf("Invalid order status")
}
if existingOrder.Status == orderReq.Status {
return nil, fmt.Errorf("Order status already %s", existingOrder.Status)
}
existingOrder.ToUpdatedOrder(ctx.RequestedBy(), *orderReq)
_, err = s.repo.UpdateOrder(ctx, existingOrder)
if err != nil {
logger.ContextLogger(ctx).Error("error when update user", zap.Error(err))
return nil, err
}
return existingOrder.ToOrder(), nil
}