<template>
  <div class="ListButtons">
    <r-btn
      v-if="isShowBtn"
      @click="opened = !opened"
      icon="pgs-import"
      label="Выгрузить"
      :loading="loading"
    >
    </r-btn>
    <operation-dialog v-model="opened" title="Параметры выгрузки" @hide="clear">
      <q-form ref="form">
        <data-block :form-data="{ label: 'Период' }" bolder no-padding>
          <x-date-time-range
            :format="backendDateFormat"
            :default="rangeFields.value"
            :focus="rangeFields.focus"
            :from="rangeFields.value.from"
            :to="rangeFields.value.to"
            :required="true"
            @input="(v) => setFieldValue(v)"
          />
        </data-block>
      </q-form>
      <div class="ListButtons__CountInfo">
        <div class="ListButtons__InfoText">
          <p>Количество записей за выбранный период - {{ count }}</p>
          <p v-if="isOverLimit">
            Максимальное количество записей в выгрузке - {{ limit }}. Для
            успешного скачивания требуется изменить период на менее
            продолжительный
          </p>
        </div>
      </div>
      <template #right-actions>
        <r-btn
          @click="requestReport()"
          icon="pgs-import"
          label="Скачать"
          :loading="loading"
          :disable="isDisableImportBtn"
        >
          <template v-slot:loading>
            <q-spinner color="primary" size="1em" />
          </template>
        </r-btn>
      </template>
    </operation-dialog>
  </div>
</template>

<style lang="scss" scoped>
.ListButtons {
  &__CountInfo {
    height: 100%;
    display: flex;
    align-items: center;
  }
  &__InfoText {
    width: 100%;
    text-align: center;
  }
}
</style>

<script lang="ts">
import { mapGetters } from 'vuex';
import { Component, Mixins, Watch, Ref } from 'vue-property-decorator';
import NotificationsListener from '@/recruits/mixins/notifications-listener';

import { notifyError } from '@utils/notify';
import { DateFormat } from '@constants/utils/format-date';
import { convertDateFormat, doMathWithDate } from '@utils/format-date';
import { getNameStrings } from '@components/reports/utils';
import { reportScheduler as reportSchedulerApi } from '@/recruits/api/stat-report-scheduler';
import { reports as reportsApi } from '@/recruits/api/ervu-reports';
import { fetchDocumentAttachment } from '@utils/fetch-document-attachment';
import dataBlock from '@components/cards/statements/components/dataBlock.vue';
import XDateTimeRange from '@/recruits/components/reports/list/components/x-date-time-range.vue';
import XDateInput from '@/recruits/components/common/x-date-input.vue';
import { USER_SCOPES } from '@constants/entities/Scope';
import { JournalServiceApi } from '@/recruits/openapi/journal-service';
import { debounce } from 'lodash';
import { QForm } from 'quasar';

const JOURNAL_SERVICE_API = new JournalServiceApi();

@Component({
  components: {
    XDateTimeRange,
    dataBlock,
    XDateInput,
  },
  computed: {
    ...mapGetters('oidcClient', ['currentUser']),
    backendDateFormat() {
      return DateFormat.backend;
    },
  },
})
export default class LogImportButtons extends Mixins(NotificationsListener) {
  @Ref('form') formRef: QForm;

  count = 0;
  limit = 0;
  loadCountFn: () => void;

  rangeFields = {
    dense: true,
    filled: true,
    hideBottomSpace: true,
    format: DateFormat.backend,
    focus: false,
    hideBottomSpaceFrom: true,
    value: {
      to: convertDateFormat(new Date(), '', DateFormat.backend),
      from: convertDateFormat(
        doMathWithDate('subMonths', new Date(), 1),
        '',
        DateFormat.backend
      ),
    },
  };

  setFieldValue(v: { to: string; from: string }) {
    this.rangeFields.value = v;
    this.loadCountFn();
  }

  get isShowBtn(): boolean {
    return this.$AC.haveOneOfScope([
      USER_SCOPES.GOMU_OBSERVER,
      USER_SCOPES.GOMU_SPECIALIST,
    ]);
  }

  currentUser: any;
  opened = false;
  public loading = false;
  private targetReportId = '';

  protected clear() {
    this.opened = false;
  }

  @Watch('rangeFields', { deep: true })
  private showValue(value: any) {
    console.log(value);
  }

  async requestReport() {
    if (this.currentUser) {
      const {
        given_name,
        middle_name,
        family_name,
        sub,
        domain_id,
      } = this.currentUser;
      const payload = {
        creator: {
          id: sub,
          organizationId: domain_id,
          firstname: given_name,
          middlename: middle_name,
          surname: family_name,
          ...getNameStrings(given_name, middle_name, family_name),
        },
        name: 'Журнал загрузки записей',
        number: +convertDateFormat(new Date(), '', DateFormat.dateNumber),
        // TODO: Параметры нужно брать из диалога
        params: {
          range: {
            from: this.rangeFields.value.from,
            to: this.rangeFields.value.to,
            timeZone: Intl.DateTimeFormat().resolvedOptions().timeZone,
          },
        },
        parentId: '3',
        queryDefinitionId: '9c436752-54e5-4cf7-88bc-0415d51283be',
        source: 'ervu-journal-service',
        hideNotification: true,
      };

      try {
        this.loading = true;
        this.targetReportId = await reportSchedulerApi.create(payload);
      } catch (error: any) {
        notifyError(error.message.toString());
        this.loading = false;
      }
    }
  }

  handleNotification(messageData: any): void {
    if (
      messageData &&
      messageData.body &&
      messageData.body.statementId === this.targetReportId
    ) {
      Promise.resolve(messageData.body)
        .then((body) => {
          if (body.type !== 'error') {
            return reportsApi
              .get(body.statementId)
              .then((report: any) => {
                fetchDocumentAttachment(
                  report,
                  'download',
                  's3filename',
                  's3uri'
                );
              })
              .catch((error: any) => {
                notifyError(error.message.toString());
              });
          }
        })
        .finally(() => {
          this.targetReportId = '';
          this.loading = false;
          this.clear();
        });
    }
  }

  get isOverLimit(): boolean {
    return this.count > this.limit;
  }

  get isDisableImportBtn(): boolean {
    return !this.count || this.isOverLimit;
  }

  clearCountData(): void {
    this.limit = 0;
    this.count = 0;
  }

  created(): void {
    this.loadCountFn = debounce(() => {
      this.formRef.validate().then((isValidDateRange) => {
        if (isValidDateRange) {
          JOURNAL_SERVICE_API.getImportSuccessCount({
            search: {
              dateFrom: this.rangeFields.value.from,
              dateTo: this.rangeFields.value.to,
            },
          })
            .then(({ data }) => {
              this.count = data.count || 0;
              this.limit = data.limit || 0;
            })
            .catch(() => this.clearCountData);
        } else this.clearCountData();
      });
    }, 500);
  }
}
</script>
