import { AbsoluteTime, AmountJson, TranslatedString } from "@gnu-taler/taler-util";
import { format } from "date-fns";
import { Fragment, VNode, h } from "preact";
import { AmlEvent } from "./CaseDetails.js";
import { DefaultForm, FlexibleForm, UIFormField, useTranslationContext } from "@gnu-taler/web-util/browser";
import { amlStateConverter } from "../utils/converter.js";
import { AmlExchangeBackend } from "../utils/types.js";

export function ShowConsolidated({
  history,
  until,
}: {
  history: AmlEvent[];
  until: AbsoluteTime;
}): VNode {
  const { i18n } = useTranslationContext();

  const cons = getConsolidated(history, until);

  const form: FlexibleForm<Consolidated> = {
    behavior: (form) => {
      return {
        aml: {
          threshold: {
            hidden: !form.aml
          },
          since: {
            hidden: !form.aml
          },
          state: {
            hidden: !form.aml
          }
        }
      };
    },
    design: [
      {
        title: i18n.str`AML`,
        fields: [
          {
            type: "amount",
            props: {
              label: i18n.str`Threshold`,
              name: "aml.threshold",
            },
          },
          {
            type: "choiceHorizontal",
            props: {
              label: i18n.str`State`,
              name: "aml.state",
              converter: amlStateConverter,
              choices: [
                {
                  label: i18n.str`Frozen`,
                  value: AmlExchangeBackend.AmlState.frozen,
                },
                {
                  label: i18n.str`Pending`,
                  value: AmlExchangeBackend.AmlState.pending,
                },
                {
                  label: i18n.str`Normal`,
                  value: AmlExchangeBackend.AmlState.normal,
                },
              ],
            },
          },
        ],
      },
      Object.entries(cons.kyc).length > 0
        ? {
          title: i18n.str`KYC`,
          fields: Object.entries(cons.kyc).map(([key, field]) => {
            const result: UIFormField = {
              type: "text",
              props: {
                label: key as TranslatedString,
                name: `kyc.${key}.value`,
                help: `${field.provider} since ${field.since.t_ms === "never"
                  ? "never"
                  : format(field.since.t_ms, "dd/MM/yyyy")
                  }` as TranslatedString,
              },
            };
            return result;
          }),
        }
        : undefined,
    ],
  };
  return (
    <Fragment>
      <h1 class="text-base font-semibold leading-7 text-black">
        Consolidated information {until.t_ms === "never"
          ? ""
          : `after ${format(until.t_ms, "dd MMMM yyyy")}`}
      </h1>
      <DefaultForm
        key={`${String(Date.now())}`}
        form={form}
        initial={cons}
        readOnly
        onUpdate={() => { }}
      />
    </Fragment>
  );
}

interface Consolidated {
  aml: {
    state: AmlExchangeBackend.AmlState;
    threshold: AmountJson;
    since: AbsoluteTime;
  };
  kyc: {
    [field: string]: {
      value: any;
      provider: string;
      since: AbsoluteTime;
    };
  };
}

function getConsolidated(
  history: AmlEvent[],
  when: AbsoluteTime,
): Consolidated {
  const initial: Consolidated = {
    aml: {
      state: AmlExchangeBackend.AmlState.normal,
      threshold: {
        currency: "ARS",
        value: 1000,
        fraction: 0,
      },
      since: AbsoluteTime.never()
    },
    kyc: {},
  };
  return history.reduce((prev, cur) => {
    if (AbsoluteTime.cmp(when, cur.when) < 0) {
      return prev;
    }
    switch (cur.type) {
      case "kyc-expiration": {
        cur.fields.forEach((field) => {
          delete prev.kyc[field];
        });
        break;
      }
      case "aml-form": {
        prev.aml = {
          since: cur.when,
          state: cur.state,
          threshold: cur.threshold
        }
        break;
      }
      case "kyc-collection": {
        Object.keys(cur.values).forEach((field) => {
          prev.kyc[field] = {
            value: (cur.values as any)[field],
            provider: cur.provider,
            since: cur.when,
          };
        });
        break;
      }
    }
    return prev;
  }, initial);
}