From 8fdc1e3684a0a2bb713e4c12bb7fc32febf1d49a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C5=A0imon=20Brandner?= Date: Tue, 8 Aug 2023 13:46:51 +0200 Subject: [PATCH] Store shared keys in local storage MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: Šimon Brandner --- src/e2ee/sharedKeyManagement.ts | 20 ++++++++++++ src/room/GroupCallView.tsx | 37 +++++++++++++++++---- src/room/LobbyView.tsx | 57 ++------------------------------- src/settings/useSetting.ts | 2 +- 4 files changed, 54 insertions(+), 62 deletions(-) create mode 100644 src/e2ee/sharedKeyManagement.ts diff --git a/src/e2ee/sharedKeyManagement.ts b/src/e2ee/sharedKeyManagement.ts new file mode 100644 index 00000000..0a819066 --- /dev/null +++ b/src/e2ee/sharedKeyManagement.ts @@ -0,0 +1,20 @@ +/* +Copyright 2023 New Vector Ltd + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +import { useSetting } from "../settings/useSetting"; + +export const useRoomSharedKey = (roomId: string, initialValue?: string) => + useSetting(`room-shared-key-${roomId}`, initialValue); diff --git a/src/room/GroupCallView.tsx b/src/room/GroupCallView.tsx index d8e2fd6b..45bcac3b 100644 --- a/src/room/GroupCallView.tsx +++ b/src/room/GroupCallView.tsx @@ -32,13 +32,14 @@ import { CallEndedView } from "./CallEndedView"; import { useSentryGroupCallHandler } from "./useSentryGroupCallHandler"; import { PosthogAnalytics } from "../analytics/PosthogAnalytics"; import { useProfile } from "../profile/useProfile"; -import { E2EEConfig } from "../livekit/useLiveKit"; import { findDeviceByName } from "../media-utils"; import { OpenIDLoader } from "../livekit/OpenIDLoader"; import { ActiveCall } from "./InCallView"; import { Config } from "../config/Config"; import { MuteStates, useMuteStates } from "./MuteStates"; import { useMediaDevices, MediaDevices } from "../livekit/MediaDevicesContext"; +import { useRoomSharedKey } from "../e2ee/sharedKeyManagement"; +import { useUrlParams } from "../UrlParams"; declare global { interface Window { @@ -73,6 +74,8 @@ export function GroupCallView({ otelGroupCallMembership, } = useGroupCall(groupCall, client); + const { password } = useUrlParams(); + const { t } = useTranslation(); useEffect(() => { @@ -241,8 +244,31 @@ export function GroupCallView({ } }, [groupCall, state, leave]); - const [e2eeConfig, setE2EEConfig] = useState( - undefined + const [e2eeSharedKey, setE2EESharedKey] = useRoomSharedKey( + groupCall.room.roomId, + password ?? undefined + ); + + useEffect(() => { + if (!password || password === e2eeSharedKey) return; + + setE2EESharedKey(password); + }, [password, e2eeSharedKey, setE2EESharedKey]); + + useEffect(() => { + const originalHash = location.hash; + let hash = originalHash === "" ? "#" : originalHash; + hash = hash.split("?password=")[0]; + hash += `?password=${e2eeSharedKey ?? ""}`; + + if (originalHash !== hash) { + location.replace(hash); + } + }, [e2eeSharedKey]); + + const e2eeConfig = useMemo( + () => (e2eeSharedKey ? { sharedKey: e2eeSharedKey } : undefined), + [e2eeSharedKey] ); const onReconnect = useCallback(() => { @@ -319,10 +345,7 @@ export function GroupCallView({ { - setE2EEConfig(e2eeConfig); - enter(); - }} + onEnter={() => enter()} isEmbedded={isEmbedded} hideHeader={hideHeader} /> diff --git a/src/room/LobbyView.tsx b/src/room/LobbyView.tsx index 5880c362..d77f4d1d 100644 --- a/src/room/LobbyView.tsx +++ b/src/room/LobbyView.tsx @@ -14,14 +14,7 @@ See the License for the specific language governing permissions and limitations under the License. */ -import { - useRef, - useEffect, - useState, - useCallback, - ChangeEvent, - FC, -} from "react"; +import { useRef, useEffect, FC } from "react"; import { Trans, useTranslation } from "react-i18next"; import styles from "./LobbyView.module.css"; @@ -32,16 +25,12 @@ import { UserMenuContainer } from "../UserMenuContainer"; import { Body, Link } from "../typography/Typography"; import { useLocationNavigation } from "../useLocationNavigation"; import { MatrixInfo, VideoPreview } from "./VideoPreview"; -import { E2EEConfig } from "../livekit/useLiveKit"; -import { InputField } from "../input/Input"; -import { useEnableE2EE } from "../settings/useSetting"; import { MuteStates } from "./MuteStates"; -import { useUrlParams } from "../UrlParams"; interface Props { matrixInfo: MatrixInfo; muteStates: MuteStates; - onEnter: (e2eeConfig?: E2EEConfig) => void; + onEnter: () => void; isEmbedded: boolean; hideHeader: boolean; } @@ -53,13 +42,9 @@ export const LobbyView: FC = ({ isEmbedded, hideHeader, }) => { - const { password } = useUrlParams(); - const { t } = useTranslation(); useLocationNavigation(); - const [enableE2EE] = useEnableE2EE(); - const joinCallButtonRef = useRef(null); useEffect(() => { if (joinCallButtonRef.current) { @@ -67,29 +52,6 @@ export const LobbyView: FC = ({ } }, [joinCallButtonRef]); - const [e2eeSharedKey, setE2EESharedKey] = useState( - password ?? undefined - ); - - const onE2EESharedKeyChanged = useCallback( - (event: ChangeEvent) => { - const value = event.target.value; - setE2EESharedKey(value === "" ? undefined : value); - }, - [setE2EESharedKey] - ); - - useEffect(() => { - const originalHash = location.hash; - let hash = originalHash === "" ? "#" : originalHash; - hash = hash.split("?password=")[0]; - hash += `?password=${e2eeSharedKey ?? ""}`; - - if (originalHash !== hash) { - location.replace(hash); - } - }, [e2eeSharedKey]); - return (
{!hideHeader && ( @@ -105,25 +67,12 @@ export const LobbyView: FC = ({
- {enableE2EE && ( - - )}