Modo scripts.
npm install modo-scriptsmodo-scripts is a toolkit for the Modo Material Project that encapsulates functionality for building, testing, automating documentation, and more.
``bash``
npm install modo-scripts -D
modo-scripts organizes the default configuration internally, but allows users to extend it through configuration files. The configuration file is located in the .config directory of the project root directory and has the following structure:
``text``
.config
├── babel.config.js (configure Babel)
├── docgen.config.js (configure automatic document generation)
├── jest.config.js (configured unit tests)
├── style.config.js (configuration style, static resource construction)
└── webpack.config.js (configuration project UMD product build)
Almost all configuration files follow the form:
``js``
/**
* @param config Default config in modo-scripts
*/
module.exports = (config) => {
// You can directly modify the config object
config.xxx = true;
config.plugins.push('xxx');
// or return a new object as the configuration to use
return {
xxx: true,
plugins: ['xxx'],
};
};
Since unit tests are divided into client tests and node tests, the configuration form of .config/jest.config.js is slightly different:
``javascript
// .config/jest.config.js
module.exports = {
client: (config) => {
// Return a new config or modify default config directly
},
node: (config) => {
// Return a new config or modify default config directly
},
};
``
For the default values and parameter descriptions of each configuration, please refer to: https://github.com/arco-design/arco-cli/tree/main/packages/modo-scripts/src/config.
modo-scripts divides the construction of JS files and style files (such as less) into two parts, and observing the directory structure of the product will help us understand the whole process of construction. The build products include three module types: ESModule, CommonJS, and UMD, which correspond to files in the /es, /lib, and /dist directories respectively.
* ESModule (CommonJS and ESModule product directory structure is the same, no additional description)
``text``
es/Button
├── index.js (compiled product conforming to ESModule specification)
├── index.d.ts (TS type file)
└── style
├── css.js (used for on-demand loading of styles, the file content is similar: import './index.css')
├── index.js (for style on-demand loading, the file content is similar: import './index.less')
├── index.css (the style product of the current component)
└── index.less (original style file, .less or .sass)
* UMD
``text``
dist
├── index.min.js (compiled product conforming to UMD specification)
└── css
├── index.css (aggregates the style products of all components)
└── index.less (original style file that aggregates all components, .less or .sass)
#### ESM/CJS
ESM/CJS artifacts are compiled with tsc by default, which means that only .ts(x) and .js( x) file type. If you need to do more compilation with Babel, you can tell modo-scripts to compile with Babel via the Node Env parameter.
`bash``
BUILD_ENV_TS_COMPILER=babel modo-scripts build:component
By default, due to the use of tsc for source code compilation, only the configuration in tsconfig.json takes effect, and the build process cannot be changed by modifying the Babel configuration. Babel configuration can only be extended via the .config/babel.config.js file after you have set up to build with Babel.
#### UMD
UMD artifacts are built with Webpack, but only include JS artifacts (styles and static resource files are handled by Gulp). You can extend your Webpack configuration via the .config/webpack.config.js file.
modo-scripts style builds and static resources are streamed with gulp, extending the default configuration by extending .config/style.config.js. E.g:
* Use sass
``javascript
// .config/style.config.js
const sass = require('gulp-sass')(require('sass'));
module.exports = (config) => {
config.css.entry = ['src/**/index.sass'];
config.css.watch.push('src/*/.sass');
config.css.compiler = sass;
config.css.compilerOptions = { /* Sass compiler options / };
};
``
* use hook
``javascript
// .config/style.config.js
const cssnano = require('cssnano');
const postcss = require('gulp-postcss');
const through = require('through2');
module.exports = (config) => {
const postcssPlugins = [
autoprefixer({browsers: ['last 1 version']}),
cssnano()
];
config.hook.beforeCompile = () => through.obj((file, _, cb) => {
file.contents = Buffer.from(/* Modify file contents before compile /)
cb(null, file);
});
// Pass in postcss params by bind()``
config.hook.afterCompile = postcss.bind(null, postcssPlugins, { /* Postcss options / });
};
The material documentation consists of two areas: component props parameters and sample code. With modo-scripts, a complete material documentation can be generated automatically. First, the /src directory structure of the material is as follows:
````
src
├── TEMPLATE.md
├── demo
│ └── basic.jsx
├── index.tsx
└── style
You need to pay attention to TEMPLATE.md and demo. In projects using TypeScript, modo-scripts can quickly generate component interface documentation by extracting comment content. TEMPLATE.md Template generated for documentation. Its contents are as follows:
``markdown
---
file: index
---
%%Props%%
##Demos
%%Demos%%
``
Where %%Props%% will be filled in the Props parameter of the component after the docgen command, and %%Demos%% will be filled with the demo code in /src/demo. The final generated document is as follows:
``markdownTooltipButton
| parameter name | description | type | default value |
| ------ | :------------: | :---------: | -----: |
| title | button hint | ReactNode | - |
##Demos
~~~jsx
import React from 'react';
import TooltipButton from '@arco-design/rc-xxx';
/**
* Basic usage
*/
export default () => {
return
};
~~~
``
The docgen command generates documentation by parsing the comments in the TypeScript interface, so you need to write comments for the interface in the form of TSDoc.
Since 1.23.0 modo-scripts provides two optional low-level tools (ts-document, [react-docgen] -typescript](https://www.npmjs.com/package/react-docgen-typescript)) is used for TS parsing. These two tools correspond to two different annotation writing methods. You can specify tools by modifying .config/docgen.config.js in the project root directory:
``javascript``
// .config/docgen.config.js
module.exports = (config) => {
// ...
// ['react-docgen-typescript'] is default
config.tsParseTool = ['ts-document']
}
We recommended to use ts-document, which is an Modo self-developed tool with better syntax compatibility and dual language support. As you read this document, all newly created material items already use ts-document for API parameter extraction by default.
Write comments in the following way, all interface or type declarations with @title will be extracted. Property annotations have the following tags available:
- Chinese description of the @zh attribute@en
- English description of the attribute (optional)@defaultValue
- the default value of the attribute (optional)@version
- The version from which the property was added (optional)
When @zh or @en is missing, the content in /* Some comment / will be extracted as the attribute description.
` typescripttitle
/**
* @title Button (required, only interfaces or types described by will be collected)
*/
interfaceButtonProps {
/**
* @zh button size (Chinese description of attribute)
* @en Size of Button (optional, the English description of the property)
* @version 1.2.0 (optional, in which version the new properties are supported)
* @defaultValue 'default' (optional, the default value of the property)
*/
size?: 'mini' | 'small' | 'default' | 'large';
/**
* @zh button state
* @en Status of Button
*/
status?: 'danger' | 'error' | 'success';
}
``
To generate bilingual documentation, configure docgen.config.js as follows:
``javascript
// .config/docgen.config.js
module.exports = (config) => {
config.tsParseTool = ['ts-document'];
config.languages = ['zh-CN', 'en-US'];
// Need to prepare two files TEMPLATE.zh-CN.md and TEMPLATE.en-US.md respectively
config.template = 'TEMPLATE.[language].md';
// You can also share the same template file in both Chinese and English (default value)
// config.template = 'TEMPLATE.md';
// Will output README.zh-CN.md and README.en-US.md two files
config.outputFileName = 'README.[language].md';
}
``
When writing comments in the following way, you need to pay attention to the following aspects:
- Comments must be written in the form of TSDoc (single-line comments in the form // cannot be extracted)
- Components that need to be extracted documents must be additionally exported in the form of export const Component = (props: ComponentProps) => {}, otherwise they will not be recognized by the tool;Component.defaultProps = {}
- Default values must be written in the form to be picked up by tools.
- If you encounter other problems, please refer to the react-docgen-typescript repository.
`typescript
interface ButtonProps {
/**
* button size
*/
size?: 'mini' | 'small' | 'default' | 'large';
/**
* button state
*/
status?: 'danger' | 'error' | 'success';
}
// Button needs to be declared as const and exported, otherwise the tool may not recognize it
export const Button = (props: ButtonProps) => {
// ...
};
// Only default values declared with defaultProps can be picked up by the tool
Button.defaultProps = {
size: 'default',
};
export default Button;
``
The test function encapsulated by modo-scripts is completely inherited from Jest, and the default configuration can be extended by modifying .config/jest.config.js. At the same time, both modo-scripts test:client and modo-scripts test:node commands can pass Jest CLI parameters in full.
`bash```Pass Jest CLI parameters
modo-scripts test:clent --watch