package de.htwsaar.webshop.service.impl;

import de.htwsaar.webshop.model.OrderItemModel;
import de.htwsaar.webshop.model.OrderModel;
import de.htwsaar.webshop.repository.OrderRepository;
import de.htwsaar.webshop.repository.entities.Order;
import de.htwsaar.webshop.repository.entities.OrderItem;
import de.htwsaar.webshop.service.ArticleService;
import de.htwsaar.webshop.service.CustomerService;
import de.htwsaar.webshop.service.OrderService;
import de.htwsaar.webshop.util.TimeUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Service
@Slf4j
public class OrderServiceImpl implements OrderService {
    private final OrderRepository orderRepository;
    private final CustomerService customerService;
    private final ArticleService articleService;

    @Autowired
    public OrderServiceImpl(OrderRepository orderRepository, CustomerService customerService, ArticleService articleService) {
        this.orderRepository = orderRepository;
        this.customerService = customerService;
        this.articleService = articleService;
    }

    @Override
    public List<Order> findAll() {
        return orderRepository.findAll();
    }

    @Override
    public Order save(Order order) {
        return orderRepository.save(order);
    }

    @Override
    public Order save(OrderModel model) {
        Order order = new Order(
                model.getId(),
                customerService.findById(model.getCustomerId()),
                model.getTime(),
                model.getStatus(),
                null
        );
        order.setOrderItems(
                model.getOrderItems().stream().map(oim -> this.from(oim, order)).toList()
        );
        log.info("Created Order from Model: {}", order);
        return save(order);
    }

    OrderItem from(OrderItemModel model, Order order) {
        OrderItem orderItem = new OrderItem(model.getId(), model.getAmount(), order, articleService.findByUUID(model.getArticle()));
        log.info("Created OrderItem from Model: {}", orderItem);
        return orderItem;
    }

    @Override
    public void delete(Long orderId) {
        orderRepository.deleteById(orderId);
    }

    @Override
    public Order getOrderById(Long orderId) {
        return orderRepository.findById(orderId).orElse(null);
    }

    @Override
    public List<Order> getAllOrders(Long customerId) {
        return orderRepository.getOrdersByCustomer_Id(customerId);
    }

    @Override
    public Map<Long, List<Order>> getTimeSortedOrders(long fromMilli, long months) {
        Map<Long, List<Order>> orders = new HashMap<>();
        long lower = fromMilli;
        long upper;
        while (months > 0) {
            upper = fromMilli + TimeUtil.monthLength(fromMilli);
            log.info("Getting Orders from {} to {}", lower, upper);
            orders.put(fromMilli, orderRepository.getOrdersByTimeBetween(lower, upper));
            lower = upper;
            months--;
        }
        return orders;
    }
}
