Skip to content

Instantly share code, notes, and snippets.

Last active December 5, 2018 18:07
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save vijithassar/c99df3063237bfc3c3d6b32d210cb107 to your computer and use it in GitHub Desktop.
Save vijithassar/c99df3063237bfc3c3d6b32d210cb107 to your computer and use it in GitHub Desktop.
debugging lit-node + esm [UNLISTED]

Literate programming is a software development practice which treats source code like written material intended for humans instead of instructions intended for execution by computers. The most popular modern approach is to embed the source code in Markdown code blocks, surrounded by written explanatory text, comments, and other documentation, and then parse the Markdown before executing or compiling in order to extract only the code portions. In Node.js, one of the cleanest ways to do this is with the lit-node module, which works by adding a hook to the global require() function which is automatically added to the Node.js environment in order to load CommonJS modules, after which Markdown documents can be transpiled on the fly. Unfortunately lit-node seems to conflict with the esm module loader, which means it is not currently possible to use both literate style and ESM module format simultaneously from the Node CLI directly. It can still be done with a more elaborate setup based on or blaze, but this is a fairly obvious combination and it would be better for the module loading tools to cooperate.

To reproduce, start by cloning this repository and installing both modules.

# install modules
$ npm install

You can now execute JavaScript code from Markdown documents, including this very README!

For example, here's some JavaScript:

// log a message
console.log('hello world')

Note that lit-node only executes code which is explicitly marked as javascript or js after the triple backticks. The rest of the code blocks in this document are bash, and are thus ignored.

You'll see the message above logged to the terminal if you run Node with the require() hook supplied by lit-node and specify this Markdown document as the script to be executed:

# execute the JavaScript code in this README
$ node --require lit-node/register

This doesn't work with esm, however. The included file should be executable in much the same way, but it fails because it contains an ESM import that the esm module doesn't resolve.

# test ES6 module loading

$ node --require esm --require lit-node/register
# or
$ npm run esm

The specific error message suggests that even though the esm module has been loaded, Node is still confused by ESM import syntax by the time it gets to the lit-node hook:

> lit-node-esm-debug@0.0.1 esm /path
> node --require esm --require lit-node/register

import { ok } from 'assert'

SyntaxError: Unexpected token {
    at new Script (vm.js:83:7)
    at Object.<anonymous> (/path/node_modules/esm/esm.js:1)
    at Object.o._compile (/path/node_modules/esm/esm.js:1)
    at Object.o._compile (/path/node_modules/esm/esm.js:1)
    at (/path/node_modules/lit-node/register.js:7:16)
    at /path/node_modules/esm/esm.js:1
    at /path/node_modules/esm/esm.js:1
    at /path/node_modules/esm/esm.js:1
    at su (/path/node_modules/esm/esm.js:1)
    at Su (/path/node_modules/esm/esm.js:1)

Now, the test is not failing, exactly; rather, the entire testing script is crashing because the assert module cannot be imported with ESM syntax.

For convenience, this repository also includes a test for importing CommonJS modules (which already works just fine), and npm run test runs both the CommonJS and ESM tests.

# test CommonJS module loading
$ npm run cjs

# test both CommonJS and ESM module loading
$ npm run test

This problem will be fixed when the npm run test command exits without any errors.

See also:

test CommonJS module loader

const ok = require('assert').ok
ok(true, 'failed to load module with CommonJS require() function')

test ES6 module loader

import { ok } from 'assert'
ok(true, 'failed to load module with ESM import statement')
"name": "lit-node-esm-debug",
"version": "0.0.1",
"description": "demonstration to help with debugging module loading problems",
"main": null,
"dependencies": {
"esm": "^3.0.84",
"lit-node": "^0.1.1"
"scripts": {
"test": "npm run cjs && npm run esm",
"cjs": "node --require lit-node/register",
"esm": "node --require esm --require lit-node/register"
"keywords": [
"author": "Vijith Assar",
"license": "UNLICENSED"
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment