diff --git a/package-lock.json b/package-lock.json index c74d1d63b..a86c2e29a 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,6 +1,6 @@ { "name": "saleor-dashboard", - "version": "3.1.0-dev", + "version": "3.4.0-dev", "lockfileVersion": 1, "requires": true, "dependencies": { diff --git a/src/categories/components/CategoryDetailsForm/CategoryDetailsForm.tsx b/src/categories/components/CategoryDetailsForm/CategoryDetailsForm.tsx index ce9f33d39..a6e1b71b2 100644 --- a/src/categories/components/CategoryDetailsForm/CategoryDetailsForm.tsx +++ b/src/categories/components/CategoryDetailsForm/CategoryDetailsForm.tsx @@ -3,6 +3,7 @@ import { Card, CardContent, TextField } from "@material-ui/core"; import CardTitle from "@saleor/components/CardTitle"; import FormSpacer from "@saleor/components/FormSpacer"; import RichTextEditor from "@saleor/components/RichTextEditor"; +import { RichTextEditorLoading } from "@saleor/components/RichTextEditor/RichTextEditorLoading"; import { ProductErrorFragment } from "@saleor/graphql"; import { commonMessages } from "@saleor/intl"; import { getFormErrors, getProductErrorMessage } from "@saleor/utils/errors"; @@ -58,7 +59,7 @@ export const CategoryDetailsForm: React.FC = ({ /> - {isReadyForMount && ( + {isReadyForMount ? ( = ({ })} name="description" /> + ) : ( + )} diff --git a/src/categories/components/CategoryUpdatePage/form.tsx b/src/categories/components/CategoryUpdatePage/form.tsx index 73d471c71..2857cd7b4 100644 --- a/src/categories/components/CategoryUpdatePage/form.tsx +++ b/src/categories/components/CategoryUpdatePage/form.tsx @@ -78,6 +78,7 @@ function useCategoryUpdateForm( const richText = useRichText({ initial: category?.description, + loading: !category, triggerChange }); diff --git a/src/collections/components/CollectionDetails/CollectionDetails.tsx b/src/collections/components/CollectionDetails/CollectionDetails.tsx index 0b4821047..512b334f3 100644 --- a/src/collections/components/CollectionDetails/CollectionDetails.tsx +++ b/src/collections/components/CollectionDetails/CollectionDetails.tsx @@ -3,6 +3,7 @@ import { Card, CardContent, TextField } from "@material-ui/core"; import CardTitle from "@saleor/components/CardTitle"; import FormSpacer from "@saleor/components/FormSpacer"; import RichTextEditor from "@saleor/components/RichTextEditor"; +import { RichTextEditorLoading } from "@saleor/components/RichTextEditor/RichTextEditorLoading"; import { CollectionErrorFragment } from "@saleor/graphql"; import { commonMessages } from "@saleor/intl"; import { getFormErrors, getProductErrorMessage } from "@saleor/utils/errors"; @@ -56,7 +57,7 @@ const CollectionDetails: React.FC = ({ fullWidth /> - {isReadyForMount && ( + {isReadyForMount ? ( = ({ name="description" disabled={disabled} /> + ) : ( + )} diff --git a/src/collections/components/CollectionDetailsPage/form.tsx b/src/collections/components/CollectionDetailsPage/form.tsx index 9e862120e..fe1503763 100644 --- a/src/collections/components/CollectionDetailsPage/form.tsx +++ b/src/collections/components/CollectionDetailsPage/form.tsx @@ -96,6 +96,7 @@ function useCollectionUpdateForm( const richText = useRichText({ initial: collection?.description, + loading: !collection, triggerChange }); diff --git a/src/components/RichTextEditor/RichTextEditorLoading.tsx b/src/components/RichTextEditor/RichTextEditorLoading.tsx new file mode 100644 index 000000000..910a5b43d --- /dev/null +++ b/src/components/RichTextEditor/RichTextEditorLoading.tsx @@ -0,0 +1,28 @@ +import React from "react"; + +import RichTextEditor, { RichTextEditorProps } from "./RichTextEditor"; + +interface RichTextEditorLoadingProps + extends Omit< + RichTextEditorProps, + | "disabled" + | "editorRef" + | "onChange" + | "defaultValue" + | "error" + | "helperText" + > { + helperText?: RichTextEditorProps["helperText"]; +} + +export const RichTextEditorLoading = (props: RichTextEditorLoadingProps) => ( + +); diff --git a/src/pages/components/PageDetailsPage/form.tsx b/src/pages/components/PageDetailsPage/form.tsx index d88d768c4..274f6c002 100644 --- a/src/pages/components/PageDetailsPage/form.tsx +++ b/src/pages/components/PageDetailsPage/form.tsx @@ -163,6 +163,7 @@ function usePageForm( const richText = useRichText({ initial: pageExists ? page?.content : null, + loading: pageExists ? !page : false, triggerChange }); diff --git a/src/pages/components/PageInfo/PageInfo.tsx b/src/pages/components/PageInfo/PageInfo.tsx index c473ac8ca..f4b7ca435 100644 --- a/src/pages/components/PageInfo/PageInfo.tsx +++ b/src/pages/components/PageInfo/PageInfo.tsx @@ -2,6 +2,7 @@ import { Card, CardContent, TextField } from "@material-ui/core"; import CardTitle from "@saleor/components/CardTitle"; import FormSpacer from "@saleor/components/FormSpacer"; import RichTextEditor from "@saleor/components/RichTextEditor"; +import { RichTextEditorLoading } from "@saleor/components/RichTextEditor/RichTextEditorLoading"; import { PageErrorFragment } from "@saleor/graphql"; import { commonMessages } from "@saleor/intl"; import { makeStyles } from "@saleor/macaw-ui"; @@ -64,7 +65,7 @@ const PageInfo: React.FC = props => { onChange={onChange} /> - {isReadyForMount && ( + {isReadyForMount ? ( = props => { })} name={"content" as keyof PageData} /> + ) : ( + )} diff --git a/src/products/components/ProductDetailsForm/ProductDetailsForm.tsx b/src/products/components/ProductDetailsForm/ProductDetailsForm.tsx index 86be69b7b..7600ac46b 100644 --- a/src/products/components/ProductDetailsForm/ProductDetailsForm.tsx +++ b/src/products/components/ProductDetailsForm/ProductDetailsForm.tsx @@ -5,6 +5,7 @@ import FormSpacer from "@saleor/components/FormSpacer"; import Grid from "@saleor/components/Grid"; import Hr from "@saleor/components/Hr"; import RichTextEditor from "@saleor/components/RichTextEditor"; +import { RichTextEditorLoading } from "@saleor/components/RichTextEditor/RichTextEditorLoading"; import { ProductErrorFragment } from "@saleor/graphql"; import { commonMessages } from "@saleor/intl"; import { getFormErrors, getProductErrorMessage } from "@saleor/utils/errors"; @@ -60,7 +61,7 @@ export const ProductDetailsForm: React.FC = ({ onChange={onChange} /> - {isReadyForMount && ( + {isReadyForMount ? ( = ({ label={intl.formatMessage(commonMessages.description)} name="description" /> + ) : ( + )}
diff --git a/src/products/components/ProductUpdatePage/form.tsx b/src/products/components/ProductUpdatePage/form.tsx index 0235eb52e..7c4ceb54e 100644 --- a/src/products/components/ProductUpdatePage/form.tsx +++ b/src/products/components/ProductUpdatePage/form.tsx @@ -281,6 +281,7 @@ function useProductUpdateForm( const stocks = useFormset(getStockInputFromProduct(product)); const richText = useRichText({ initial: product?.description, + loading: !product, triggerChange }); diff --git a/src/shipping/components/ShippingRateInfo/ShippingRateInfo.tsx b/src/shipping/components/ShippingRateInfo/ShippingRateInfo.tsx index c3570a688..9831bf02c 100644 --- a/src/shipping/components/ShippingRateInfo/ShippingRateInfo.tsx +++ b/src/shipping/components/ShippingRateInfo/ShippingRateInfo.tsx @@ -3,6 +3,7 @@ import { Card, CardContent, TextField } from "@material-ui/core"; import CardSpacer from "@saleor/components/CardSpacer"; import CardTitle from "@saleor/components/CardTitle"; import RichTextEditor from "@saleor/components/RichTextEditor"; +import { RichTextEditorLoading } from "@saleor/components/RichTextEditor/RichTextEditorLoading"; import { ShippingErrorFragment } from "@saleor/graphql"; import { commonMessages } from "@saleor/intl"; import { makeStyles } from "@saleor/macaw-ui"; @@ -100,7 +101,7 @@ const ShippingRateInfo: React.FC = props => { onChange={onChange} /> - {isReadyForMount && ( + {isReadyForMount ? ( = props => { label={intl.formatMessage(messages.description)} name="description" /> + ) : ( + )}
diff --git a/src/shipping/components/ShippingZoneRatesPage/ShippingZoneRatesPage.tsx b/src/shipping/components/ShippingZoneRatesPage/ShippingZoneRatesPage.tsx index 0534fa061..28c3d5a03 100644 --- a/src/shipping/components/ShippingZoneRatesPage/ShippingZoneRatesPage.tsx +++ b/src/shipping/components/ShippingZoneRatesPage/ShippingZoneRatesPage.tsx @@ -130,6 +130,7 @@ export const ShippingZoneRatesPage: React.FC = ({ const richText = useRichText({ initial: rate?.description, + loading: !rate, triggerChange }); diff --git a/src/storybook/__snapshots__/Stories.test.ts.snap b/src/storybook/__snapshots__/Stories.test.ts.snap index 76b28c4a6..46e7ed577 100644 --- a/src/storybook/__snapshots__/Stories.test.ts.snap +++ b/src/storybook/__snapshots__/Stories.test.ts.snap @@ -41756,6 +41756,20 @@ exports[`Storyshots Views / Categories / Update category loading 1`] = `
+
+ +

+

+
+ +

+

+
+ +

+

+
+ +

+

@@ -233540,6 +233596,20 @@ exports[`Storyshots Views / Shipping / Shipping rate loading 1`] = `
+
+ +

+

diff --git a/src/translations/components/TranslationFields/TranslationFieldsRich.tsx b/src/translations/components/TranslationFields/TranslationFieldsRich.tsx index c63876b08..a3858a45d 100644 --- a/src/translations/components/TranslationFields/TranslationFieldsRich.tsx +++ b/src/translations/components/TranslationFields/TranslationFieldsRich.tsx @@ -3,6 +3,7 @@ import { Typography } from "@material-ui/core"; import { useExitFormDialog } from "@saleor/components/Form/useExitFormDialog"; import RichTextEditor from "@saleor/components/RichTextEditor"; import RichTextEditorContent from "@saleor/components/RichTextEditor/RichTextEditorContent"; +import { RichTextEditorLoading } from "@saleor/components/RichTextEditor/RichTextEditorLoading"; import { SubmitPromise } from "@saleor/hooks/useForm"; import { ConfirmButtonTransitionState } from "@saleor/macaw-ui"; import useRichText from "@saleor/utils/richText/useRichText"; @@ -51,7 +52,7 @@ const TranslationFieldsRich: React.FC = ({ return edit ? (
- {isReadyForMount && ( + {isReadyForMount ? ( = ({ name="translation" data-test-id="translation-field" /> + ) : ( + )} ({ const getDefaultValue = useCallback( (id: TKey) => { + if (initial[id] === undefined) { + setShouldMountById(id, true); + return ""; + } + try { const result = JSON.parse(initial[id]); setShouldMountById(id, true); diff --git a/src/utils/richText/useRichText.test.ts b/src/utils/richText/useRichText.test.ts index 9ed1ef3d9..aa2e31d7a 100644 --- a/src/utils/richText/useRichText.test.ts +++ b/src/utils/richText/useRichText.test.ts @@ -23,13 +23,15 @@ describe("useRichText", () => { it("properly informs RichTextEditor when data is ready to mount", () => { // eslint-disable-next-line prefer-const let initial: string | undefined; + let loading = true; const { result, rerender } = renderHook(() => - useRichText({ initial, triggerChange }) + useRichText({ initial, loading, triggerChange }) ); expect(result.current.isReadyForMount).toBe(false); initial = JSON.stringify(fixtures.short); // for JSON.parse() + loading = false; rerender(); expect(result.current.defaultValue).toStrictEqual(fixtures.short); @@ -39,13 +41,15 @@ describe("useRichText", () => { it("returns undefined when JSON cannot be parsed", () => { // eslint-disable-next-line prefer-const let initial: string | undefined; + let loading = true; const { result, rerender } = renderHook(() => - useRichText({ initial, triggerChange }) + useRichText({ initial, loading, triggerChange }) ); expect(result.current.isReadyForMount).toBe(false); initial = "this-isnt-valid-json"; + loading = false; rerender(); expect(result.current.defaultValue).toBe(undefined); diff --git a/src/utils/richText/useRichText.ts b/src/utils/richText/useRichText.ts index 0a723544e..cbf225ab2 100644 --- a/src/utils/richText/useRichText.ts +++ b/src/utils/richText/useRichText.ts @@ -4,10 +4,15 @@ import { useMemo, useRef, useState } from "react"; interface UseRichTextOptions { initial: string | null; + loading?: boolean; triggerChange: () => void; } -export function useRichText({ initial, triggerChange }: UseRichTextOptions) { +export function useRichText({ + initial, + loading, + triggerChange +}: UseRichTextOptions) { const editorRef = useRef(null); const [isReadyForMount, setIsReadyForMount] = useState(false); @@ -24,6 +29,15 @@ export function useRichText({ initial, triggerChange }: UseRichTextOptions) { }; const defaultValue = useMemo(() => { + if (loading) { + return; + } + + if (initial === undefined) { + setIsReadyForMount(true); + return ""; + } + try { const result = JSON.parse(initial); setIsReadyForMount(true);