@dr.pogodin/react-utils
Version:
Collection of generic ReactJS components and utils
137 lines (136 loc) • 6.88 kB
TypeScript
import nodeFs from 'node:fs';
import { type Configuration, type RuleSetRule } from 'webpack';
export type BuildInfoT = {
key: string;
publicPath: string;
timestamp: string;
useServiceWorker: boolean;
};
export type OptionsT = {
babelEnv: string;
babelLoaderExclude?: RuleSetRule['exclude'];
babelLoaderOptions?: object;
context: string;
cssLocalIdent?: string;
dontEmitBuildInfo?: boolean;
dontUseProgressPlugin?: boolean;
entry: string | string[];
fs?: typeof nodeFs;
keepBuildInfo?: boolean | BuildInfoT;
mode: 'development' | 'none' | 'production';
outputPath?: string;
publicPath?: string;
sitemap?: string;
typescript?: boolean;
workbox?: boolean | object;
};
/**
* Creates a new Webpack config object, and performs some auxiliary operations
* on the way.
* @param {object} ops Configuration params. This allows to modify some
* frequently changed options in a convenient way, without a need to manipulate
* directly with the created config object.
* @param {string} ops.babelEnv Babel environment to use for the Babel
* compilation step.
* @param [ops.babelLoaderExclude] Overrides the default value of `exclude`
* option of babel-loader, which is [/node_modules/].
* @param {object} [ops.babelLoaderOptions] Overrides for default Babel options
* of JSX and SVG files loader.
* @param ops.context Base URL for resolution of relative config paths.
* @param {string} [ops.cssLocalIdent=hash:base64:6] The template for
* CSS classnames generation by the Webpack's `css-loader`; it is passed into
* the `localIdentName` param of the loader. It should match the corresponding
* setting in the Babel config.
* @param {boolean} [ops.dontEmitBuildInfo] If set the `.build-info` file won't
* be created at the disk during the compilation.
* @param [ops.dontUseProgressPlugin] Set to not include progress
* plugin.
* @param {string|string[]} ops.entry Entry points for "main" chunk. The config
* will prepend them by some necessary polyfills, e.g.:
* ([babel-polyfill](https://babeljs.io/docs/usage/polyfill/),
* [nodelist-foreach-polyfill](https://www.npmjs.com/package/nodelist-foreach-polyfill)).
* @param {boolean|object} ops.workbox If evaluates to a truthy value,
* [Workbox's InjectManifest plugin](https://developers.google.com/web/tools/workbox/modules/workbox-webpack-plugin#injectmanifest_plugin)
* is added to the array of Webpack plugins, to generate service worker for
* browser. If the value is an object, it is merged into the options passed
* into the plugin, otherwise default options are used:
* ```json
* {
* "importWorkboxFrom": "local",
* "swSrc": "@dr.pogodin/react-utils/config/workbox/default.js",
* "swDest": "__service-worker.js"
* }
* ```
* If service worker is generated by this option, it will be automatically
* initiated at the client side by the standard
* [client-side initialization script](docs/client.md)
* provided by **@dr.pogodin/react-utils**. Note that `swDest`'s value cannot be
* overriden by config options provided via `workbox` object.
* @param {object} [ops.fs] Filesystem to use instead of the Node's FS.
* @param {boolean|object} [ops.keepBuildInfo] If `true` and a `.build-info`
* file from a previous build exists in the context directory, it will be
* loaded and used, rather than re-generated by the config factory. It allows
* to re-create the Webpack config during a server launch without re-generation
* of the build info file created during a previous build (and thus bundled
* into the frontend bundle). If an object is provided, it will be used as
* the build info, instead of trying to load it from the filesystem. This
* feature is intended for testing context.
* @param {string} ops.mode
* [Webpack mode](https://webpack.js.org/concepts/mode/).
* @param {string} [ops.outputPath=build] Optional. Output path for the build.
* @param {string} ops.publicPath Base URL for the output of the build assets.
* @param {string} [ops.sitemap] The path to JS or JSON config for sitemap.
* It can be relative to the context, and can be a factory, which returns
* the config. The config should be compatible with
* [`sitemap`](https://www.npmjs.com/package/sitemap) library, and if
* provided the Webpack config factory will use it to gererate `sitemap.xml`
* file in the output folder, and then serve it from the app root.
* @return The generated config will opt to:
* - Bundle the font assets (EOF, OTF, TTF, WOFF, WOFF2 files from
* the `src/assets/fonts` folder of your source code will be bundled
* and output into the `[PUBLIC_PATH]/fonts` folder);
* - Bundle image assets (GIF, JPEG, JPG, PNG files from any folder of
* your source code will be bundled and output into the
* `[PUBLIC_PATH]/images` folder);
* - Bundle SCSS files from any folder of your source code, beside
* `node_modules` and its subfolders. The files will be compiled,
* bundled and extracted into the `[PUBLIC_PATH]/[CHUNK_NAME].css`
* bundles;
* - Bundle CSS files from any folder of your code. The files will be
* bundled and extracted into the `[PUBLIC_PATH]/[CHUNK_NAME].css`
* bundles;
* - Bundle JS, JSX, and SVG files; they will be compiled into the
* `[PUBLIC_PATH]/[CHUNK_NAME].js` bundles, using the Babel environment
* specified in the factory options, and
* [`config/babel/webpack`](./babel-config.js#webpack) config.
*
* - The following path aliases will be automatically set:
* - **`assets`** for `[CONTEXT]/src/assets`;
* - **`components`** for `[CONTEXT]/src/shared/components`;
* - **`fonts`** for `[CONTEXT]/src/assets/fonts`;
* - **`styles`** for `[CONTEXT]/src/styles`.
*
* Also `resolve.symlinks` Webpack option is set to *false* to avoid problems
* with resolution of assets from packages linked with `npm link`.
*
* - The following global variables will be emulated inside the output
* JS bundle:
* - **`BUILD_RNDKEY`** — A random 32 bit key that can be used
* for encryption, it is set just as a global variable accessible in
* the code;
* - **`BUILD_TIMESTAMP`** — UTC timestamp of the beginning of
* the build;
* - **`FRONT_END`** — It will be set *true* inside the bundle,
* so that shared code can use it to determine that it is executed
* at the client side.
*
* - It also opts to polyfill the `__dirname` global variable,
* and to ignore imports of the `fs` Node package;
*
* - Also, it will store to the disk (re-writes if exists) the file
* `[CONTEXT]/.build-info` which will contain a stringified JSON
* object with the following fields:
* - **`rndkey`** — The value set for `BUILD_RNDKEY`;
* - **`timestamp`** — The value set for `BUILD_TIMESTAMP`.
*/
export default function configFactory(ops: OptionsT): Configuration;