how to import a class in code splitting using import()? - javascript

I cannot find out how to import a class in my React app after using the code splitting.
Before (it works!):
import React, {PureComponent} from 'react';
import Tus from './components/test';
class Shopper extends PureComponent {
constructor (props) {
super(props); }
uploadModal () {
/* some function code... */
.use(Tus, {
endpoint: 'http://192.168.22.124:3000/upload/'
})
/* more codes... */
}
After using code splitting (does not work):
import React, {PureComponent} from 'react';
class Shopper extends PureComponent {
constructor (props) {
super(props); }
uploadModal () {
/* some function code... */
.use(import('./components/test').then(Tus => Tus, {
endpoint: 'http://192.168.22.124:3000/upload/'
})
/* more codes... */
}
I am getting this error after using code split
TypeError: Expected a plugin class, but got object. Please verify that
the plugin was imported and spelled correctly.
When I console.log
import('./component/test').then(Tus => console.log(Tus))
I get this:
ƒ Tus(uppy, opts) {
_classCallCheck(this, Tus);
var _this = _possibleConstructorReturn(this, _Plugin.call(this, uppy, opts));
_this.type = 'uploader';
_this.id = 'Tus';
_this.titl…

It seems that on your working example (before code split), you're importing the default export from `'./components/test'.
After you dynamically import to allow code-splitting, you should use Tus.default to achieve the same result. You can read more about it on webpack code splitting documentation.
In other words, import('./component/test').then(Tus => Tus.default)
I hope this helps! Cheers!

You can aslo use react-loadable it provides you loading component fallback:
function Loading() {
return <div>Loading...</div>;
}
const Test= Loadable({
loader: () => import('./components/test'),
loading: Loading,
});
In your route:
<Route exact path="/" component={Test} />
You should have installed:
in your package.json:
"#babel/plugin-syntax-dynamic-import": "7.0.0-beta.54",
in .babelrc
"plugins": [
"#babel/plugin-syntax-dynamic-import",]
It works great.

Related

Webpack loader for .md file import for "react-markdown" npm library?

When i import a .md file , it gave me error, saying that it cannot read this particular .md file syntax,
I know there needs to be some kind of loader for it to parse the import, but when i looked online there was a loader called 'markdown-loader' which was only for marked npm package.
I am using react-markdown package to read md files
/* eslint-disable react/prefer-stateless-function */
import React, { Component } from 'react';
import ReactMarkdown from 'react-markdown';
import AppMarkdown from './posts/sample.md';
// import PropTypes from 'prop-types';
class CardDetails extends Component {
constructor() {
super();
this.state = { markdown: '' };
}
componentDidMount() {
// Get the contents from the Markdown file and put them in the React state, so we can reference it in render() below.
fetch(AppMarkdown)
.then(res => res.text())
.then(text => this.setState({ markdown: text }));
}
render() {
const { markdown } = this.state;
return <ReactMarkdown source={markdown} />;
}
}
CardDetails.propTypes = {};
export default CardDetails;
here's my markdown content sample.md
# React & Markdown App
- Benefits of using React... but...
- Write layout in Markdown!
i could not find package , i looked everywhere, do you know about the loader ?
Thankyou
Try to use raw-loader:
module.exports = {
module: {
rules: [
{
test: /\.md$/,
use: 'raw-loader'
}
]
}
}

Imports not finding modules and namespaces with react-monaco-editor in typescript files in Electron

I am trying to use the react-monaco-editor npm package component to import the monaco editor into my react application. These are the version of the packages I downloaded from npm:
"react-monaco-editor": "^0.13.0",
"#types/react-monaco-editor": "^0.10.0"
Everything seems to be working great (Less, html, javascript and even doing requires in javascript), except I am getting syntax errors saying that I can't find modules I am importing or namespaces (such as Electron). This is an example error of one of the typescript files trying to import a module and also the error for not being able to find the Electron namespace.
This is the same code in VS Code with their usage of the monaco editor:
This is the example of the code I am using where I am referencing the MonacoEditor component.
import React, { Component } from 'react';
import ReactDOM from 'react-dom';
import { connect } from 'react-redux';
import MonacoEditor from 'react-monaco-editor';
import { IEditorFile, IEditorFilePassedProps, IEditorFileReduxProps } from './editor-file-interfaces';
import { IReduxState } from '../../shared/interfaces/redux-state';
import './editor-file.less';
class EditorFile extends Component<IEditorFile, any> {
editor = null;
constructor(props: IEditorFile) {
super(props);
this.state = {
code: this.props.file.content
};
}
componentWillReceiveProps(nextProps: any) {
if (typeof nextProps.file !== undefined) {
this.setState({ code: nextProps.file.content });
}
}
render() {
const code = this.state.code;
const options = {
selectOnLineNumbers: true,
roundedSelection: false,
readOnly: false,
cursorStyle: 'line',
automaticLayout: false
};
return (
<div>
<div className='file-content-container'>
<MonacoEditor
language={this.props.file.fileType}
value={code}
theme='vs-dark'
options={options}
/>
</div>
</div>
);
}
}
const mapStateToProps = (state: IReduxState): IEditorFileReduxProps => {
return {
fileExplorerInfo: state.fileExplorer
};
};
export default connect<IEditorFileReduxProps, null, IEditorFilePassedProps, IReduxState>(mapStateToProps)(EditorFile);
The language that is being passed into the MonacoEditor component is "typescript" for the tsx/ts files. I am not sure how to go about this so any help is greatly appreciated!

Flow is not catching type errors for an imported component

I have a simple component ErrorBoundary that is used in another component. Both components are checked by flow (i.e. they have the /* #flow */ flag). But flow is not catching an error if I misuse ErrorBoundary by not providing the correct props. Here's ErrorBoundary:
/* #flow */
import * as React from 'react';
type Props = {
children: React.Node,
ErrorComponent: React.ComponentType<any>,
};
type State = {
hasError: boolean,
};
class ErrorBoundary extends React.Component<Props, State> {
constructor(props: Props) {
super(props);
this.state = { hasError: false };
}
componentDidCatch(error: Error, info: string) {
console.log(error, info); // eslint-disable-line
this.setState({ hasError: true });
}
render() {
const { ErrorComponent } = this.props;
if (this.state.hasError) {
return <ErrorComponent />;
}
return this.props.children;
}
}
export default ErrorBoundary;
And here it is being misused:
/* #flow */
import * as React from 'react';
import ErrorBoundary from '/path/to/ErrorBoundary';
type Props = {};
class SomeComponent extends React.Component<Props> {
render() {
return (
<ErrorBoundary>
{..some markup}
</ErrorBoundary>
)
}
}
Despite the fact that I've not provided the necessary component ErrorComponent to ErrorBoundary, when I run flow it reports "No Errors!". If, however, I were to import a typed function from the same file, it works. Or if I were to try to use ErrorBoundary incorrectly inside its own module file, flow also catches the error.
The problem seems to have something to do with importing React components that have been typed using flow specifically. Does anyone know what I might be doing wrong?
The problem was that my import happens through a intermediary index.js file in the same directory as ErrorBoundary. That index.js file had not been marked with the // #flow tag. Once I added it, the type checking worked correctly.

MobX + React Native : way to inject stores

I'm trying to work with MobX for a new project.
I started it on May 2017, and everything was working well. I had to stop, and now I go on developing it. I had to make an npm install to manage making it working, but now, I have some problem with stores...
I rely on this tutorial for the structure : https://blog.callstack.io/write-react-native-apps-in-2017-style-with-mobx-e2dffc209fcb
This is my structure :
Main index.js
import { Provider } from 'mobx-react';
import Stack from './router';
import stores from './stores';
export default class App extends Component {
render() {
return (
<Provider {...stores}>
<Stack />
</Provider>
);
}
}
Index.js of my stores in ./stores/index.js
import ChatStore from './ChatStore';
import UserStore from './UserStore';
export default {
UserStore: new UserStore(),
ChatStore: new ChatStore(),
};
./stores/UserStore.js (important parts)
import { observer, inject } from 'mobx-react';
import {autobind} from 'core-decorators';
...
#inject(['ChatStore'])
#observer
#autobind
export default class UserStore {
#observable isAuthenticated = false;
#observable isConnecting = false;
#observable user = null;
#observable messages = [];
#observable hasMoreMessages = false;
#observable skip = 0;
...
login() {
const payload = {
strategy: 'local',
material_id: DeviceInfo.getManufacturer(),
password: DeviceInfo.getManufacturer()
};
return this.authenticate(payload);
}
...
Now, for components part :
Router.js
import { StackNavigator } from 'react-navigation';
import Home from './containers/Home';
const stackNavigatorConfig = {
initialRouteName: 'Home',
};
export default StackNavigator({
Home: {
screen: Home,
},
}, stackNavigatorConfig);
./containers/Home.js
import React, { Component } from 'react';
import { AsyncStorage } from 'react-native';
import { observable } from 'mobx';
import { observer, inject } from 'mobx-react';
#inject('UserStore')
#observer
export default class Home extends Component {
props: Props;
...
render() {
this.props.UserStore.login().catch(error => {
console.log('LOGIN', 'ERROR', JSON.stringify(error), error.message);
});
return {
...
}
}
And then, I get an error :
So, I sum up :
I use <Provider> from MobX, to give all my stores to my app
Then, I get the Store I want in my component with #inject
I use it as a props, using this.props.UserStore...
But it does not work. I rely on this tutorial for the structure : https://blog.callstack.io/write-react-native-apps-in-2017-style-with-mobx-e2dffc209fcb
Maybe there was an update between May 2017 and today, that makes things different... It was working well on May 2017.
I think this is a dummy error, but I can't find which one...
Everything looks good except the decorators on your UserStore class: #inject(['ChatStore']) #observer #autobind. #inject(['ChatStore']) #observer is used on React components, #autobind might still work as intended.
It should work if you remove those.
maybe worth using #action from mobx

Webpack module source code

I need to save the code of a es6 code module and dump it.
So ideally what I would need is something like:
import React, {PropTypes} from 'react';
// this function get the source code of the
// module I am running in
function getMyModuleSourceCode = {
...
}
class DemoComponent extends React.Component {
render() {
const myCode = getMyModuleSourceCode();
processMySourceCode(myCode);
}
}
If the module is in a different file, you can import twice, once normally to run code, once with the raw-loader to just pull in the file verbatim.
import module from './module'; //compiled code
import moduleSource from '!!raw!./module'; //source as text
The !! is necessary to override the existing loaders if you are just testing for .js extensions.
You could use the file-loader in webpack and then require whatever file you need in your function:
import React, {PropTypes} from 'react';
// this function get the source code of the
// module I am running in
function getMyModuleSourceCode = {
return require('!!file!./path/to/module.js');
}
class DemoComponent extends React.Component {
render() {
const myCode = getMyModuleSourceCode();
processMySourceCode(myCode);
}
}

Categories