2
1
Fork 0
mirror of https://github.com/TryGhost/Ghost.git synced 2023-12-13 21:00:40 +01:00

Switched to dynamically loaded external react-mobiledoc-editor package

no issue

- dropped the bundled `react-mobiledoc-editor` package
- updated `<ReactMobiledocEditor>` component to pull in editor components dynamically
  - added a resource function to dynamically import the external module
  - added `Container` and `Editor` components that read from the resource function and wrap components of the same name from the external module
  - added `<Suspense>` around the `Container` and `Editor` components so that React will show a loading state whilst the external components are still being fetched
  - added `<ErrorHandler>` so we can show an error state if loading fails
This commit is contained in:
Kevin Ansfield 2022-07-19 11:34:26 +01:00
parent d991da399c
commit 896cd4888f
5 changed files with 97 additions and 17 deletions

View file

@ -1,12 +1,85 @@
import React from 'react';
import {Container, Editor} from 'react-mobiledoc-editor';
import React, {Suspense} from 'react';
class ErrorHandler extends React.Component {
state = {
hasError: false
};
static getDerivedStateFromError() {
return {hasError: true};
}
export default class ReactMobiledocEditor extends React.Component {
render() {
return (<Container
mobiledoc={this.props.mobiledoc}
>
<Editor />
</Container>);
if (this.state.hasError) {
return (
<p>Loading has failed. Try refreshing the browser!</p>
);
}
return this.props.children;
}
}
const fetchMobiledocEditor = function () {
let status = 'pending';
let response;
const fetchPackage = async () => {
if (window.ReactMobiledocEditor) {
return window.ReactMobiledocEditor;
}
await import('https://unpkg.com/kevinansfield-react-mobiledoc-editor@~0.13.2/dist/main.js');
return window.ReactMobiledocEditor;
};
const suspender = fetchPackage().then(
(res) => {
status = 'success';
response = res;
},
(err) => {
status = 'error';
response = err;
}
);
const read = () => {
switch (status) {
case 'pending':
throw suspender;
case 'error':
throw response;
default:
return response;
}
};
return {read};
};
const editorResource = fetchMobiledocEditor();
const Container = (props) => {
const MobiledocEditor = editorResource.read();
return <MobiledocEditor.Container {...props} />;
};
const Editor = (props) => {
const MobiledocEditor = editorResource.read();
return <MobiledocEditor.Editor {...props} />;
};
export default function ReactMobiledocEditorComponent(props) {
return (
<ErrorHandler>
<Suspense fallback={<p>Loading editor...</p>}>
<Container
mobiledoc={props.mobiledoc}
>
<Editor />
</Container>
</Suspense>
</ErrorHandler>
);
}

View file

@ -278,6 +278,9 @@ module.exports = function (defaults) {
// support `import React from 'react'`
app.import('vendor/shims/react.js');
app.import('vendor/shims/react-dom.js');
// required dependency for dynamically fetched react-mobiledoc-editor
app.import('node_modules/prop-types/prop-types.min.js');
app.import('vendor/shims/prop-types.js');
return app.toTree();
};

View file

@ -150,7 +150,6 @@
"pretender": "3.4.7",
"react": "^18.2.0",
"react-dom": "^18.2.0",
"react-mobiledoc-editor": "^0.13.1",
"reframe.js": "3.0.3",
"simplemde": "https://github.com/kevinansfield/simplemde-markdown-editor.git#ghost",
"testem": "3.7.0",

12
ghost/admin/vendor/shims/prop-types.js vendored Normal file
View file

@ -0,0 +1,12 @@
(function() {
function vendorModule() {
'use strict';
return {
'default': self['prop-types'],
__esModule: true,
};
}
define('prop-types', [], vendorModule);
})();

View file

@ -13469,7 +13469,7 @@ promise.hash.helper@^1.0.7:
resolved "https://registry.yarnpkg.com/promise.hash.helper/-/promise.hash.helper-1.0.8.tgz#8c5fa0570f6f96821f52364fd72292b2c5a114f7"
integrity sha512-KYcnXctWUWyVD3W3Ye0ZDuA1N8Szrh85cVCxpG6xYrOk/0CttRtYCmU30nWsUch0NuExQQ63QXvzRE6FLimZmg==
prop-types@^15.7.2, prop-types@^15.8.1:
prop-types@^15.8.1:
version "15.8.1"
resolved "https://registry.yarnpkg.com/prop-types/-/prop-types-15.8.1.tgz#67d87bf1a694f48435cf332c24af10214a3140b5"
integrity sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==
@ -13666,13 +13666,6 @@ react-is@^16.13.1:
resolved "https://registry.yarnpkg.com/react-is/-/react-is-16.13.1.tgz#789729a4dc36de2999dc156dd6c1d9c18cea56a4"
integrity sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==
react-mobiledoc-editor@^0.13.1:
version "0.13.1"
resolved "https://registry.yarnpkg.com/react-mobiledoc-editor/-/react-mobiledoc-editor-0.13.1.tgz#cc5f06b835efd6ba7b0e9e7b82ddcbd7b02aad9b"
integrity sha512-3H2tiTiykBjV7SmVkb+1slAtAJJygG7JD+NRNV/9wUHEDRdoOlcxCRd8BpXoFoJOrxIpaKCaQ7gWFHPWcIpldg==
dependencies:
prop-types "^15.7.2"
react@^18.2.0:
version "18.2.0"
resolved "https://registry.yarnpkg.com/react/-/react-18.2.0.tgz#555bd98592883255fa00de14f1151a917b5d77d5"