import {
  InitData,
  LogLevel,
  TracedFetch,
  LocalLogger,
  ObjectValue,
  InitDataProvider,
  InitQuery,
  HashData,
} from "../../shared/types";
import { hashRequest, initRequest } from "../edge";
import { defaultBranchName } from "../../shared";
import newTracedFetch from "../../shared/helpers/newTracedFetch";
import defaultLocalLogger from "../../shared/helpers/defaultLocalLogger";

export default class HypertuneEdgeInitDataProvider implements InitDataProvider {
  private readonly baseUrl: string;
  private readonly token: string;
  private readonly branchName: string | null;
  private readonly tracedFetch: TracedFetch;

  // eslint-disable-next-line max-params
  constructor({
    baseUrl,
    token,
    branchName = null,
    localLogger = defaultLocalLogger,
    timeoutMs = 10_000,
  }: {
    baseUrl: string;
    token: string;
    branchName?: string | null;
    localLogger?: LocalLogger;
    timeoutMs?: number;
  }) {
    if (branchName !== null && branchName !== defaultBranchName) {
      localLogger(
        LogLevel.Warn,
        `using non default branch name: "${branchName}"`,
        {}
      );
    }
    this.baseUrl = baseUrl;
    this.token = token;
    this.branchName = branchName;
    this.tracedFetch = newTracedFetch({
      timeoutMs,
      localLogger,
    });
  }

  // eslint-disable-next-line class-methods-use-this
  getName(): string {
    return "Hypertune Edge";
  }

  getInitData({
    traceId,
    initQuery,
    variableValues,
  }: {
    traceId: string;
    initQuery: InitQuery;
    variableValues: ObjectValue;
  }): Promise<InitData> {
    return initRequest({
      traceId,
      query: initQuery,
      variables: variableValues,
      token: this.token,
      branchName: this.branchName,
      edgeBaseUrl: this.baseUrl,
      tracedFetch: this.tracedFetch,
    });
  }

  getHashData({
    traceId,
    initQuery,
    variableValues,
  }: {
    traceId: string;
    initQuery: InitQuery;
    variableValues: ObjectValue;
  }): Promise<HashData> {
    return hashRequest({
      traceId,
      query: initQuery,
      variables: variableValues,
      token: this.token,
      branchName: this.branchName,
      edgeBaseUrl: this.baseUrl,
      tracedFetch: this.tracedFetch,
    });
  }
}
