import { RejectedActionPayload, ServerErrorResponse } from '@/interface/Shared';
import {
  PipCheckIn,
  PipCheckInResponse,
  CreatePipCheckInPayload,
} from '@/interface/PerformanceImprovementPlan';
import { apiDelete, apiGet, apiPost, apiPut } from '@/services/api/api';
import Helpers from '@/utilities/Helpers';
import { createAsyncThunk, createSlice, Draft, PayloadAction } from '@reduxjs/toolkit';
import { message } from 'antd';
import axios, { AxiosResponse } from 'axios';
import { PipCheckInActions } from './actionTypes';

interface PipCheckInState {
  pipCheckIns: PipCheckIn[];
  currentPipCheckIn: PipCheckIn | null;
  loading: boolean;
  error: string | null;
}

const initialState: PipCheckInState = {
  pipCheckIns: [],
  currentPipCheckIn: null,
  loading: false,
  error: null,
};

export const fetchPipCheckIns = createAsyncThunk(
  PipCheckInActions.FETCH_PIP_CHECK_INS_REQUEST,
  async (pipId: string) => {
    const response = (await apiGet(`/pips/${pipId}/pip-check-ins`)) as AxiosResponse<{ data: PipCheckIn[] }>;
    return response.data.data;
  },
);

export const createPipCheckIn = createAsyncThunk(
  PipCheckInActions.CREATE_PIP_CHECK_IN_REQUEST,
  async ({ pipId, ...payload }: CreatePipCheckInPayload & { pipId: string }, { rejectWithValue }) => {
    try {
      const response = (await apiPost(`/pips/${pipId}/pip-check-ins`, payload)) as AxiosResponse<PipCheckInResponse>;
      return response.data.data;
    } catch (error) {
      if (axios.isAxiosError(error) && error.response) {
        return rejectWithValue(error.response.data as ServerErrorResponse);
      }
      throw error;
    }
  },
);

export const updatePipCheckIn = createAsyncThunk(
  PipCheckInActions.UPDATE_PIP_CHECK_IN_REQUEST,
  async ({ pipId, id, ...payload }: Partial<CreatePipCheckInPayload> & { pipId: string; id: string }, { rejectWithValue }) => {
    try {
      const response = (await apiPut(`/pips/${pipId}/pip-check-ins/${id}`, payload)) as AxiosResponse<PipCheckInResponse>;
      return response.data.data;
    } catch (error) {
      if (axios.isAxiosError(error) && error.response) {
        return rejectWithValue(error.response.data as ServerErrorResponse);
      }
      throw error;
    }
  },
);

export const deletePipCheckIn = createAsyncThunk(
  PipCheckInActions.DELETE_PIP_CHECK_IN_REQUEST,
  async ({ pipId, id }: { pipId: string; id: string }, { rejectWithValue }) => {
    try {
      const response = (await apiDelete(`/pips/${pipId}/pip-check-ins/${id}`)) as AxiosResponse<{ message: string }>;
      return { message: response.data.message, id };
    } catch (error) {
      if (axios.isAxiosError(error) && error.response) {
        return rejectWithValue(error.response.data as ServerErrorResponse);
      }
      throw error;
    }
  },
);

export const PipCheckInSlice = createSlice({
  name: 'pipCheckIns',
  initialState,
  reducers: {
    clearPipCheckIns: (state: Draft<PipCheckInState>) => {
      state.pipCheckIns = [];
      state.currentPipCheckIn = null;
    },
  },
  extraReducers(builder) {
    builder
      .addCase(fetchPipCheckIns.pending, (state: Draft<PipCheckInState>) => {
        state.loading = true;
      })
      .addCase(fetchPipCheckIns.fulfilled, (state: Draft<PipCheckInState>, action: PayloadAction<PipCheckIn[]>) => {
        state.pipCheckIns = action.payload;
        state.loading = false;
      })
      .addCase(fetchPipCheckIns.rejected, (state: Draft<PipCheckInState>, action: RejectedActionPayload) => {
        state.loading = false;
        message.error(Helpers.handleServerError(action.payload), 8);
      });

    builder
      .addCase(createPipCheckIn.pending, (state: Draft<PipCheckInState>) => {
        state.loading = true;
      })
      .addCase(createPipCheckIn.fulfilled, (state: Draft<PipCheckInState>, action: PayloadAction<PipCheckIn>) => {
        state.pipCheckIns.push(action.payload);
        state.loading = false;
        message.success('PIP check-in recorded successfully', 10);
      })
      .addCase(createPipCheckIn.rejected, (state: Draft<PipCheckInState>, action: RejectedActionPayload) => {
        state.loading = false;
        message.error(Helpers.handleServerError(action.payload), 10);
      });

    builder
      .addCase(updatePipCheckIn.pending, (state: Draft<PipCheckInState>) => {
        state.loading = true;
      })
      .addCase(updatePipCheckIn.fulfilled, (state: Draft<PipCheckInState>, action: PayloadAction<PipCheckIn>) => {
        const idx = state.pipCheckIns.findIndex((c) => c.id === action.payload.id);
        if (idx !== -1) state.pipCheckIns[idx] = action.payload;
        state.loading = false;
        message.success('PIP check-in updated successfully', 10);
      })
      .addCase(updatePipCheckIn.rejected, (state: Draft<PipCheckInState>, action: RejectedActionPayload) => {
        state.loading = false;
        message.error(Helpers.handleServerError(action.payload), 10);
      });

    builder
      .addCase(deletePipCheckIn.pending, (state: Draft<PipCheckInState>) => {})
      .addCase(deletePipCheckIn.fulfilled, (state: Draft<PipCheckInState>, action: PayloadAction<{ message: string; id: string }>) => {
        state.pipCheckIns = state.pipCheckIns.filter((c) => c.id !== action.payload.id);
        message.success(action.payload.message, 10);
      })
      .addCase(deletePipCheckIn.rejected, (state: Draft<PipCheckInState>, action: RejectedActionPayload) => {
        message.error(Helpers.handleServerError(action.payload), 8);
      });
  },
});

export const { clearPipCheckIns } = PipCheckInSlice.actions;
export default PipCheckInSlice;
export type { PipCheckInState };
