import { createSlice, createAsyncThunk } from "@reduxjs/toolkit";
import { GET, POST } from "../../utils/api";
import { API } from "../../endpoints/common_endpoints";

// Thunk for getting home banners
//original
// export const getAllProducts = createAsyncThunk(
//   "all-products",
//   async (
//     {
//       category_id,
//       subcategory_id,
//       childcategory_id,
//       brand_id,
//       name = "",
//       priceOrder,
//       type = "",
//       need_id,
//       sortBy,
//       shape_id,
//     },
//     { rejectWithValue },
//   ) => {
//     try {
//       const Data = await GET(
//         API.GET_ALL_PRODUCTS
//           +`?category_id=${category_id ||
//             ""}&sub_category_id=${subcategory_id ||
//             ""}&child_category_id=${childcategory_id || ""}` +
//           `&brand_id=${brand_id || ""}&need_id=${need_id || ""}&name=${name ||
//             ""}&priceOrder=${priceOrder || ""}&sortBy=${sortBy ||
//             ""}&shape_id=${shape_id || ""}`,
//       );

//       return Data?.data;
//     } catch (error) {
//       return rejectWithValue(error.message);
//     }
//   },
// );

export const getAllProducts = createAsyncThunk(
  "all-products",
  async (
    {
      category_id,
      subcategory_id,
      childcategory_id,
      brand_id,
      name = "",
      priceOrder,
      type = "",
      need_id,
      sortBy,
      shape_id,
      metal_id,
      size_id,
      min_price,
      max_price,
      page,
    },
    { rejectWithValue },
  ) => {
    try {
      const Data = await GET(
        API.GET_ALL_PRODUCTS +
          `?category_id=${category_id || ""}&sub_category_id=${subcategory_id || ""}&child_category_id=${childcategory_id || ""}` +
          `&brand_id=${brand_id || ""}&need_id=${need_id || ""}&name=${name || ""}&priceOrder=${priceOrder || ""}&sortBy=${sortBy || ""}&shape_id=${shape_id || ""}` +
          `&metal_id=${metal_id || ""}&size_id=${size_id || ""}&min_price=${min_price || ""}&max_price=${max_price || ""}&page=${page || 1}`,
      );

      return Data?.data;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

export const getAllTimeFavsProducts = createAsyncThunk(
  "all-products-material",
  async (
    {
      category_id,
      subcategory_id,
      childcategory_id,
      brand_id,
      name,
      priceOrder,
      type = "",
      need_id,
      shape_id,
    },
    { rejectWithValue },
  ) => {
    try {
      const Data = await GET(
        API.GET_ALL_TIME_PRODUCTS +
          `/${type}` +
          `?category_id=${category_id || ""}&sub_category_id=${
            subcategory_id || ""
          }&child_category_id=${childcategory_id || ""}` +
          `&brand_id=${brand_id || ""}&need_id=${need_id || ""}&name=${
            name || ""
          }&priceOrder=${priceOrder || ""}&shape_id=${shape_id || ""}`,
      );

      return Data?.data;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

export const getAllProductsHARVESTED = createAsyncThunk(
  "all-products-shape",
  async (
    {
      category_id,
      subcategory_id,
      childcategory_id,
      brand_id,
      name,
      priceOrder,
      type = "",
      need_id,
    },
    { rejectWithValue },
  ) => {
    try {
      const Data = await GET(
        API.GET_ALL_PRODUCTS +
          `/${type}` +
          `?category_id=${category_id || ""}&sub_category_id=${
            subcategory_id || ""
          }&child_category_id=${childcategory_id || ""}` +
          `&brand_id=${brand_id || ""}&need_id=${need_id || ""}&name=${
            name || ""
          }&priceOrder=${priceOrder || ""}`,
      );

      return Data?.data?.data;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

export const getAllProductsNewLaunch = createAsyncThunk(
  "all-products-newlaunch",
  async (
    {
      category_id,
      subcategory_id,
      childcategory_id,
      brand_id,
      name,
      priceOrder,
      type = "",
      need_id,
    },
    { rejectWithValue },
  ) => {
    try {
      const Data = await GET(
        API.GET_ALL_PRODUCTS +
          `/${type}` +
          `?category_id=${category_id || ""}&sub_category_id=${
            subcategory_id || ""
          }&child_category_id=${childcategory_id || ""}` +
          `&brand_id=${brand_id || ""}&need_id=${need_id || ""}&name=${
            name || ""
          }&priceOrder=${priceOrder || ""}`,
      );

      return Data?.data?.data;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

export const getAllOURProduct = createAsyncThunk(
  "all-products-populer",
  async (
    {
      category_id,
      subcategory_id,
      childcategory_id,
      brand_id,
      name,
      priceOrder,
      type = "",
      need_id,
    },
    { rejectWithValue },
  ) => {
    try {
      const Data = await GET(
        API.GET_ALL_OUR_PRODUCTS +
          `?category_id=${category_id || ""}&sub_category_id=${
            subcategory_id || ""
          }&child_category_id=${childcategory_id || ""}` +
          `&brand_id=${brand_id || ""}&need_id=${need_id || ""}&name=${
            name || ""
          }&priceOrder=${priceOrder || ""}`,
      );

      return Data?.data;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

// Thunk for gettingStore
export const getProduct = createAsyncThunk(
  "product",
  async (id, { rejectWithValue }) => {
    try {
      const data = await GET(API.GET_PRODUCT + `/${id}`);
      return data;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

export const getCommonVariant = createAsyncThunk(
  "product-variant",
  async (id, { rejectWithValue }) => {
    try {
      const data = await GET(API.GET_PRODUCT + `/variant/${id}`);
      return data;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

export const getSizeVariant = createAsyncThunk(
  "product-variant-size",
  async ({ id, metal_id, diamond_id }, { rejectWithValue }) => {
    try {
      const data = await GET(
        API.GET_PRODUCT +
          `/size-variant/${id}?metal_id=${metal_id}&diamond_id=${diamond_id}`,
      );
      return data;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

// Thunk for gettingStore
export const getLinkedProduct = createAsyncThunk(
  "linked-product",
  async (id, { rejectWithValue }) => {
    try {
      const data = await GET(API.GET_LINKED_PRODUCT + `/${id}`);
      return data;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

export const getTopSellingProduct = createAsyncThunk(
  "topsellingproducts-product",
  async ( { rejectWithValue }) => {
    try {
      const data = await GET(API.GET_TOP_SELLING_PRODUCTS);
      console.log(data," data for top selling products =")
      return data;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

// Thunk for gettingStore
export const getGroupByProduct = createAsyncThunk(
  "group-by-product",
  async ({ p_category_id }, { rejectWithValue }) => {
    try {
      const data = await GET(
        API.GET_ALL_PRODUCT_GROUP_BY_SUB_CATEGORIES +
          `?p_category_id=${p_category_id || ""}`,
      );
      return data;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

export const findCombination = createAsyncThunk(
  "auth/product-combination",
  async (data, { rejectWithValue }) => {
    try {
      const combinationdata = await POST(
        API.GET_PRODUCT + `/combination`,
        data,
      );

      return combinationdata;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

export const pincodeCheck = createAsyncThunk(
  "auth/product-pincode",
  async (data, { rejectWithValue }) => {
    try {
      const combinationdata = await POST(
        API.GET_PRODUCT + `/${data?.product_id}`,
        data,
      );

      return combinationdata;
    } catch (error) {
      console.log("catch value");

      return rejectWithValue(error.message);
    }
  },
);

// Thunk for getting Add banners
export const getspecialitystatus = createAsyncThunk(
  "product/add-specialstatus",
  async (_, { rejectWithValue }) => {
    try {
      const specialstatusData = await GET(API.GET_SPECIAL_STATUS);
      return specialstatusData;
    } catch (error) {
      return rejectWithValue(error.message);
    }
  },
);

const handleAsyncState = (state, action, isSignin = false) => {
  switch (action.type) {
    case "pending":
      state.status = "loading";
      break;
    case "fulfilled":
      state.status = "succeeded";
      if (isSignin) {
        state.token = action.payload;
        state.is_signin = true;
      }
      break;
    case "rejected":
      state.status = "failed";
      state.error = action.payload;
      if (isSignin) state.is_signin = false;
      break;
    default:
      return state;
  }
};
// Create the slice
const productSlice = createSlice({
  name: "product",
  initialState: {
    allProducts: [],
    allProductsGroup: [],
    allProductsFavs: [],
    topsellingproducts: [],
    allProductsSHARED: [],
    allProductsNewLaunch: [],
    allOurProducts: [],
    product: {},
    priceBounds: { max: 0, min: 0 },

    product_variant: {},
    variant_size: [],
    linked_products: [],
    addSpecialstatus: [],
    error: null,
    status: "idle",
  },
  reducers: {},
  extraReducers: (builder) => {
    builder
      .addCase(getAllProducts.pending, (state) => {
        state.status = "loading";
      })
      .addCase(getAllProducts.fulfilled, (state, action) => {
        state.status = "succeeded";
        state.allProducts = action.payload || [];
        state.priceBounds = {
          min: action.payload?.min_price,
          max: action.payload?.max_price,
        };
      })

      .addCase(getAllProducts.rejected, (state, action) => {
        state.status = "failed";
        state.error = action.payload;
      })
      .addCase(getAllTimeFavsProducts.pending, (state) => {
        state.status = "loading";
      })
      .addCase(getAllTimeFavsProducts.fulfilled, (state, action) => {
        state.status = "succeeded";
        state.allProductsFavs = action.payload || [];
      })

       .addCase(getTopSellingProduct.rejected, (state, action) => {
        state.status = "failed";
        state.error = action.payload;
      })
      .addCase(getTopSellingProduct.pending, (state) => {
        state.status = "loading";
      })
      .addCase(getTopSellingProduct.fulfilled, (state, action) => {
        state.status = "succeeded";

        state.topsellingproducts = action.payload || [];
        console.log("+++callingggggggggg")
      })

      .addCase(getAllTimeFavsProducts.rejected, (state, action) => {
        state.status = "failed";
        state.error = action.payload;
      })

      .addCase(getAllProductsHARVESTED.pending, (state) => {
        state.status = "loading";
      })
      .addCase(getAllProductsHARVESTED.fulfilled, (state, action) => {
        state.status = "succeeded";

        state.allProductsSHARED = action.payload || [];
      })
      .addCase(getAllProductsHARVESTED.rejected, (state, action) => {
        state.status = "failed";
        state.error = action.payload;
      })
      .addCase(getAllProductsNewLaunch.pending, (state) => {
        state.status = "loading";
      })
      .addCase(getAllProductsNewLaunch.fulfilled, (state, action) => {
        state.status = "succeeded";

        state.allProductsNewLaunch = action.payload || [];
      })
      .addCase(getAllProductsNewLaunch.rejected, (state, action) => {
        state.status = "failed";
        state.error = action.payload;
      })

      .addCase(getAllOURProduct.pending, (state) => {
        state.status = "loading";
      })
      .addCase(getAllOURProduct.fulfilled, (state, action) => {
        state.status = "succeeded";

        state.allOurProducts = action.payload || [];
      })
      .addCase(getAllOURProduct.rejected, (state, action) => {
        state.status = "failed";
        state.error = action.payload;
      })

      .addCase(getProduct.pending, (state) => {
        state.status = "loading";
      })
      .addCase(getProduct.fulfilled, (state, action) => {
        state.status = "succeeded";

        state.product = action.payload?.data || {};
      })
      .addCase(getProduct.rejected, (state, action) => {
        state.status = "failed";
        state.error = action.payload;
      })

      .addCase(getSizeVariant.pending, (state) => {
        state.status = "loading";
      })
      .addCase(getSizeVariant.fulfilled, (state, action) => {
        state.status = "succeeded";

        state.variant_size = action.payload?.data || [];
      })
      .addCase(getSizeVariant.rejected, (state, action) => {
        state.status = "failed";
        state.error = action.payload;
      })

      .addCase(getCommonVariant.pending, (state) => {
        state.status = "loading";
      })
      .addCase(getCommonVariant.fulfilled, (state, action) => {
        state.status = "succeeded";

        state.product_variant = action.payload?.data || {};
      })
      .addCase(getCommonVariant.rejected, (state, action) => {
        state.status = "failed";
        state.error = action.payload;
      })

      .addCase(getLinkedProduct.pending, (state) => {
        state.status = "loading";
      })
      .addCase(getLinkedProduct.fulfilled, (state, action) => {
        state.status = "succeeded";

        state.linked_products = action.payload?.data || {};
      })
      .addCase(getLinkedProduct.rejected, (state, action) => {
        state.status = "failed";
        state.error = action.payload;
      })

      .addCase(getGroupByProduct.pending, (state) => {
        state.status = "loading";
      })
      .addCase(getGroupByProduct.fulfilled, (state, action) => {
        state.status = "succeeded";
        state.allProductsGroup = action.payload || [];
      })
      .addCase(getGroupByProduct.rejected, (state, action) => {
        state.status = "failed";
        state.error = action.payload;
      })

      .addCase(findCombination.pending, (state) =>
        handleAsyncState(state, { type: "pending" }, true),
      )
      .addCase(findCombination.fulfilled, (state, action) =>
        handleAsyncState(
          state,
          { type: "fulfilled", payload: action.payload },
          true,
        ),
      )
      .addCase(findCombination.rejected, (state, action) =>
        handleAsyncState(
          state,
          { type: "rejected", payload: action.payload },
          true,
        ),
      )
      .addCase(pincodeCheck.pending, (state) =>
        handleAsyncState(state, { type: "pending" }, true),
      )
      .addCase(pincodeCheck.fulfilled, (state, action) =>
        handleAsyncState(
          state,
          { type: "fulfilled", payload: action.payload },
          true,
        ),
      )
      .addCase(pincodeCheck.rejected, (state, action) =>
        handleAsyncState(
          state,
          { type: "rejected", payload: action.payload },
          true,
        ),
      )

      .addCase(getspecialitystatus.pending, (state) => {
        state.status = "loading";
      })
      .addCase(getspecialitystatus.fulfilled, (state, action) => {
        state.status = "succeeded";
        state.addSpecialstatus = action.payload?.data || [];
      })
      .addCase(getspecialitystatus.rejected, (state, action) => {
        state.status = "failed";
        state.error = action.payload;
      });
  },
});

export default productSlice.reducer;
