From 7ac07b7b73928779e7ec2bc5a9897824061d838c Mon Sep 17 00:00:00 2001 From: Prateek Shourya Date: Mon, 10 Jun 2024 19:05:32 +0530 Subject: [PATCH] chore: app dir improvement (#4750) * chore: remove constants package. * fix: useRouter import in editor. * chore: improve `peekCycle` and `peekModule` logic. * style: update app progress bar color. --- admin/package.json | 1 - packages/constants/package.json | 10 - packages/constants/src/auth.ts | 372 ------------------ packages/constants/src/index.ts | 1 - .../src/ui/mentions/mention-node-view.tsx | 3 +- space/package.json | 1 - web/app/onboarding/page.tsx | 3 +- web/app/provider.tsx | 2 +- .../cycles/board/cycles-board-card.tsx | 2 +- .../cycles/list/cycles-list-item.tsx | 2 +- web/components/modules/module-card-item.tsx | 2 +- web/components/modules/module-list-item.tsx | 2 +- web/package.json | 1 - yarn.lock | 2 +- 14 files changed, 10 insertions(+), 394 deletions(-) delete mode 100644 packages/constants/package.json delete mode 100644 packages/constants/src/auth.ts delete mode 100644 packages/constants/src/index.ts diff --git a/admin/package.json b/admin/package.json index 9c4567070..ff7178066 100644 --- a/admin/package.json +++ b/admin/package.json @@ -14,7 +14,6 @@ "@headlessui/react": "^1.7.19", "@plane/types": "*", "@plane/ui": "*", - "@plane/constants": "*", "@tailwindcss/typography": "^0.5.9", "@types/lodash": "^4.17.0", "autoprefixer": "10.4.14", diff --git a/packages/constants/package.json b/packages/constants/package.json deleted file mode 100644 index 28d84c32b..000000000 --- a/packages/constants/package.json +++ /dev/null @@ -1,10 +0,0 @@ -{ - "name": "@plane/constants", - "version": "0.21.0", - "private": true, - "main": "./src/index.ts", - "exports": { - ".": "./src/index.ts", - "./*": "./src/*" - } -} diff --git a/packages/constants/src/auth.ts b/packages/constants/src/auth.ts deleted file mode 100644 index 065b188cf..000000000 --- a/packages/constants/src/auth.ts +++ /dev/null @@ -1,372 +0,0 @@ -import { ReactNode } from "react"; -// import Link from "next/link"; -// import { EAuthenticationErrorCodes } from "@/helpers/authentication.helper"; - -export enum EPageTypes { - PUBLIC = "PUBLIC", - NON_AUTHENTICATED = "NON_AUTHENTICATED", - SET_PASSWORD = "SET_PASSWORD", - ONBOARDING = "ONBOARDING", - AUTHENTICATED = "AUTHENTICATED", -} - -export enum EAuthModes { - SIGN_IN = "SIGN_IN", - SIGN_UP = "SIGN_UP", -} - -export enum EAuthSteps { - EMAIL = "EMAIL", - PASSWORD = "PASSWORD", - UNIQUE_CODE = "UNIQUE_CODE", -} - -// TODO: remove this -export enum EErrorAlertType { - BANNER_ALERT = "BANNER_ALERT", - INLINE_FIRST_NAME = "INLINE_FIRST_NAME", - INLINE_EMAIL = "INLINE_EMAIL", - INLINE_PASSWORD = "INLINE_PASSWORD", - INLINE_EMAIL_CODE = "INLINE_EMAIL_CODE", -} - -export enum EAuthErrorCodes { - // Global - INSTANCE_NOT_CONFIGURED = "5000", - INVALID_EMAIL = "5005", - EMAIL_REQUIRED = "5010", - SIGNUP_DISABLED = "5015", - MAGIC_LINK_LOGIN_DISABLED = "5017", - PASSWORD_LOGIN_DISABLED = "5019", - SMTP_NOT_CONFIGURED = "5025", - // Password strength - INVALID_PASSWORD = "5020", - // Sign Up - // USER_ACCOUNT_DEACTIVATED = "5019", - USER_ALREADY_EXIST = "5030", - AUTHENTICATION_FAILED_SIGN_UP = "5035", - REQUIRED_EMAIL_PASSWORD_SIGN_UP = "5040", - INVALID_EMAIL_SIGN_UP = "5045", - INVALID_EMAIL_MAGIC_SIGN_UP = "5050", - MAGIC_SIGN_UP_EMAIL_CODE_REQUIRED = "5055", - // Sign In - USER_DOES_NOT_EXIST = "5060", - AUTHENTICATION_FAILED_SIGN_IN = "5065", - REQUIRED_EMAIL_PASSWORD_SIGN_IN = "5070", - INVALID_EMAIL_SIGN_IN = "5075", - INVALID_EMAIL_MAGIC_SIGN_IN = "5080", - MAGIC_SIGN_IN_EMAIL_CODE_REQUIRED = "5085", - // Both Sign in and Sign up for magic - INVALID_MAGIC_CODE = "5090", - EXPIRED_MAGIC_CODE = "5095", - EMAIL_CODE_ATTEMPT_EXHAUSTED = "5100", - // Oauth - GOOGLE_NOT_CONFIGURED = "5105", - GITHUB_NOT_CONFIGURED = "5110", - GOOGLE_OAUTH_PROVIDER_ERROR = "5115", - GITHUB_OAUTH_PROVIDER_ERROR = "5120", - // Reset Password - INVALID_PASSWORD_TOKEN = "5125", - EXPIRED_PASSWORD_TOKEN = "5130", - // Change password - INCORRECT_OLD_PASSWORD = "5135", - MISSING_PASSWORD= "5138", - INVALID_NEW_PASSWORD = "5140", - // set passowrd - PASSWORD_ALREADY_SET = "5145", - // Admin - ADMIN_ALREADY_EXIST = "5150", - REQUIRED_ADMIN_EMAIL_PASSWORD_FIRST_NAME = "5155", - INVALID_ADMIN_EMAIL = "5160", - INVALID_ADMIN_PASSWORD = "5165", - REQUIRED_ADMIN_EMAIL_PASSWORD = "5170", - ADMIN_AUTHENTICATION_FAILED = "5175", - ADMIN_USER_ALREADY_EXIST = "5180", - ADMIN_USER_DOES_NOT_EXIST = "5185", -} - -export type TAuthErrorInfo = { - type: EErrorAlertType; - code: EAuthErrorCodes; - title: string; - message: ReactNode; -}; - -// const errorCodeMessages: { -// [key in EAuthErrorCodes]: { title: string; message: (email?: string | undefined) => ReactNode }; -// } = { -// // global -// [EAuthErrorCodes.INSTANCE_NOT_CONFIGURED]: { -// title: `Instance not configured`, -// message: () => `Instance not configured. Please contact your administrator.`, -// }, -// [EAuthErrorCodes.SIGNUP_DISABLED]: { -// title: `Sign up disabled`, -// message: () => `Sign up disabled. Please contact your administrator.`, -// }, -// [EAuthErrorCodes.INVALID_PASSWORD]: { -// title: `Invalid password`, -// message: () => `Invalid password. Please try again.`, -// }, -// [EAuthErrorCodes.SMTP_NOT_CONFIGURED]: { -// title: `SMTP not configured`, -// message: () => `SMTP not configured. Please contact your administrator.`, -// }, - - // email check in both sign up and sign in -// [EAuthErrorCodes.INVALID_EMAIL]: { -// title: `Invalid email`, -// message: () => `Invalid email. Please try again.`, -// }, -// [EAuthenticationErrorCodes.EMAIL_REQUIRED]: { -// title: `Email required`, -// message: () => `Email required. Please try again.`, -// }, - -// // sign up -// [EAuthenticationErrorCodes.USER_ALREADY_EXIST]: { -// title: `User already exists`, -// message: (email = undefined) => ( -//
-// Your account is already registered.  -// -// Sign In -// -//  now. -//
-// ), -// }, -// [EAuthenticationErrorCodes.REQUIRED_EMAIL_PASSWORD_SIGN_UP]: { -// title: `Email and password required`, -// message: () => `Email and password required. Please try again.`, -// }, -// [EAuthenticationErrorCodes.AUTHENTICATION_FAILED_SIGN_UP]: { -// title: `Authentication failed`, -// message: () => `Authentication failed. Please try again.`, -// }, -// [EAuthenticationErrorCodes.INVALID_EMAIL_SIGN_UP]: { -// title: `Invalid email`, -// message: () => `Invalid email. Please try again.`, -// }, -// [EAuthenticationErrorCodes.MAGIC_SIGN_UP_EMAIL_CODE_REQUIRED]: { -// title: `Email and code required`, -// message: () => `Email and code required. Please try again.`, -// }, -// [EAuthenticationErrorCodes.INVALID_EMAIL_MAGIC_SIGN_UP]: { -// title: `Invalid email`, -// message: () => `Invalid email. Please try again.`, -// }, - -// // sign in -// [EAuthenticationErrorCodes.USER_ACCOUNT_DEACTIVATED]: { -// title: `User account deactivated`, -// message: () =>
Your account is deactivated. Contact support@plane.so.
, -// }, -// [EAuthenticationErrorCodes.USER_DOES_NOT_EXIST]: { -// title: `User does not exist`, -// message: (email = undefined) => ( -//
-// No account found.  -// -// Create one -// -//  to get started. -//
-// ), -// }, -// [EAuthenticationErrorCodes.REQUIRED_EMAIL_PASSWORD_SIGN_IN]: { -// title: `Email and password required`, -// message: () => `Email and password required. Please try again.`, -// }, -// [EAuthenticationErrorCodes.AUTHENTICATION_FAILED_SIGN_IN]: { -// title: `Authentication failed`, -// message: () => `Authentication failed. Please try again.`, -// }, -// [EAuthenticationErrorCodes.INVALID_EMAIL_SIGN_IN]: { -// title: `Invalid email`, -// message: () => `Invalid email. Please try again.`, -// }, -// [EAuthenticationErrorCodes.MAGIC_SIGN_IN_EMAIL_CODE_REQUIRED]: { -// title: `Email and code required`, -// message: () => `Email and code required. Please try again.`, -// }, -// [EAuthenticationErrorCodes.INVALID_EMAIL_MAGIC_SIGN_IN]: { -// title: `Invalid email`, -// message: () => `Invalid email. Please try again.`, -// }, - -// // Both Sign in and Sign up -// [EAuthenticationErrorCodes.INVALID_MAGIC_CODE]: { -// title: `Authentication failed`, -// message: () => `Invalid magic code. Please try again.`, -// }, -// [EAuthenticationErrorCodes.EXPIRED_MAGIC_CODE]: { -// title: `Expired magic code`, -// message: () => `Expired magic code. Please try again.`, -// }, -// [EAuthenticationErrorCodes.EMAIL_CODE_ATTEMPT_EXHAUSTED]: { -// title: `Expired magic code`, -// message: () => `Expired magic code. Please try again.`, -// }, - -// // Oauth -// [EAuthenticationErrorCodes.GOOGLE_NOT_CONFIGURED]: { -// title: `Google not configured`, -// message: () => `Google not configured. Please contact your administrator.`, -// }, -// [EAuthenticationErrorCodes.GITHUB_NOT_CONFIGURED]: { -// title: `GitHub not configured`, -// message: () => `GitHub not configured. Please contact your administrator.`, -// }, -// [EAuthenticationErrorCodes.GOOGLE_OAUTH_PROVIDER_ERROR]: { -// title: `Google OAuth provider error`, -// message: () => `Google OAuth provider error. Please try again.`, -// }, -// [EAuthenticationErrorCodes.GITHUB_OAUTH_PROVIDER_ERROR]: { -// title: `GitHub OAuth provider error`, -// message: () => `GitHub OAuth provider error. Please try again.`, -// }, - -// // Reset Password -// [EAuthenticationErrorCodes.INVALID_PASSWORD_TOKEN]: { -// title: `Invalid password token`, -// message: () => `Invalid password token. Please try again.`, -// }, -// [EAuthenticationErrorCodes.EXPIRED_PASSWORD_TOKEN]: { -// title: `Expired password token`, -// message: () => `Expired password token. Please try again.`, -// }, - -// // Change password - -// [EAuthenticationErrorCodes.MISSING_PASSWORD]: { -// title: `Password required`, -// message: () => `Password required. Please try again.`, -// }, -// [EAuthenticationErrorCodes.INCORRECT_OLD_PASSWORD]: { -// title: `Incorrect old password`, -// message: () => `Incorrect old password. Please try again.`, -// }, -// [EAuthenticationErrorCodes.INVALID_NEW_PASSWORD]: { -// title: `Invalid new password`, -// message: () => `Invalid new password. Please try again.`, -// }, - -// // set password -// [EAuthenticationErrorCodes.PASSWORD_ALREADY_SET]: { -// title: `Password already set`, -// message: () => `Password already set. Please try again.`, -// }, - -// // admin -// [EAuthenticationErrorCodes.ADMIN_ALREADY_EXIST]: { -// title: `Admin already exists`, -// message: () => `Admin already exists. Please try again.`, -// }, -// [EAuthenticationErrorCodes.REQUIRED_ADMIN_EMAIL_PASSWORD_FIRST_NAME]: { -// title: `Email, password and first name required`, -// message: () => `Email, password and first name required. Please try again.`, -// }, -// [EAuthenticationErrorCodes.INVALID_ADMIN_EMAIL]: { -// title: `Invalid admin email`, -// message: () => `Invalid admin email. Please try again.`, -// }, -// [EAuthenticationErrorCodes.INVALID_ADMIN_PASSWORD]: { -// title: `Invalid admin password`, -// message: () => `Invalid admin password. Please try again.`, -// }, -// [EAuthenticationErrorCodes.REQUIRED_ADMIN_EMAIL_PASSWORD]: { -// title: `Email and password required`, -// message: () => `Email and password required. Please try again.`, -// }, -// [EAuthenticationErrorCodes.ADMIN_AUTHENTICATION_FAILED]: { -// title: `Authentication failed`, -// message: () => `Authentication failed. Please try again.`, -// }, -// [EAuthenticationErrorCodes.ADMIN_USER_ALREADY_EXIST]: { -// title: `Admin user already exists`, -// message: () => ( -//
-// Admin user already exists.  -// -// Sign In -// -//  now. -//
-// ), -// }, -// [EAuthenticationErrorCodes.ADMIN_USER_DOES_NOT_EXIST]: { -// title: `Admin user does not exist`, -// message: () => ( -//
-// Admin user does not exist.  -// -// Sign In -// -//  now. -//
-// ), -// }, -// }; - -// export const authErrorHandler = ( -// errorCode: EAuthenticationErrorCodes, -// email?: string | undefined -// ): TAuthErrorInfo | undefined => { -// const bannerAlertErrorCodes = [ -// EAuthenticationErrorCodes.INSTANCE_NOT_CONFIGURED, -// EAuthenticationErrorCodes.INVALID_EMAIL, -// EAuthenticationErrorCodes.EMAIL_REQUIRED, -// EAuthenticationErrorCodes.SIGNUP_DISABLED, -// EAuthenticationErrorCodes.INVALID_PASSWORD, -// EAuthenticationErrorCodes.SMTP_NOT_CONFIGURED, -// EAuthenticationErrorCodes.USER_ALREADY_EXIST, -// EAuthenticationErrorCodes.AUTHENTICATION_FAILED_SIGN_UP, -// EAuthenticationErrorCodes.REQUIRED_EMAIL_PASSWORD_SIGN_UP, -// EAuthenticationErrorCodes.INVALID_EMAIL_SIGN_UP, -// EAuthenticationErrorCodes.INVALID_EMAIL_MAGIC_SIGN_UP, -// EAuthenticationErrorCodes.MAGIC_SIGN_UP_EMAIL_CODE_REQUIRED, -// EAuthenticationErrorCodes.USER_DOES_NOT_EXIST, -// EAuthenticationErrorCodes.AUTHENTICATION_FAILED_SIGN_IN, -// EAuthenticationErrorCodes.REQUIRED_EMAIL_PASSWORD_SIGN_IN, -// EAuthenticationErrorCodes.INVALID_EMAIL_SIGN_IN, -// EAuthenticationErrorCodes.INVALID_EMAIL_MAGIC_SIGN_IN, -// EAuthenticationErrorCodes.MAGIC_SIGN_IN_EMAIL_CODE_REQUIRED, -// // EAuthenticationErrorCodes.INVALID_MAGIC_CODE, -// // EAuthenticationErrorCodes.EXPIRED_MAGIC_CODE, -// // EAuthenticationErrorCodes.EMAIL_CODE_ATTEMPT_EXHAUSTED, -// EAuthenticationErrorCodes.GOOGLE_NOT_CONFIGURED, -// EAuthenticationErrorCodes.GITHUB_NOT_CONFIGURED, -// EAuthenticationErrorCodes.GOOGLE_OAUTH_PROVIDER_ERROR, -// EAuthenticationErrorCodes.GITHUB_OAUTH_PROVIDER_ERROR, -// EAuthenticationErrorCodes.INVALID_PASSWORD_TOKEN, -// EAuthenticationErrorCodes.EXPIRED_PASSWORD_TOKEN, -// EAuthenticationErrorCodes.INCORRECT_OLD_PASSWORD, -// EAuthenticationErrorCodes.INVALID_NEW_PASSWORD, -// EAuthenticationErrorCodes.PASSWORD_ALREADY_SET, -// EAuthenticationErrorCodes.ADMIN_ALREADY_EXIST, -// EAuthenticationErrorCodes.REQUIRED_ADMIN_EMAIL_PASSWORD_FIRST_NAME, -// EAuthenticationErrorCodes.INVALID_ADMIN_EMAIL, -// EAuthenticationErrorCodes.INVALID_ADMIN_PASSWORD, -// EAuthenticationErrorCodes.REQUIRED_ADMIN_EMAIL_PASSWORD, -// EAuthenticationErrorCodes.ADMIN_AUTHENTICATION_FAILED, -// EAuthenticationErrorCodes.ADMIN_USER_ALREADY_EXIST, -// EAuthenticationErrorCodes.ADMIN_USER_DOES_NOT_EXIST, -// ]; - -// if (bannerAlertErrorCodes.includes(errorCode)) -// return { -// type: EErrorAlertType.BANNER_ALERT, -// code: errorCode, -// title: errorCodeMessages[errorCode]?.title || "Error", -// message: errorCodeMessages[errorCode]?.message(email) || "Something went wrong. Please try again.", -// }; - -// return undefined; -// }; diff --git a/packages/constants/src/index.ts b/packages/constants/src/index.ts deleted file mode 100644 index 97ccf7649..000000000 --- a/packages/constants/src/index.ts +++ /dev/null @@ -1 +0,0 @@ -export * from "./auth"; diff --git a/packages/editor/core/src/ui/mentions/mention-node-view.tsx b/packages/editor/core/src/ui/mentions/mention-node-view.tsx index 0a1f1b5e0..939528785 100644 --- a/packages/editor/core/src/ui/mentions/mention-node-view.tsx +++ b/packages/editor/core/src/ui/mentions/mention-node-view.tsx @@ -2,12 +2,13 @@ // @ts-nocheck import { NodeViewWrapper } from "@tiptap/react"; import { cn } from "src/lib/utils"; -import { useRouter } from "next/router"; +import { useRouter } from "next/navigation"; import { IMentionHighlight } from "src/types/mention-suggestion"; import { useEffect, useState } from "react"; // eslint-disable-next-line import/no-anonymous-default-export export const MentionNodeView = (props) => { + // TODO: move it to web app const router = useRouter(); const [highlightsState, setHighlightsState] = useState(); diff --git a/space/package.json b/space/package.json index 0932d7abf..9ab1e423b 100644 --- a/space/package.json +++ b/space/package.json @@ -17,7 +17,6 @@ "@emotion/styled": "^11.11.0", "@headlessui/react": "^1.7.13", "@mui/material": "^5.14.1", - "@plane/constants": "*", "@plane/document-editor": "*", "@plane/lite-text-editor": "*", "@plane/rich-text-editor": "*", diff --git a/web/app/onboarding/page.tsx b/web/app/onboarding/page.tsx index b36628ff2..88c2df438 100644 --- a/web/app/onboarding/page.tsx +++ b/web/app/onboarding/page.tsx @@ -5,7 +5,6 @@ import { observer } from "mobx-react"; import { useRouter } from "next/navigation"; import useSWR from "swr"; // types -import { EPageTypes } from "@plane/constants"; import { TOnboardingSteps, TUserProfile } from "@plane/types"; // components import { LogoSpinner } from "@/components/common"; @@ -13,6 +12,8 @@ import { InviteMembers, CreateOrJoinWorkspaces, ProfileSetup } from "@/component // constants import { USER_ONBOARDING_COMPLETED } from "@/constants/event-tracker"; import { USER_WORKSPACES_LIST } from "@/constants/fetch-keys"; +// helpers +import { EPageTypes } from "@/helpers/authentication.helper"; // hooks import { useUser, useWorkspace, useUserProfile, useEventTracker } from "@/hooks/store"; // wrappers diff --git a/web/app/provider.tsx b/web/app/provider.tsx index e2e91bf51..0cecd1ab7 100644 --- a/web/app/provider.tsx +++ b/web/app/provider.tsx @@ -29,7 +29,7 @@ export const AppProvider: FC = (props) => { const { resolvedTheme } = useTheme(); return ( <> - + diff --git a/web/components/cycles/board/cycles-board-card.tsx b/web/components/cycles/board/cycles-board-card.tsx index 25c4efd33..c16f4826e 100644 --- a/web/components/cycles/board/cycles-board-card.tsx +++ b/web/components/cycles/board/cycles-board-card.tsx @@ -142,7 +142,7 @@ export const CyclesBoardCard: FC = observer((props) => { if (searchParams.has("peekCycle")) { router.push(`${pathname}?${query}`); } else { - router.push(`${pathname}?${query}&peekCycle=${cycleId}`); + router.push(`${pathname}?${query && `${query}&`}peekCycle=${cycleId}`); } }; diff --git a/web/components/cycles/list/cycles-list-item.tsx b/web/components/cycles/list/cycles-list-item.tsx index ab9becbfa..4adb644e2 100644 --- a/web/components/cycles/list/cycles-list-item.tsx +++ b/web/components/cycles/list/cycles-list-item.tsx @@ -72,7 +72,7 @@ export const CyclesListItem: FC = observer((props) => { if (searchParams.has("peekCycle")) { router.push(`${pathname}?${query}`); } else { - router.push(`${pathname}?${query}&peekCycle=${cycleId}`); + router.push(`${pathname}?${query && `${query}&`}peekCycle=${cycleId}`); } }; diff --git a/web/components/modules/module-card-item.tsx b/web/components/modules/module-card-item.tsx index 0ad8675ef..c19629242 100644 --- a/web/components/modules/module-card-item.tsx +++ b/web/components/modules/module-card-item.tsx @@ -115,7 +115,7 @@ export const ModuleCardItem: React.FC = observer((props) => { if (searchParams.has("peekModule")) { router.push(`${pathname}?${query}`); } else { - router.push(`${pathname}?${query}&peekModule=${moduleId}`); + router.push(`${pathname}?${query && `${query}&`}peekModule=${moduleId}`); } }; diff --git a/web/components/modules/module-list-item.tsx b/web/components/modules/module-list-item.tsx index 475ba5fe7..cf756795e 100644 --- a/web/components/modules/module-list-item.tsx +++ b/web/components/modules/module-list-item.tsx @@ -70,7 +70,7 @@ export const ModuleListItem: React.FC = observer((props) => { if (searchParams.has("peekModule")) { router.push(`${pathname}?${query}`); } else { - router.push(`${pathname}?${query}&peekModule=${moduleId}`); + router.push(`${pathname}?${query && `${query}&`}peekModule=${moduleId}`); } }; diff --git a/web/package.json b/web/package.json index 8c0f88ade..377fa80b8 100644 --- a/web/package.json +++ b/web/package.json @@ -24,7 +24,6 @@ "@nivo/line": "0.80.0", "@nivo/pie": "0.80.0", "@nivo/scatterplot": "0.80.0", - "@plane/constants": "*", "@plane/document-editor": "*", "@plane/lite-text-editor": "*", "@plane/rich-text-editor": "*", diff --git a/yarn.lock b/yarn.lock index e579a4b66..0c2f8d2ec 100644 --- a/yarn.lock +++ b/yarn.lock @@ -4533,7 +4533,7 @@ dependencies: "@types/react" "*" -"@types/react@*", "@types/react@^16.8.0 || ^17.0.0 || ^18.0.0", "@types/react@^18.2.42", "@types/react@^18.2.48": +"@types/react@*", "@types/react@18.2.48", "@types/react@^16.8.0 || ^17.0.0 || ^18.0.0", "@types/react@^18.2.42", "@types/react@^18.2.48": version "18.2.48" resolved "https://registry.yarnpkg.com/@types/react/-/react-18.2.48.tgz#11df5664642d0bd879c1f58bc1d37205b064e8f1" integrity sha512-qboRCl6Ie70DQQG9hhNREz81jqC1cs9EVNcjQ1AU+jH6NFfSAhVVbrrY/+nSF+Bsk4AOwm9Qa61InvMCyV+H3w==