import { whenRequest } from '@wix/fe-essentials/http-client/testkit/client';
import {
  listDataExtensionSchemas,
  updateDataExtensionSchema,
} from '@wix/bex-utils/@wix/ambassador-data-extensions-v1-data-extension-schema/http';
import type { DataExtensionSchema } from '@wix/bex-utils/@wix/ambassador-data-extensions-v1-data-extension-schema/types';
import { InMemoryBackend } from '../testkit/backend';
import { Chance } from 'chance';

export function createSchema(chance: Chance.Chance) {
  return ({
    createdDate = chance.date({
      min: new Date(Date.now() - 365 * 24 * 60 * 60 * 1000),
      max: new Date(),
    }) as Date,
    updatedDate = createdDate,
    fqdn = 'wix.patterns.dummyservice.v1.dummy_entity',
    namespace = '_user_fields',
    ...overrides
  }: Partial<DataExtensionSchema> = {}) =>
    ({
      id: chance.guid(),
      createdDate,
      updatedDate,
      namespace,
      fqdn,
      ...overrides,
    } as DataExtensionSchema);
}

export function createBackend(
  initialSchema: DataExtensionSchema,
  appSchemas: DataExtensionSchema[],
) {
  const chance = new Chance();
  return new InMemoryBackend<DataExtensionSchema>({
    total: 1 + appSchemas.length,
    paginationMode: 'offset',
    delay: { min: 100, max: 2000 },
    createOne: (i) =>
      createSchema(chance)(i === 0 ? initialSchema : appSchemas[i - 1]),
    predicate: (query) => {
      const filters = query.filters ?? {};
      const { fqdn } = filters;
      return (item) => item.fqdn === fqdn;
    },
    orderBy: (query) => {
      return [...(query.sort ?? [])];
    },
    itemKey: (item) => item.id!,
  });
}

export const dataExtensionAPIHttpClientMocks = (
  initialSchema: DataExtensionSchema = {},
  appSchemas: DataExtensionSchema[] = [],
) => {
  const dataExtensionBackend = createBackend(initialSchema, appSchemas);
  return [
    whenRequest(listDataExtensionSchemas)
      .reply(200, async ({ fqdn }) => {
        return dataExtensionBackend
          .fetchData({
            limit: 1 + appSchemas.length,
            filters: {
              fqdn,
            },
          })
          .then(({ items }) => {
            return { dataExtensionSchemas: items };
          });
      })
      .persist(),
    whenRequest(updateDataExtensionSchema)
      .reply(200, async (updatedSchema) => {
        return dataExtensionBackend
          .update(updatedSchema.dataExtensionSchema!)
          .then(() => {
            return updatedSchema;
          });
      })
      .persist(),
  ];
};
