Use source loader for email sprite icons
[ProtonMail-WebClient.git] / packages / calendar / calendars / index.ts
blobb3b8f02555434cb591a75d9a6dce5a2a53243c24
1 import type { PayloadAction } from '@reduxjs/toolkit';
2 import { createSlice } from '@reduxjs/toolkit';
4 import type { AddressesState, ModelState } from '@proton/account';
5 import { getInitialModelState } from '@proton/account/initialModelState';
6 import type { ProtonThunkArguments } from '@proton/redux-shared-store-types';
7 import { createAsyncModelThunk, handleAsyncModel, previousSelector } from '@proton/redux-utilities';
8 import { queryCalendars } from '@proton/shared/lib/api/calendars';
9 import { CALENDAR_DISPLAY } from '@proton/shared/lib/calendar/constants';
10 import type { CalendarWithOwnMembers } from '@proton/shared/lib/interfaces/calendar';
12 export interface CalendarsState extends AddressesState {
13     calendars: ModelState<CalendarWithOwnMembers[]>;
16 const name = 'calendars' as const;
17 type SliceState = CalendarsState[typeof name];
18 type Model = NonNullable<SliceState['value']>;
20 export const selectCalendars = (state: CalendarsState) => state[name];
22 export const selectCalendarsWithMembers = (state: CalendarsState) => state[name].value;
24 const modelThunk = createAsyncModelThunk<Model, CalendarsState, ProtonThunkArguments>(`${name}/fetch`, {
25     miss: ({ extraArgument }) => {
26         return extraArgument
27             .api<{ Calendars: CalendarWithOwnMembers[] }>({
28                 ...queryCalendars(),
29                 silence: true,
30             })
31             .then(({ Calendars }) => {
32                 return Calendars;
33             });
34     },
35     previous: previousSelector(selectCalendars),
36 });
38 const initialState = getInitialModelState<Model>();
39 const slice = createSlice({
40     name,
41     initialState,
42     reducers: {
43         updateCalendarVisibility: (
44             state,
45             action: PayloadAction<{ calendarID: string; memberID: string; display: boolean }>
46         ) => {
47             if (!state.value) {
48                 return;
49             }
50             const calendar = state.value.find(({ ID }) => ID === action.payload.calendarID);
51             if (!calendar) {
52                 return;
53             }
54             const member = calendar.Members.find(({ ID }) => ID === action.payload.memberID);
55             if (!member) {
56                 return;
57             }
58             member.Display = action.payload.display ? CALENDAR_DISPLAY.VISIBLE : CALENDAR_DISPLAY.HIDDEN;
59         },
60         updateCalendars: (state, action: PayloadAction<CalendarWithOwnMembers[]>) => {
61             state.value = action.payload;
62             state.error = undefined;
63         },
64     },
65     extraReducers: (builder) => {
66         handleAsyncModel(builder, modelThunk);
67     },
68 });
70 export const calendarsReducer = { [name]: slice.reducer };
71 export const calendarsActions = slice.actions;
72 export const calendarsThunk = modelThunk.thunk;