<template>
  <div>
    <DefaultHeaderPage
      :show-filter-icon="false"
      title="Contas a Pagar"
    />

    <div class="row q-pa-md q-gutter-md">
      <FinancialCard
        :financial-value="totals.paid"
        :integer="totals.paidCount"
        icon="mdi-check-circle-outline"
        integer-label="pagamentos"
        title="Pago"
      />

      <FinancialCard
        :financial-value="totals.pending"
        :integer="totals.pendingCount"
        icon="mdi-cash-minus"
        integer-label="pendentes"
        title="A Pagar"
      />

      <FinancialCard
        :financial-value="totals.overdue"
        :integer="totals.overdueCount"
        icon="mdi-alert-circle-outline"
        integer-label="em atraso"
        title="Vencidas"
      />
    </div>

    <div class="q-px-md">
      <DefaultTable
        v-model:rows="rows"
        :add-item="canAdd"
        :columns="columns"
        :female="true"
        description="contas"
        no-api-call
        title="Contas a Pagar"
        @on-add-item="openCreate"
      >
        <template #body-cell-origin="{ row }">
          <q-td class="text-left">
            <q-chip
              :color="
                row.origin === 'tbr'
                  ? 'deep-purple-5'
                  : 'blue-grey-5'
              "
              :label="row.origin === 'tbr' ? 'TBR' : 'Manual'"
              dense
              square
              text-color="white"
            />
          </q-td>
        </template>

        <template #body-cell-value="{ row }">
          <q-td class="text-left">
            {{ formatCurrency(row.value) }}
          </q-td>
        </template>

        <template #body-cell-status="{ row }">
          <q-td class="text-left">
            <q-btn
              :color="row.status === 'paid' ? 'positive' : 'secondary'"
              :disable="!canEdit || row.status === 'paid'"
              :label="row.status === 'paid' ? 'Pago' : 'Não pago'"
              dense
              no-caps
              unelevated
              @click.stop="changeStatus(row)"
            >
              <q-tooltip v-if="canEdit && row.status !== 'paid'">
                Dar baixa
              </q-tooltip>
            </q-btn>
          </q-td>
        </template>

        <template #body-cell-actions="{ row }">
          <q-td auto-width>
            <q-btn
              v-if="row.invoice_url"
              aria-label="Abrir cobrança"
              color="teal-7"
              dense
              flat
              icon="mdi-open-in-new"
              round
              @click="openInvoice(row)"
            >
              <q-tooltip>
                Abrir cobrança no Asaas
              </q-tooltip>
            </q-btn>
          </q-td>
        </template>
      </DefaultTable>
    </div>

    <q-dialog v-model="settleDialog">
      <q-card
        class="dialog-form-card"
        style="min-width: 360px; max-width: 460px"
      >
        <DefaultDialogHeader
          title="Dar baixa"
          @close="settleDialog = false"
        />

        <DefaultForm @submit="onSettle">
          <q-scroll-area class="dialog-form-scroll dialog-form-scroll--sm">
            <q-card-section class="q-gutter-sm">
              <div class="text-body2 text-grey-8">
                {{ selected?.history }}
              </div>

              <DefaultInputDatePicker
                v-model="settleForm.payment_date"
                v-model:untreated-date="settleForm.payment_date_iso"
                label="Data do pagamento"
              />

              <div class="row q-col-gutter-sm">
                <DefaultCurrencyInput
                  v-model="settleForm.discount"
                  class="col-6"
                  label="Desconto"
                  outlined
                />

                <DefaultCurrencyInput
                  v-model="settleForm.fine"
                  class="col-6"
                  label="Multa/Juros"
                  outlined
                />
              </div>

              <div class="text-caption text-grey-7">
                Valor da conta: {{ formatCurrency(selected?.value) }} ·

                <span class="text-weight-medium">
                  Pago: {{ formatCurrency(settleNetValue) }}
                </span>
              </div>
            </q-card-section>
          </q-scroll-area>

          <q-card-actions
            align="right"
            class="q-px-md q-pb-md"
          >
            <q-btn
              color="primary"
              label="Cancelar"
              no-caps
              outline
              @click="settleDialog = false"
            />

            <q-btn
              color="primary"
              label="Confirmar baixa"
              no-caps
              type="submit"
              :loading="settling"
            />
          </q-card-actions>
        </DefaultForm>
      </q-card>
    </q-dialog>

    <q-dialog v-model="createDialog">
      <q-card
        class="dialog-form-card"
        style="min-width: 360px; max-width: 460px"
      >
        <DefaultDialogHeader
          title="Nova conta a pagar"
          @close="createDialog = false"
        />

        <DefaultForm
          ref="createFormRef"
          @submit="onCreate"
        >
          <q-scroll-area
            ref="createScrollAreaRef"
            class="dialog-form-scroll dialog-form-scroll--sm"
          >
            <q-card-section class="q-gutter-sm">
              <DefaultInput
                v-model="createForm.history"
                v-model:error="createValidationErrors.history"
                label="Descrição"
                outlined
                :rules="[inputRules.required]"
              />

              <div
                style="
                  display: grid;
                  grid-template-columns: minmax(0, 5fr) minmax(0, 7fr);
                  gap: 8px;
                "
              >
                <DefaultCurrencyInput
                  v-model="createForm.value"
                  v-model:error="createValidationErrors.value"
                  label="Valor"
                  outlined
                  :rules="[inputRules.required, positiveAmountRule]"
                />

                <DefaultInputDatePicker
                  v-model="createForm.due_date"
                  v-model:error="createValidationErrors.due_date"
                  v-model:untreated-date="createForm.due_date_iso"
                  label="Vencimento"
                  :rules="[inputRules.required]"
                />
              </div>

              <DefaultInput
                v-model="createForm.obs"
                label="Observação (opcional)"
                outlined
                type="textarea"
              />
            </q-card-section>
          </q-scroll-area>

          <q-card-actions
            align="right"
            class="q-px-md q-pb-md"
          >
            <q-btn
              color="primary"
              label="Cancelar"
              no-caps
              outline
              @click="createDialog = false"
            />

            <q-btn
              color="primary"
              label="Salvar"
              no-caps
              type="submit"
              :loading="creating"
            />
          </q-card-actions>
        </DefaultForm>
      </q-card>
    </q-dialog>
  </div>
</template>

<script setup>
import {
  createPayableMe,
  getPayablesMe,
  settlePayableMe,
} from "src/api/unit_payable";

import { computed, onMounted, ref, useTemplateRef } from "vue";
import { permissionStore } from "src/stores/permission";
import { useForm } from "src/composables/useForm";
import { useInputRules } from "src/composables/useInputRules";
import { useScroll } from "src/composables/useScroll";
import { useSubmitHandler } from "src/composables/useSubmitHandler";

import DefaultCurrencyInput from "src/components/defaults/DefaultCurrencyInput.vue";
import DefaultDialogHeader from "src/components/defaults/DefaultDialogHeader.vue";
import DefaultForm from "src/components/defaults/DefaultForm.vue";
import DefaultHeaderPage from "src/components/layout/DefaultHeaderPage.vue";
import DefaultInput from "src/components/defaults/DefaultInput.vue";
import DefaultInputDatePicker from "src/components/defaults/DefaultInputDatePicker.vue";
import DefaultTable from "src/components/defaults/DefaultTable.vue";
import FinancialCard from "src/components/financial/FinancialCard.vue";

const { inputRules } = useInputRules();
const { scrollToComponent } = useScroll();

const permissions = permissionStore();

const createFormRef = useTemplateRef("createFormRef");
const createScrollAreaRef = useTemplateRef("createScrollAreaRef");

const createDialog = ref(false);
const rows = ref([]);
const selected = ref(null);
const settleDialog = ref(false);

const settleForm = ref({
  discount: 0,
  fine: 0,
  payment_date: null,
  payment_date_iso: null,
});

const settling = ref(false);

const canAdd = computed(() =>
  permissions.getAccess("franchisee_financial", "add"),
);

const canEdit = computed(() =>
  permissions.getAccess("franchisee_financial", "edit"),
);

const settleNetValue = computed(() => {
  const baseValue = Number(selected.value?.value ?? 0);
  const discount = Number(settleForm.value.discount ?? 0);
  const fine = Number(settleForm.value.fine ?? 0);

  return baseValue - discount + fine;
});

const totals = computed(() => {
  const accumulatedTotals = {
    overdue: 0,
    overdueCount: 0,
    paid: 0,
    paidCount: 0,
    pending: 0,
    pendingCount: 0,
  };

  for (const row of rows.value) {
    if (row.status === "paid") {
      accumulatedTotals.paid += Number(row.paid_value ?? 0);
      accumulatedTotals.paidCount += 1;

      continue;
    }

    if (row.status === "overdue") {
      accumulatedTotals.overdue += Number(row.value ?? 0);
      accumulatedTotals.overdueCount += 1;

      continue;
    }

    if (row.status === "pending") {
      accumulatedTotals.pending += Number(row.value ?? 0);
      accumulatedTotals.pendingCount += 1;
    }
  }

  return accumulatedTotals;
});

const columns = [
  {
    align: "left",
    field: "origin",
    label: "Origem",
    name: "origin",
  },
  {
    align: "left",
    field: "history",
    label: "Descrição",
    name: "history",
  },
  {
    align: "left",
    field: "value",
    label: "Valor",
    name: "value",
  },
  {
    align: "left",
    field: "due_date",
    label: "Vencimento",
    name: "due_date",
  },
  {
    align: "left",
    field: "status",
    label: "Status",
    name: "status",
  },
  {
    align: "right",
    field: "actions",
    label: "Ações",
    name: "actions",
  },
];

const defaultCreateForm = () => {
  const today = new Date();

  return {
    due_date: today.toLocaleDateString("pt-BR"),
    due_date_iso: today.toISOString().slice(0, 10),
    history: "",
    obs: "",
    value: 0,
  };
};

const { form: createForm } = useForm(defaultCreateForm());

const {
  loading: creating,
  validationErrors: createValidationErrors,
  execute: executeCreate,
} = useSubmitHandler({
  containerRef: createScrollAreaRef,
  formRef: createFormRef,
  onSuccess: async () => {
    createDialog.value = false;

    await loadData();
  },
  scrollFn: scrollToComponent,
});

const changeStatus = (row) => {
  if (row.status === "paid") return;

  openSettle(row);
};

const formatCurrency = (value) =>
  new Intl.NumberFormat("pt-BR", {
    currency: "BRL",
    style: "currency",
  }).format(Number(value ?? 0));

const loadData = async () => {
  try {
    rows.value = await getPayablesMe();
  } catch (error) {
    console.error("Erro ao buscar contas a pagar:", error);
  }
};

const onCreate = async () => {
  await executeCreate(() =>
    createPayableMe({
      due_date: createForm.due_date_iso,
      history: createForm.history,
      obs: createForm.obs || null,
      value: createForm.value,
    }),
  );
};

const onSettle = async () => {
  if (!selected.value) return;

  settling.value = true;

  try {
    await settlePayableMe(selected.value.id, {
      discount: settleForm.value.discount,
      fine: settleForm.value.fine,
      payment_date: settleForm.value.payment_date_iso,
    });

    settleDialog.value = false;

    await loadData();
  } catch (error) {
    console.error(error);
  } finally {
    settling.value = false;
  }
};

const openCreate = () => {
  Object.assign(createForm, defaultCreateForm());

  createDialog.value = true;
};

const openInvoice = (row) => {
  window.open(row.invoice_url, "_blank");
};

const openSettle = (row) => {
  const today = new Date();

  selected.value = row;

  settleForm.value = {
    discount: Number(row.discount ?? 0),
    fine: Number(row.fine ?? 0),
    payment_date: today.toLocaleDateString("pt-BR"),
    payment_date_iso: today.toISOString().slice(0, 10),
  };

  settleDialog.value = true;
};

const positiveAmountRule = (value) =>
  Number(value) > 0 || "Informe um valor maior que zero.";

onMounted(loadData);
</script>