From db38962f8857c19bd25fb2fb0a890316b919196f Mon Sep 17 00:00:00 2001 From: Suren Date: Tue, 20 Jun 2023 17:42:28 +0530 Subject: [PATCH] #9219: Fix - Session restoration on reload by statically loading FeatureEditor (#9236) --- web/client/plugins/FeatureEditor.jsx | 32 +++++++-- .../plugins/__tests__/FeatureEditor-test.jsx | 66 +++++++++---------- .../plugins/featuregrid/FeatureEditor.jsx | 21 +----- web/client/product/plugins.js | 3 +- 4 files changed, 61 insertions(+), 61 deletions(-) diff --git a/web/client/plugins/FeatureEditor.jsx b/web/client/plugins/FeatureEditor.jsx index a6eade5f14..40202d1333 100644 --- a/web/client/plugins/FeatureEditor.jsx +++ b/web/client/plugins/FeatureEditor.jsx @@ -8,13 +8,14 @@ import React, { lazy } from 'react'; import { connect } from 'react-redux'; import { createSelector } from 'reselect'; +import isEqual from "lodash/isEqual"; import { createPlugin } from '../utils/PluginsUtils'; import * as epics from '../epics/featuregrid'; import featuregrid from '../reducers/featuregrid'; import FeatureEditorFallback from '../components/data/featuregrid/FeatureEditorFallback'; import withSuspense from '../components/misc/withSuspense'; import {compose, lifecycle} from "recompose"; -import {setViewportFilter} from "../actions/featuregrid"; +import { initPlugin, setViewportFilter } from "../actions/featuregrid"; import {isViewportFilterActive} from "../selectors/featuregrid"; /** @@ -160,17 +161,38 @@ const EditorPlugin = connect( ], (open, viewportFilter) => ({ open, viewportFilterInitialized: viewportFilter !== null })), { - setViewportFilter + setViewportFilter, + initPlugin } )(compose( lifecycle({ componentDidMount() { - // Initialize configuration for viewportFilter once plugin is loaded + // Initialize configurations once plugin is loaded !this.props.viewportFilterInitialized && this.props.filterByViewport && this.props.setViewportFilter(true); + this.props.initPlugin({ + virtualScroll: this.props.virtualScroll ?? true, + editingAllowedRoles: this.props.editingAllowedRoles, + editingAllowedGroups: this.props.editingAllowedGroups, + maxStoredPages: this.props.maxStoredPages + }); }, - componentDidUpdate() { - // Re-Initialize configuration + componentDidUpdate(prevProps) { + // Re-Initialize configurations !this.props.viewportFilterInitialized && this.props.filterByViewport && this.props.setViewportFilter(true); + + const {virtualScroll, editingAllowedRoles, editingAllowedGroups, maxStoredPages} = this.props ?? {}; + if (prevProps.virtualScroll !== virtualScroll + || !isEqual(prevProps.editingAllowedRoles, editingAllowedRoles) + || !isEqual(prevProps.editingAllowedGroups, editingAllowedGroups) + || prevProps.maxStoredPages !== maxStoredPages + ) { + this.props.initPlugin({ + virtualScroll: virtualScroll ?? true, + editingAllowedRoles, + editingAllowedGroups, + maxStoredPages + }); + } } }), withSuspense( diff --git a/web/client/plugins/__tests__/FeatureEditor-test.jsx b/web/client/plugins/__tests__/FeatureEditor-test.jsx index aab6c987c9..5671448d0e 100644 --- a/web/client/plugins/__tests__/FeatureEditor-test.jsx +++ b/web/client/plugins/__tests__/FeatureEditor-test.jsx @@ -8,7 +8,7 @@ import expect from 'expect'; import React from 'react'; import ReactDOM from 'react-dom'; -import { waitFor } from '@testing-library/react'; +import isEqual from 'lodash/isEqual'; import { getPluginForTest } from './pluginsTestUtils'; import FeatureEditor from "../FeatureEditor"; @@ -24,65 +24,59 @@ describe('FeatureEditor Plugin', () => { document.body.innerHTML = ''; setTimeout(done); }); - it('render FeatureEditor plugin', (done) => { + it('render FeatureEditor plugin', () => { const {Plugin, store} = getPluginForTest(FeatureEditor, {featuregrid: { open: true }}); ReactDOM.render(, document.getElementById("container")); - waitFor(() => expect(document.querySelector('.feature-grid-container')).toBeTruthy()) - .then(() => { - const state = store.getState().featuregrid; - expect(state.virtualScroll).toBe(true); - done(); - }); + const state = store.getState().featuregrid; + expect(state.virtualScroll).toBe(true); }); - it('onInit FeatureEditor plugin', (done) => { + it('onInit FeatureEditor plugin', () => { const props = { virtualScroll: false, editingAllowedRoles: ['USER', 'ADMIN'], maxStoredPages: 5 }; - const {Plugin, store} = getPluginForTest(FeatureEditor, { featuregrid: { open: true } }); + const {Plugin, store} = getPluginForTest(FeatureEditor, { featuregrid: { open: false } }); ReactDOM.render(, document.getElementById("container")); - waitFor(() => expect(document.querySelector('.feature-grid-container')).toBeTruthy()) - .then(() => { - const state = store.getState().featuregrid; - expect(state.virtualScroll).toBeFalsy(); - expect(state.editingAllowedRoles).toEqual(props.editingAllowedRoles); - expect(state.maxStoredPages).toBe(props.maxStoredPages); - done(); - }); + const state = store.getState().featuregrid; + expect(state.virtualScroll).toBeFalsy(); + expect(state.editingAllowedRoles).toEqual(props.editingAllowedRoles); + expect(state.maxStoredPages).toBe(props.maxStoredPages); }); - it('onInit FeatureEditor plugin be-recalled when props change', (done) => { + it('onInit FeatureEditor plugin be-recalled when props change', () => { const props = { virtualScroll: false, editingAllowedRoles: ['ADMIN'], + editingAllowedGroups: ['GROUP1'], maxStoredPages: 5 }; const props2 = { editingAllowedRoles: ['USER', 'ADMIN'], + editingAllowedGroups: ['GROUP1', 'GROUP2'], maxStoredPages: 5 }; const props3 = { editingAllowedRoles: ['USER', 'ADMIN'], + editingAllowedGroups: ['GROUP1', 'GROUP2'], maxStoredPages: 5 }; - const {Plugin, store} = getPluginForTest(FeatureEditor, { featuregrid: { open: true } }); + const {Plugin, store} = getPluginForTest(FeatureEditor, { featuregrid: { open: false } }); ReactDOM.render(, document.getElementById("container")); - waitFor(() => expect(document.querySelector('.feature-grid-container')).toBeTruthy()) - .then(() => { - const state = store.getState().featuregrid; - expect(state.virtualScroll).toBeFalsy(); - expect(state.editingAllowedRoles).toEqual(props.editingAllowedRoles); - expect(state.maxStoredPages).toBe(props.maxStoredPages); - ReactDOM.render(, document.getElementById("container")); - const state2 = store.getState().featuregrid; - expect(state2.virtualScroll).toBeTruthy(); // the default - expect(state2.editingAllowedRoles).toEqual(props2.editingAllowedRoles); // changed - expect(state2.maxStoredPages).toBe(props2.maxStoredPages); - ReactDOM.render(, document.getElementById("container")); - const state3 = store.getState().featuregrid; - expect(state2.editingAllowedRoles === state3.editingAllowedRoles).toBeTruthy(); // no double call - done(); - }); + const state = store.getState().featuregrid; + expect(state.virtualScroll).toBeFalsy(); + expect(state.editingAllowedRoles).toEqual(props.editingAllowedRoles); + expect(state.editingAllowedGroups).toEqual(props.editingAllowedGroups); + expect(state.maxStoredPages).toBe(props.maxStoredPages); + ReactDOM.render(, document.getElementById("container")); + const state2 = store.getState().featuregrid; + expect(state2.virtualScroll).toBeTruthy(); // the default + expect(state2.editingAllowedRoles).toEqual(props2.editingAllowedRoles); // changed + expect(state2.editingAllowedGroups).toEqual(props2.editingAllowedGroups); // changed + expect(state2.maxStoredPages).toBe(props2.maxStoredPages); + ReactDOM.render(, document.getElementById("container")); + const state3 = store.getState().featuregrid; + expect(isEqual(state2.editingAllowedRoles, state3.editingAllowedRoles)).toBeTruthy(); // no double call + expect(isEqual(state2.editingAllowedGroups, state3.editingAllowedGroups)).toBeTruthy(); // no double call }); }); diff --git a/web/client/plugins/featuregrid/FeatureEditor.jsx b/web/client/plugins/featuregrid/FeatureEditor.jsx index 059c70ed36..80f0c55723 100644 --- a/web/client/plugins/featuregrid/FeatureEditor.jsx +++ b/web/client/plugins/featuregrid/FeatureEditor.jsx @@ -5,7 +5,7 @@ * This source code is licensed under the BSD-style license found in the * LICENSE file in the root directory of this source tree. */ -import React, {useEffect} from 'react'; +import React from 'react'; import {connect} from 'react-redux'; import {createSelector, createStructuredSelector} from 'reselect'; import {bindActionCreators} from 'redux'; @@ -17,7 +17,7 @@ import ContainerDimensions from 'react-container-dimensions'; import Grid from '../../components/data/featuregrid/FeatureGrid'; import BorderLayout from '../../components/layout/BorderLayout'; import { toChangesMap} from '../../utils/FeatureGridUtils'; -import { initPlugin, sizeChange, setUp, setSyncTool} from '../../actions/featuregrid'; +import { sizeChange, setUp, setSyncTool } from '../../actions/featuregrid'; import {mapLayoutValuesSelector} from '../../selectors/maplayout'; import {paginationInfo, describeSelector, wfsURLSelector, typeNameSelector} from '../../selectors/query'; import {modeSelector, changesSelector, newFeaturesSelector, hasChangesSelector, selectedLayerFieldsSelector, selectedFeaturesSelector, getDockSize} from '../../selectors/featuregrid'; @@ -185,24 +185,8 @@ const FeatureDock = (props = { setDockSize: () => {}, zIndex: 1060 }; - // columns={[]} const items = props?.items ?? []; const toolbarItems = items.filter(({target}) => target === 'toolbar'); - // const editors = items.filter(({target}) => target === 'editors'); - - useEffect(() => { - props.initPlugin({ - virtualScroll, - editingAllowedRoles: props.editingAllowedRoles, - editingAllowedGroups: props.editingAllowedGroups, - maxStoredPages: props.maxStoredPages - }); - }, [ - virtualScroll, - (props.editingAllowedRoles ?? []).join(","), // this avoids multiple calls when the array remains the equal - (props.editingAllowedGroups ?? []).join(","), - props.maxStoredPages - ]); return ( { props.onSizeChange(size, dockProps); }}> @@ -322,7 +306,6 @@ const EditorPlugin = compose( (dispatch) => ({ gridEvents: bindActionCreators(gridEvents, dispatch), pageEvents: bindActionCreators(pageEvents, dispatch), - initPlugin: bindActionCreators((options) => initPlugin(options), dispatch), toolbarEvents: bindActionCreators(toolbarEvents, dispatch), gridTools: gridTools.map((t) => ({ ...t, diff --git a/web/client/product/plugins.js b/web/client/product/plugins.js index a84dcd8d43..34c02c2721 100644 --- a/web/client/product/plugins.js +++ b/web/client/product/plugins.js @@ -23,6 +23,7 @@ import Print from "../plugins/Print"; import UserSession from "../plugins/UserSession"; import Login from '../plugins/Login'; import Identify from '../plugins/Identify'; +import FeatureEditor from '../plugins/FeatureEditor'; /** @@ -45,6 +46,7 @@ export const plugins = { UserSessionPlugin: UserSession, LoginPlugin: Login, IdentifyPlugin: Identify, + FeatureEditorPlugin: FeatureEditor, // ### DYNAMIC PLUGINS ### // // product plugins @@ -78,7 +80,6 @@ export const plugins = { DetailsPlugin: toModulePlugin('Details', () => import(/* webpackChunkName: 'plugins/details' */ '../plugins/Details')), DrawerMenuPlugin: toModulePlugin('DrawerMenu', () => import(/* webpackChunkName: 'plugins/drawerMenu' */ '../plugins/DrawerMenu')), ExpanderPlugin: toModulePlugin('Expander', () => import(/* webpackChunkName: 'plugins/expander' */ '../plugins/Expander')), - FeatureEditorPlugin: toModulePlugin('FeatureEditor', () => import(/* webpackChunkName: 'plugins/featureEditor' */ '../plugins/FeatureEditor')), FeaturedMaps: toModulePlugin('FeaturedMaps', () => import(/* webpackChunkName: 'plugins/featuredMaps' */ '../plugins/FeaturedMaps')), FilterLayerPlugin: toModulePlugin('FilterLayer', () => import(/* webpackChunkName: 'plugins/filterLayer' */ '../plugins/FilterLayer')), FloatingLegendPlugin: toModulePlugin('FloatingLegend', () => import(/* webpackChunkName: 'plugins/floatingLegend' */ '../plugins/FloatingLegend')),