const Accounts = require('../models/AccountModel');
const Transactions = require('../models/TransactionModel');
const Transfers = require('../models/TransferModel');
const Categories = require('../models/CategoryModel');
const { Op } = require('sequelize');

const getAccountReport = async (req, res) => {
    const { id } = req.params;
    const { startDate, endDate, type } = req.query;

    try {
        // 1. Pastikan akun milik user yang login
        const account = await Accounts.findOne({
            where: {
                id,
                user_id: req.userId
            }
        });

        if (!account) {
            return res.status(404).json({ msg: "Akun tidak ditemukan" });
        }

        // Normalisasi tipe filter
        const filterType = (type || 'ALL').toUpperCase(); // ALL, INCOME, EXPENSE, TRANSFER
        const allowedTypes = ['ALL', 'INCOME', 'EXPENSE', 'TRANSFER'];

        if (!allowedTypes.includes(filterType)) {
            return res.status(400).json({
                msg: "Parameter type tidak valid. Gunakan: ALL, INCOME, EXPENSE, TRANSFER"
            });
        }

        // Helper filter tanggal
        const buildDateFilter = (fieldName) => {
            if (startDate && endDate) {
                return { [fieldName]: { [Op.between]: [startDate, endDate] } };
            } else if (startDate) {
                return { [fieldName]: { [Op.gte]: startDate } };
            }
            return {};
        };

        // =========================
        // 2. Ambil TRANSACTIONS (INCOME / EXPENSE)
        // =========================
        let incomeTransactions = [];
        let expenseTransactions = [];

        const includeTransactions = (filterType === 'ALL' ||
                                     filterType === 'INCOME' ||
                                     filterType === 'EXPENSE');

        if (includeTransactions) {
            const txWhere = {
                user_id: req.userId,
                account_id: id,
                ...buildDateFilter('date')
            };

            const allTx = await Transactions.findAll({
                where: txWhere,
                include: [
                    { model: Categories, attributes: ['id', 'name', 'type'] }
                ],
                order: [
                    ['date', 'DESC'],
                    ['id', 'DESC']
                ]
            });

            incomeTransactions = allTx.filter(tx => tx.type === 'INCOME');
            expenseTransactions = allTx.filter(tx => tx.type === 'EXPENSE');

            if (filterType === 'INCOME') {
                // kalau user minta income saja
                expenseTransactions = [];
            } else if (filterType === 'EXPENSE') {
                // kalau user minta expense saja
                incomeTransactions = [];
            }
        }

        // =========================
        // 3. Ambil TRANSFERS (masuk & keluar)
        // =========================
        let transfersIn = [];
        let transfersOut = [];

        const includeTransfers = (filterType === 'ALL' || filterType === 'TRANSFER');

        if (includeTransfers) {
            const transferWhere = {
                user_id: req.userId,
                ...buildDateFilter('date'),
                [Op.or]: [
                    { from_account_id: id },
                    { to_account_id: id }
                ]
            };

            const allTransfers = await Transfers.findAll({
                where: transferWhere,
                include: [
                    { model: Accounts, as: 'from_account', attributes: ['id', 'name', 'type'] },
                    { model: Accounts, as: 'to_account', attributes: ['id', 'name', 'type'] }
                ],
                order: [
                    ['date', 'DESC'],
                    ['id', 'DESC']
                ]
            });

            transfersOut = allTransfers.filter(tr => tr.from_account_id == id);
            transfersIn = allTransfers.filter(tr => tr.to_account_id == id);
        }

        // =========================
        // 4. Hitung summary
        // =========================
        const sumAmount = (arr) =>
            arr.reduce((acc, item) => acc + parseFloat(item.amount || 0), 0);

        const totalIncome = sumAmount(incomeTransactions);
        const totalExpense = sumAmount(expenseTransactions);
        const totalTransferIn = sumAmount(transfersIn);
        const totalTransferOut = sumAmount(transfersOut);

        const netChange =
            totalIncome - totalExpense + (totalTransferIn - totalTransferOut);

        // =========================
        // 5. Response
        // =========================
        return res.json({
            account: {
                id: account.id,
                name: account.name,
                type: account.type,
                balance: parseFloat(account.balance || 0)
            },
            filter: {
                type: filterType,
                startDate: startDate || null,
                endDate: endDate || null
            },
            summary: {
                total_income: totalIncome,
                total_expense: totalExpense,
                total_transfer_in: totalTransferIn,
                total_transfer_out: totalTransferOut,
                net_change: netChange
            },
            transactions: {
                income: incomeTransactions,
                expense: expenseTransactions
            },
            transfers: {
                in: transfersIn,
                out: transfersOut
            }
        });
    } catch (error) {
        console.log(error);
        res.status(500).json({ msg: "Gagal mengambil laporan akun" });
    }
};

module.exports = {
    getAccountReport
};
