import {
  AddressSchema,
  CommunicationDetailsSchema,
  EntityContainerSchema,
  EntitySchema,
  GenderSchema,
  KeyValueOfStringAndStringSchema,
  LabelSchema,
  NotificationChannelSchema,
  OrganisationSchema,
} from '@isa/common/data-access';
import { z } from 'zod';
import { CustomerType } from '../models';
import { AssignedPayerSchema } from './assigned-payer.schema';
import { AttributeSchema } from './attribute.schema';
import { BonusCardSchema } from './bonus-card.schema';
import { BranchSchema } from './branch.schema';
import { LinkedRecordSchema } from './linked-record.schema';
import { ShippingAddressSchema } from './shipping-address.schema';
import { UserSchema } from './user.schema';

export const CustomerSchema = z
  .object({
    address: AddressSchema.describe('Address').optional(),
    agentComment: z.string().describe('Agent comment').optional(),
    attributes: z
      .array(EntityContainerSchema(AttributeSchema))
      .describe('Attribute list')
      .optional(),
    bonusCard: EntityContainerSchema(BonusCardSchema)
      .describe('Bonus card information')
      .optional(),
    campaignCode: z.string().describe('Campaign code').optional(),
    clientChannel: z.number().describe('Client channel').optional(),
    communicationDetails: CommunicationDetailsSchema.describe(
      'Communication details',
    ).optional(),
    createdInBranch: EntityContainerSchema(BranchSchema)
      .describe('Created in branch')
      .optional(),
    customerGroup: z.string().describe('Customer group').optional(),
    customerNumber: z.string().describe('Customer number').optional(),
    customerStatus: z.number().describe('Customer status').optional(),
    customerType: z.nativeEnum(CustomerType).describe('Customer type'),
    dateOfBirth: z.string().describe('Date of birth').optional(),
    deactivationComment: z.string().describe('Deactivation comment').optional(),
    features: z
      .array(KeyValueOfStringAndStringSchema)
      .describe('Features')
      .optional(),
    fetchOnDeliveryNote: z
      .boolean()
      .describe('Fetch on delivery note')
      .optional(),
    firstName: z.string().describe('First name').optional(),
    gender: GenderSchema.describe('Gender').optional(),
    hasOnlineAccount: z
      .boolean()
      .describe('Whether has onlineAccount')
      .optional(),
    isGuestAccount: z.boolean().describe('Whether guestAccount').optional(),
    label: EntityContainerSchema(LabelSchema).describe('Label').optional(),
    lastName: z.string().describe('Last name').optional(),
    linkedRecords: z
      .array(LinkedRecordSchema)
      .describe('List of linked records')
      .optional(),
    notificationChannels: NotificationChannelSchema.describe(
      'Notification channels',
    ).optional(),
    orderCount: z.number().describe('Number of orders').optional(),
    organisation: OrganisationSchema.describe(
      'Organisation information',
    ).optional(),
    payers: z.array(AssignedPayerSchema).describe('Payers').optional(),
    preferredPaymentType: z
      .number()
      .describe('PreferredPayment type')
      .optional(),
    shippingAddresses: z
      .array(EntityContainerSchema(ShippingAddressSchema))
      .describe('Shipping addresses')
      .optional(),
    statusChangeComment: z
      .string()
      .describe('Status change comment')
      .optional(),
    statusComment: z.string().describe('Status comment').optional(),
    title: z.string().describe('Title').optional(),
    user: EntityContainerSchema(UserSchema)
      .describe('User information')
      .optional(),
  })
  .extend(EntitySchema.shape)
  .describe('Customer');

export type Customer = z.infer<typeof CustomerSchema>;
