Gathering detailed insights and metrics for unified-engine
Gathering detailed insights and metrics for unified-engine
Gathering detailed insights and metrics for unified-engine
Gathering detailed insights and metrics for unified-engine
unified-args
create CLIs for unified processors
unified-engine-gulp
unified engine to create a Gulp plugin from a processor
unified-engine-atom
Deprecated. [Atom is archived](https://github.blog/2022-06-08-sunsetting-atom/).
@unifiedts/engine
Engine to process multiple files with unified
npm install unified-engine
Typescript
Module System
Node Version
NPM Version
JavaScript (100%)
Total Downloads
0
Last Day
0
Last Week
0
Last Month
0
Last Year
0
MIT License
61 Stars
298 Commits
24 Forks
9 Watchers
3 Branches
19 Contributors
Updated on Jul 08, 2025
Latest Version
11.2.2
Package Id
unified-engine@11.2.2
Unpacked Size
170.16 kB
Size
39.90 kB
File Count
72
NPM Version
10.9.0
Node Version
22.7.0
Published on
Oct 31, 2024
Cumulative downloads
Total Downloads
Last Day
0%
NaN
Compared to previous day
Last Week
0%
NaN
Compared to previous week
Last Month
0%
NaN
Compared to previous month
Last Year
0%
NaN
Compared to previous year
21
unified engine to process multiple files, lettings users configure from the file system.
options.alwaysStringify
options.configTransform
options.defaultConfig
options.detectConfig
options.detectIgnore
options.extensions
options.filePath
options.files
options.frail
options.ignoreName
options.ignorePath
options.ignorePathResolveFrom
options.ignorePatterns
options.ignoreUnconfigured
options.inspect
options.out
options.output
options.packageField
options.pluginPrefix
options.plugins
options.processor
options.quiet
options.rcName
options.rcPath
options.reporter
and options.reporterOptions
options.settings
options.silent
options.streamError
options.streamIn
options.streamOut
options.tree
options.treeIn
options.treeOut
This package is the engine.
It’s what you use underneath when you use remark-cli
or a
language server.
Compared to unified, this deals with multiple files, often from the file
system, and with configuration files and
ignore files.
You typically use something that wraps this, such as:
unified-args
— create CLIsunified-engine-gulp
— create Gulp pluginsunified-language-server
— create language serversYou can use this to make such things.
This package is ESM only. In Node.js (version 16+), install with npm:
1npm install unified-engine
The following example processes all files in the current folder with a
markdown extension with remark, allows configuration
from .remarkrc
and package.json
files, ignoring files from .remarkignore
files, and more.
1/** 2 * @import {Callback} from 'unified-engine' 3 */ 4 5import process from 'node:process' 6import {remark} from 'remark' 7import {engine} from 'unified-engine' 8 9engine( 10 { 11 color: true, 12 extensions: ['md', 'markdown', 'mkd', 'mkdn', 'mkdown'], 13 files: ['.'], 14 ignoreName: '.remarkignore', 15 packageField: 'remarkConfig', 16 pluginPrefix: 'remark', 17 processor: remark, 18 rcName: '.remarkrc' 19 }, 20 done 21) 22 23/** @type {Callback} */ 24function done(error, code) { 25 if (error) throw error 26 process.exitCode = code 27}
This package exports the identifiers Configuration
and
engine
.
There is no default export.
engine(options, callback)
Process.
Nothing (undefined
).
Configuration
Internal class to load configuration files.
Exposed to build more complex integrations.
options
(subset of Options
, required)
— configuration (cwd
is required)load(string, (Error?[, ConfigResult?]): undefined): undefined
— get the config for a fileCompleter
Completer (TypeScript type).
1type Completer = (CompleterCallback | CompleterRegular) & { 2 pluginId?: string | symbol | undefined 3} 4 5type CompleterCallback = (set: FileSet, next: CompleterCallbackNext) => undefined 6type CompleterCallbackNext = (error?: Error | null | undefined) => undefined 7type CompleterRegular = (set: FileSet) => Promise<undefined> | undefined
Callback
Callback called when done (TypeScript type).
Called with a fatal error if things went horribly wrong (probably due to incorrect configuration), or a status code and the processing context.
error
(Error
, optional)
— errorcode
(0
or 1
, optional)
— exit code, 0
if successful or 1
if unsuccessfulcontext
(Context
, optional)
— processing contextNothing (undefined
).
ConfigResult
Resolved configuration from Configuration
(TypeScript
type).
filePath
(string
)
— file path of found configurationplugins
(Array<PluginTuple>
from unified
)
— resolved pluginssettings
(Settings
from unified
)
— resolved settingsConfigTransform
Transform arbitrary configs to our format (TypeScript type).
config
(unknown
)
— arbitrary configfilePath
(string
)
— file path of config fileOur config format (Preset
).
Context
Processing context (TypeScript type).
fileSet
(FileSet
)
— internally used infofiles
(Array<VFile>
)
— processed filesFileSet
A FileSet is created to process multiple files through unified processors (TypeScript type).
This set, containing all files, is exposed to plugins as the second parameter.
None.
valueOf(): Array<VFile>
— get files in a setuse(completer: Completer): this
— add middleware to be called when done (see: Completer
)add(file: VFile | string): this
— add a file; the given file is processed like other files with a few
differences: it’s ignored when their file path is already added, never
written to the file system or streamOut
, and not included in the reportOptions
Configuration (TypeScript type).
👉 Note:
options.processor
is required.
alwaysStringify
(boolean
, default: false
)
— whether to always serialize successfully processed filescolor
(boolean
, default: false
)
— whether to report with ANSI color sequences; given to the reporterconfigTransform
(ConfigTransform
, optional)
— transform config files from a different schemacwd
(URL
or string
, default: process.cwd()
)
— folder to search files in, load plugins from, and moredefaultConfig
(Preset
, optional)
— default configuration to use if no config file is given or founddetectConfig
(boolean
, default: true
if options.packageField
or
options.rcName
)
— whether to search for configuration filesdetectIgnore
(boolean
, default: true
if options.ignoreName
)
— whether to search for ignore filesextensions
(Array<string>
, optional)
— search for files with these extensions, when folders are passed;
generated files are also given the first extension if treeIn
is on and
output
is on or points to a folderfilePath
(URL
or string
, optional)
— file path to process the given file on streamIn
asfiles
(Array<URL | VFile | string>
, optional)
— paths or globs to files and folder, or virtual files, to
processfrail
(boolean
, default: false
)
— call back with an unsuccessful (1
) code on warnings as well as errorsignoreName
(string
, optional)
— name of ignore files to loadignorePath
(URL
or string
, optional)
— filepath to an ignore file to loadignorePathResolveFrom
(ResolveFrom
, default:
'dir'
)
— resolve patterns in ignorePath
from the current working folder
('cwd'
) or the ignore file’s folder ('dir'
)ignorePatterns
(optional)
— patterns to ignore in addition to ignore filesignoreUnconfigured
(boolean
, default: false
)
— ignore files that do not have an associated detected configuration file;
either rcName
or packageField
must be defined too; cannot be combined
with rcPath
or detectConfig: false
inspect
(boolean
, default: false
)
— whether to output a formatted syntax tree for debuggingout
(boolean
, default: false
)
— whether to write the processed file to streamOut
output
(URL
, boolean
or string
, default: false
)
— whether to write successfully processed files, and where to; when true
,
overwrites the given files, when false
, does not write to the file system;
when pointing to an existing folder, files are written to that folder and
keep their original basenames; when the parent folder of the given path
exists and one file is processed, the file is written to the given pathpackageField
(string
, optional)
— field where configuration can be found in package.json
filespluginPrefix
(string
, optional)
— prefix to use when searching for pluginsplugins
(Preset['plugins']
, optional)
— plugins to useprocessor
(Processor
, required)
— unified processor to transform filesquiet
(boolean
, default: false
)
— do not report successful files; given to the reporterrcName
(string
, optional)
— name of configuration files to loadrcPath
(URL
or string
, optional)
— filepath to a configuration file to loadreporter
(VFileReporter
or string
, default:
vfile-reporter
)
— reporter to use; if a string
is passed, it’s loaded from cwd
, and
'vfile-reporter-'
can be omittedreporterOptions
(Options
from
vfile-reporter
, optional)
— config to pass to the used reportersettings
(Settings
from unified
, optional)
— configuration for the parser and compiler of the processorsilent
(boolean
, default: false
)
— report only fatal errors; given to the reportersilentlyIgnore
(boolean
, default: false
)
— skip given files if they are ignoredstreamError
(WritableStream
from Node.js,
default: process.stderr
)
— stream to write the report (if any) tostreamIn
(ReadableStream
from Node.js,
default: process.stdin
)
— stream to read from if no files are found or givenstreamOut
(WritableStream
from Node.js,
default: process.stdout
)
— stream to write processed files to, nothing is streamed if either out
is false
, output
is not false
, multiple files are processed, or a
fatal error occurred while processing a filetree
(boolean
, default: false
)
— whether to treat both input and output as a syntax treetreeIn
(boolean
, default: options.tree
)
— whether to treat input as a syntax treetreeOut
(boolean
, default: options.tree
)
— whether to output as a syntax treeverbose
(boolean
, default: false
)
— report extra info; given to the reporterPreset
Sharable configuration, with support for specifiers (TypeScript type).
Specifiers should not be used in actual presets (because they can’t be used by regular unified), but they can be used in config files locally, as those are only for the engine.
They can contain plugins and settings.
1import type { 2 Plugin as UnifiedPlugin, 3 PluginTuple as UnifiedPluginTuple, 4 Preset as UnifiedPreset, 5 Settings 6} from 'unified' 7 8type Preset = { 9 plugins?: PluggableList | PluggableMap | undefined 10 settings?: Settings | undefined 11} 12 13type Pluggable = Plugin | PluginTuple | UnifiedPreset 14type PluggableList = Array<Pluggable> 15type PluggableMap = Record<string, unknown> 16type Plugin = UnifiedPlugin | string 17type PluginTupleSupportingSpecifiers = 18 | [plugin: string, ...parameters: Array<unknown>] 19 | UnifiedPluginTuple
ResolveFrom
How to resolve (TypeScript type).
1type ResolveFrom = 'cwd' | 'dir';
VFileReporter
Transform arbitrary configs to our format (TypeScript type).
This is essentially the interface of vfile-reporter
, with
added support for unknown fields in options and async support.
files
(Array<VFile>
)
— filesoptions
(Options
from vfile-reporter
,
optional)
— configurationReport (Promise<string>
or string
).
unified-engine
accepts configuration through options and through
configuration files (rc files).
One configuration file can be given through options.rcPath
, this is loaded
regardless of options.detectConfig
and options.rcName
.
Otherwise, configuration files are detected if options.detectConfig
is turned
on, depending on the following options:
options.rcName
is given, $rcName
(JSON), $rcName.js
(CommonJS or
ESM depending on the type
field of the closest package.json
),
$rcName.cjs
(CommonJS), $rcName.mjs
(ESM), $rcName.yml
(YAML),
and $rcName.yaml
(YAML) are loadedoptions.packageField
is given, package.json
(JSON) files are loaded
and the configuration at their $packageField
field is usedThe first file that is searched for in a folder is used as the configuration. If no file is found, the parent folder is searched, and so on.
The schema (type) of rc files is Preset
.
An example rc file could look as follows:
1{ 2 "plugins": [ 3 "remark-inline-links", 4 "remark-lint-recommended" 5 ], 6 "settings": { 7 "bullet": "*", 8 "ruleRepetition": 3, 9 "fences": true 10 } 11}
Another example, rc.js, could look as follows:
1exports.plugins = [ 2 './script/natural-language.js', 3 'remark-lint-recommended', 4 'remark-license' 5] 6 7exports.settings = {bullet: '*'}
When using ESM (ECMAScript modules), rc.mjs could look as folows:
1export default { 2 plugins: [ 3 './script/natural-language.js', 4 'remark-lint-recommended', 5 'remark-license' 6 ], 7 settings: {bullet: '*'} 8}
Another example, rc.yaml, could look as follows:
1plugins: 2 - 'rehype-document' 3 - 'rehype-preset-minify' 4settings: 5 preferUnquoted: true 6 quote: "'" 7 quoteSmart: true 8 verbose: true
unified-engine
accepts patterns to ignore when searching for files to process
through ignore files.
One ignore file can be given through options.ignorePath
, this is loaded
regardless of options.detectIgnore
and options.ignoreName
.
Otherwise, ignore files are detected if options.detectIgnore
is turned on and
options.ignoreName
is given.
The first file named $ignoreName
in the parent folder of a checked file is
used.
Or, if no file is found, the parent folder if searched, and so on.
In addition to explicit and implicit ignore files, other patterns can be given
with options.ignorePatterns
.
The format of each pattern in ignorePatterns
is the same as a line in an
ignore file.
Patterns and files are resolved based on the current working folder.
It is also possible to ignore files that do not have an associated detected
configuration file by turning on options.ignoreUnconfigured
.
Ignoring is used when searching for files in folders.
If paths (including those expanded from globs) are passed in that
are ignored, an error is thrown.
These files can be silently ignored by turning on options.silentlyIgnore
.
Normally, files are ignored based on the path of the found ignore file and the
patterns inside it.
Patterns passed with options.ignorePatterns
are resolved based on the current
working directory.
Patterns in an explicit ignore file passed in with options.ignorePath
can be
resolved from the current working directory instead, by setting
options.ignorePathResolveFrom
to 'cwd'
instead of 'dir'
(default).
If paths or globs to folders are given to the engine, they will be searched
for matching files, but node_modules
are normally not searched.
Pass paths (or globs) to the node_modules
you want to include in
options.files
to search them.
The format for ignore files is the same as .gitignore
, so it’s
possible to pass a .gitignore
in as options.ignorePath
.
node-ignore
is used under the hood, see its documentation
for more information.
An example ignore file could look as follows:
1# Ignore files in `.github`. 2.github/ 3 4# Bower. 5bower_components/ 6# Duo dependencies. 7components/ 8 9# Fixtures. 10test/{input,tree}/
If we had an ignore file folder/.remarkignore
, with the value: index.txt
,
and our file system looked as follows:
1folder/.remarkignore 2folder/index.txt 3index.txt
Then folder/index.txt
would be ignored but index.txt
would not be.
Normally, unified plugins receive a single options
argument upon attaching
(an Object
users can provide to configure the plugin).
If a plugin is attached by unified-engine, a second argument is given:
FileSet
.
unified-engine
can be configured extensively by engine authors.
options.alwaysStringify
This example shows how you can use options.alwaysStringify
when you don’t
want the engine to write to the file system, but still want to get the compiled
results.
One example that does this is unified-engine-gulp
.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3import {VFile} from 'vfile' 4 5const file = new VFile({path: 'example.md', value: '_hi_'}) 6 7engine( 8 {alwaysStringify: true, files: [file], processor: remark}, 9 function (error, code, context) { 10 if (error) throw error 11 console.log(context?.files.map((d) => String(d))) 12 } 13)
Yields:
1example.md: no issues found
1[ '*hi*\n' ]
options.configTransform
To support custom rc files, that have a different format than what the engine
supports, pass as ConfigTransform
.
This example processes readme.md
and loads options from custom
(from a
package.json
).
configTransform
is called with those options and transforms it to
configuration unified-engine
understands.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 configTransform, 7 files: ['readme.md'], 8 packageField: 'custom', 9 processor: remark() 10 }, 11 function (error) { 12 if (error) throw error 13 } 14) 15 16function configTransform(config) { 17 return {settings: (config || {}).options} 18}
Where package.json
contains:
1{ 2 "name": "foo", 3 "private": true, 4 "custom": { 5 "options": { 6 "bullet": "+" 7 } 8 } 9}
options.defaultConfig
This example processes readme.md
.
If package.json
exists, that config is used, otherwise the configuration at
defaultConfig
is used.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 defaultConfig: {settings: {bullet: '+'}}, 7 files: ['readme.md'], 8 packageField: 'remarkConfig', 9 processor: remark() 10 }, 11 function (error) { 12 if (error) throw error 13 } 14)
Where package.json
contains:
1{ 2 "name": "foo", 3 "private": true, 4 "remarkConfig": { 5 "settings": { 6 "bullet": "-" 7 } 8 } 9}
options.detectConfig
This example processes readme.md
but does not allow configuration from
.remarkrc
or package.json
files, as detectConfig
is false
.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 detectConfig: false, 7 files: ['readme.md'], 8 processor: remark(), 9 packageField: 'remarkConfig', 10 rcName: '.remarkrc' 11 }, 12 function (error) { 13 if (error) throw error 14 } 15)
options.detectIgnore
This example processes files in the current working directory with an md
extension but does not ignore file paths from the closest .remarkignore
file, because detectIgnore
is false
.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 detectIgnore: false, 7 extensions: ['md'], 8 files: ['.'], 9 ignoreName: '.remarkignore', 10 processor: remark() 11 }, 12 function (error) { 13 if (error) throw error 14 } 15)
options.extensions
This example reformats all files with md
, markdown
, and mkd
extensions in the current folder.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 extensions: ['md', 'mkd', 'markdown'], 7 files: ['.'], 8 output: true, 9 processor: remark 10 }, 11 function (error) { 12 if (error) throw error 13 } 14)
options.filePath
This example shows that streamIn
is named as filePath
:
1import {PassThrough} from 'node:stream' 2import {remark} from 'remark' 3import remarkPresetLintRecommended from 'remark-preset-lint-recommended' 4import {engine} from 'unified-engine' 5 6const streamIn = new PassThrough() 7 8streamIn.write('doc') 9 10setImmediate(function () { 11 streamIn.end('ument') 12}) 13 14engine( 15 { 16 filePath: '~/alpha/bravo/charlie.md', 17 out: false, 18 plugins: [remarkPresetLintRecommended], 19 processor: remark(), 20 streamIn 21 }, 22 function (error) { 23 if (error) throw error 24 } 25)
Yields:
1~/alpha/bravo/charlie.md 2 1:1 warning Missing newline character at end of file final-newline remark-lint 3 4⚠ 1 warning
options.files
This example processes LICENSE
and all files with an md
extension in doc
.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 extensions: ['md'], 7 files: ['LICENSE', 'doc/'], 8 processor: remark 9 }, 10 function (error) { 11 if (error) throw error 12 } 13)
options.frail
This example uses remark-lint
to lint readme.md
and exits
with the given exit code.
Normally, only errors turn the code
to 1
, but in frail
mode lint warnings
result in the same.
1import process from 'node:process' 2import {remark} from 'remark' 3import {engine} from 'unified-engine' 4 5engine( 6 { 7 files: ['readme.md'], 8 frail: true, 9 plugins: ['remark-preset-lint-recommended'], 10 processor: remark() 11 }, 12 function (error, code) { 13 process.exitCode = error ? 1 : code 14 } 15)
options.ignoreName
This example processes files in the current working directory with an md
extension, and is configured to ignore file paths from the closest
.remarkignore
file.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 extensions: ['md'], 7 files: ['.'], 8 ignoreName: '.remarkignore', 9 processor: remark() 10 }, 11 function (error) { 12 if (error) throw error 13 } 14)
options.ignorePath
This example processes files in the current working directory with an md
extension and ignores file paths specified in .gitignore
.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 extensions: ['md'], 7 files: ['.'], 8 ignorePath: '.gitignore', 9 processor: remark() 10 }, 11 function (error) { 12 if (error) throw error 13 } 14)
options.ignorePathResolveFrom
This example processes files in the current working directory with an md
extension and takes a reusable configuration file from a dependency.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 extensions: ['md'], 7 files: ['.'], 8 ignorePath: 'node_modules/my-config/my-ignore', 9 ignorePathResolveFrom: 'cwd', 10 processor: remark() 11 }, 12 function (error) { 13 if (error) throw error 14 } 15)
options.ignorePatterns
This example processes files in the current working directory with an md
extension, except for readme.md
:
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 extensions: ['md'], 7 files: ['.'], 8 ignorePatterns: ['readme.md'], 9 processor: remark() 10 }, 11 function (error) { 12 if (error) throw error 13 } 14)
options.ignoreUnconfigured
This example processes files in the current working directory with an
md
extension, but only if there is an explicit .remarkrc
config file near
(upwards) to them:
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 extensions: ['md'], 7 files: ['.'], 8 ignoreUnconfigured: true, 9 processor: remark(), 10 rcName: '.remarkrc' 11 }, 12 function (error) { 13 if (error) throw error 14 } 15)
options.inspect
This example shows a module which reads and parses doc.md
, then
remark-unlink
transforms the syntax tree, the tree is
formatted with unist-util-inspect
, and finally written
to stdout(4).
1import {remark} from 'remark' 2import remarkUnlink from 'remark-unlink' 3import {engine} from 'unified-engine' 4 5engine( 6 { 7 files: ['doc.md'], 8 inspect: true, 9 plugins: [remarkUnlink], 10 processor: remark() 11 }, 12 function (error) { 13 if (error) throw error 14 } 15)
Where doc.md
looks as follows:
1[foo](https://example.com)
Yields:
1root[1] (1:1-2:1, 0-27) 2└─ paragraph[1] (1:1-1:27, 0-26) 3 └─ text: "foo" (1:2-1:5, 1-4)
options.out
This example uses remark-lint
to lint readme.md
, writes the
report, and ignores the serialized document.
1import {remark} from 'remark' 2import remarkPresetLintRecommended from 'remark-preset-lint-recommended' 3import {engine} from 'unified-engine' 4 5engine( 6 { 7 files: ['readme.md'], 8 out: false, 9 plugins: [remarkPresetLintRecommended], 10 processor: remark() 11 }, 12 function (error) { 13 if (error) throw error 14 } 15)
options.output
This example writes all files in src/
with an md
extension compiled to
dest/
.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 extensions: ['md'], 7 files: ['src/'], 8 output: 'dest/', 9 processor: remark() 10 }, 11 function (error) { 12 if (error) throw error 13 } 14)
options.packageField
This example processes readme.md
, and allows configuration from
remarkConfig
fields in package.json
files.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 files: ['readme.md'], 7 packageField: 'remarkConfig', 8 processor: remark() 9 }, 10 function (error) { 11 if (error) throw error 12 } 13)
options.pluginPrefix
This example processes readme.md
and loads the
preset-lint-recommended
plugin.
Because pluginPrefix
is given, this resolves to
remark-preset-lint-recommended
(from
node_modules/
) if available.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 files: ['readme.md'], 7 pluginPrefix: 'remark', 8 plugins: ['preset-lint-recommended'], 9 processor: remark() 10 }, 11 function (error) { 12 if (error) throw error 13 } 14)
options.plugins
This example processes readme.md
and loads the
remark-preset-lint-recommended
preset.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 files: ['readme.md'], 7 plugins: ['remark-preset-lint-recommended'], 8 processor: remark() 9 }, 10 function (error) { 11 if (error) throw error 12 } 13)
options.processor
This example reformats stdin(4) using remark, writes the report to stderr(4), and formatted document to stdout(4).
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine({processor: remark}, function (error) { 5 if (error) throw error 6})
options.quiet
This example uses remark-lint
to lint readme.md
.
Nothing is reported if the file processed successfully.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 files: ['readme.md'], 7 plugins: ['remark-preset-lint-recommended'], 8 processor: remark(), 9 quiet: true 10 }, 11 function (error) { 12 if (error) throw error 13 } 14)
options.rcName
This example processes readme.md
and allows configuration from .remarkrc
,
.remarkrc.json
, .remarkrc.yml
, .remarkrc.yaml
, .remarkrc.js
,
.remarkrc.cjs
, and .remarkrc.mjs
files.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 {files: ['readme.md'], processor: remark(), rcName: '.remarkrc'}, 6 function (error) { 7 if (error) throw error 8 } 9)
options.rcPath
This example processes readme.md
and loads configuration from config.json
.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 {files: ['readme.md'], processor: remark(), rcPath: 'config.json'}, 6 function (error) { 7 if (error) throw error 8 } 9)
options.reporter
and options.reporterOptions
This example processes all HTML files in the current folder with rehype,
configures the processor with .rehyperc
files, and prints a report in
JSON using vfile-reporter-json
with
reporter options.
1import {rehype} from 'rehype' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 extensions: ['html'], 7 files: ['.'], 8 processor: rehype(), 9 rcName: '.rehyperc', 10 reporter: 'json', 11 reporterOptions: {pretty: true} 12 }, 13 function (error) { 14 if (error) throw error 15 } 16)
options.settings
This example processes readme.md
and configures the compiler
(remark-stringify
) with bullet: '+'
.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 {files: ['readme.md'], processor: remark(), settings: {bullet: '+'}}, 6 function (error) { 7 if (error) throw error 8 } 9)
options.silent
This example uses remark-lint
to lint readme.md
but does not
report any warnings or success messages, only fatal errors, if they occur.
1import {remark} from 'remark' 2import {engine} from 'unified-engine' 3 4engine( 5 { 6 files: ['readme.md'], 7 plugins: ['remark-preset-lint-recommended'], 8 processor: remark(), 9 silent: true 10 }, 11 function (error) { 12 if (error) throw error 13 } 14)
options.streamError
This example uses remark-lint
to lint readme.md
and writes
the report to report.txt
.
1import fs from 'node:fs' 2import {remark} from 'remark' 3import remarkPresetLintRecommended from 'remark-preset-lint-recommended' 4import {engine} from 'unified-engine' 5 6engine( 7 { 8 files: ['readme.md'], 9 out: false, 10 plugins: [remarkPresetLintRecommended], 11 processor: remark(), 12 streamErr: fs.createWriteStream('report.txt') 13 }, 14 function (error) { 15 if (error) throw error 16 } 17)
options.streamIn
This example uses remark-lint
to lint an incoming
stream.
1import {PassThrough} from 'node:stream' 2import {remark} from 'remark' 3import remarkPresetLintRecommended from 'remark-preset-lint-recommended' 4import {engine} from 'unified-engine' 5 6const streamIn = new PassThrough() 7 8streamIn.write('doc') 9 10setImmediate(function () { 11 streamIn.end('ument') 12}) 13 14engine( 15 { 16 out: false, 17 plugins: [remarkPresetLintRecommended], 18 processor: remark(), 19 streamIn 20 }, 21 function (error) { 22 if (error) throw error 23 } 24)
Yields:
1<stdin> 2 1:1 warning Missing newline character at end of file final-newline remark-lint 3 4⚠ 1 warning
options.streamOut
This example reads readme.md
and writes the serialized document to
readme-two.md
.
This can also be achieved by passing output: 'readme-two.md'
instead of
streamOut
.
1import fs from 'node:fs' 2import {remark} from 'remark' 3import {engine} from 'unified-engine' 4 5const streamOut = fs.createWriteStream('readme-two.md') 6 7engine( 8 {files: ['readme.md'], processor: remark(), streamOut}, 9 function (error) { 10 if (error) throw error 11 } 12)
options.tree
This example reads tree.json
, then remark-unlink
transforms the syntax tree, and the transformed tree is written to
stdout(4).
1import {remark} from 'remark' 2import remarkUnlink from 'remark-unlink' 3import {engine} from 'unified-engine' 4 5engine( 6 { 7 files: ['tree.json'], 8 plugins: [remarkUnlink], 9 processor: remark(), 10 tree: true 11 }, 12 function (error) { 13 if (error) throw error 14 } 15)
Where tree.json
looks as follows:
1{ 2 "type": "paragraph", 3 "children": [{ 4 "type": "link", 5 "url": "https://example.com", 6 "children": [{ 7 "type": "text", 8 "value": "foo" 9 }] 10 }] 11}
Yields:
1{ 2 "type": "paragraph", 3 "children": [{ 4 "type": "text", 5 "value": "foo" 6 }] 7}
options.treeIn
This example reads tree.json
, then remark-unlink
transforms the syntax tree, the tree is serialized, and the resulting document
is written to stdout(4).
1import {remark} from 'remark' 2import remarkUnlink from 'remark-unlink' 3import {engine} from 'unified-engine' 4 5engine( 6 { 7 files: ['tree.json'], 8 plugins: [remarkUnlink], 9 processor: remark(), 10 treeIn: true 11 }, 12 function (error) { 13 if (error) throw error 14 } 15)
Where tree.json
looks as follows:
1{ 2 "type": "paragraph", 3 "children": [{ 4 "type": "link", 5 "url": "https://example.com", 6 "children": [{ 7 "type": "text", 8 "value": "foo" 9 }] 10 }] 11}
Yields:
1foo
options.treeOut
This example shows a module which reads and parses doc.md
, then
remark-unlink
transforms the syntax tree, and the tree is
written to stdout(4).
1import {remark} from 'remark' 2import remarkUnlink from 'remark-unlink' 3import {engine} from 'unified-engine' 4 5engine( 6 { 7 files: ['doc.md'], 8 plugins: [remarkUnlink], 9 processor: remark(), 10 treeOut: true 11 }, 12 function (error) { 13 if (error) throw error 14 } 15)
Where doc.md
looks as follows:
1[foo](https://example.com)
Yields:
1{ 2 "type": "paragraph", 3 "children": [{ 4 "type": "text", 5 "value": "foo" 6 }] 7}
This package is fully typed with TypeScript.
It exports the additional types
Completer
,
Callback
,
ConfigResult
,
ConfigTransform
,
Context
,
FileSet
,
Options
,
Preset
,
ResolveFrom
, and
VFileReporter
.
Projects maintained by the unified collective are compatible with maintained versions of Node.js.
When we cut a new major release, we drop support for unmaintained versions of
Node.
This means we try to keep the current release line, unified-engine@^11
,
compatible with Node.js 16.
unified-engine
loads and evaluates configuration files, plugins, and presets
from the file system (often from node_modules/
).
That means code that is on your file system runs.
Make sure you trust the workspace where you run unified-engine
and be careful
with packages from npm and changes made by contributors.
See contributing.md
in unifiedjs/.github
for ways
to get started.
See support.md
for ways to get help.
This project has a code of conduct. By interacting with this repository, organization, or community you agree to abide by its terms.
No vulnerabilities found.
Reason
no dangerous workflow patterns detected
Reason
no binaries found in the repo
Reason
license file detected
Details
Reason
0 existing vulnerabilities detected
Reason
security policy file detected
Details
Reason
2 commit(s) and 3 issue activity found in the last 90 days -- score normalized to 4
Reason
Found 0/30 approved changesets -- score normalized to 0
Reason
detected GitHub workflow tokens with excessive permissions
Details
Reason
no effort to earn an OpenSSF best practices badge detected
Reason
no SAST tool detected
Details
Reason
dependency not pinned by hash detected -- score normalized to 0
Details
Reason
project is not fuzzed
Details
Reason
branch protection not enabled on development/release branches
Details
Score
Last Scanned on 2025-06-30
The Open Source Security Foundation is a cross-industry collaboration to improve the security of open source software (OSS). The Scorecard provides security health metrics for open source projects.
Learn More