/* eslint no-param-reassign: "error" */
import { createAsyncThunk, createSlice } from '@reduxjs/toolkit';
import type { AxiosResponse } from 'axios';
import axios from 'axios';

import environment from '../../Environments/environment';
import type { CompanyDbModel } from '../../Pages/Companies/Components/CompaniesComponents.helper';
import type { UserModel } from '../../Store/User/user-context.helper';
import type { RootState } from '../store';

const { apiUrl, backendRoutes } = environment;

interface LoginState {
	isLoggedIn: boolean;
	user: UserModel;
	fetchingFinished: boolean;
	companies: CompanyDbModel[] | null;
	accountDeleted: boolean;
}

const initialState: LoginState = {
	isLoggedIn: false,
	user: null,
	fetchingFinished: false,
	companies: null,
	accountDeleted: false
};

const loginSlice = createSlice({
	name: 'login',
	initialState,
	reducers: {
		login: (state) => {
			state.isLoggedIn = true;
		},
		logout: (state) => {
			state.isLoggedIn = false;
			state.user = null;
			const selectedFinancials = localStorage.getItem('selectedFinancials');
			console.log('selectedFinancials', selectedFinancials);
			localStorage.clear();
			if (selectedFinancials) {
				localStorage.setItem('selectedFinancials', selectedFinancials);
			}
		}
	},
	extraReducers: (builder) => {
		builder
			.addCase(fetchUserData.pending, (state, action) => {
				state.isLoggedIn = false;
				if (action.payload) {
					state.user = action.payload;
				}
			})
			.addCase(fetchUserData.fulfilled, (state, action) => {
				state.isLoggedIn = true;
				state.fetchingFinished = true;
				if (action.payload) {
					// const [user, companies] = action.payload;
					// state.user = user;
					state.user = action.payload;
				}
			})
			.addCase(updateUserData.fulfilled, (state, action) => {
				if (action.payload) {
					if (state.user && action.payload.name && action.payload.email) {
						state.user.name = action.payload.name;
						state.user.email = action.payload.email;
					}
				}
			})
			.addCase(updateSelectedCharts.fulfilled, (state, action) => {
				console.log('payload in', action);
				if (action.payload) {
					if (state.user) {
						const updatedUser = {
							...state.user,
							selectedCharts: action.payload.selectedDashboardCharts
						};
						console.log('payload in', action.payload);
						state.user = updatedUser;
					}
				}
			})
			.addCase(deleteEmptyUserAccount.fulfilled, (state, action) => {
				console.log('payload in deleteEmptyUserAccount', action);
				if (action.payload) {
					state.accountDeleted = true;
				}
			});
		builder.addCase(logout, (state) => {
			state.fetchingFinished = false;
			state.isLoggedIn = false;
			state.user = null;
		});
	}
});

export const fetchUserData = createAsyncThunk('login/fetchUserData', async () => {
	// fetch user data
	const user = await axios
		.get(apiUrl + backendRoutes.getAccount)
		.then((results: AxiosResponse<UserModel>) => results.data as UserModel)
		.catch((error) => {
			console.error(error.message);
			return null;
		});
	return user;
});

export const updateUserData = createAsyncThunk(
	'login/updateUserData',
	async (payload: { name: string; email: string }) => {
		if (!payload.email || !payload.name) {
			throw new Error('Invalid payload');
		}
		// fetch user data
		const user = await axios
			.patch(apiUrl + backendRoutes.patchAccount, payload)
			.then((results: AxiosResponse<any>) => payload)
			.catch((error) => {
				console.error(error.message);
				return null;
			});
		return user;
	}
);

export const updateSelectedCharts = createAsyncThunk(
	'login/updateSelectedCharts',
	async (payload: { selectedDashboardCharts: string[] }) => {
		if (!payload.selectedDashboardCharts) {
			throw new Error('Invalid payload');
		}
		// fetch user data
		const user = await axios
			.post(apiUrl + backendRoutes.updateSelectedCharts, payload)
			.then((results: AxiosResponse<any>) => payload)
			.catch((error) => {
				console.error(error.message);
				return null;
			});
		return user;
	}
);

export const deleteEmptyUserAccount = createAsyncThunk(
	'login/deleteEmptyAccount',
	async (payload: { user: UserModel | undefined }, thunkAPI) => {
		const state = thunkAPI.getState();
		console.log('deleting', payload, state);
		if (!payload.user || payload.user?._id !== (state as RootState)?.login?.user?._id) {
			console.error('Invalid payload', payload.user?._id, (state as RootState)?.login?.user?._id);
			throw new Error('Invalid payload');
		}
		console.log('deleting', payload);
		// delete user data
		const user = await axios
			.delete(apiUrl + backendRoutes.account.deleteAccountEmpty, { data: payload })
			.then((results: AxiosResponse<any>) => payload)
			.catch((error) => {
				console.error(error.message);
				return null;
			});
		return user;
	}
);

export const deleteUserAccount = createAsyncThunk(
	'login/deleteAccount',
	async (payload: { user: UserModel | undefined }, thunkAPI) => {
		const state = thunkAPI.getState();
		console.log('deleting', payload, state);
		if (!payload.user || payload.user?._id !== (state as RootState)?.login?.user?._id) {
			console.error('Invalid payload', payload.user?._id, (state as RootState)?.login?.user?._id);
			throw new Error('Invalid payload');
		}
		console.log('deleting', payload);
		// delete user data
		const user = await axios
			.delete(apiUrl + backendRoutes.account.deleteAccount, { data: payload })
			.then((results: AxiosResponse<any>) => payload)
			.catch((error) => {
				console.error(error.message);
				return null;
			});
		return user;
	}
);

export const { login, logout } = loginSlice.actions;

export default loginSlice.reducer;
