Skip to content

Commit

Permalink
[4278] Always use onData callback for useSubscription
Browse files Browse the repository at this point in the history
Bug: #4278
Signed-off-by: Michaël Charfadi <[email protected]>
  • Loading branch information
mcharfadi authored and sbegaudeau committed Dec 16, 2024
1 parent 4a63ce3 commit 030ade4
Show file tree
Hide file tree
Showing 24 changed files with 404 additions and 341 deletions.
1 change: 1 addition & 0 deletions CHANGELOG.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -2160,6 +2160,7 @@ The `label` value is displayed before the widget to be consistent with other pro
- https://github.com/eclipse-sirius/sirius-components/issues/1341[#1341] [diagram] Expose source and target node variables during EdgeTool execution
- [core] The input and payloads manipulated by the `EditingContextEventProcessor` can now be logged using `
logging.level.org.eclipse.sirius.components.collaborative.editingcontext.EditingContextEventProcessor=trace`
- https://github.com/eclipse-sirius/sirius-web/issues/4278[#4278] Always use onData callback with useSubscription

=== New features

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,10 @@
* Contributors:
* Obeo - initial API and implementation
*******************************************************************************/
import { gql, useSubscription } from '@apollo/client';
import { ApolloError, gql, OnDataOptions, useSubscription } from '@apollo/client';
import { useMachine } from '@xstate/react';
import { useEffect } from 'react';
import { flushSync } from 'react-dom';
import { makeStyles } from 'tss-react/mui';
import { StateMachine } from 'xstate';
import { useComponent } from '../extension/useComponent';
Expand Down Expand Up @@ -97,35 +98,39 @@ export const Workbench = ({

const { data: representationFactories } = useData(representationFactoryExtensionPoint);

const { error } = useSubscription<GQLEditingContextEventSubscription>(editingContextEventSubscription, {
const onData = ({ data }: OnDataOptions<GQLEditingContextEventSubscription>) => {
flushSync(() => {
const handleDataEvent: HandleSubscriptionResultEvent = {
type: 'HANDLE_SUBSCRIPTION_RESULT',
result: data,
};
dispatch(handleDataEvent);
});
};

const onError = ({ message }: ApolloError) => {
const showToastEvent: ShowToastEvent = { type: 'SHOW_TOAST', message };
dispatch(showToastEvent);
};

const onComplete = () => {
const completeEvent: HandleCompleteEvent = { type: 'HANDLE_COMPLETE' };
dispatch(completeEvent);
};

useSubscription<GQLEditingContextEventSubscription>(editingContextEventSubscription, {
variables: {
input: {
id,
editingContextId,
},
},
fetchPolicy: 'no-cache',
onData: ({ data }) => {
const handleDataEvent: HandleSubscriptionResultEvent = {
type: 'HANDLE_SUBSCRIPTION_RESULT',
result: data,
};
dispatch(handleDataEvent);
},
onComplete: () => {
const completeEvent: HandleCompleteEvent = { type: 'HANDLE_COMPLETE' };
dispatch(completeEvent);
},
onData,
onComplete,
onError,
});

useEffect(() => {
if (error) {
const { message } = error;
const showToastEvent: ShowToastEvent = { type: 'SHOW_TOAST', message };
dispatch(showToastEvent);
}
}, [error, dispatch]);

useEffect(() => {
const updateSelectedRepresentation: UpdateSelectedRepresentationEvent = {
type: 'UPDATE_SELECTED_REPRESENTATION',
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
* Obeo - initial API and implementation
*******************************************************************************/

import { useSubscription } from '@apollo/client';
import { ApolloError, OnDataOptions, useSubscription } from '@apollo/client';
import {
RepresentationComponentProps,
UseSelectionValue,
Expand All @@ -20,8 +20,8 @@ import {
} from '@eclipse-sirius/sirius-components-core';
import Typography from '@mui/material/Typography';
import { Theme, useTheme } from '@mui/material/styles';
import { makeStyles } from 'tss-react/mui';
import { useEffect, useState } from 'react';
import { makeStyles } from 'tss-react/mui';
import { Deck } from '../Deck';
import { Card, CardMetadata, Lane } from '../Deck.types';
import {
Expand All @@ -42,6 +42,7 @@ import {
GQLLane,
} from './deckSubscription.types';

import { flushSync } from 'react-dom';
import { useDeckMutations } from './useDeckMutations';

const useDeckRepresentationStyles = makeStyles()(() => ({
Expand All @@ -68,18 +69,9 @@ export const DeckRepresentation = ({ editingContextId, representationId }: Repre
complete: false,
});

const { error } = useSubscription<GQLDeckEventSubscription>(deckEventSubscription, {
variables: {
input: {
id,
editingContextId,
deckId: representationId,
},
},
fetchPolicy: 'no-cache',

onData: ({ data }) => {
if (data?.data) {
const onData = ({ data }: OnDataOptions<GQLDeckEventSubscription>) => {
flushSync(() => {
if (data.data) {
const { deckEvent } = data.data;
if (isDeckRefreshedEventPayload(deckEvent)) {
setState((prevState) => {
Expand All @@ -89,23 +81,32 @@ export const DeckRepresentation = ({ editingContextId, representationId }: Repre
addMessages(deckEvent.messages);
}
}
});
};

const onError = ({ message }: ApolloError) => {
addErrorMessage(message);
};

const onComplete = () => setState((prevState) => ({ ...prevState, complete: true, deck: undefined }));

useSubscription<GQLDeckEventSubscription>(deckEventSubscription, {
variables: {
input: {
id,
editingContextId,
deckId: representationId,
},
},
onComplete: () => {
setState((prevState) => {
return { ...prevState, complete: true, deck: undefined };
});
},
fetchPolicy: 'no-cache',
onData,
onComplete,
onError,
});

const { deleteCard, editDeckCard, createCard, dropDeckCard, editDeckLane, dropDeckLane, changeLaneCollapsedState } =
useDeckMutations(editingContextId, representationId);

useEffect(() => {
if (error) {
addErrorMessage(error.message);
}
}, [error]);

useEffect(() => {
if (deck && selection.entries) {
const selectionIds: string[] = selection.entries.map((entry) => entry.id);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import { gql, OnDataOptions, useQuery, useSubscription } from '@apollo/client';
import { RepresentationComponentProps, useMultiToast } from '@eclipse-sirius/sirius-components-core';
import { ReactFlowProvider } from '@xyflow/react';
import { memo, useEffect, useState } from 'react';
import { flushSync } from 'react-dom';
import { DiagramContext } from '../contexts/DiagramContext';
import { DiagramDescriptionContext } from '../contexts/DiagramDescriptionContext';
import { DialogContextProvider } from '../dialog/DialogContext';
Expand Down Expand Up @@ -97,16 +98,6 @@ export const DiagramRepresentation = memo(
},
};

const onData = ({ data }: OnDataOptions<GQLDiagramEventData>) => {
if (data.data) {
const { diagramEvent } = data.data;
if (isDiagramRefreshedEventPayload(diagramEvent)) {
setState((prevState) => ({ ...prevState, diagramRefreshedEventPayload: diagramEvent }));
}
setState((prevState) => ({ ...prevState, payload: diagramEvent }));
}
};

const {
loading: diagramDescriptionLoading,
data: diagramDescriptionData,
Expand All @@ -132,6 +123,18 @@ export const DiagramRepresentation = memo(
}
}, [diagramDescriptionLoading, diagramDescriptionData, diagramDescriptionError]);

const onData = ({ data }: OnDataOptions<GQLDiagramEventData>) => {
flushSync(() => {
if (data.data) {
const { diagramEvent } = data.data;
if (isDiagramRefreshedEventPayload(diagramEvent)) {
setState((prevState) => ({ ...prevState, diagramRefreshedEventPayload: diagramEvent }));
}
setState((prevState) => ({ ...prevState, payload: diagramEvent }));
}
});
};

const onComplete = () => {
setState((prevState) => ({ ...prevState, diagramRefreshedEventPayload: null, complete: true }));
};
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,14 +10,15 @@
* Contributors:
* Obeo - initial API and implementation
*******************************************************************************/
import { gql, useSubscription } from '@apollo/client';
import { gql, OnDataOptions, useSubscription } from '@apollo/client';
import { RepresentationComponentProps, Toast, useData } from '@eclipse-sirius/sirius-components-core';
import { widgetContributionExtensionPoint } from '@eclipse-sirius/sirius-components-forms';
import ViewAgendaIcon from '@mui/icons-material/ViewAgenda';
import WebIcon from '@mui/icons-material/Web';
import Typography from '@mui/material/Typography';
import { useMachine } from '@xstate/react';
import React, { useEffect } from 'react';
import { flushSync } from 'react-dom';
import { makeStyles } from 'tss-react/mui';
import { StateMachine } from 'xstate';
import { formDescriptionEditorEventSubscription } from './FormDescriptionEditorEventFragment';
Expand All @@ -30,13 +31,13 @@ import { WidgetDescriptor } from './FormDescriptionEditorRepresentation.types';
import {
FormDescriptionEditorRepresentationContext,
FormDescriptionEditorRepresentationEvent,
formDescriptionEditorRepresentationMachine,
FormDescriptionEditorRepresentationStateSchema,
HandleSubscriptionResultEvent,
HideToastEvent,
InitializeRepresentationEvent,
SchemaValue,
ShowToastEvent,
formDescriptionEditorRepresentationMachine,
} from './FormDescriptionEditorRepresentationMachine';
import { PageList } from './PageList';
import { coreWidgets } from './coreWidgets';
Expand Down Expand Up @@ -168,22 +169,29 @@ export const FormDescriptionEditorRepresentation = ({
formDescriptionEditorId: representationId,
};
const variables: GQLFormDescriptionEditorEventVariables = { input };

const onData = ({ data }: OnDataOptions<GQLFormDescriptionEditorEventSubscription>) => {
flushSync(() => {
const handleDataEvent: HandleSubscriptionResultEvent = {
type: 'HANDLE_SUBSCRIPTION_RESULT',
result: data,
};
dispatch(handleDataEvent);
});
};

const onComplete = () => {
dispatch({ type: 'HANDLE_COMPLETE' });
};

const { error } = useSubscription<GQLFormDescriptionEditorEventSubscription, GQLFormDescriptionEditorEventVariables>(
gql(formDescriptionEditorEventSubscription),
{
variables,
fetchPolicy: 'no-cache',
skip: formDescriptionEditorRepresentation !== 'ready',
onData: ({ data }) => {
const handleDataEvent: HandleSubscriptionResultEvent = {
type: 'HANDLE_SUBSCRIPTION_RESULT',
result: data,
};
dispatch(handleDataEvent);
},
onComplete: () => {
dispatch({ type: 'HANDLE_COMPLETE' });
},
onData,
onComplete,
}
);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,10 @@
* Obeo - initial API and implementation
*******************************************************************************/

import { gql, OnDataOptions, useSubscription } from '@apollo/client';
import { ApolloError, gql, OnDataOptions, useSubscription } from '@apollo/client';
import { useMultiToast } from '@eclipse-sirius/sirius-components-core';
import { useEffect, useState } from 'react';
import { useState } from 'react';
import { flushSync } from 'react-dom';
import { formRefreshedEventPayloadFragment } from '../form/FormEventFragments';
import {
GQLFormEventInput,
Expand Down Expand Up @@ -44,6 +45,7 @@ export const useFormSubscription = (editingContextId: string, formId: string): U
const [state, setState] = useState<UseFormSubscriptionState>({
id: crypto.randomUUID(),
complete: false,
payload: null,
});

const input: GQLFormEventInput = {
Expand All @@ -56,37 +58,34 @@ export const useFormSubscription = (editingContextId: string, formId: string): U

const onComplete = () => setState((prevState) => ({ ...prevState, complete: true }));

const { addErrorMessage } = useMultiToast();
const onError = ({ message }: ApolloError) => {
addErrorMessage(message);
};

const onData = ({ data }: OnDataOptions<GQLFormEventSubscription>) => {
const { data: gqlDetailsEventSubscription } = data;
if (gqlDetailsEventSubscription) {
const { formEvent: payload } = gqlDetailsEventSubscription;
setState((prevState) => ({ ...prevState, payload, complete: false }));
if (isFormRefreshedEventPayload(payload)) {
setState((prevState) => ({ ...prevState, complete: false }));
flushSync(() => {
if (data.data) {
const { formEvent } = data.data;
setState((prevState) => ({ ...prevState, payload: data.data.formEvent, complete: false }));
if (isFormRefreshedEventPayload(formEvent)) {
setState((prevState) => ({ ...prevState, complete: false }));
}
}
}
});
};

const { data, error, loading } = useSubscription<GQLFormEventSubscription, GQLFormEventVariables>(
gql(formEventSubscription),
{
variables,
fetchPolicy: 'no-cache',
onData,
onComplete,
}
);

const { addErrorMessage } = useMultiToast();
useEffect(() => {
if (error) {
addErrorMessage('An unexpected error has occurred, please refresh the page');
}
}, [error]);
const { loading } = useSubscription<GQLFormEventSubscription, GQLFormEventVariables>(gql(formEventSubscription), {
variables,
fetchPolicy: 'no-cache',
onData,
onComplete,
onError,
});

return {
loading,
payload: !!data?.formEvent ? data.formEvent : null,
payload: state.payload,
complete: state.complete,
};
};
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ export interface UseFormSubscriptionValue {
export interface UseFormSubscriptionState {
id: string;
complete: boolean;
payload: GQLFormEventPayload | null;
}

export interface GQLFormEventInput {
Expand Down
Loading

0 comments on commit 030ade4

Please sign in to comment.