package br.gov.sigefp.treasury.api;

import br.gov.sigefp.treasury.api.dto.CashFlowDTO;
import br.gov.sigefp.treasury.api.dto.CreateCashFlowDTO;
import br.gov.sigefp.treasury.service.CashFlowService;
import jakarta.validation.Valid;
import lombok.RequiredArgsConstructor;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;

import java.math.BigDecimal;
import java.time.LocalDate;
import java.util.List;
import java.util.Map;
import java.util.UUID;

@RestController
@RequestMapping("/api/treasury/cash-flow")
@RequiredArgsConstructor
public class CashFlowController {

    private final CashFlowService cashFlowService;

    @PostMapping
    public ResponseEntity<CashFlowDTO> registerFlow(@Valid @RequestBody CreateCashFlowDTO dto) {
        CashFlowDTO created = cashFlowService.registerFlow(dto);
        return ResponseEntity.status(HttpStatus.CREATED).body(created);
    }

    @GetMapping("/{id}")
    public ResponseEntity<CashFlowDTO> findById(@PathVariable UUID id) {
        CashFlowDTO cashFlow = cashFlowService.findById(id);
        return ResponseEntity.ok(cashFlow);
    }

    @GetMapping
    public ResponseEntity<Page<CashFlowDTO>> findByCashAccount(
            @RequestParam UUID cashAccountId,
            @RequestParam(required = false) LocalDate startDate,
            @RequestParam(required = false) LocalDate endDate,
            @RequestParam(defaultValue = "0") int page,
            @RequestParam(defaultValue = "20") int size,
            @RequestParam(defaultValue = "transactionDate") String sortBy,
            @RequestParam(defaultValue = "DESC") String sortDirection) {

        Sort sort = Sort.by(Sort.Direction.fromString(sortDirection), sortBy);
        Pageable pageable = PageRequest.of(page, size, sort);

        Page<CashFlowDTO> result;
        if (startDate != null && endDate != null) {
            result = cashFlowService.findByCashAccountIdAndDateRange(
                    cashAccountId, startDate, endDate, pageable);
        } else {
            result = cashFlowService.findByCashAccountId(cashAccountId, pageable);
        }

        return ResponseEntity.ok(result);
    }

    @GetMapping("/{cashAccountId}/projected-balance")
    public ResponseEntity<BigDecimal> calculateProjectedBalance(
            @PathVariable UUID cashAccountId,
            @RequestParam LocalDate targetDate) {
        BigDecimal balance = cashFlowService.calculateProjectedBalance(cashAccountId, targetDate);
        return ResponseEntity.ok(balance);
    }

    @GetMapping("/{cashAccountId}/summary")
    public ResponseEntity<Map<String, BigDecimal>> getFlowSummary(
            @PathVariable UUID cashAccountId,
            @RequestParam LocalDate startDate,
            @RequestParam LocalDate endDate) {
        Map<String, BigDecimal> summary = cashFlowService.getFlowSummary(
                cashAccountId, startDate, endDate);
        return ResponseEntity.ok(summary);
    }
}

