
const datetime = require("../../config/datetime");
const { AppEvent, AppEventType } = require("../event/my.event");
const Admin = require("../model/Admin");
const Deposit = require("../model/Deposit");
const Method = require("../model/Method");
const User = require("../model/User");
const Controller = require("./Controller");
module.exports = new class DepositController extends Controller {
    request = async (req, res, next) => {
        try {
            const { method, fromNumber, taka } = req.body;
            if (!method || !fromNumber || !taka) return next("input data not found");
            const user = req.user;
            const setting = await this.setting();
            // min deposit and max diposit check 
            if (parseInt(setting.diposit_min) > parseInt(taka) || parseInt(setting.diposit_max) < parseInt(taka)) return next(`Your min deposit ${this.getTaka(setting.diposit_min)} and max ${setting.diposit_max}`);
            // check pending/active request
            const activeRequest = await Deposit.where("user_id", user.id).where("status", Deposit.status.pending);
            if (activeRequest.length > 0) return next("Your deposit request all ready active!");
            // check parmition user
            if (user.dp_permition != "1") return next("Your deposit parmition deactive!");
            // check app setting dp parmition
            if (setting.dp_parmition == "deactive") return next("Sumtime deposit inactive!");
            // method data get/andmethod id valid!
            const methods = await Method.where("id", "=", method).where("is_diposite", "=", "active").andWhere("is_active", "=", "yes").first();
            if (!methods) return next("invalid method id");
            const body = {
                user_id: user.id,
                method_name: methods.name,
                method_type: methods.type,
                method_number: methods.number,
                user_number: fromNumber,
                taka: this.getTaka(taka),
                bonus: methods.bonus,
                request_date: datetime.today() + " " + datetime.time()
            }
            await Deposit.add(body);
            AppEvent.emit(AppEventType.NOTIFACATION);
            return res.success("request suuccessfull")
        } catch (error) {
            return next(error);
        }
    }
    histroy = async (req, res, next) => {
        try {
            const datas = await Deposit.where("user_id", "=", req.user.id);
            const send = [];
            for (const data of datas) {
                send.push({
                    Date: data.request_date,
                    Method: `${data.method_name} (${data.method_type})`,
                    From: data.user_number,
                    To: data.method_number,
                    Amount: this.getTaka(data.taka),
                    Status: data.status
                })
            }
            return res.success(`data success`, send);
        } catch (error) {
            return next(error);
        }
    }
    accespt = async (req, res, next) => {
        try {
            const id = req.params.id;
            const findDeposit = await Deposit.find(id);
            if (findDeposit.status !== Deposit.status.pending) return next("invalid id");
            const datetim = datetime.today() + " " + datetime.time();
            const admin = req.user;
            // update dp info
            await Deposit.update(id, value => {
                return {
                    accespt_date: datetim,
                    accesptor_id: admin.id,
                    status: Deposit.status.success
                }
            })
            // add taka from user
            await this.addTakaToUser(findDeposit.user_id, findDeposit.taka, this.transectionType.deposit, ` Deposit success`);
            // calculation bonus
            const bonus = ((findDeposit.taka * findDeposit.bonus) / 100);
            await this.addTakaToUser(findDeposit.user_id, bonus, this.transectionType.deposit, `Deposit Bonus ${findDeposit.bonus}%`);
            // responce
            AppEvent.emit(AppEventType.NOTIFACATION);
            return res.success("Depost accespt successfull");
        } catch (error) {
            return next(error);
        }
    }
    cansel = async (req, res, next) => {
        try {
            const id = req.params.id;
            const findDeposit = await Deposit.find(id);
            if (findDeposit.status != Deposit.status.pending) return next("invalid id");
            const datetim = datetime.today() + " " + datetime.time();
            const admin = req.user;
            // update dp info
            await Deposit.update(id, value => {
                return {
                    accespt_date: datetim,
                    accesptor_id: admin.id,
                    status: Deposit.status.cansel
                }
            })
            AppEvent.emit(AppEventType.NOTIFACATION);
            return res.success("cansel successfull");
        } catch (error) {
            return next(error);
        }
    }
    edite = async (req, res, next) => {
        try {
            const id = req.params.id;
            const taka = req.body.taka;
            if (!taka) return next("Invalid taka");
            const findDeposit = await Deposit.find(id);
            if (findDeposit.status != Deposit.status.pending) return next("invalid id");
            const admin = req.user;
            const paload = {
                taka: this.getTaka(taka),
                editor_id: admin.id
            }
            console.log(paload);
            await Deposit.update(id, value => paload)
            AppEvent.emit(AppEventType.NOTIFACATION);
            return res.success("update success");
        } catch (error) {
            return next(error);
        }
    }
    data = async () => {
        const datas = await Deposit.get().orderBy("id", "desc");
        const alldata = await Promise.all(
            datas.map(async (item) => {
                let accesptor_name = null;
                let editor_name = null;
                let user_name = (await User.find(item.user_id))?.name || "";

                if (item.accesptor_id) {
                    const accesptor = await Admin.find(item.accesptor_id);
                    accesptor_name = accesptor?.name || null;
                }

                if (item.editor_id) {
                    const editor = await Admin.find(item.editor_id);
                    editor_name = editor?.name || null;
                }

                return {
                    ...item,
                    user_name,
                    accesptor_id: accesptor_name,
                    editor_id: editor_name
                };
            })
        );
        return alldata
    }
    index = async (req, res, next) => {
        try {
            return res.success(`data success`, await this.data());
        } catch (error) {
            return next(error);
        }
    }
    old = async (req, res, next) => {
        try {
            const olddata = (await this.data()).filter((data) => data.status != Deposit.status.pending);
            return res.success(`data success`, olddata);
        } catch (error) {
            return next(error);
        }
    }

};

