diff --git a/src/components/appointment/Appointments.tsx b/src/components/appointment/Appointments.tsx index 0ee4f9f1e..ba8223a73 100644 --- a/src/components/appointment/Appointments.tsx +++ b/src/components/appointment/Appointments.tsx @@ -4,6 +4,7 @@ import { Overlay, OVERLAY_FUNCTIONS, OverlayItem } from '../overlay/Overlay'; import { Button, BUTTON_TYPES, ButtonItem } from '../button/Button'; import './appointments.styles.scss'; import { + AgencySpecificContext, NOTIFICATION_TYPE_SUCCESS, NotificationsContext } from '../../globalState'; @@ -31,6 +32,7 @@ import { ListInfo } from '../listInfo/ListInfo'; export const Appointments = () => { const { t: translate } = useTranslation(); const legalLinks = useContext(LegalLinksContext); + const { specificAgency } = useContext(AgencySpecificContext); const { addNotification } = useContext(NotificationsContext); const [loading, setLoading] = useState(true); @@ -310,7 +312,11 @@ export const Appointments = () => {
{legalLinks.map((legalLink, index) => ( - + {index > 0 && ( { /> )} diff --git a/src/components/formAccordion/FormAccordion.tsx b/src/components/formAccordion/FormAccordion.tsx index 510181cda..b9e35bd34 100644 --- a/src/components/formAccordion/FormAccordion.tsx +++ b/src/components/formAccordion/FormAccordion.tsx @@ -13,7 +13,7 @@ import { RequiredComponentsInterface, RegistrationNotesInterface, useTenant, - LegalLinkInterface + AgencySpecificContext } from '../../globalState'; import { FormAccordionItem } from '../formAccordion/FormAccordionItem'; import { RegistrationUsername } from '../registration/RegistrationUsername'; @@ -35,6 +35,7 @@ import { ProposedAgencies } from '../../containers/registration/components/Propo import { useConsultantAgenciesAndConsultingTypes } from '../../containers/registration/hooks/useConsultantAgenciesAndConsultingTypes'; import { FormAccordionData } from '../registration/RegistrationForm'; import { UrlParamsContext } from '../../globalState/provider/UrlParamsProvider'; +import { TProvidedLegalLink } from '../../globalState/provider/LegalLinksProvider'; interface FormAccordionProps { formAccordionData: FormAccordionData; @@ -43,7 +44,7 @@ interface FormAccordionProps { onValidation: Dispatch>; additionalStepsData?: RequiredComponentsInterface; registrationNotes?: RegistrationNotesInterface; - legalLinks: Array; + legalLinks: TProvidedLegalLink[]; handleSubmitButtonClick: Function; isSubmitButtonDisabled: boolean; setIsDataProtectionSelected: Dispatch>; @@ -67,6 +68,9 @@ export const FormAccordion = ({ const tenantData = useTenant(); const { consultingType, consultant } = useContext(UrlParamsContext); + const { setSpecificAgency, specificAgency } = useContext( + AgencySpecificContext + ); const { consultingTypes } = useConsultantAgenciesAndConsultingTypes(); const [activeItem, setActiveItem] = useState(1); @@ -108,7 +112,12 @@ export const FormAccordion = ({ ); formAccordionData.agency?.tenantId && setIsDataProtectionSelected(false); - }, [formAccordionData.agency, setIsDataProtectionSelected]); + setSpecificAgency(formAccordionData.agency); + }, [ + formAccordionData.agency, + setSpecificAgency, + setIsDataProtectionSelected + ]); useEffect(() => { onValidation( @@ -205,9 +214,9 @@ export const FormAccordion = ({ 'registration.dataProtection.label.and' ) : '') + - `` + `` ) .join(''), translate('registration.dataProtection.label.suffix') diff --git a/src/components/profile/Profile.tsx b/src/components/profile/Profile.tsx index c27896454..87e271302 100644 --- a/src/components/profile/Profile.tsx +++ b/src/components/profile/Profile.tsx @@ -2,6 +2,7 @@ import * as React from 'react'; import { useState, useRef, useContext, useEffect, Fragment } from 'react'; import { logout } from '../logout/logout'; import { + AgencySpecificContext, AUTHORITIES, ConsultingTypesContext, hasUserAuthority, @@ -60,6 +61,7 @@ export const Profile = () => { const legalLinks = useContext(LegalLinksContext); const { userData } = useContext(UserDataContext); + const { specificAgency } = useContext(AgencySpecificContext); const { consultingTypes } = useContext(ConsultingTypesContext); const [mobileMenu, setMobileMenu] = useState< @@ -467,7 +469,9 @@ export const Profile = () => {
{legalLinks.map((legalLink, index) => ( - + {index > 0 && ( { /> )} diff --git a/src/components/sessionMenu/SessionMenu.tsx b/src/components/sessionMenu/SessionMenu.tsx index c1e6d37c2..2e57e131c 100644 --- a/src/components/sessionMenu/SessionMenu.tsx +++ b/src/components/sessionMenu/SessionMenu.tsx @@ -596,8 +596,12 @@ export const SessionMenu = (props: SessionMenuProps) => {
{legalLinks.map((legalLink) => ( diff --git a/src/components/stageLayout/StageLayout.tsx b/src/components/stageLayout/StageLayout.tsx index 3748c80c8..5928af323 100644 --- a/src/components/stageLayout/StageLayout.tsx +++ b/src/components/stageLayout/StageLayout.tsx @@ -4,7 +4,7 @@ import { Button } from '../button/Button'; import { Text } from '../text/Text'; import './StageLayout.styles.scss'; import clsx from 'clsx'; -import { LocaleContext } from '../../globalState'; +import { AgencySpecificContext, LocaleContext } from '../../globalState'; import { useTranslation } from 'react-i18next'; import { LocaleSwitch } from '../localeSwitch/LocaleSwitch'; import { LegalLinksContext } from '../../globalState/provider/LegalLinksProvider'; @@ -33,6 +33,7 @@ export const StageLayout = ({ const { t: translate } = useTranslation(); const legalLinks = useContext(LegalLinksContext); const { selectableLocales } = useContext(LocaleContext); + const { specificAgency } = useContext(AgencySpecificContext); const settings = useAppConfig(); const { fromL } = useResponsive(); @@ -102,7 +103,11 @@ export const StageLayout = ({ {showLegalLinks && (
{legalLinks.map((legalLink, index) => ( - + {index > 0 && ( - window.open(legalLink.url, '_blank') + window.open( + legalLink.getUrl({ + aid: specificAgency?.id + }), + '_blank' + ) } > ${translate( - legalLink.label + `${translate( + legalLink.getUrl({ aid: null }) )}` ) .join('') diff --git a/src/components/waitingRoom/WaitingRoom.tsx b/src/components/waitingRoom/WaitingRoom.tsx index 78c03fe50..1d9005896 100644 --- a/src/components/waitingRoom/WaitingRoom.tsx +++ b/src/components/waitingRoom/WaitingRoom.tsx @@ -301,9 +301,9 @@ export const WaitingRoom = (props: WaitingRoomProps) => { 'registration.dataProtection.label.and' ) : '') + - `${translate(legalLink.label)}` + `${translate(legalLink.label)}` ) .join(''), translate( diff --git a/src/globalState/index.ts b/src/globalState/index.ts index b127a6723..6893fba9e 100644 --- a/src/globalState/index.ts +++ b/src/globalState/index.ts @@ -9,6 +9,7 @@ export * from './interfaces/LegalLinkInterface'; export * from './interfaces/ServerAppConfigInterface'; export * from './interfaces/AppConfig'; +export * from './provider/AgencySpecificProvider'; export * from './provider/AnonymousConversationFinishedProvider'; export * from './provider/AnonymousEnquiryAcceptedProvider'; export * from './provider/AnonymousConversationStartedProvider'; diff --git a/src/globalState/interfaces/TenantDataInterface.ts b/src/globalState/interfaces/TenantDataInterface.ts index a28016c5b..d2b993e52 100644 --- a/src/globalState/interfaces/TenantDataInterface.ts +++ b/src/globalState/interfaces/TenantDataInterface.ts @@ -14,6 +14,7 @@ export interface TenantDataInterface { claim: string; dataPrivacyConfirmation: string; termsAndConditionsConfirmation: string; + renderedPrivacy: string; }; settings?: TenantDataSettingsInterface; } diff --git a/src/globalState/interfaces/UserDataInterface.ts b/src/globalState/interfaces/UserDataInterface.ts index 93fea8c14..72e5af58f 100644 --- a/src/globalState/interfaces/UserDataInterface.ts +++ b/src/globalState/interfaces/UserDataInterface.ts @@ -51,6 +51,7 @@ export interface AgencyDataInterface { url?: string; external?: boolean; tenantId?: number; + agencySpecificPrivacy?: string; } export interface ConsultingTypeDataInterface { diff --git a/src/globalState/provider/AgencySpecificProvider.tsx b/src/globalState/provider/AgencySpecificProvider.tsx new file mode 100644 index 000000000..10d20e964 --- /dev/null +++ b/src/globalState/provider/AgencySpecificProvider.tsx @@ -0,0 +1,39 @@ +import * as React from 'react'; +import { + createContext, + useState, + useContext, + Dispatch, + SetStateAction, + useEffect +} from 'react'; +import { UserDataContext } from './UserDataProvider'; +import { AgencyDataInterface } from '../interfaces/UserDataInterface'; +import useUrlParamsLoader from '../../utils/useUrlParamsLoader'; + +export const AgencySpecificContext = createContext<{ + specificAgency: AgencyDataInterface; + setSpecificAgency: Dispatch>; +}>(null); + +export function AgencySpecificProvider(props) { + const { userData } = useContext(UserDataContext); + const { agency: urlAgency } = useUrlParamsLoader(); + const [agency, setAgency] = useState(); + + useEffect(() => { + if (userData?.agencies?.length > 0) { + setAgency(userData.agencies[0]); + } else if (urlAgency) { + setAgency(urlAgency); + } + }, [urlAgency, userData]); + + return ( + + {props.children} + + ); +} diff --git a/src/globalState/provider/LegalLinksProvider.tsx b/src/globalState/provider/LegalLinksProvider.tsx index ddddf111a..2352891cc 100644 --- a/src/globalState/provider/LegalLinksProvider.tsx +++ b/src/globalState/provider/LegalLinksProvider.tsx @@ -1,9 +1,15 @@ -import { createContext, ReactNode } from 'react'; +import { createContext, ReactNode, useCallback, useMemo } from 'react'; import { LegalLinkInterface } from '../interfaces/LegalLinkInterface'; import * as React from 'react'; import { useAppConfig } from '../../hooks/useAppConfig'; -export const LegalLinksContext = createContext([]); +export type TProvidedLegalLink = Omit & { + getUrl: (params?: { + [key: string]: string | number | null | undefined; + }) => string; +}; + +export const LegalLinksContext = createContext([]); type TLegalLinksProvider = { legalLinks?: LegalLinkInterface[]; @@ -11,15 +17,46 @@ type TLegalLinksProvider = { }; export function LegalLinksProvider({ - legalLinks, + legalLinks: externalLegalLinks, children }: TLegalLinksProvider) { const settings = useAppConfig(); + const getUrl = useCallback( + ( + url: string, + params: { [key: string]: string | number | null | undefined } + ) => { + const urlObject = Object.entries(params || {}) + .filter(([, value]) => !!value) + .map(([key, value]) => [ + key, + typeof value === 'number' ? value.toString() : value + ]) + .reduce((acc, [key, value]) => { + acc.searchParams.append(key, value); + return acc; + }, new URL(url)); + return urlObject.toString(); + }, + [] + ); + + const legalLinks = useMemo( + () => + (externalLegalLinks ?? settings.legalLinks ?? []).map( + ({ url, ...legalLink }) => ({ + ...legalLink, + getUrl: (params: { + [key: string]: string | number | null | undefined; + }) => getUrl(url, params) + }) + ), + [externalLegalLinks, settings.legalLinks, getUrl] + ); + return ( - + {children} ); diff --git a/src/globalState/state.tsx b/src/globalState/state.tsx index da9c28625..91aa2a867 100644 --- a/src/globalState/state.tsx +++ b/src/globalState/state.tsx @@ -11,7 +11,8 @@ import { RocketChatGlobalSettingsProvider, AnonymousConversationStartedProvider, SessionsDataProvider, - ModalProvider + ModalProvider, + AgencySpecificProvider } from '.'; function ProviderComposer({ contexts, children }) { @@ -35,6 +36,7 @@ function ContextProvider({ children }) { , , , + , , , , diff --git a/src/types/rc/User.ts b/src/types/rc/User.ts index f18f87f79..068061d78 100644 --- a/src/types/rc/User.ts +++ b/src/types/rc/User.ts @@ -37,10 +37,6 @@ interface ILoginToken { twoFactorAuthorizedHash?: string; } -interface IMeteorLoginToken extends ILoginToken { - when: Date; -} - interface IPersonalAccessToken extends ILoginToken { type: 'personalAccessToken'; createdAt: Date;