import { generateQueryString } from "@/utils/queryStringUtil";
import { apiSlice } from ".";
import URLS from "./constants";

interface GetIndividualPropertiesListResponse {
  data: {
    results: individualProperties[];
    page: number;
    limit: number;
    totalPages: number;
    totalResults: number;
  };
  code: number;
  message: string;
  success: boolean;
  error?: object;
}

interface GetIndividualPropertiesByIdResponse {
  data: individualProperties;
  code: number;
  message: string;
  success: boolean;
  error?: object;
}

interface CreateIndividualPropertiesResponse {
  data: individualProperties;
  code: number;
  message: string;
  success: boolean;
  error?: object;
}

interface GetIndividualPropertiesParams {
  page?: number;
  limit?: number;
  search?: string;
  propertyType?: string;
  availableFor?: string;
  size?: string;
  price?: string;
  availability?: string;
  addedBy?: string;
  populate?: string;
  includeTimeStamps?: boolean;
  companyId?: string;
  /** Request unitOfMeasurement in list response (if backend uses select/fields) */
  select?: string;
}

interface GetIndividualPropertiesByIdParams {
  [key: string]: unknown;
}

interface UpdateIndividualPropertiesArg {
  id: string;
  data: Partial<individualProperties>;
}

interface PropertyVisitor {
  id?: string;
  leadId?: string;
  contactId?: string;
  name?: string;
  email?: string;
  phone?: string;
  visitedAt?: string;
  [key: string]: unknown;
}

interface GetPropertyVisitorsResponse {
  data: PropertyVisitor[] | { results: PropertyVisitor[] };
  code: number;
  message: string;
  success: boolean;
  error?: object;
}

interface GetPropertyProjectNamesParams {
  status?: "active" | "inactive" | "draft";
  isViewOnly?: boolean;
}

interface GetPropertyProjectNamesResponse {
  data: {
    id: string;
    projectName: string;
    locality?: { id: string; name: string | null };
    city?: { id: string; name: string | null };
  }[];
  code: number;
  message: string;
  success: boolean;
}

interface GeneratePropertyNameDescriptionRequest {
  property_data: Record<string, unknown>;
}

interface GeneratePropertyNameDescriptionResponse {
  data: {
    title: string;
    description: string;
  };
  code: number;
  message: string;
  success: boolean;
  error?: object;
}

interface PropertyVisibilityResponse {
  data: {
    visibleToUsers: Array<string | { id?: string; _id?: string }>;
    visibleToTeams: Array<string | { id?: string; _id?: string }>;
  };
  code: number;
  message: string;
  success: boolean;
  error?: object;
}

interface UpdatePropertyVisibilityPayload {
  propertyId: string;
  visibleToUsers: string[];
  visibleToTeams: string[];
}

interface BulkUpdateIndividualPropertiesResponse {
  code: number;
  message: string;
  success: boolean;
  data?: individualProperties[];
  error?: object;
}

interface BulkUpdateVisibilityPayload {
  propertyIds: string[];
  isPublicVisibility: boolean;
}

interface BulkDeleteIndividualPropertiesResponse {
  code: number;
  message: string;
  success: boolean;
  data?: individualProperties[];
  error?: object;
}

interface SuggestedPropertiesResponse {
  code: number;
  message: string;
  success: boolean;
  data?: any;
  error?: object;
}

export const individualPropertiesApi = apiSlice.injectEndpoints({
  endpoints: (builder) => ({
    getIndividualProperties: builder.query<
      GetIndividualPropertiesListResponse,
      GetIndividualPropertiesParams
    >({
      query: (params: GetIndividualPropertiesParams) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}?${generateQueryString(
          params as Record<string, unknown>,
        )}`,
        method: "GET",
      }),
      providesTags: ["individualProperties"],
    }),

    getIndividualPropertiesById: builder.query<
      GetIndividualPropertiesByIdResponse,
      string
    >({
      query: (id) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/${id}`,
        method: "GET",
      }),
      providesTags: ["editIndividualProperties"],
    }),

    getPropertyProjectNames: builder.query<
      GetPropertyProjectNamesResponse,
      GetPropertyProjectNamesParams | void
    >({
      query: (params = { status: "active", isViewOnly: true }) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/project-names?${generateQueryString(
          params as Record<string, unknown>,
        )}`,
        method: "GET",
      }),
    }),

    getIndividualPropertiesPublicById: builder.query<
      GetIndividualPropertiesByIdResponse,
      string
    >({
      query: (id) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/${id}/public`,
        method: "GET",
      }),
      providesTags: ["editIndividualProperties"],
    }),

    createIndividualProperties: builder.mutation<
      CreateIndividualPropertiesResponse,
      Partial<individualProperties>
    >({
      query: (body: Partial<individualProperties>) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}`,
        method: "POST",
        body,
      }),
      invalidatesTags: (result, _error, _arg) =>
        result ? ["individualProperties"] : [],
    }),

    updateIndividualProperties: builder.mutation<
      CreateIndividualPropertiesResponse,
      UpdateIndividualPropertiesArg
    >({
      query: ({ id, data }: UpdateIndividualPropertiesArg) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/${id}`,
        method: "PATCH",
        body: data,
      }),
      invalidatesTags: ["individualProperties", "editIndividualProperties"],
    }),

    deleteIndividualProperties: builder.mutation<{ success: boolean }, string>({
      query: (id: string) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/${id}`,
        method: "DELETE",
      }),
      invalidatesTags: ["individualProperties", "editIndividualProperties"],
    }),

    getProspects: builder.query({
      query: (id) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/${id}/prospects`,
        method: "GET",
      }),
      providesTags: ["individualPropertiesProspects"],
    }),

    getPropertyVisitors: builder.query<GetPropertyVisitorsResponse, string>({
      query: (propertyId) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/${propertyId}/visitors`,
        method: "GET",
      }),
      providesTags: ["individualPropertiesVisitors"],
    }),
    getDefaultFormValues: builder.query({
      query: () => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/defaultFormValues`,
        method: "GET",
      }),
    }),

    updatePropertySource: builder.mutation<
      CreateIndividualPropertiesResponse,
      {
        propertyId: string;
        source: Array<{ sourceProjectId: string; id: string }>;
      }
    >({
      query: ({ propertyId, source }) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/${propertyId}/source`,
        method: "PATCH",
        body: { source },
      }),
      invalidatesTags: ["individualProperties", "editIndividualProperties"],
    }),

    getIndividualPropertyVisibility: builder.query<
      PropertyVisibilityResponse,
      string
    >({
      query: (propertyId) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/${propertyId}/visibility`,
        method: "GET",
      }),
      providesTags: ["propertyVisibility"],
    }),

    updateIndividualPropertyVisibility: builder.mutation<
      PropertyVisibilityResponse,
      UpdatePropertyVisibilityPayload
    >({
      query: ({ propertyId, visibleToUsers, visibleToTeams }) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/${propertyId}/visibility`,
        method: "PUT",
        body: { visibleToUsers, visibleToTeams },
      }),
      invalidatesTags: ["propertyVisibility"],
    }),

    bulkUpdateIndividualProperties: builder.mutation<
      BulkUpdateIndividualPropertiesResponse,
      { propertyIds: string[]; possessionStatus: string }
    >({
      query: (body) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/bulk-update`,
        method: "PATCH",
        body,
      }),
      invalidatesTags: ["individualProperties"],
    }),
    bulkDeleteIndividualProperties: builder.mutation<
      BulkDeleteIndividualPropertiesResponse,
      { propertyIds: string[] }
    >({
      query: (body) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/bulk-delete`,
        method: "DELETE",
        body,
      }),
      invalidatesTags: ["individualProperties"],
    }),

    bulkUpdateVisibility: builder.mutation<
      BulkUpdateIndividualPropertiesResponse,
      BulkUpdateVisibilityPayload
    >({
      query: (body) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/bulk-update-visibility`,
        method: "PATCH",
        body,
      }),
      invalidatesTags: ["individualProperties"],
    }),

    suggestedProperties: builder.mutation<
      SuggestedPropertiesResponse,
      { leadId: string; propertyIds: string[]; model?: "lead" | "contact" }
    >({
      query: ({ leadId, propertyIds, model = "lead" }) => ({
        url: `${URLS.LEAD}/suggestedProperties/${leadId}?model=${model}`,
        method: "POST",
        body: { propertyIds },
      }),
    }),

    generatePropertyNameDescription: builder.mutation<
      GeneratePropertyNameDescriptionResponse,
      GeneratePropertyNameDescriptionRequest
    >({
      query: (body) => ({
        url: `${URLS.INDIVIDUAL_PROPERTIES}/generate-name-description`,
        method: "POST",
        body,
      }),
    }),
  }),
  overrideExisting: false,
});

export const {
  useGetIndividualPropertiesQuery,
  useGetIndividualPropertiesByIdQuery,
  useGetIndividualPropertiesPublicByIdQuery,
  useCreateIndividualPropertiesMutation,
  useUpdateIndividualPropertiesMutation,
  useDeleteIndividualPropertiesMutation,
  useGetProspectsQuery,
  useGetPropertyVisitorsQuery,
  useGetDefaultFormValuesQuery,
  useGetPropertyProjectNamesQuery,
  useUpdatePropertySourceMutation,
  useGetIndividualPropertyVisibilityQuery,
  useUpdateIndividualPropertyVisibilityMutation,
  useBulkUpdateIndividualPropertiesMutation,
  useBulkDeleteIndividualPropertiesMutation,
  useBulkUpdateVisibilityMutation,
  useSuggestedPropertiesMutation,
  useGeneratePropertyNameDescriptionMutation,
} = individualPropertiesApi;
