Skip to content

Commit

Permalink
chore: decouple editor components (#37102)
Browse files Browse the repository at this point in the history
## Description
Decouple editor components and codemirror from the main chunk, the main
chunk has dropped by 200Kb to 1.1Mb


Fixes #`Issue Number`  
_or_  
Fixes `Issue URL`
> [!WARNING]  
> _If no issue exists, please create an issue first, and check with the
maintainers if the issue is valid._

## Automation

/ok-to-test tags="@tag.All"

### 🔍 Cypress test results
<!-- This is an auto-generated comment: Cypress test results  -->
> [!TIP]
> 🟢 🟢 🟢 All cypress tests have passed! 🎉 🎉 🎉
> Workflow run:
<https://github.com/appsmithorg/appsmith/actions/runs/11593047595>
> Commit: 4a5b3bc
> <a
href="https://internal.appsmith.com/app/cypress-dashboard/rundetails-65890b3c81d7400d08fa9ee5?branch=master&workflowId=11593047595&attempt=3"
target="_blank">Cypress dashboard</a>.
> Tags: `@tag.All`
> Spec:
> <hr>Wed, 30 Oct 2024 13:57:44 UTC
<!-- end of auto-generated comment: Cypress test results  -->


## Communication
Should the DevRel and Marketing teams inform users about this change?
- [ ] Yes
- [ ] No


<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->
## Summary by CodeRabbit

- **New Features**
- Implemented lazy loading for several components, enhancing performance
and user experience during loading states.
- Introduced new error handling UI with `EntityNotFoundPane` for better
feedback when data is unavailable.
- Added `LazilyLoadedChecklist` for optimized loading of the checklist
component in onboarding.

- **Bug Fixes**
- Improved asynchronous handling in test cases for more reliable
rendering assertions.

- **Documentation**
- Updated export statements for components to default exports for
consistency.

- **Chores**
- Refactored routing logic to utilize lazy-loaded components across
various sections of the application.
<!-- end of auto-generated comment: release notes by coderabbit.ai -->
  • Loading branch information
vsvamsi1 authored Nov 4, 2024
1 parent f2c3125 commit bc165cf
Show file tree
Hide file tree
Showing 10 changed files with 259 additions and 93 deletions.
1 change: 1 addition & 0 deletions app/client/cypress/support/Pages/JSEditor.ts
Original file line number Diff line number Diff line change
Expand Up @@ -113,6 +113,7 @@ export class JSEditor {
);
//Checking JS object was created successfully
this.assertHelper.AssertNetworkStatus("@createNewJSCollection", 201);
cy.get(this._jsObjName).click({ force: true });
this.agHelper.AssertElementVisibility(this._jsObjTxt);
// Assert that the name of the JS Object is focused when newly created
this.agHelper.PressEnter();
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { useCallback } from "react";
import { lazy, Suspense, useCallback, useMemo } from "react";
import React from "react";
import { useDispatch, useSelector } from "react-redux";
import { createNewJSCollection } from "actions/jsPaneActions";
import { getCurrentPageId } from "selectors/editorSelectors";
Expand All @@ -7,17 +8,16 @@ import { createMessage, EDITOR_PANE_TEXTS } from "ee/constants/messages";
import { JsFileIconV2 } from "pages/Editor/Explorer/ExplorerIcons";
import { SEARCH_ITEM_TYPES } from "components/editorComponents/GlobalSearch/utils";
import type { UseRoutes } from "ee/entities/IDE/constants";
import JSEditor from "pages/Editor/JSEditor";
import AddJS from "pages/Editor/IDE/EditorPane/JS/Add";
import { ADD_PATH } from "ee/constants/routes/appRoutes";
import history from "utils/history";
import { FocusEntity, identifyEntityFromPath } from "navigation/FocusEntity";
import { useModuleOptions } from "ee/utils/moduleInstanceHelpers";
import { getJSUrl } from "ee/pages/Editor/IDE/EditorPane/JS/utils";
import { JSBlankState } from "pages/Editor/JSEditor/JSBlankState";
import { getIDEViewMode } from "selectors/ideSelectors";
import { EditorViewMode } from "ee/entities/IDE/constants";
import { setListViewActiveState } from "actions/ideActions";
import { retryPromise } from "utils/AppsmithUtils";
import Skeleton from "widgets/Skeleton";

export const useJSAdd = () => {
const pageId = useSelector(getCurrentPageId);
Expand Down Expand Up @@ -93,25 +93,64 @@ export const useGroupedAddJsOperations = (): GroupedAddOperations => {
];
};

const AddJS = lazy(async () =>
retryPromise(
async () =>
import(
/* webpackChunkName: "AddJS" */ "pages/Editor/IDE/EditorPane/JS/Add"
),
),
);
const JSEditor = lazy(async () =>
retryPromise(
async () =>
import(/* webpackChunkName: "JSEditor" */ "pages/Editor/JSEditor"),
),
);

const JSEmpty = lazy(async () =>
retryPromise(
async () =>
import(
/* webpackChunkName: "JSEmpty" */ "pages/Editor/JSEditor/JSBlankState"
),
),
);

export const useJSEditorRoutes = (path: string): UseRoutes => {
return [
{
exact: true,
key: "AddJS",
component: AddJS,
path: [`${path}${ADD_PATH}`, `${path}/:baseCollectionId${ADD_PATH}`],
},
{
exact: true,
key: "JSEditor",
component: JSEditor,
path: [path + "/:baseCollectionId"],
},
{
key: "JSEmpty",
component: JSBlankState,
exact: true,
path: [path],
},
];
return useMemo(
() => [
{
exact: true,
key: "AddJS",
component: (args) => (
<Suspense fallback={<Skeleton />}>
<AddJS {...args} />
</Suspense>
),
path: [`${path}${ADD_PATH}`, `${path}/:baseCollectionId${ADD_PATH}`],
},
{
exact: true,
key: "JSEditor",
component: (args) => (
<Suspense fallback={<Skeleton />}>
<JSEditor {...args} />
</Suspense>
),
path: [path + "/:baseCollectionId"],
},
{
key: "JSEmpty",
component: (args) => (
<Suspense fallback={<Skeleton />}>
<JSEmpty {...args} />
</Suspense>
),
exact: true,
path: [path],
},
],
[path],
);
};
149 changes: 104 additions & 45 deletions app/client/src/ce/pages/Editor/IDE/EditorPane/Query/hooks.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { useCallback, useMemo } from "react";
import { lazy, Suspense, useCallback, useMemo } from "react";
import React from "react";
import history from "utils/history";
import { useLocation } from "react-router";
import { FocusEntity, identifyEntityFromPath } from "navigation/FocusEntity";
Expand All @@ -23,19 +24,17 @@ import {
BUILDER_PATH_DEPRECATED,
} from "ee/constants/routes/appRoutes";
import { SAAS_EDITOR_API_ID_PATH } from "pages/Editor/SaaSEditor/constants";
import ApiEditor from "pages/Editor/APIEditor";
import type { UseRoutes } from "ee/entities/IDE/constants";
import QueryEditor from "pages/Editor/QueryEditor";
import AddQuery from "pages/Editor/IDE/EditorPane/Query/Add";
import type { AppState } from "ee/reducers";
import keyBy from "lodash/keyBy";
import { getPluginEntityIcon } from "pages/Editor/Explorer/ExplorerIcons";
import type { ListItemProps } from "@appsmith/ads";
import { createAddClassName } from "pages/Editor/IDE/EditorPane/utils";
import { QueriesBlankState } from "pages/Editor/QueryEditor/QueriesBlankState";
import { getIDEViewMode } from "selectors/ideSelectors";
import { EditorViewMode } from "ee/entities/IDE/constants";
import { setListViewActiveState } from "actions/ideActions";
import { retryPromise } from "utils/AppsmithUtils";
import Skeleton from "widgets/Skeleton";

export const useQueryAdd = () => {
const location = useLocation();
Expand Down Expand Up @@ -114,47 +113,107 @@ export const useGroupedAddQueryOperations = (): GroupedAddOperations => {
return groups;
};

const ApiEditor = lazy(async () =>
retryPromise(
async () =>
import(/* webpackChunkName: "APIEditor" */ "pages/Editor/APIEditor"),
),
);

const AddQuery = lazy(async () =>
retryPromise(
async () =>
import(
/* webpackChunkName: "AddQuery" */ "pages/Editor/IDE/EditorPane/Query/Add"
),
),
);
const QueryEditor = lazy(async () =>
retryPromise(
async () =>
import(/* webpackChunkName: "QueryEditor" */ "pages/Editor/QueryEditor"),
),
);

const QueryEmpty = lazy(async () =>
retryPromise(
async () =>
import(
/* webpackChunkName: "QueryEmpty" */ "pages/Editor/QueryEditor/QueriesBlankState"
),
),
);

export const useQueryEditorRoutes = (path: string): UseRoutes => {
return [
{
key: "ApiEditor",
component: ApiEditor,
exact: true,
path: [
BUILDER_PATH + API_EDITOR_ID_PATH,
BUILDER_CUSTOM_PATH + API_EDITOR_ID_PATH,
BUILDER_PATH_DEPRECATED + API_EDITOR_ID_PATH,
],
},
{
key: "AddQuery",
exact: true,
component: AddQuery,
path: [`${path}${ADD_PATH}`, `${path}/:baseQueryId${ADD_PATH}`],
},
{
key: "SAASEditor",
component: QueryEditor,
exact: true,
path: [
BUILDER_PATH + SAAS_EDITOR_API_ID_PATH,
BUILDER_CUSTOM_PATH + SAAS_EDITOR_API_ID_PATH,
BUILDER_PATH_DEPRECATED + SAAS_EDITOR_API_ID_PATH,
],
},
{
key: "QueryEditor",
component: QueryEditor,
exact: true,
path: [path + "/:baseQueryId"],
},
{
key: "QueryEmpty",
component: QueriesBlankState,
exact: true,
path: [path],
},
];
return useMemo(
() => [
{
key: "ApiEditor",
component: (args) => {
return (
<Suspense fallback={<Skeleton />}>
<ApiEditor {...args} />
</Suspense>
);
},
exact: true,
path: [
BUILDER_PATH + API_EDITOR_ID_PATH,
BUILDER_CUSTOM_PATH + API_EDITOR_ID_PATH,
BUILDER_PATH_DEPRECATED + API_EDITOR_ID_PATH,
],
},
{
key: "AddQuery",
exact: true,
component: (args) => (
<Suspense fallback={<Skeleton />}>
<AddQuery {...args} />
</Suspense>
),
path: [`${path}${ADD_PATH}`, `${path}/:baseQueryId${ADD_PATH}`],
},
{
key: "SAASEditor",
component: (args) => {
return (
<Suspense fallback={<Skeleton />}>
<QueryEditor {...args} />
</Suspense>
);
},
exact: true,
path: [
BUILDER_PATH + SAAS_EDITOR_API_ID_PATH,
BUILDER_CUSTOM_PATH + SAAS_EDITOR_API_ID_PATH,
BUILDER_PATH_DEPRECATED + SAAS_EDITOR_API_ID_PATH,
],
},
{
key: "QueryEditor",
component: (args) => {
return (
<Suspense fallback={<Skeleton />}>
<QueryEditor {...args} />
</Suspense>
);
},
exact: true,
path: [path + "/:baseQueryId"],
},
{
key: "QueryEmpty",
component: (args) => (
<Suspense fallback={<Skeleton />}>
<QueryEmpty {...args} />
</Suspense>
),
exact: true,
path: [path],
},
],
[path],
);
};

export const useAddQueryListItems = () => {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,6 @@ import {
WIDGETS_EDITOR_ID_PATH,
} from "constants/routes";
import CreateNewDatasourceTab from "pages/Editor/IntegrationEditor/CreateNewDatasourceTab";
import OnboardingChecklist from "pages/Editor/FirstTimeUserOnboarding/Checklist";
import {
SAAS_EDITOR_API_ID_ADD_PATH,
SAAS_EDITOR_API_ID_PATH,
Expand All @@ -38,7 +37,28 @@ import GeneratePage from "pages/Editor/GeneratePage";
import type { RouteProps } from "react-router";
import { useSelector } from "react-redux";
import { combinedPreviewModeSelector } from "selectors/editorSelectors";
import { lazy, Suspense } from "react";
import React from "react";

import { retryPromise } from "utils/AppsmithUtils";
import Skeleton from "widgets/Skeleton";

const FirstTimeUserOnboardingChecklist = lazy(async () =>
retryPromise(
async () =>
import(
/* webpackChunkName: "FirstTimeUserOnboardingChecklist" */ "pages/Editor/FirstTimeUserOnboarding/Checklist"
),
),
);

export const LazilyLoadedFirstTimeUserOnboardingChecklist = () => {
return (
<Suspense fallback={<Skeleton />}>
<FirstTimeUserOnboardingChecklist />
</Suspense>
);
};
export interface RouteReturnType extends RouteProps {
key: string;
}
Expand Down Expand Up @@ -95,7 +115,9 @@ function useRoutes(path: string): RouteReturnType[] {
},
{
key: "OnboardingChecklist",
component: isPreviewMode ? WidgetsEditor : OnboardingChecklist,
component: isPreviewMode
? WidgetsEditor
: FirstTimeUserOnboardingChecklist,
exact: true,
path: `${path}${BUILDER_CHECKLIST_PATH}`,
},
Expand Down
24 changes: 21 additions & 3 deletions app/client/src/pages/Editor/FirstTimeUserOnboarding/Modal.tsx
Original file line number Diff line number Diff line change
@@ -1,11 +1,29 @@
import React from "react";
import React, { lazy, Suspense } from "react";
import { MenuContent } from "@appsmith/ads";
import styled from "styled-components";
import Checklist from "./Checklist";
import HelpMenu from "./HelpMenu";
import { useDispatch } from "react-redux";
import { showSignpostingModal } from "actions/onboardingActions";

import { retryPromise } from "utils/AppsmithUtils";
import Skeleton from "widgets/Skeleton";

const Checklist = lazy(async () =>
retryPromise(
async () =>
import(
/* webpackChunkName: "FirstTimeUserOnboardingChecklist" */ "./Checklist"
),
),
);

export const LazilyLoadedChecklist = () => {
return (
<Suspense fallback={<Skeleton />}>
<Checklist />
</Suspense>
);
};
const SIGNPOSTING_POPUP_WIDTH = "360px";

const StyledMenuContent = styled(MenuContent)<{ animate: boolean }>`
Expand Down Expand Up @@ -48,7 +66,7 @@ function OnboardingModal(props: {
width={SIGNPOSTING_POPUP_WIDTH}
>
<Wrapper>
{!props.showIntercomConsent && <Checklist />}
{!props.showIntercomConsent && <LazilyLoadedChecklist />}
<HelpMenu
setShowIntercomConsent={props.setShowIntercomConsent}
showIntercomConsent={props.showIntercomConsent}
Expand Down
Loading

0 comments on commit bc165cf

Please sign in to comment.