import api from '@/lib/axios';
import { createSlice, createAsyncThunk, type PayloadAction } from '@reduxjs/toolkit';
import { toast } from 'sonner';
import messages from '@/messages/en.json';

// Define a type for the vehicle
export interface VehiclesInsurance {
    id: number;
    policy_number: string;
    start_date: string;
    end_date: string;
    insurance_provider: string;
    coverage_type: string;
    isActive: string;
    document: string;
    status?: string;
    fleet_id?: number;
}

// Define the state interface
export interface VehiclesState {
    items: VehiclesInsurance[];
    status: 'idle' | 'loading' | 'succeeded' | 'failed';
    error: string | null;
    filters: {
        search: string;
        limit: number;
        skip: number;
        sortBy: string;
        sortOrder: string;
    };
    totalCount: number;
    driver: any;
}

// Initial state
const initialState: VehiclesState = {
    items: [],
    status: 'idle',
    error: null,
    filters: {
        search: '',
        limit: 10,
        skip: 0,
        sortBy: 'maintenance_date',
        sortOrder: 'DESC',
    },
    totalCount: 0,
    driver: [],
};

// Define types for adding a new vehicle
export interface AddVehiclePayload {
    document_file: File;
    start_date: Date;
    fleet_id: number;
    coverage_type: string;
    end_date: Date;
    insurance_provider: number;
    is_active_policy: string;
    policy_number: number;
}

// Async thunk for fetching vehicles
export const fetchVehiclesInsurance = createAsyncThunk(
    'vehicles/fetchVehiclesInsurance',
    async (
        params: {
            skip?: number;
            limit?: number;
            sortBy?: string;
            sortOrder?: 'ASC' | 'DESC';
            fleet_id?: number;
            search?: string;
        },
        { rejectWithValue },
    ) => {
        try {
            const response = await api.get('vehicle-insurance', {
                params: {
                    skip: params.skip || 0,
                    limit: params.limit || 10,
                    sortBy: params.sortBy || 'name',
                    sortOrder: params.sortOrder || 'ASC',
                    fleet_id: params.fleet_id,
                    search: params.search || '',
                },
            });
            return response?.data;
        } catch (error) {
            return rejectWithValue('Failed to fetch vehicles');
        }
    },
);

// Async thunk for adding a new vehicle
export const addVehicleInsurance = createAsyncThunk(
    'vehicles/addVehicleInsurance',
    async (payload: AddVehiclePayload, { rejectWithValue }) => {
        try {
            const response = await api.post('/vehicle-insurance/create', payload, {
                headers: {
                    'Content-Type': 'multipart/form-data',
                },
            });

            return response.data;
        } catch (error) {
            return rejectWithValue('Failed to add vehicle');
        }
    },
);

export const fetchVehicleInsuranceDetail = createAsyncThunk('vehicles/details', async (id: number, { rejectWithValue }) => {
    try {
        const response = await api.get(`vehicle-insurance/${id}`);
        return response.data.data;
    } catch (error) {
        return rejectWithValue('Failed to add vehicle');
    }
});

// Async thunk for deleting a vehicle
export const deleteVehicleInsurance = createAsyncThunk(
    'vehicles/deleteVehicle',
    async (vehicleId: number, { rejectWithValue }) => {
        try {
            const response = await api.delete(`vehicle-insurance/${vehicleId}`);
            if (response.data.code === 200) {
                toast.success(messages.toasts.success.vehicle_insurance_deleted);
                return vehicleId;
            } else {
                toast.error(messages.toasts.error.failed_to_delete_vehicle_insurance);
                return rejectWithValue(messages.toasts.error.failed_to_delete_vehicle_insurance);
            }
        } catch (error) {
            toast.error(messages.toasts.error.failed_to_delete_vehicle_insurance);
            return rejectWithValue(messages.toasts.error.failed_to_delete_vehicle_insurance);
        }
    },
);

export const deleteInsuranceDocument = createAsyncThunk('vehicles/deleteInsuranceDocument', async (id: number) => {
    const response = await api.delete(`vehicle-insurance/${id}/document`);
    return response.data;
});

// Async thunk for updating a vehicle
export const updateVehicleInsurance = createAsyncThunk(
    'vehicles/updateVehicleInsurance',
    async ({ id, payload }: { id: number; payload: Partial<AddVehiclePayload> }, { rejectWithValue, getState }) => {
        try {
            // In a real app, this would be an API call
            const response = await api.patch(`vehicle-insurance/${id}`, payload, {
                headers: {
                    'Content-Type': 'multipart/form-data',
                },
            });

            return response.data;
        } catch (error) {
            return rejectWithValue('Failed to update vehicle');
        }
    },
);

export const getAllDriver = createAsyncThunk('vehicles/driver', async (_, { rejectWithValue }) => {
    try {
        const response = await api.get('/team-member/drivers-by-role');
        return response;
    } catch (error: any) {
        return rejectWithValue(error?.response?.data?.message || 'Failed to fetch drivers');
    }
});

// Reducers
const vehiclesInsuranceSlice = createSlice({
    name: 'vehiclesInsurance',
    initialState,
    reducers: {
        setFilters: (state, action: PayloadAction<Partial<VehiclesState['filters']>>) => {
            state.filters = { ...state.filters, ...action.payload };
        },
        resetFilters: (state) => {
            state.filters = initialState.filters;
        },
    },
    extraReducers: (builder) => {
        builder
            .addCase(fetchVehiclesInsurance.pending, (state) => {
                state.status = 'loading';
            })
            .addCase(fetchVehiclesInsurance.fulfilled, (state, action) => {
                state.status = 'succeeded';
                state.items = action.payload?.data?.data;
                state.totalCount = action.payload?.data.count;
            })
            .addCase(fetchVehiclesInsurance.rejected, (state, action) => {
                state.status = 'failed';
                state.error = action.payload as string;
            })
            .addCase(addVehicleInsurance.fulfilled, (state, action) => {
                const code = action.payload.code;

                if (code === 200 || code === 201) {
                    toast.success(messages.toasts.success.vehicle_insurance_added);
                } else if (code === 422) {
                    toast.error(messages.toasts.error.vehicle_insurance_exists);
                } else {
                    toast.error(messages.toasts.error.generic);
                }
            })
            .addCase(deleteVehicleInsurance.pending, (state) => {
                state.status = 'loading';
            })
            .addCase(deleteVehicleInsurance.fulfilled, (state, action) => {
                state.status = 'succeeded';
            })
            .addCase(deleteVehicleInsurance.rejected, (state, action) => {
                state.status = 'failed';
                state.error = action.payload as string;
            })
            .addCase(updateVehicleInsurance.pending, (state) => {
                state.status = 'loading';
            })
            .addCase(updateVehicleInsurance.fulfilled, (state, action) => {
                const code = action?.payload?.code;
                if (code === 200 || code === 201) {
                    toast.success(messages.toasts.success.vehicle_insurance_updated);
                } else if (code === 422) {
                    toast.error(messages.toasts.error.vehicle_insurance_exists);
                } else {
                    toast.error(messages.toasts.error.generic);
                }
            })
            .addCase(updateVehicleInsurance.rejected, (state, action) => {
                state.status = 'failed';
                state.error = action.payload as string;
                toast.error(action.payload as string);
            })
            .addCase(getAllDriver.pending, (state) => {
                state.status = 'loading';
            })
            .addCase(getAllDriver.fulfilled, (state, action) => {
                state.status = 'succeeded';
                state.driver = action.payload?.data?.data || [];
            })
            .addCase(getAllDriver.rejected, (state, action) => {
                state.status = 'failed';
                state.error = action.payload as string;
            })
            .addCase(fetchVehicleInsuranceDetail.pending, (state) => {
                state.status = 'loading';
            })
            .addCase(fetchVehicleInsuranceDetail.fulfilled, (state, action) => {
                state.status = 'succeeded';
            })
            .addCase(fetchVehicleInsuranceDetail.rejected, (state, action) => {
                state.status = 'failed';
                state.error = action.payload as string;
            })
            .addCase(deleteInsuranceDocument.pending, (state) => {
                state.status = 'loading';
            })
            .addCase(deleteInsuranceDocument.fulfilled, (state, action) => {
                state.status = 'succeeded';
            })
            .addCase(deleteInsuranceDocument.rejected, (state, action) => {
                state.status = 'failed';
                state.error = action.payload as string;
            });
    },
});

export const { setFilters, resetFilters } = vehiclesInsuranceSlice.actions;

export default vehiclesInsuranceSlice.reducer;
