diff --git a/.buildignore b/.buildignore index 51289604a..1824a52a0 100644 --- a/.buildignore +++ b/.buildignore @@ -3,4 +3,4 @@ tsconfig.json yarn.lock README.md .gitignore -*.tar.gz \ No newline at end of file +*.tar.gz diff --git a/.editorconfig b/.editorconfig new file mode 100644 index 000000000..f0de91639 --- /dev/null +++ b/.editorconfig @@ -0,0 +1,13 @@ +# EditorConfig: https://EditorConfig.org + +[*] +charset = utf-8 +insert_final_newline = true # Type of newline is managed by git in .gitattributes +trim_trailing_whitespace = true + +[{*.{Dockerfile,css,js,jsx,ts,tsx},Dockerfile}] +indent_style = tab + +[*.{yml,yaml}] # YAML does not allow tab indentation +indent_style = space +indent_size = 2 diff --git a/.env.template b/.env.template index 34cce26b0..08993bd34 100644 --- a/.env.template +++ b/.env.template @@ -13,4 +13,4 @@ REACT_APP_FIREBASE_APP_ID= REACT_APP_FIREBASE_MEASUREMENT_ID= REACT_APP_DID_KEY_VERSION=jwk_jcs-pub REACT_APP_VERSION=$npm_package_version -REACT_APP_CONSOLE_TYPES=info,warn,error \ No newline at end of file +REACT_APP_CONSOLE_TYPES=info,warn,error diff --git a/.github/workflows/code-formatting.yml b/.github/workflows/code-formatting.yml new file mode 100644 index 000000000..d7142ab16 --- /dev/null +++ b/.github/workflows/code-formatting.yml @@ -0,0 +1,26 @@ +# This name is shown in status badges +name: code-formatting + +on: + push: + branches-ignore: + - 'tmp**' + pull_request: + branches-ignore: + - 'tmp**' + +jobs: + editorconfig: + name: Check EditorConfig compliance + + runs-on: ubuntu-latest + + steps: + - name: Check out code + uses: actions/checkout@v3 + + - name: Set up editorconfig-checker + uses: editorconfig-checker/action-editorconfig-checker@v2 + + - name: Check code formatting + run: editorconfig-checker diff --git a/.gitignore b/.gitignore index 5157b62be..56d4b421c 100644 --- a/.gitignore +++ b/.gitignore @@ -44,4 +44,4 @@ src/config/config.dev.ts src/config/config.prod.js ssl_keys/* *.tar.gz -.npmrc \ No newline at end of file +.npmrc diff --git a/.htaccess b/.htaccess index 152dce1fe..62d0312c1 100644 --- a/.htaccess +++ b/.htaccess @@ -1,4 +1,4 @@ Options -MultiViews RewriteEngine On RewriteCond %{REQUEST_FILENAME} !-f -RewriteRule ^ index.html [QSA,L] \ No newline at end of file +RewriteRule ^ index.html [QSA,L] diff --git a/.vscode/settings.json b/.vscode/settings.json index 4a664bbc1..e70c03c9d 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -2,4 +2,4 @@ "editor.tabSize": 2, "editor.detectIndentation": false, "editor.insertSpaces": false -} \ No newline at end of file +} diff --git a/Dockerfile b/Dockerfile index cdc2ec3a6..c3dcb8950 100644 --- a/Dockerfile +++ b/Dockerfile @@ -4,7 +4,7 @@ WORKDIR /home/node/app COPY . . RUN --mount=type=secret,id=npmrc,required=true,target=./.npmrc,uid=1000 \ - yarn cache clean -f && yarn install && yarn build + yarn cache clean -f && yarn install && yarn build FROM nginx:alpine as deploy @@ -17,4 +17,4 @@ COPY --from=builder /home/node/app/build/ . EXPOSE 80 -CMD ["nginx", "-g", "daemon off;"] \ No newline at end of file +CMD ["nginx", "-g", "daemon off;"] diff --git a/README.md b/README.md index a8b361aba..f4657d093 100644 --- a/README.md +++ b/README.md @@ -39,7 +39,7 @@ Our Web Wallet provides a range of features tailored to enhance the credential m ```bash git clone https://github.com/your-username/wallet-frontend.git ``` - + - **Option 2: Using SSH** ```bash git clone git@github.com:your-username/wallet-frontend.git @@ -63,12 +63,12 @@ The project uses environment variables to manage different configurations. A `.e - REACT_APP_WS_URL: The URL of the websocket service. - REACT_APP_WALLET_BACKEND_URL: The URL of your backend service. - REACT_APP_LOGIN_WITH_PASSWORD: A Boolean value which show/hide the classic login/signup. - - REACT_APP_FIREBASE_API_KEY: Your API key for Firebase. + - REACT_APP_FIREBASE_API_KEY: Your API key for Firebase. - REACT_APP_FIREBASE_AUTH_DOMAIN: Your Firebase authentication domain. - REACT_APP_FIREBASE_PROJECT_ID: Your Firebase project ID. - REACT_APP_FIREBASE_STORAGE_BUCKET: Your Firebase storage bucket. - REACT_APP_FIREBASE_MESSAGING_SENDER_ID: Your Firebase Messaging Sender ID. - - REACT_APP_FIREBASE_APP_ID: Your Firebase App ID. + - REACT_APP_FIREBASE_APP_ID: Your Firebase App ID. - REACT_APP_FIREBASE_MEASUREMENT_ID: Your Firebase Measurement ID. - REACT_APP_CONSOLE_TYPES: Enable console logs (info, warn, error) separated by commas or leave empty for none. @@ -101,7 +101,7 @@ The PRF (Pseudo Random Function) extension in WebAuthn enables the evaluation of | Windows | ✔ | ✔ | ❌ | ✔ | | ✔ | | MacOS | ✔ | ✔ | ❌ | ✔ | ❌ | ✔ | | Android | ✔ | ✔ | ❌ | ✔ | | ✔ | -| iOS | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | +| iOS | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ### PRF Compatibility Scenarios @@ -123,7 +123,7 @@ The PRF (Pseudo Random Function) extension in WebAuthn enables the evaluation of | iOS | FIDO Security Key | NFC | ❌ | -***Note:** In this table, we use the term "FIDO Security Key" to refer to compatible security keys. It's important to understand that any security key should work with the hmac-secret extension, provided it supports this feature. +***Note:** In this table, we use the term "FIDO Security Key" to refer to compatible security keys. It's important to understand that any security key should work with the hmac-secret extension, provided it supports this feature. For a detailed list of security key models that support hmac-secret, you can refer to the [FIDO MDS Explorer](https://opotonniee.github.io/fido-mds-explorer/), where hmac-secret support is listed under metadataStatement > authenticatorGetInfo > extensions.* The wwWallet is committed to delivering a secure and adaptable authentication experience with an emphasis on PRF extension compatibility. @@ -162,7 +162,7 @@ We welcome contributions from the community to help improve the wwWallet Fronten 1. **Create a New Branch:** Create a new branch for your feature or bug fix - ```bash + ```bash git checkout -b my-feature ``` Replace my-feature with a descriptive name. @@ -172,14 +172,14 @@ We welcome contributions from the community to help improve the wwWallet Fronten 3. **Commit Changes:** Commit your changes with a descriptive commit message: - ```bash + ```bash git commit -m "Add new feature" ``` 4. **Push Changes:** Push your changes to your new branrch: - ```bash + ```bash git push --set-upstream origin my-feature - ``` + ``` 5. **Create a Pull Request:** Open a pull request on the original repository. Provide a detailed description of your changes and their purpose. diff --git a/development.Dockerfile b/development.Dockerfile index 2e7b892cd..4e7008f8a 100644 --- a/development.Dockerfile +++ b/development.Dockerfile @@ -5,7 +5,7 @@ WORKDIR /dependencies # Install dependencies first so rebuild of these layers is only needed when dependencies change COPY package.json yarn.lock . RUN --mount=type=secret,id=npmrc,required=true,target=./.npmrc,uid=1000 \ - yarn install && yarn cache clean -f + yarn install && yarn cache clean -f FROM node:16-bullseye-slim as development diff --git a/nginx/nginx.conf b/nginx/nginx.conf index 38a61e01f..f03614a8d 100644 --- a/nginx/nginx.conf +++ b/nginx/nginx.conf @@ -8,4 +8,4 @@ server { } # Add any additional Nginx configuration here as needed -} \ No newline at end of file +} diff --git a/postcss.config.js b/postcss.config.js index 9a5389100..5c1449894 100644 --- a/postcss.config.js +++ b/postcss.config.js @@ -3,4 +3,4 @@ module.exports = { require('tailwindcss'), require('autoprefixer'), ], -}; \ No newline at end of file +}; diff --git a/src/ConsoleBehavior.js b/src/ConsoleBehavior.js index f95c0fefe..e183285a3 100644 --- a/src/ConsoleBehavior.js +++ b/src/ConsoleBehavior.js @@ -13,30 +13,30 @@ function isMethodAllowed(method) { } function ConsoleBehavior() { - const originalConsole = { ...console }; - - const originalPrepareStackTrace = Error.prepareStackTrace; - - Object.keys(console).forEach(method => { - if (typeof console[method] === 'function') { - console[method] = (...args) => { - if (isMethodAllowed(method)) { - Error.prepareStackTrace = (_, stack) => stack; - const stack = new Error().stack; - Error.prepareStackTrace = originalPrepareStackTrace; - - const callSite = stack[1]; - if (callSite) { - const fileName = callSite.getFileName(); - const lineNumber = callSite.getLineNumber(); - args.push(`(at ${fileName}:${lineNumber})`); - } - - originalConsole[method].apply(console, args); - } - }; - } - }); + const originalConsole = { ...console }; + + const originalPrepareStackTrace = Error.prepareStackTrace; + + Object.keys(console).forEach(method => { + if (typeof console[method] === 'function') { + console[method] = (...args) => { + if (isMethodAllowed(method)) { + Error.prepareStackTrace = (_, stack) => stack; + const stack = new Error().stack; + Error.prepareStackTrace = originalPrepareStackTrace; + + const callSite = stack[1]; + if (callSite) { + const fileName = callSite.getFileName(); + const lineNumber = callSite.getLineNumber(); + args.push(`(at ${fileName}:${lineNumber})`); + } + + originalConsole[method].apply(console, args); + } + }; + } + }); } -export default ConsoleBehavior; \ No newline at end of file +export default ConsoleBehavior; diff --git a/src/components/ChistmasAnimation/Snowfalling.js b/src/components/ChistmasAnimation/Snowfalling.js index a83c8df40..0c8ec8691 100644 --- a/src/components/ChistmasAnimation/Snowfalling.js +++ b/src/components/ChistmasAnimation/Snowfalling.js @@ -2,27 +2,27 @@ import React, { useEffect, useState } from 'react'; import Snowfall from 'react-snowfall'; const Snowfalling = () => { - const [isChristmasSeason, setIsChristmasSeason] = useState(false); + const [isChristmasSeason, setIsChristmasSeason] = useState(false); - useEffect(() => { - const checkSeason = () => { - const today = new Date(); - const currentYear = today.getFullYear(); - - const start = new Date(currentYear, 11, 20); - const end = new Date(currentYear + 1, 0, 6); - - return today >= start && today <= end; - }; + useEffect(() => { + const checkSeason = () => { + const today = new Date(); + const currentYear = today.getFullYear(); - setIsChristmasSeason(checkSeason()); - }, []); + const start = new Date(currentYear, 11, 20); + const end = new Date(currentYear + 1, 0, 6); - return ( - <> - {isChristmasSeason && } - - ); + return today >= start && today <= end; + }; + + setIsChristmasSeason(checkSeason()); + }, []); + + return ( + <> + {isChristmasSeason && } + + ); } export default Snowfalling; diff --git a/src/components/Credentials/ApiFetchCredential.ts b/src/components/Credentials/ApiFetchCredential.ts index 272ba1400..b1aa94512 100644 --- a/src/components/Credentials/ApiFetchCredential.ts +++ b/src/components/Credentials/ApiFetchCredential.ts @@ -4,42 +4,42 @@ import { BackendApi } from '../../api'; import parseJwt from '../../functions/ParseJwt'; export async function fetchCredentialData(api: BackendApi, id = null) { - try { - const response = await api.get('/storage/vc'); + try { + const response = await api.get('/storage/vc'); - if (id) { - const targetImage = response.data.vc_list.find((img) => img.id.toString() === id); - const newImages = targetImage - ? [targetImage].map((item) => ({ - id: item.id, - credentialIdentifier:item.credentialIdentifier, - src: item.logoURL, - alt: item.issuerFriendlyName, - data: parseJwt(item.credential)["vc"]['credentialSubject'], - type: parseJwt(item.credential)['vc']["type"]["2"], - expdate: parseJwt(item.credential)['vc']["expirationDate"], - json:JSON.stringify(parseJwt(item.credential)["vc"], null, 2) + if (id) { + const targetImage = response.data.vc_list.find((img) => img.id.toString() === id); + const newImages = targetImage + ? [targetImage].map((item) => ({ + id: item.id, + credentialIdentifier: item.credentialIdentifier, + src: item.logoURL, + alt: item.issuerFriendlyName, + data: parseJwt(item.credential)["vc"]['credentialSubject'], + type: parseJwt(item.credential)['vc']["type"]["2"], + expdate: parseJwt(item.credential)['vc']["expirationDate"], + json: JSON.stringify(parseJwt(item.credential)["vc"], null, 2) - })) - : []; + })) + : []; - return newImages[0]; - } else { - const newImages = response.data.vc_list.map((item) => ({ - id: item.id, - credentialIdentifier:item.credentialIdentifier, - src: item.logoURL, - alt: item.issuerFriendlyName, - data: parseJwt(item.credential)["vc"]['credentialSubject'], - type: parseJwt(item.credential)['vc']["type"]["2"], - expdate: parseJwt(item.credential)['vc']["expirationDate"], - json:JSON.stringify(parseJwt(item.credential)["vc"], null, 2) - })); + return newImages[0]; + } else { + const newImages = response.data.vc_list.map((item) => ({ + id: item.id, + credentialIdentifier: item.credentialIdentifier, + src: item.logoURL, + alt: item.issuerFriendlyName, + data: parseJwt(item.credential)["vc"]['credentialSubject'], + type: parseJwt(item.credential)['vc']["type"]["2"], + expdate: parseJwt(item.credential)['vc']["expirationDate"], + json: JSON.stringify(parseJwt(item.credential)["vc"], null, 2) + })); - return newImages; - } - } catch (error) { - console.error('Failed to fetch data', error); - return null; - } + return newImages; + } + } catch (error) { + console.error('Failed to fetch data', error); + return null; + } } diff --git a/src/components/Credentials/CredentialDeleteButton.js b/src/components/Credentials/CredentialDeleteButton.js index a02931543..ae1525c7c 100644 --- a/src/components/Credentials/CredentialDeleteButton.js +++ b/src/components/Credentials/CredentialDeleteButton.js @@ -5,11 +5,11 @@ import { useTranslation } from 'react-i18next'; const CredentialDeleteButton = ({ onDelete }) => { const { t } = useTranslation(); - const handleClick = () => { - onDelete(); - }; + const handleClick = () => { + onDelete(); + }; - return ( + return (
- ); + ); }; export default CredentialDeleteButton; diff --git a/src/components/Credentials/CredentialInfo.js b/src/components/Credentials/CredentialInfo.js index 25b8ba3be..cc146c392 100644 --- a/src/components/Credentials/CredentialInfo.js +++ b/src/components/Credentials/CredentialInfo.js @@ -7,62 +7,62 @@ import { GiLevelEndFlag } from 'react-icons/gi'; import { formatDate } from '../../functions/DateFormat'; const getFieldIcon = (fieldName) => { - switch (fieldName) { - case 'type': - return ; - case 'expdate': - return ; - case 'dateOfBirth': - return ; - case 'familyName': - case 'firstName': - return ; - case 'diplomaTitle': - return ; - case 'eqfLevel': - return ; - case 'grade': - return ; - default: - return null; - } + switch (fieldName) { + case 'type': + return ; + case 'expdate': + return ; + case 'dateOfBirth': + return ; + case 'familyName': + case 'firstName': + return ; + case 'diplomaTitle': + return ; + case 'eqfLevel': + return ; + case 'grade': + return ; + default: + return null; + } }; const renderRow = (fieldName, fieldValue) => { - if (fieldValue) { - return ( - - - {getFieldIcon(fieldName)} - - {fieldValue} - - ); - } - return null; + if (fieldValue) { + return ( + + + {getFieldIcon(fieldName)} + + {fieldValue} + + ); + } + return null; }; const CredentialInfo = ({ credential }) => { - return ( -
- - - {credential && ( - <> - {renderRow('type', credential.type)} - {renderRow('expdate', formatDate(credential.expdate))} - {renderRow('familyName', credential.data.familyName)} - {renderRow('firstName', credential.data.firstName)} - {renderRow('dateOfBirth', credential.data.dateOfBirth)} - {renderRow('diplomaTitle', credential.data.diplomaTitle)} - {renderRow('eqfLevel', credential.data.eqfLevel)} - {renderRow('grade', credential.data.grade)} - - )} - -
-
- ); + return ( +
+ + + {credential && ( + <> + {renderRow('type', credential.type)} + {renderRow('expdate', formatDate(credential.expdate))} + {renderRow('familyName', credential.data.familyName)} + {renderRow('firstName', credential.data.firstName)} + {renderRow('dateOfBirth', credential.data.dateOfBirth)} + {renderRow('diplomaTitle', credential.data.diplomaTitle)} + {renderRow('eqfLevel', credential.data.eqfLevel)} + {renderRow('grade', credential.data.grade)} + + )} + +
+
+ ); }; export default CredentialInfo; diff --git a/src/components/Credentials/CredentialJson.js b/src/components/Credentials/CredentialJson.js index e91e2fc8a..c021395fc 100644 --- a/src/components/Credentials/CredentialJson.js +++ b/src/components/Credentials/CredentialJson.js @@ -7,23 +7,23 @@ import { AiOutlineDown, AiOutlineUp } from 'react-icons/ai'; const CredentialJson = ({ credential }) => { const [showJsonCredentials, setShowJsonCredentials] = useState(false); - return ( + return (
- +
-
+
{showJsonCredentials && credential ? (
@@ -41,4 +41,4 @@ const CredentialJson = ({ credential }) => { ); }; -export default CredentialJson; \ No newline at end of file +export default CredentialJson; diff --git a/src/components/HandlerNotification.js b/src/components/HandlerNotification.js index 2f5d3f87d..62ec5596b 100644 --- a/src/components/HandlerNotification.js +++ b/src/components/HandlerNotification.js @@ -5,72 +5,72 @@ import { AiOutlineClose } from 'react-icons/ai'; import logo from '../assets/images/logo.png'; const ToastDisplay = ({ id, notification }) => { - return ( -
window.location.href = '/'} - > -
- Logo -
-
-

{notification?.title}

-

{notification?.body}

-
- -
- ); + return ( +
window.location.href = '/'} + > +
+ Logo +
+
+

{notification?.title}

+

{notification?.body}

+
+ +
+ ); }; const HandlerNotification = ({ children }) => { - const [notification, setNotification] = useState({ title: '', body: '' }); - const [isMessageReceived, setMessageReceived] = useState(null); + const [notification, setNotification] = useState({ title: '', body: '' }); + const [isMessageReceived, setMessageReceived] = useState(null); - const showToast = () => - toast((t) => , { - onClick: () => { - window.location.href = '/'; - }, - }); + const showToast = () => + toast((t) => , { + onClick: () => { + window.location.href = '/'; + }, + }); - useEffect(() => { - if (notification?.title) { - showToast(); - } - }, [notification]); + useEffect(() => { + if (notification?.title) { + showToast(); + } + }, [notification]); - useEffect(() => { - let messageReceived = false; + useEffect(() => { + let messageReceived = false; const unregisterMessageListener = onMessageListener() - .then((payload) => { - // Process the received message - setNotification({ - title: payload?.notification?.title, - body: payload?.notification?.body, + .then((payload) => { + // Process the received message + setNotification({ + title: payload?.notification?.title, + body: payload?.notification?.body, + }); + setMessageReceived(true); // Message has been received + }) + .catch((err) => { + console.log('Failed to receive message:', err); + setMessageReceived(false); // Set isMessageReceived to false if there's an error }); - setMessageReceived(true); // Message has been received - }) - .catch((err) => { - console.log('Failed to receive message:', err); - setMessageReceived(false); // Set isMessageReceived to false if there's an error - }); - - return () => { - if (!messageReceived) { - setMessageReceived(false); // Set isMessageReceived to false if no message was received before unmount - } - }; - }, []); - // Render just children when waiting for message reception + return () => { + if (!messageReceived) { + setMessageReceived(false); // Set isMessageReceived to false if no message was received before unmount + } + }; + }, []); + + // Render just children when waiting for message reception if (isMessageReceived === null || isMessageReceived === false) { // Render children when waiting for a message return ( @@ -90,4 +90,4 @@ const HandlerNotification = ({ children }) => { }; -export default HandlerNotification; \ No newline at end of file +export default HandlerNotification; diff --git a/src/components/Popups/DeletePopup.js b/src/components/Popups/DeletePopup.js index 92e07a38c..775c7b601 100644 --- a/src/components/Popups/DeletePopup.js +++ b/src/components/Popups/DeletePopup.js @@ -44,4 +44,4 @@ const DeletePopup = ({ isOpen, onConfirm, onCancel, message, loading }) => { ); }; -export default DeletePopup; \ No newline at end of file +export default DeletePopup; diff --git a/src/components/Popups/PinInput.js b/src/components/Popups/PinInput.js index fc2c8e692..4cae24ea5 100644 --- a/src/components/Popups/PinInput.js +++ b/src/components/Popups/PinInput.js @@ -47,7 +47,7 @@ function PinInput({ showPopup, setShowPopup }) { inputRefs[index - 1].current.focus(); newPin[index - 1] = ''; } else if (value !== '' && index < 3) { - // Move focus to the next input and clean it + // Move focus to the next input and clean it const nextInput = inputRefs[index + 1].current; newPin[index + 1] = ''; setPin(newPin); diff --git a/src/components/Popups/SelectCredentials.js b/src/components/Popups/SelectCredentials.js index 70f3375e6..964980376 100644 --- a/src/components/Popups/SelectCredentials.js +++ b/src/components/Popups/SelectCredentials.js @@ -69,7 +69,7 @@ function SelectCredentials({ showPopup, setShowPopup, setSelectionMap, conforman

- + {t('selectCredentialPopup.title')}


diff --git a/src/components/PrivateRoute.js b/src/components/PrivateRoute.js index d62ee7831..fce26b410 100644 --- a/src/components/PrivateRoute.js +++ b/src/components/PrivateRoute.js @@ -7,60 +7,60 @@ import Layout from './Layout'; import Spinner from './Spinner'; // Import your spinner component const PrivateRoute = ({ children }) => { - const api = useApi(); - const [isPermissionGranted, setIsPermissionGranted] = useState(false); + const api = useApi(); + const [isPermissionGranted, setIsPermissionGranted] = useState(false); const [isPermissionValue, setispermissionValue] = useState(''); - const [loading, setLoading] = useState(false); - const keystore = useLocalStorageKeystore(); - const isLoggedIn = api.isLoggedIn() && keystore.isOpen(); - - const location = useLocation(); - const navigate = useNavigate(); - - useEffect(() => { - const requestNotificationPermission = async () => { - console.log(Notification.permission); - try { - if (Notification.permission !== 'granted') { + const [loading, setLoading] = useState(false); + const keystore = useLocalStorageKeystore(); + const isLoggedIn = api.isLoggedIn() && keystore.isOpen(); + + const location = useLocation(); + const navigate = useNavigate(); + + useEffect(() => { + const requestNotificationPermission = async () => { + console.log(Notification.permission); + try { + if (Notification.permission !== 'granted') { sessionStorage.setItem('tokenSentInSession', 'false'); - const permissionResult = await Notification.requestPermission(); - if (permissionResult === 'granted') { - setIsPermissionGranted(true); - } + const permissionResult = await Notification.requestPermission(); + if (permissionResult === 'granted') { + setIsPermissionGranted(true); + } setispermissionValue(permissionResult); - } else { - setIsPermissionGranted(true); - } - } catch (error) { - console.error('Error requesting notification permission:', error); - } - }; - - if (isLoggedIn) { - requestNotificationPermission(); - } - }, [isLoggedIn,location]); + } else { + setIsPermissionGranted(true); + } + } catch (error) { + console.error('Error requesting notification permission:', error); + } + }; + + if (isLoggedIn) { + requestNotificationPermission(); + } + }, [isLoggedIn, location]); useEffect(() => { const sendFcmTokenToBackend = async () => { - console.log('isPermissionGranted:',isPermissionGranted); + console.log('isPermissionGranted:', isPermissionGranted); if (isPermissionGranted) { // Check if the token has already been sent in the current session const tokenSentInSession = sessionStorage.getItem('tokenSentInSession'); - console.log('tokenSentInSession:',tokenSentInSession); + console.log('tokenSentInSession:', tokenSentInSession); - if (tokenSentInSession==='false') { + if (tokenSentInSession === 'false') { setLoading(true); try { const fcmToken = await fetchToken(); - await api.post('/user/session/fcm_token/add', { fcm_token: fcmToken }); - // Set a flag in sessionStorage to indicate that the token has been sent - sessionStorage.setItem('tokenSentInSession', 'true'); - console.log('send FCM Token:', fcmToken); - + await api.post('/user/session/fcm_token/add', { fcm_token: fcmToken }); + // Set a flag in sessionStorage to indicate that the token has been sent + sessionStorage.setItem('tokenSentInSession', 'true'); + console.log('send FCM Token:', fcmToken); + console.log('FCM Token:', fcmToken); } catch (error) { console.error('Error sending FCM token to the backend:', error); @@ -70,33 +70,33 @@ const PrivateRoute = ({ children }) => { } } } - + sendFcmTokenToBackend(); }, [isPermissionGranted]); - useEffect(() => { - if (!isLoggedIn) { - const destination = location.pathname + location.search; - navigate('/login', { state: { from: destination } }); - } - }, [isLoggedIn, location, navigate]); + useEffect(() => { + if (!isLoggedIn) { + const destination = location.pathname + location.search; + navigate('/login', { state: { from: destination } }); + } + }, [isLoggedIn, location, navigate]); - if (!isLoggedIn) { - return ; - } + if (!isLoggedIn) { + return ; + } return ( - <> - {loading && } - {!loading && ( - - {children} - - )} - - ); + <> + {loading && } + {!loading && ( + + {children} + + )} + + ); }; -export default PrivateRoute; \ No newline at end of file +export default PrivateRoute; diff --git a/src/components/QRCodeScanner/CornerBox.js b/src/components/QRCodeScanner/CornerBox.js index eaa4dccca..fba38c88d 100644 --- a/src/components/QRCodeScanner/CornerBox.js +++ b/src/components/QRCodeScanner/CornerBox.js @@ -23,4 +23,4 @@ const CornerBox = ({ qrDetected, side, position, boxSize }) => { return
; }; -export default CornerBox; \ No newline at end of file +export default CornerBox; diff --git a/src/components/Sidebar.js b/src/components/Sidebar.js index d64e2f2bc..d15add45b 100644 --- a/src/components/Sidebar.js +++ b/src/components/Sidebar.js @@ -11,21 +11,19 @@ import { Trans, useTranslation } from 'react-i18next'; const NavItem = ({ - children, - handleNavigate, - location, - path, + children, + handleNavigate, + location, + path, }) => { - return ( -
  • handleNavigate(path)} - className={`cursor-pointer flex items-center space-x-2 mb-4 p-2 rounded-r-xl ${ - location.pathname === path ? 'bg-white text-custom-blue' : 'nav-item-animate-hover' - }`} - > - {children} -
  • - ); + return ( +
  • handleNavigate(path)} + className={`cursor-pointer flex items-center space-x-2 mb-4 p-2 rounded-r-xl ${location.pathname === path ? 'bg-white text-custom-blue' : 'nav-item-animate-hover'}`} + > + {children} +
  • + ); }; @@ -33,9 +31,9 @@ const NavItem = ({ const Sidebar = ({ isOpen, toggle }) => { - const api = useApi(); + const api = useApi(); const { username, displayName } = api.getSession(); - const location=useLocation(); + const location = useLocation(); const navigate = useNavigate(); const keystore = useLocalStorageKeystore(); const { t } = useTranslation(); @@ -50,19 +48,19 @@ const Sidebar = ({ isOpen, toggle }) => { if (location.pathname === path) { window.location.reload(); } else { - navigate(path); - if (window.innerWidth <= 639) { - toggle(); - } } + navigate(path); + if (window.innerWidth <= 639) { + toggle(); + } + } }; return (