import Protocol from "@/app/providers/ProtocolProvider/protocol/protocol"; import { createContext, useEffect, useMemo, useState } from "react"; import { usePublicKey } from "../AccountProvider/usePublicKey"; import { usePrivateKeyHash } from "../AccountProvider/usePrivateKeyHash"; import { useLogger } from "@/app/hooks/useLogger"; import { useMemory } from "../MemoryProvider/useMemory"; import { useDeviceId } from "../DeviceProvider/useDeviceId"; import { useNavigate } from "react-router-dom"; export enum ProtocolState { CONNECTED, HANDSHAKE_EXCHANGE, DISCONNECTED, RECONNECTING, DEVICE_VERIFICATION_REQUIRED } export const ProtocolContext = createContext<[Protocol|null, ProtocolState]>([null, ProtocolState.DISCONNECTED]); interface ProtocolProviderProps { children: React.ReactNode; serverAddress : string; } export function ProtocolProvider(props : ProtocolProviderProps) { const publicKey = usePublicKey(); const privateKey = usePrivateKeyHash(); const protocol = useMemo(() => { return new Protocol(props.serverAddress) }, [props.serverAddress, publicKey, privateKey]); const log = useLogger('ProtocolProvider'); const [connect, setConnect] = useState(ProtocolState.DISCONNECTED); const [_, setOnlineSubscribes] = useMemory("online_subscribes", [], true); const deviceId = useDeviceId(); const navigate = useNavigate(); useEffect(() => { if(publicKey.trim() == "" || privateKey.trim() == "" || deviceId == "") { return; } const device = { deviceId: deviceId, deviceName: window.deviceName || "Unknown Device" } protocol.startHandshakeExchange(publicKey, privateKey, device); protocol.on('connect', () => { protocol.startHandshakeExchange(publicKey, privateKey, device); /** * Сбрасываем подписки на онлайн статусы пользователей * так как при переподключении они слетают */ setOnlineSubscribes([]); }); protocol.on('reconnect', () => { log("Connection lost, reconnecting and starting handshake exchange"); setConnect(ProtocolState.RECONNECTING); }); protocol.on('handshake_start', () => { log("Handshake exchange started"); setConnect(ProtocolState.HANDSHAKE_EXCHANGE); }); protocol.on('handshake_complete', () => { log("Handshake exchange complete"); setConnect(ProtocolState.CONNECTED); }); protocol.on('handshake_need_device_verification', () => { log("Handshake exchange needs device verification"); setConnect(ProtocolState.DEVICE_VERIFICATION_REQUIRED); navigate('/deviceconfirm'); }); }, [publicKey, privateKey, deviceId]); return ( {props.children} ); }