Fix: add a adapters manager to lock loading while data sync
This commit is contained in:
parent
5f17c76b6a
commit
210eb0911c
@ -10,11 +10,8 @@ import LoadingScreenHOC from '/imports/ui/components/common/loading-screen/loadi
|
||||
import IntlLoaderContainer from '/imports/startup/client/intlLoader';
|
||||
import LocatedErrorBoundary from '/imports/ui/components/common/error-boundary/located-error-boundary/component';
|
||||
import StartupDataFetch from '/imports/ui/components/connection-manager/startup-data-fetch/component';
|
||||
import UserGrapQlMiniMongoAdapter from '/imports/ui/components/components-data/userGrapQlMiniMongoAdapter/component';
|
||||
import VoiceUserGrapQlMiniMongoAdapter from '/imports/ui/components/components-data/voiceUserGraphQlMiniMongoAdapter/component';
|
||||
import MeetingGrapQlMiniMongoAdapter from '/imports/ui/components/components-data/meetingGrapQlMiniMongoAdapter/component';
|
||||
import ScreenShareGraphQlMiniMongoAdapterContainer from '/imports/ui/components/components-data/screenshareGraphQlMiniMongoAdapter/component';
|
||||
import VideoStreamAdapter from '/imports/ui/components/video-provider/video-provider-graphql/adapter';
|
||||
|
||||
import GraphqlToMiniMongoAdapterManager from '/imports/ui/components/components-data/graphqlToMiniMongoAdapterManager/component';
|
||||
|
||||
const Main: React.FC = () => {
|
||||
// Meteor.disconnect();
|
||||
@ -27,12 +24,9 @@ const Main: React.FC = () => {
|
||||
<LocatedErrorBoundary Fallback={ErrorScreen}>
|
||||
<ConnectionManager>
|
||||
<PresenceManager>
|
||||
<SettingsLoader />
|
||||
<UserGrapQlMiniMongoAdapter />
|
||||
<VoiceUserGrapQlMiniMongoAdapter />
|
||||
<MeetingGrapQlMiniMongoAdapter />
|
||||
<ScreenShareGraphQlMiniMongoAdapterContainer />
|
||||
<VideoStreamAdapter />
|
||||
<GraphqlToMiniMongoAdapterManager>
|
||||
<SettingsLoader />
|
||||
</GraphqlToMiniMongoAdapterManager>
|
||||
</PresenceManager>
|
||||
</ConnectionManager>
|
||||
</LocatedErrorBoundary>
|
||||
|
@ -0,0 +1,58 @@
|
||||
import React, {
|
||||
useCallback,
|
||||
useMemo,
|
||||
useRef,
|
||||
useState,
|
||||
} from 'react';
|
||||
|
||||
import UserGrapQlMiniMongoAdapter from '/imports/ui/components/components-data/userGrapQlMiniMongoAdapter/component';
|
||||
import VoiceUserGrapQlMiniMongoAdapter from '/imports/ui/components/components-data/voiceUserGraphQlMiniMongoAdapter/component';
|
||||
import MeetingGrapQlMiniMongoAdapter from '/imports/ui/components/components-data/meetingGrapQlMiniMongoAdapter/component';
|
||||
import ScreenShareGraphQlMiniMongoAdapterContainer from '/imports/ui/components/components-data/screenshareGraphQlMiniMongoAdapter/component';
|
||||
import VideoStreamAdapter from '/imports/ui/components/video-provider/video-provider-graphql/adapter';
|
||||
|
||||
interface GraphqlToMiniMongoAdapterManagerProps {
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
export interface AdapterProps extends GraphqlToMiniMongoAdapterManagerProps {
|
||||
onReady: (key:string) => void;
|
||||
}
|
||||
|
||||
const GraphqlToMiniMongoAdapterManager: React.FC<GraphqlToMiniMongoAdapterManagerProps> = ({ children }) => {
|
||||
const [adapterLoaded, setAdapterLoaded] = useState(false);
|
||||
const loadedComponents = useRef<{
|
||||
[key: string]: number;
|
||||
}>({});
|
||||
const adapterComponents = useRef([
|
||||
UserGrapQlMiniMongoAdapter,
|
||||
MeetingGrapQlMiniMongoAdapter,
|
||||
VideoStreamAdapter,
|
||||
VoiceUserGrapQlMiniMongoAdapter,
|
||||
]);
|
||||
|
||||
const onReady = useCallback((key: string) => {
|
||||
loadedComponents.current[key] = 1;
|
||||
if (Object.keys(loadedComponents.current).length >= adapterComponents.current.length) {
|
||||
setAdapterLoaded(true);
|
||||
}
|
||||
}, []);
|
||||
|
||||
const nestAdapters = useMemo(() => {
|
||||
return adapterComponents.current.reduce((acc, Component) => (
|
||||
<Component onReady={onReady}>
|
||||
{acc}
|
||||
</Component>
|
||||
), <span />);
|
||||
}, []);
|
||||
return (
|
||||
<>
|
||||
{/* screenshare loads conditionally so can't be used on lock loading */}
|
||||
<ScreenShareGraphQlMiniMongoAdapterContainer />
|
||||
{nestAdapters}
|
||||
{adapterLoaded ? children : null}
|
||||
</>
|
||||
);
|
||||
};
|
||||
|
||||
export default GraphqlToMiniMongoAdapterManager;
|
@ -1,10 +1,15 @@
|
||||
import React, { useEffect } from 'react';
|
||||
import React, { useEffect, useRef } from 'react';
|
||||
import { useCreateUseSubscription } from '/imports/ui/core/hooks/createUseSubscription';
|
||||
import MEETING_SUBSCRIPTION from '/imports/ui/core/graphql/queries/meetingSubscription';
|
||||
import { Meeting } from '/imports/ui/Types/meeting';
|
||||
import Meetings from '/imports/api/meetings';
|
||||
import { AdapterProps } from '../graphqlToMiniMongoAdapterManager/component';
|
||||
|
||||
const MeetingGrapQlMiniMongoAdapter: React.FC = () => {
|
||||
const MeetingGrapQlMiniMongoAdapter: React.FC<AdapterProps> = ({
|
||||
onReady,
|
||||
children,
|
||||
}) => {
|
||||
const ready = useRef(false);
|
||||
const meetingSubscription = useCreateUseSubscription<Meeting>(MEETING_SUBSCRIPTION, {}, true);
|
||||
const {
|
||||
data: meetingData,
|
||||
@ -12,12 +17,16 @@ const MeetingGrapQlMiniMongoAdapter: React.FC = () => {
|
||||
|
||||
useEffect(() => {
|
||||
if (meetingData) {
|
||||
if (!ready.current) {
|
||||
ready.current = true;
|
||||
onReady('MeetingGrapQlMiniMongoAdapter');
|
||||
}
|
||||
const meeting = JSON.parse(JSON.stringify(meetingData[0]));
|
||||
const { meetingId } = meeting;
|
||||
Meetings.upsert({ meetingId }, meeting);
|
||||
}
|
||||
}, [meetingData]);
|
||||
return null;
|
||||
return children;
|
||||
};
|
||||
|
||||
export default MeetingGrapQlMiniMongoAdapter;
|
||||
|
@ -1,15 +1,20 @@
|
||||
import { useSubscription } from '@apollo/client';
|
||||
import React, { useEffect, useState } from 'react';
|
||||
import React, { useEffect, useRef, useState } from 'react';
|
||||
import CURRENT_USER_SUBSCRIPTION from '/imports/ui/core/graphql/queries/currentUserSubscription';
|
||||
import { User } from '/imports/ui/Types/user';
|
||||
import Users from '/imports/api/users';
|
||||
import logger from '/imports/startup/client/logger';
|
||||
import { AdapterProps } from '../graphqlToMiniMongoAdapterManager/component';
|
||||
|
||||
interface UserCurrentResponse {
|
||||
user_current: Array<User>;
|
||||
}
|
||||
|
||||
const UserGrapQlMiniMongoAdapter: React.FC = () => {
|
||||
const UserGrapQlMiniMongoAdapter: React.FC<AdapterProps> = ({
|
||||
onReady,
|
||||
children,
|
||||
}) => {
|
||||
const ready = useRef(false);
|
||||
const {
|
||||
error,
|
||||
data,
|
||||
@ -24,6 +29,10 @@ const UserGrapQlMiniMongoAdapter: React.FC = () => {
|
||||
|
||||
useEffect(() => {
|
||||
if (data && data.user_current) {
|
||||
if (!ready.current) {
|
||||
ready.current = true;
|
||||
onReady('UserGrapQlMiniMongoAdapter');
|
||||
}
|
||||
const { userId } = data.user_current[0];
|
||||
Users.upsert({ userId }, data.user_current[0]);
|
||||
if (!userDataSetted) {
|
||||
@ -31,7 +40,7 @@ const UserGrapQlMiniMongoAdapter: React.FC = () => {
|
||||
}
|
||||
}
|
||||
}, [data]);
|
||||
return null;
|
||||
return children;
|
||||
};
|
||||
|
||||
export default UserGrapQlMiniMongoAdapter;
|
||||
|
@ -1,17 +1,21 @@
|
||||
import { useSubscription } from '@apollo/client';
|
||||
import React, { useEffect, useState } from 'react';
|
||||
import React, { useEffect, useRef, useState } from 'react';
|
||||
import VoiceUsers from '/imports/api/voice-users/';
|
||||
import logger from '/imports/startup/client/logger';
|
||||
import { UserVoiceStreamResponse, voiceUserStream } from './queries';
|
||||
import { AdapterProps } from '../graphqlToMiniMongoAdapterManager/component';
|
||||
|
||||
const VoiceUserGrapQlMiniMongoAdapter: React.FC = () => {
|
||||
const VoiceUserGrapQlMiniMongoAdapter: React.FC<AdapterProps> = ({
|
||||
onReady,
|
||||
children,
|
||||
}) => {
|
||||
const ready = useRef(false);
|
||||
const {
|
||||
loading,
|
||||
error,
|
||||
data,
|
||||
} = useSubscription<UserVoiceStreamResponse>(voiceUserStream);
|
||||
const [voiceUserDataSetted, setVoiceUserDataSetted] = useState(false);
|
||||
|
||||
useEffect(() => {
|
||||
if (error) {
|
||||
logger.error('Error in VoiceUserGrapQlMiniMongoAdapter', error);
|
||||
@ -30,12 +34,17 @@ const VoiceUserGrapQlMiniMongoAdapter: React.FC = () => {
|
||||
|
||||
useEffect(() => {
|
||||
if (loading) {
|
||||
// loading turns false only first audio join of the meeting, probably because it's a stream
|
||||
if (!ready.current) {
|
||||
ready.current = true;
|
||||
onReady('VoiceUserGrapQlMiniMongoAdapter');
|
||||
}
|
||||
if (!voiceUserDataSetted) {
|
||||
setVoiceUserDataSetted(true);
|
||||
}
|
||||
}
|
||||
}, [loading]);
|
||||
return null;
|
||||
return children;
|
||||
};
|
||||
|
||||
export default VoiceUserGrapQlMiniMongoAdapter;
|
||||
|
@ -1,14 +1,19 @@
|
||||
// @ts-nocheck
|
||||
/* eslint-disable */
|
||||
import { useEffect } from 'react';
|
||||
import { useEffect, useRef } from 'react';
|
||||
import { useSubscription } from '@apollo/client';
|
||||
import {
|
||||
VIDEO_STREAMS_SUBSCRIPTION,
|
||||
VideoStreamsResponse,
|
||||
} from './queries';
|
||||
import { setStreams } from './state';
|
||||
import { AdapterProps } from '../../components-data/graphqlToMiniMongoAdapterManager/component';
|
||||
|
||||
const VideoStreamAdapter: React.FC = () => {
|
||||
const VideoStreamAdapter: React.FC<AdapterProps> = ({
|
||||
onReady,
|
||||
children,
|
||||
}) => {
|
||||
const ready = useRef(false);
|
||||
const { data, loading, error } = useSubscription<VideoStreamsResponse>(VIDEO_STREAMS_SUBSCRIPTION);
|
||||
|
||||
useEffect(() => {
|
||||
@ -19,6 +24,8 @@ const VideoStreamAdapter: React.FC = () => {
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
|
||||
const streams = data.user_camera.map(({ streamId, user, voice }) => ({
|
||||
stream: streamId,
|
||||
deviceId: streamId.split('_')[2],
|
||||
@ -34,7 +41,14 @@ const VideoStreamAdapter: React.FC = () => {
|
||||
setStreams(streams);
|
||||
}, [data]);
|
||||
|
||||
return null;
|
||||
useEffect(()=>{
|
||||
if (!ready.current && !loading) {
|
||||
ready.current = true;
|
||||
onReady('VideoStreamAdapter');
|
||||
}
|
||||
}, [loading])
|
||||
|
||||
return children;
|
||||
};
|
||||
|
||||
export default VideoStreamAdapter;
|
||||
|
Loading…
Reference in New Issue
Block a user