Skip to content

Commit

Permalink
Merge pull request #1685 from innovationacademy-kr/fe/dev/fix_firebas…
Browse files Browse the repository at this point in the history
…e_error/#1680

[FE] FIX: 모바일로 접속시 발생되는 firebase error 해결 #1680
  • Loading branch information
jnkeniaem authored Nov 5, 2024
2 parents 37fa31a + 85e9941 commit c860114
Show file tree
Hide file tree
Showing 27 changed files with 774 additions and 607 deletions.
2 changes: 1 addition & 1 deletion config
983 changes: 543 additions & 440 deletions frontend/package-lock.json

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion frontend/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@
"@sentry/react": "^8.18.0",
"@types/react-color": "^3.0.7",
"axios": "^1.7.2",
"firebase": "^10.4.0",
"firebase": "^10.14.1",
"react": "^18.2.0",
"react-color": "^2.19.3",
"react-cookie": "^4.1.1",
Expand Down
4 changes: 2 additions & 2 deletions frontend/src/App.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ import PostLogin from "@/Cabinet/pages/PostLogin";
import ProfilePage from "@/Cabinet/pages/ProfilePage";
import StoreMainPage from "@/Cabinet/pages/StoreMainPage";
import AdminMainPage from "@/Cabinet/pages/admin/AdminMainPage";
import AdminSlackNotiPage from "@/Cabinet/pages/admin/AdminSlackNotiPage";
import AdminSlackAlarmPage from "@/Cabinet/pages/admin/AdminSlackAlarmPage";
import AdminStorePage from "@/Cabinet/pages/admin/AdminStorePage";
import LoadingAnimation from "@/Cabinet/components/Common/LoadingAnimation";
import DetailPage from "@/Presentation/pages/DetailPage";
Expand Down Expand Up @@ -74,7 +74,7 @@ function App(): React.ReactElement {
<Route path="main" element={<AdminMainPage />} />
<Route path="search" element={<SearchPage />} />
<Route path="club" element={<AdminClubPage />} />
<Route path="slack-notification" element={<AdminSlackNotiPage />} />
<Route path="slack-alarm" element={<AdminSlackAlarmPage />} />
<Route path="available" element={<AvailablePage />} />
<Route path="store" element={<AdminStorePage />} />
</Route>
Expand Down
21 changes: 13 additions & 8 deletions frontend/src/Cabinet/api/axios/axios.custom.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,10 +28,15 @@ export const axiosMyInfo = async (): Promise<any> => {
}
};

const axiosUpdateAlarmURL = "/v4/users/me/alarms";
export const axiosUpdateAlarm = async (alarm: AlarmInfo): Promise<any> => {
const axiosUpdateAlarmReceptionPathURL = "/v4/users/me/alarms";
export const axiosUpdateAlarmReceptionPath = async (
alarm: AlarmInfo
): Promise<any> => {
try {
const response = await instance.put(axiosUpdateAlarmURL, alarm);
const response = await instance.put(
axiosUpdateAlarmReceptionPathURL,
alarm
);
return response;
} catch (error) {
throw error;
Expand Down Expand Up @@ -891,13 +896,13 @@ export const axiosGetAvailableCabinets = async (): Promise<any> => {
}
};

const axiosSendSlackNotificationToUserURL = "/slack/send";
export const axiosSendSlackNotificationToUser = async (
const axiosSendSlackAlarmToUserURL = "/slack/send";
export const axiosSendSlackAlarmToUser = async (
receiverName: string,
message: string
): Promise<any> => {
try {
const response = await instance.post(axiosSendSlackNotificationToUserURL, {
const response = await instance.post(axiosSendSlackAlarmToUserURL, {
receiverName: receiverName,
message: message,
});
Expand All @@ -907,13 +912,13 @@ export const axiosSendSlackNotificationToUser = async (
}
};

export const axiosSendSlackNotificationToChannel = async (
export const axiosSendSlackAlarmToChannel = async (
receiverName: string,
message: string,
channel: string | undefined
): Promise<any> => {
try {
await instance.post(axiosSendSlackNotificationToUserURL + `/${channel}`, {
await instance.post(axiosSendSlackAlarmToUserURL + `/${channel}`, {
receiverName: receiverName,
message: message,
});
Expand Down
2 changes: 2 additions & 0 deletions frontend/src/Cabinet/api/axios/axios.log.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { captureException } from "@sentry/react";
import { HttpStatusCode } from "axios";
import ErrorType from "@/Cabinet/types/enum/error.type.enum";
import { getCookie } from "@/Cabinet/api/react_cookie/cookies";

Expand All @@ -12,6 +13,7 @@ export const logAxiosError = (
errorMsg: string,
isAdmin = false
) => {
if (error.response?.status === HttpStatusCode.BadRequest) return;
error.message = (isAdmin ? "[Admin] " : "") + errorMsg;
captureException(error, {
tags: {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,69 +3,83 @@ import {
requestFcmAndGetDeviceToken,
} from "@/Cabinet/firebase/firebase-messaging-sw";
import { useEffect, useMemo, useState } from "react";
import NotificationCard from "@/Cabinet/components/Card/NotificationCard/NotificationCard";
import AlarmCard from "@/Cabinet/components/Card/AlarmCard/AlarmCard";
import ModalPortal from "@/Cabinet/components/Modals/ModalPortal";
import {
FailResponseModal,
SuccessResponseModal,
} from "@/Cabinet/components/Modals/ResponseModal/ResponseModal";
import { AlarmInfo } from "@/Cabinet/types/dto/alarm.dto";
import {
axiosUpdateAlarm,
axiosUpdateAlarmReceptionPath,
axiosUpdateDeviceToken,
} from "@/Cabinet/api/axios/axios.custom";
import useDebounce from "@/Cabinet/hooks/useDebounce";

const NotificationCardContainer = ({ alarm }: { alarm: AlarmInfo | null }) => {
const AlarmCardContainer = ({ alarm }: { alarm: AlarmInfo | null }) => {
const [showResponseModal, setShowResponseModal] = useState(false);
const [hasErrorOnResponse, setHasErrorOnResponse] = useState(false);
const [modalTitle, setModalTitle] = useState("");
const [modalContents, setModalContents] = useState<string | null>(null);
const [alarms, setAlarms] = useState({ current: alarm, original: alarm });
const [isLoading, setIsLoading] = useState(false);
const isModified = useMemo(
() => JSON.stringify(alarms.current) !== JSON.stringify(alarms.original),
[alarms]
);
const { debounce } = useDebounce();

useEffect(() => {
setAlarms({ current: alarm, original: alarm });
}, [alarm]);

const handleToggleChange = (type: keyof AlarmInfo, checked: boolean) => {
setAlarms((prev) => {
const current = prev.current
? { ...prev.current, [type]: checked }
: null;
return {
...prev,
current,
};
});
};

const handleSave = async () => {
if (!alarms.current) return;
const updateAlarmReceptionPath = async () => {
try {
await axiosUpdateAlarm(alarms.current);
// 푸쉬 알림 설정이 변경되었을 경우, 토큰을 요청하거나 삭제합니다.
if (alarms.current.push) {
if (alarms.current!.push) {
const deviceToken = await requestFcmAndGetDeviceToken();
await axiosUpdateDeviceToken(deviceToken);
} else {
await deleteFcmToken();
await axiosUpdateDeviceToken(null);
}
await axiosUpdateAlarmReceptionPath(alarms.current!);
setAlarms({ current: alarms.current, original: alarms.current });
setModalTitle("설정이 저장되었습니다");
} catch (error: any) {
setAlarms((prev) => ({ ...prev, current: prev.original }));
setHasErrorOnResponse(true);
setModalTitle(error.response.data.message);
if (error.response) setModalTitle(error.response.data.message);
else {
setModalTitle(error.name);
setModalContents(error.message);
}
} finally {
setIsLoading(false);
setShowResponseModal(true);
}
};

const handleToggleChange = (type: keyof AlarmInfo, checked: boolean) => {
setAlarms((prev) => {
const current = prev.current
? { ...prev.current, [type]: checked }
: null;
return {
...prev,
current,
};
});
};

const handleSave = async () => {
setIsLoading(true);
if (!alarms.current) return;
debounce("alarmReceptionPath", updateAlarmReceptionPath, 300);
};

const handleCancel = () => {
setAlarms((prev) => ({ ...prev, current: prev.original }));
!isLoading && setAlarms((prev) => ({ ...prev, current: prev.original }));
};

const handleCloseModal = () => {
Expand All @@ -74,7 +88,7 @@ const NotificationCardContainer = ({ alarm }: { alarm: AlarmInfo | null }) => {

return (
<>
<NotificationCard
<AlarmCard
key={JSON.stringify(alarms)}
alarm={alarms.current ?? { email: false, push: false, slack: false }}
buttons={
Expand All @@ -86,11 +100,13 @@ const NotificationCardContainer = ({ alarm }: { alarm: AlarmInfo | null }) => {
fontColor: "var(--white-text-with-bg-color)",
backgroundColor: "var(--sys-main-color)",
isClickable: true,
isLoading: isLoading,
},
{
label: "취소",
onClick: handleCancel,
isClickable: true,
isClickable: !isLoading,
isLoading: isLoading,
},
]
: [
Expand All @@ -104,17 +120,20 @@ const NotificationCardContainer = ({ alarm }: { alarm: AlarmInfo | null }) => {
]
}
onToggleChange={handleToggleChange}
isLoading={isLoading}
/>
<ModalPortal>
{showResponseModal &&
(hasErrorOnResponse ? (
<FailResponseModal
modalTitle={modalTitle}
modalContents={modalContents}
closeModal={handleCloseModal}
/>
) : (
<SuccessResponseModal
modalTitle={modalTitle}
modalContents={modalContents}
closeModal={handleCloseModal}
/>
))}
Expand All @@ -123,4 +142,4 @@ const NotificationCardContainer = ({ alarm }: { alarm: AlarmInfo | null }) => {
);
};

export default NotificationCardContainer;
export default AlarmCardContainer;
Original file line number Diff line number Diff line change
Expand Up @@ -7,17 +7,19 @@ import {
import ToggleSwitch from "@/Cabinet/components/Common/ToggleSwitch";
import { AlarmInfo } from "@/Cabinet/types/dto/alarm.dto";

interface NotificationCardProps {
interface AlarmCardProps {
alarm: AlarmInfo;
buttons: IButtonProps[];
onToggleChange: (type: keyof AlarmInfo, checked: boolean) => void;
isLoading: boolean;
}

const NotificationCard = ({
const AlarmCard = ({
alarm,
buttons,
onToggleChange,
}: NotificationCardProps) => {
isLoading,
}: AlarmCardProps) => {
const handleToggle = (type: keyof AlarmInfo) => (checked: boolean) => {
onToggleChange(type, checked);
};
Expand All @@ -26,17 +28,18 @@ const NotificationCard = ({
<CardContentStyled>
<ContentInfoStyled>{label}</ContentInfoStyled>
<ToggleSwitch
id={`${type}-notification`}
id={`${type}-alarm`}
checked={alarm[type]}
onChange={handleToggle(type)}
disabled={isLoading}
/>
</CardContentStyled>
);

return (
<Card
title={"알림"}
gridArea="notification"
gridArea="alarm"
width={"350px"}
height={"230px"}
buttons={buttons}
Expand All @@ -50,4 +53,4 @@ const NotificationCard = ({
);
};

export default NotificationCard;
export default AlarmCard;
19 changes: 15 additions & 4 deletions frontend/src/Cabinet/components/Card/Card.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ export interface IButtonProps {
icon?: React.FunctionComponent<React.SVGProps<SVGSVGElement>> | null; // NOTE: icon 이 있을 경우, icon 을 표시
isClickable: boolean;
isExtensible?: boolean;
isLoading?: boolean;
}

interface CardProps {
Expand Down Expand Up @@ -41,7 +42,7 @@ const Card = ({
{onClickToolTip && <ToolTipIcon onClick={onClickToolTip} />}
</CardTitleWrapperStyled>
{buttons.length > 0 && (
<CardButtonWrapper>
<CardButtonsWrapper>
{buttons?.map((button, index) => (
<CardButtonStyled
key={index}
Expand All @@ -51,11 +52,12 @@ const Card = ({
icon={button.icon}
isClickable={button.isClickable}
isExtensible={button.isExtensible}
isLoading={button.isLoading}
>
{!button.icon ? button.label : <button.icon />}
</CardButtonStyled>
))}
</CardButtonWrapper>
</CardButtonsWrapper>
)}
</CardHeaderStyled>
)}
Expand Down Expand Up @@ -113,7 +115,7 @@ const ToolTipIcon = styled.div`
}
`;

export const CardButtonWrapper = styled.div`
export const CardButtonsWrapper = styled.div`
display: flex;
font-size: var(--size-base);
`;
Expand All @@ -124,6 +126,7 @@ export const CardButtonStyled = styled.div<{
icon?: React.FunctionComponent<React.SVGProps<SVGSVGElement>> | null;
isClickable?: boolean;
isExtensible?: boolean;
isLoading?: boolean;
}>`
${(props) =>
props.icon
Expand Down Expand Up @@ -151,7 +154,15 @@ export const CardButtonStyled = styled.div<{
font-weight: ${props.isClickable && 400};
}
`}
cursor: ${(props) => (props.isClickable ? "pointer" : "default")};
cursor: ${(props) => {
if (props.isClickable) {
if (props.isLoading) return "wait"; // ex) 프로필 - 알림 요청 후 응답 전까지 저장 버튼 hover시
return "pointer";
}
if (props.isLoading) return "not-allowed"; // ex) 프로필 - 알림 요청 후 응답 전까지 취소 버튼 hover시
return "default";
}};
& > svg {
height: 20px;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -128,8 +128,8 @@ const LeftMainNavContainer = ({ isAdmin }: { isAdmin?: boolean }) => {
closeAll();
};

const onClickSlackNotiButton = () => {
navigator("slack-notification");
const onClickSlackAlarmButton = () => {
navigator("slack-alarm");
closeAll();
};

Expand Down Expand Up @@ -182,7 +182,7 @@ const LeftMainNavContainer = ({ isAdmin }: { isAdmin?: boolean }) => {
onClickFloorButton={onClickFloorButton}
onClickSearchButton={onClickSearchButton}
onClickLogoutButton={onClickLogoutButton}
onClickSlackNotiButton={onClickSlackNotiButton}
onClickSlackAlarmButton={onClickSlackAlarmButton}
onClickAdminClubButton={onClickAdminClubButton}
onClickMainClubButton={onClickMainClubButton}
onClickProfileButton={onClickProfileButton}
Expand Down
Loading

0 comments on commit c860114

Please sign in to comment.