-
Notifications
You must be signed in to change notification settings - Fork 22
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
#7670: Use <IsolatedComponent>
for DocumentView
, EphemeralFormContent
, CustomFormComponent
#8200
Changes from 40 commits
46d2207
708ba2b
0671574
386b02c
6a273f9
360f843
e3018e8
4760ee0
a2c75b9
9760393
df1ec00
a6dc0fe
652339a
c5aa5f6
3d139a2
123b53a
16542a2
fb4d8a4
a349a66
efb53fe
f195c5c
ccb84c2
cc46b6a
98384ca
fee63aa
e29f974
34af2e3
98b0f8e
82b3dd4
3313bc3
1334a91
0f559cb
8b2f5e8
3695681
9d86817
bf236b9
c7aaa29
ee2aa0a
de42f14
9db1a1d
4a01ac6
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -16,7 +16,8 @@ | |
*/ | ||
|
||
import React from "react"; | ||
import { render, screen } from "@testing-library/react"; | ||
import { render } from "@testing-library/react"; | ||
import { screen } from "shadow-dom-testing-library"; | ||
import ImageCropWidget from "@/components/formBuilder/ImageCropWidget"; | ||
import DescriptionField from "@/components/formBuilder/DescriptionField"; | ||
import JsonSchemaForm from "@rjsf/bootstrap-4"; | ||
|
@@ -228,9 +229,10 @@ | |
); | ||
|
||
render(<Component {...props} />); | ||
await waitForEffect(); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Appears to be needed due to the new React.lazy/Suspense usage. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||
|
||
expect(screen.queryByText("Submit")).not.toBeInTheDocument(); | ||
expect(screen.getByRole("textbox")).toBeInTheDocument(); | ||
expect(screen.getByShadowRole("textbox")).toBeInTheDocument(); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I'm not entirely sure why suddenly this is required, the component was already in a shadow DOM. For ease of use I tried mocking the Anyway this part now works. |
||
}); | ||
|
||
test("Supports postSubmitAction reset", async () => { | ||
|
@@ -261,17 +263,19 @@ | |
|
||
render(<Component {...props} />); | ||
|
||
const textBox = screen.getByRole("textbox"); | ||
await waitForEffect(); | ||
|
||
const textBox = screen.getByShadowRole("textbox"); | ||
await userEvent.type(textBox, "Some text"); | ||
expect(textBox).toHaveValue("Some text"); | ||
await userEvent.click(screen.getByRole("button", { name: "Submit" })); | ||
await userEvent.click(screen.getByShadowRole("button", { name: "Submit" })); | ||
|
||
expect(runPipelineMock).toHaveBeenCalledOnce(); | ||
|
||
expect(dataStoreSetSpy).not.toHaveBeenCalled(); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. One of these call assertions are failing. Can anyone look into them? The component is rendered fine, I see There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I don't have time today, but I may have time tomorrow |
||
|
||
// Need to get new textbox reference, because the old one is removed when the key changes | ||
expect(screen.getByRole("textbox")).toHaveValue(""); | ||
expect(screen.getByShadowRole("textbox")).toHaveValue(""); | ||
}); | ||
|
||
test.each([undefined, "save"])( | ||
|
@@ -304,18 +308,22 @@ | |
|
||
render(<Component {...props} />); | ||
|
||
await waitForEffect(); | ||
|
||
const value = "Some text"; | ||
const textBox = screen.getByRole("textbox"); | ||
const textBox = screen.getByShadowRole("textbox"); | ||
await userEvent.type(textBox, value); | ||
await userEvent.click(screen.getByRole("button", { name: "Submit" })); | ||
await userEvent.click( | ||
screen.getByShadowRole("button", { name: "Submit" }), | ||
); | ||
|
||
expect(runPipelineMock).toHaveBeenCalledOnce(); | ||
expect(dataStoreSetSpy).toHaveBeenCalledExactlyOnceWith("test", { | ||
Check failure on line 321 in src/bricks/renderers/customForm.test.tsx GitHub Actions / testCustomFormRenderer › postSubmitAction: undefined doesn't reset
Check failure on line 321 in src/bricks/renderers/customForm.test.tsx GitHub Actions / testCustomFormRenderer › postSubmitAction: save doesn't reset
|
||
name: value, | ||
}); | ||
|
||
// Need to get new textbox reference, because the old one is removed if/when the key changes | ||
expect(screen.getByRole("textbox")).toHaveValue(value); | ||
expect(screen.getByShadowRole("textbox")).toHaveValue(value); | ||
}, | ||
); | ||
|
||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -15,6 +15,7 @@ | |
* along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
*/ | ||
|
||
import React from "react"; | ||
import { type JsonObject } from "type-fest"; | ||
import { dataStore } from "@/background/messenger/strict/api"; | ||
import { validateRegistryId } from "@/types/helpers"; | ||
|
@@ -46,6 +47,8 @@ import { getOutputReference, validateOutputKey } from "@/runtime/runtimeTypes"; | |
import { type BrickConfig } from "@/bricks/types"; | ||
import { isExpression } from "@/utils/expressionUtils"; | ||
import { getPlatform } from "@/platform/platformContext"; | ||
import IsolatedComponent from "@/components/IsolatedComponent"; | ||
import { type CustomFormComponentProps } from "./CustomFormComponent"; | ||
|
||
interface DatabaseResult { | ||
success: boolean; | ||
|
@@ -297,10 +300,20 @@ export class CustomFormRenderer extends RendererABC { | |
normalizedData, | ||
}); | ||
|
||
// Changed webpackChunkName to de-conflict with the manual entry in webpack used to load in the stylesheets | ||
const { default: CustomFormComponent } = await import( | ||
/* webpackChunkName: "CustomFormRendererComponent" */ | ||
"./CustomFormComponent" | ||
const CustomFormComponent: React.FunctionComponent< | ||
CustomFormComponentProps | ||
> = (props) => ( | ||
<IsolatedComponent | ||
name="CustomFormComponent" | ||
noStyle={disableParentStyles} | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. |
||
lazy={async () => | ||
import( | ||
/* webpackChunkName: "isolated/CustomFormComponent" */ | ||
"./CustomFormComponent" | ||
) | ||
} | ||
factory={(CustomFormComponent) => <CustomFormComponent {...props} />} | ||
/> | ||
); | ||
|
||
return { | ||
|
@@ -314,7 +327,6 @@ export class CustomFormRenderer extends RendererABC { | |
submitCaption, | ||
className, | ||
stylesheets, | ||
disableParentStyles, | ||
// Option only applies if a custom onSubmit handler is provided | ||
resetOnSubmit: onSubmit != null && postSubmitAction === "reset", | ||
async onSubmit( | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -15,8 +15,8 @@ | |
* along with this program. If not, see <http://www.gnu.org/licenses/>. | ||
*/ | ||
|
||
import React from "react"; | ||
import { RendererABC } from "@/types/bricks/rendererTypes"; | ||
import DocumentViewLazy from "./documentView/DocumentViewLazy"; | ||
import { validateRegistryId } from "@/types/helpers"; | ||
import { | ||
type BrickArgs, | ||
|
@@ -28,6 +28,8 @@ import { | |
DOCUMENT_ELEMENT_TYPES, | ||
type DocumentElement, | ||
} from "@/components/documentBuilder/documentBuilderTypes"; | ||
import IsolatedComponent from "@/components/IsolatedComponent"; | ||
import { type DocumentViewProps } from "./documentView/DocumentViewProps"; | ||
|
||
export const DOCUMENT_SCHEMA: Schema = { | ||
$schema: "https://json-schema.org/draft/2019-09/schema#", | ||
|
@@ -107,12 +109,30 @@ export class DocumentRenderer extends RendererABC { | |
}>, | ||
options: BrickOptions, | ||
): Promise<ComponentRef> { | ||
const DocumentView: React.FC<DocumentViewProps> = (props) => ( | ||
<IsolatedComponent | ||
name="DocumentView" | ||
noStyle={disableParentStyles} | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. |
||
lazy={async () => | ||
import( | ||
/* webpackChunkName: "isolated/DocumentView" */ | ||
"./documentView/DocumentView" | ||
) | ||
} | ||
factory={(DocumentView) => <DocumentView {...props} />} | ||
// It must fill the frame even if `noStyle` is set, so set it as a style prop | ||
// TODO: The parent node should instead make sure that the children fill | ||
// the sidebar vertically (via a simple `.d-flex`), but this this requires | ||
// verifying that other components aren't broken by this. | ||
style={{ height: "100%" }} | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. "h-100" restored. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Nevermind, that restores the classname, but as you point out, it's not getting the stylesheet at that level. |
||
/> | ||
); | ||
|
||
return { | ||
Component: DocumentViewLazy, | ||
Component: DocumentView, | ||
props: { | ||
body, | ||
stylesheets, | ||
disableParentStyles, | ||
options, | ||
}, | ||
}; | ||
|
This file was deleted.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
disableParentStyles
removed from 2 components because now it's not the Component's responsibility to load its own stylesheets, but it's the loader's (i.e. whereIsolatedComponent
is called)