import { Inject, Injectable } from '@severo-tech/injection-decorator';
import axios, { isAxiosError } from 'axios';
import { BadGateway } from '@somma/node-errors';

import { IDebitNoticeClient, ILogger } from '../../application/contracts';
import { DebitNotice } from '../../domain/debit-notice';
import { RetryMethod } from '../../application/decorators';

type ONSDebitNoticesDTO = {
  page: number,

  perPage: number,

  count: number,

  data: DebitNotice[],
}

@Injectable()
export class ONSDebitNoticeClient implements IDebitNoticeClient {
  private readonly baseURL = process.env.ONS_API_URL;

  @Inject('ZenviaLogger')
  protected readonly logger!: ILogger;

  @RetryMethod({ ms: 500 })
  public async getDebitNotice(year: number, month: number, page: number, perPage: number): Promise<DebitNotice[]> {
    const url = `${this.baseURL}/debit-notices`;

    const params = {
      year,
      month,
      page,
      perPage,
    };

    this.logger.debug(`"ONSDebitNoticeClient.getDebitNotice" - Sending GET request to url [${url}] with params [${JSON.stringify(params)}]`);

    try {
      const { data: result } = await axios.get<ONSDebitNoticesDTO>(url, { params });

      return result.data;
    } catch (error) {
      const message = `Cannot get ONS Debit Notices: GET - "${url}" | params: [${JSON.stringify(params)}]`;
      const err = isAxiosError(error) ? error.response?.data : error;
      this.logger.error(message, err);
      throw new BadGateway(message, undefined, err);
    }
  }
}
