@churchapps/apphelper 0.4.18 → 0.4.20
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/components/DisplayBox.js +1 -1
- package/dist/components/DisplayBox.js.map +1 -1
- package/dist/components/InputBox.js +1 -1
- package/dist/components/InputBox.js.map +1 -1
- package/dist/components/Loading.js +1 -1
- package/dist/components/Loading.js.map +1 -1
- package/dist/components/PageHeader.d.ts.map +1 -1
- package/dist/components/PageHeader.js +6 -6
- package/dist/components/PageHeader.js.map +1 -1
- package/dist/components/header/SiteHeader.d.ts.map +1 -1
- package/dist/components/header/SiteHeader.js +5 -2
- package/dist/components/header/SiteHeader.js.map +1 -1
- package/dist/components/wrapper/ChurchList.d.ts +1 -0
- package/dist/components/wrapper/ChurchList.d.ts.map +1 -1
- package/dist/components/wrapper/ChurchList.js +73 -13
- package/dist/components/wrapper/ChurchList.js.map +1 -1
- package/dist/components/wrapper/Notifications.d.ts.map +1 -1
- package/dist/components/wrapper/Notifications.js +4 -4
- package/dist/components/wrapper/Notifications.js.map +1 -1
- package/dist/components/wrapper/UserMenu.d.ts +1 -3
- package/dist/components/wrapper/UserMenu.d.ts.map +1 -1
- package/dist/components/wrapper/UserMenu.js +53 -9
- package/dist/components/wrapper/UserMenu.js.map +1 -1
- package/dist/helpers/UserHelper.d.ts.map +1 -1
- package/dist/helpers/UserHelper.js +24 -0
- package/dist/helpers/UserHelper.js.map +1 -1
- package/package.json +1 -1
- package/src/components/DisplayBox.tsx +8 -8
- package/src/components/InputBox.tsx +8 -8
- package/src/components/Loading.tsx +1 -1
- package/src/components/PageHeader.tsx +8 -4
- package/src/components/header/SiteHeader.tsx +10 -8
- package/src/components/wrapper/ChurchList.tsx +83 -13
- package/src/components/wrapper/Notifications.tsx +6 -5
- package/src/components/wrapper/UserMenu.tsx +70 -28
- package/src/helpers/UserHelper.ts +26 -0
|
@@ -88,7 +88,7 @@ export const Notifications: React.FC<Props> = (props) => {
|
|
|
88
88
|
const getNotificationList = () => {
|
|
89
89
|
if (notifications.length === 0) {
|
|
90
90
|
return (
|
|
91
|
-
<Box sx={{ textAlign: 'center', py: 4 }}>
|
|
91
|
+
<Box id="notifications-empty" sx={{ textAlign: 'center', py: 4 }}>
|
|
92
92
|
<NotificationsIcon sx={{ fontSize: 48, color: 'grey.400', mb: 2 }} />
|
|
93
93
|
<Typography variant="h6" color="textSecondary">
|
|
94
94
|
No notifications
|
|
@@ -101,7 +101,7 @@ export const Notifications: React.FC<Props> = (props) => {
|
|
|
101
101
|
}
|
|
102
102
|
|
|
103
103
|
return (
|
|
104
|
-
<List sx={{ width: '100%' }}>
|
|
104
|
+
<List id="notifications-list" sx={{ width: '100%' }}>
|
|
105
105
|
{notifications.map((notification, index) => {
|
|
106
106
|
let datePosted = new Date(notification.timeSent);
|
|
107
107
|
const displayDuration = DateHelper.getDisplayDuration(datePosted);
|
|
@@ -110,6 +110,7 @@ export const Notifications: React.FC<Props> = (props) => {
|
|
|
110
110
|
return (
|
|
111
111
|
<React.Fragment key={notification.id}>
|
|
112
112
|
<ListItem
|
|
113
|
+
id={`notification-item-${notification.id}`}
|
|
113
114
|
component="button"
|
|
114
115
|
onClick={() => handleClick(notification)}
|
|
115
116
|
sx={{
|
|
@@ -194,14 +195,14 @@ export const Notifications: React.FC<Props> = (props) => {
|
|
|
194
195
|
|
|
195
196
|
|
|
196
197
|
return (
|
|
197
|
-
<Paper elevation={0} sx={{ height: '100%', display: 'flex', flexDirection: 'column' }}>
|
|
198
|
-
<Box sx={{ p: 2, borderBottom: 1, borderColor: 'divider' }}>
|
|
198
|
+
<Paper id="notifications-panel" elevation={0} sx={{ height: '100%', display: 'flex', flexDirection: 'column' }}>
|
|
199
|
+
<Box id="notifications-header" sx={{ p: 2, borderBottom: 1, borderColor: 'divider' }}>
|
|
199
200
|
<Typography variant="h6" component="h2">
|
|
200
201
|
Notifications
|
|
201
202
|
</Typography>
|
|
202
203
|
</Box>
|
|
203
204
|
|
|
204
|
-
<Box sx={{ flex: 1, overflow: 'auto' }}>
|
|
205
|
+
<Box id="notifications-content" sx={{ flex: 1, overflow: 'auto' }}>
|
|
205
206
|
{isLoading ? (
|
|
206
207
|
<Box sx={{ p: 2 }}>
|
|
207
208
|
{[...Array(3)].map((_, index) => (
|
|
@@ -19,8 +19,6 @@ interface Props {
|
|
|
19
19
|
loadCounts: () => void;
|
|
20
20
|
userName: string;
|
|
21
21
|
profilePicture: string;
|
|
22
|
-
userChurches: LoginUserChurchInterface[];
|
|
23
|
-
currentUserChurch: LoginUserChurchInterface;
|
|
24
22
|
context: UserContextInterface;
|
|
25
23
|
appName: string;
|
|
26
24
|
onNavigate: (url: string) => void;
|
|
@@ -98,8 +96,10 @@ const UserMenuContent: React.FC<Props> = React.memo((props) => {
|
|
|
98
96
|
};
|
|
99
97
|
|
|
100
98
|
const handleSwitchChurch = () => {
|
|
99
|
+
console.log('UserMenu - handleSwitchChurch called');
|
|
101
100
|
removeCookie("lastChurchId", { path: "/" });
|
|
102
101
|
setTabIndex(2);
|
|
102
|
+
console.log('UserMenu - tabIndex set to 2');
|
|
103
103
|
};
|
|
104
104
|
|
|
105
105
|
const getMainLinks = () => {
|
|
@@ -151,24 +151,64 @@ const UserMenuContent: React.FC<Props> = React.memo((props) => {
|
|
|
151
151
|
|
|
152
152
|
const [tabIndex, setTabIndex] = React.useState(0);
|
|
153
153
|
|
|
154
|
-
const getTabs = () =>
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
<
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
<
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
154
|
+
const getTabs = () => {
|
|
155
|
+
console.log('UserMenu getTabs - Current tabIndex:', tabIndex);
|
|
156
|
+
return (
|
|
157
|
+
<Box sx={{ borderBottom: 1, borderColor: "divider" }}>
|
|
158
|
+
<TabPanel value={tabIndex} index={0}>
|
|
159
|
+
{getMainLinks()}
|
|
160
|
+
</TabPanel>
|
|
161
|
+
<TabPanel value={tabIndex} index={1}>
|
|
162
|
+
<NavItem label="Back" key="AppBack" icon="arrow_back" onClick={() => { setTabIndex(0); }} />
|
|
163
|
+
<AppList currentUserChurch={props.context?.userChurch} appName={props.appName} onNavigate={props.onNavigate} />
|
|
164
|
+
</TabPanel>
|
|
165
|
+
<TabPanel value={tabIndex} index={2}>
|
|
166
|
+
<div style={{ maxHeight: '70vh', overflowY: "auto" }}>
|
|
167
|
+
<NavItem label="Back" key="ChurchBack" icon="arrow_back" onClick={() => { setTabIndex(0); }} />
|
|
168
|
+
{(() => {
|
|
169
|
+
console.log('UserMenu Church Tab - Rendering church list section');
|
|
170
|
+
console.log('UserMenu Church Tab - Full context:', props.context);
|
|
171
|
+
console.log('UserMenu Church Tab - context.userChurches:', props.context?.userChurches);
|
|
172
|
+
console.log('UserMenu Church Tab - context.userChurches[0]:', props.context?.userChurches?.[0]);
|
|
173
|
+
console.log('UserMenu Church Tab - context.userChurch:', props.context?.userChurch);
|
|
174
|
+
console.log('UserMenu Church Tab - userChurches type:', typeof props.context?.userChurches);
|
|
175
|
+
console.log('UserMenu Church Tab - userChurches is array?', Array.isArray(props.context?.userChurches));
|
|
176
|
+
console.log('UserMenu Church Tab - userChurches length:', props.context?.userChurches?.length);
|
|
177
|
+
|
|
178
|
+
// Check if userChurches is actually the userChurch object
|
|
179
|
+
if (props.context?.userChurches && !Array.isArray(props.context.userChurches) && (props.context.userChurches as any).id) {
|
|
180
|
+
console.error('UserMenu - ERROR: context.userChurches contains a single church object instead of an array!');
|
|
181
|
+
console.log('UserMenu - Attempting to use context.userChurch as single item array');
|
|
182
|
+
const churchArray = props.context.userChurch ? [props.context.userChurch] : [];
|
|
183
|
+
return <ChurchList userChurches={churchArray} currentUserChurch={props.context?.userChurch} context={props.context} onDelete={handleClose} onChurchChange={() => {
|
|
184
|
+
handleClose();
|
|
185
|
+
// Don't navigate - just close the menu and let the context update trigger re-renders
|
|
186
|
+
}} />;
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
if (!props.context?.userChurches) {
|
|
190
|
+
return <Typography sx={{ p: 2, color: 'text.secondary' }}>Loading churches...</Typography>;
|
|
191
|
+
} else if (!Array.isArray(props.context.userChurches)) {
|
|
192
|
+
return <Typography sx={{ p: 2, color: 'text.secondary', fontWeight: 'bold' }}>Error: Invalid church data format</Typography>;
|
|
193
|
+
} else if (props.context.userChurches.length === 0) {
|
|
194
|
+
return <Typography sx={{ p: 2, color: 'text.secondary' }}>No churches available</Typography>;
|
|
195
|
+
} else {
|
|
196
|
+
// Ensure we always pass an array
|
|
197
|
+
const churchesArray = Array.isArray(props.context.userChurches)
|
|
198
|
+
? props.context.userChurches
|
|
199
|
+
: [props.context.userChurches];
|
|
200
|
+
console.log('UserMenu - Passing to ChurchList:', churchesArray);
|
|
201
|
+
return <ChurchList userChurches={churchesArray} currentUserChurch={props.context?.userChurch} context={props.context} onDelete={handleClose} onChurchChange={() => {
|
|
202
|
+
handleClose();
|
|
203
|
+
// Don't navigate - just close the menu and let the context update trigger re-renders
|
|
204
|
+
}} />;
|
|
205
|
+
}
|
|
206
|
+
})()}
|
|
207
|
+
</div>
|
|
208
|
+
</TabPanel>
|
|
209
|
+
</Box>
|
|
210
|
+
);
|
|
211
|
+
};
|
|
172
212
|
|
|
173
213
|
const getModals = () => {
|
|
174
214
|
// Helper function to get label with fallback
|
|
@@ -180,6 +220,7 @@ const UserMenuContent: React.FC<Props> = React.memo((props) => {
|
|
|
180
220
|
return (
|
|
181
221
|
<>
|
|
182
222
|
<Dialog
|
|
223
|
+
id="private-messages-modal"
|
|
183
224
|
open={showPM}
|
|
184
225
|
onClose={() => {
|
|
185
226
|
modalStateStore.setShowPM(false);
|
|
@@ -195,7 +236,7 @@ const UserMenuContent: React.FC<Props> = React.memo((props) => {
|
|
|
195
236
|
}
|
|
196
237
|
}}
|
|
197
238
|
>
|
|
198
|
-
<DialogTitle>{getLabel("wrapper.messages", "Messages")}</DialogTitle>
|
|
239
|
+
<DialogTitle id="private-messages-title">{getLabel("wrapper.messages", "Messages")}</DialogTitle>
|
|
199
240
|
<DialogContent
|
|
200
241
|
sx={{
|
|
201
242
|
flex: 1,
|
|
@@ -211,6 +252,7 @@ const UserMenuContent: React.FC<Props> = React.memo((props) => {
|
|
|
211
252
|
</Dialog>
|
|
212
253
|
|
|
213
254
|
<Dialog
|
|
255
|
+
id="notifications-modal"
|
|
214
256
|
open={showNotifications}
|
|
215
257
|
onClose={() => {
|
|
216
258
|
modalStateStore.setShowNotifications(false);
|
|
@@ -218,7 +260,7 @@ const UserMenuContent: React.FC<Props> = React.memo((props) => {
|
|
|
218
260
|
maxWidth="md"
|
|
219
261
|
fullWidth
|
|
220
262
|
>
|
|
221
|
-
<DialogTitle>{getLabel("wrapper.notifications", "Notifications")}</DialogTitle>
|
|
263
|
+
<DialogTitle id="notifications-title">{getLabel("wrapper.notifications", "Notifications")}</DialogTitle>
|
|
222
264
|
<DialogContent>
|
|
223
265
|
<Notifications context={props.context} appName={props.appName} onUpdate={props.loadCounts} onNavigate={props.onNavigate} />
|
|
224
266
|
</DialogContent>
|
|
@@ -286,13 +328,13 @@ const UserMenuContent: React.FC<Props> = React.memo((props) => {
|
|
|
286
328
|
|
|
287
329
|
return (
|
|
288
330
|
<>
|
|
289
|
-
<Button onClick={handleClick} color="inherit" aria-controls={open ? "account-menu" : undefined} aria-haspopup="true" aria-expanded={open ? "true" : undefined} style={{ textTransform: "none" }} endIcon={<Icon>expand_more</Icon>}>
|
|
290
|
-
<Badge badgeContent={totalNotifcations} color="error" invisible={totalNotifcations===0}>
|
|
291
|
-
<Avatar src={getProfilePic()} sx={{ width: 32, height: 32, marginRight: 1 }}></Avatar>
|
|
331
|
+
<Button id="user-menu-button" onClick={handleClick} color="inherit" aria-controls={open ? "account-menu" : undefined} aria-haspopup="true" aria-expanded={open ? "true" : undefined} style={{ textTransform: "none" }} endIcon={<Icon>expand_more</Icon>}>
|
|
332
|
+
<Badge id="user-menu-notification-badge" badgeContent={totalNotifcations} color="error" invisible={totalNotifcations===0}>
|
|
333
|
+
<Avatar id="user-menu-avatar" src={getProfilePic()} sx={{ width: 32, height: 32, marginRight: 1 }}></Avatar>
|
|
292
334
|
</Badge>
|
|
293
335
|
</Button>
|
|
294
336
|
|
|
295
|
-
<Menu anchorEl={anchorEl} id="
|
|
337
|
+
<Menu anchorEl={anchorEl} id="user-menu-dropdown" open={open} onClose={handleClose} onClick={(e) => { handleItemClick(e) }} slotProps={{ paper: paperProps }} transformOrigin={{ horizontal: "right", vertical: "top" }} anchorOrigin={{ horizontal: "right", vertical: "bottom" }} sx={{ "& .MuiBox-root": { borderBottom: 0 } }}>
|
|
296
338
|
{getTabs()}
|
|
297
339
|
</Menu>
|
|
298
340
|
{getModals()}
|
|
@@ -326,8 +368,8 @@ export const UserMenu: React.FC<Props> = React.memo((props) => {
|
|
|
326
368
|
return false;
|
|
327
369
|
}
|
|
328
370
|
|
|
329
|
-
// Check if userChurches array changed
|
|
330
|
-
if (prevProps.userChurches?.length !== nextProps.userChurches?.length) {
|
|
371
|
+
// Check if userChurches array changed in context
|
|
372
|
+
if (prevProps.context?.userChurches?.length !== nextProps.context?.userChurches?.length) {
|
|
331
373
|
return false;
|
|
332
374
|
}
|
|
333
375
|
|
|
@@ -11,6 +11,19 @@ export class UserHelper {
|
|
|
11
11
|
static selectChurch = async (context?: UserContextInterface, churchId?: string, keyName?: string) => {
|
|
12
12
|
let userChurch = null;
|
|
13
13
|
|
|
14
|
+
// Ensure userChurches is initialized
|
|
15
|
+
if (!UserHelper.userChurches || !Array.isArray(UserHelper.userChurches)) {
|
|
16
|
+
console.error('UserHelper.userChurches is not initialized or not an array:', UserHelper.userChurches);
|
|
17
|
+
// Try to get userChurches from context if available
|
|
18
|
+
if (context?.userChurches && Array.isArray(context.userChurches)) {
|
|
19
|
+
console.log('Using userChurches from context');
|
|
20
|
+
UserHelper.userChurches = context.userChurches;
|
|
21
|
+
} else {
|
|
22
|
+
console.error('Cannot select church: no valid userChurches available');
|
|
23
|
+
return;
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
|
|
14
27
|
if (churchId) {
|
|
15
28
|
UserHelper.userChurches.forEach(uc => {
|
|
16
29
|
if (uc.church.id === churchId) userChurch = uc;
|
|
@@ -25,7 +38,20 @@ export class UserHelper {
|
|
|
25
38
|
// TODO - remove context code from here and perform the logic in the component itself.
|
|
26
39
|
if (context) {
|
|
27
40
|
if (context.userChurch !== null) UserHelper.churchChanged = true;
|
|
41
|
+
console.log('UserHelper.selectChurch - Setting userChurch in context:', userChurch);
|
|
28
42
|
context.setUserChurch(UserHelper.currentUserChurch);
|
|
43
|
+
|
|
44
|
+
// Also ensure user is still set in context
|
|
45
|
+
if (UserHelper.user && context.setUser) {
|
|
46
|
+
console.log('UserHelper.selectChurch - Ensuring user is set in context:', UserHelper.user);
|
|
47
|
+
context.setUser(UserHelper.user);
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
// Update person if available
|
|
51
|
+
if (UserHelper.person && context.setPerson) {
|
|
52
|
+
console.log('UserHelper.selectChurch - Ensuring person is set in context:', UserHelper.person);
|
|
53
|
+
context.setPerson(UserHelper.person);
|
|
54
|
+
}
|
|
29
55
|
}
|
|
30
56
|
}
|
|
31
57
|
}
|