deno icon indicating copy to clipboard operation
deno copied to clipboard

prettier npm module fails with "Maximum call stack size exceeded"

Open bershanskiy opened this issue 2 years ago • 1 comments

prettier module published on NPM is a popular code formatter (~29 million downloads a week. It is necessary for us to migrate to deno away from NodeJS without breaking our workflow. Currently, deno fails on pretter use even with trivial code.

Repro steps

Contents of repro.ts:

import prettier from 'prettier';
// The code being formatted is just empty string
// The filename is there just to indicate it is JS as opposed to HTML or CSS or TSX or something else
prettier.format('', {filename: '1.js'});

Contents of repro.json:

{
  "imports": {
    "prettier": "npm:prettier@latest"
  }
}

Output of deno run --unstable --import-map=repro.json --allow-read --allow-env repro.ts:

user@pc:~/deno-repro$ deno run --unstable --import-map=repro.json --allow-read --allow-env repro.ts 
No parser and no filepath given, using 'babel' the parser now but this will throw an error in the future. Please specify a parser or a filepath so one can be inferred.
error: Uncaught RangeError: Maximum call stack size exceeded
    at Object.get (deno:ext/node/01_node.js:35:26)
    at Object.get (deno:ext/node/01_node.js:35:26)
    at Object.get (deno:ext/node/01_node.js:35:26)
    at Object.get (deno:ext/node/01_node.js:35:26)
    at Object.get (deno:ext/node/01_node.js:35:26)
    at Object.get (deno:ext/node/01_node.js:35:26)
    at Object.get (deno:ext/node/01_node.js:35:26)
    at Object.get (deno:ext/node/01_node.js:35:26)
    at Object.get (deno:ext/node/01_node.js:35:26)
    at Object.get (deno:ext/node/01_node.js:35:26)

bershanskiy avatar Feb 07 '23 09:02 bershanskiy

This bug seems to originate from the line below.

// file:///C:/Users/ayame/AppData/Local/deno/npm/registry.npmjs.org/prettier/2.8.3/parser-babel.js:formatted
const {Buffer, clearImmediate, clearInterval, clearTimeout, console, global, process, setImmediate, setInterval, setTimeout} = globalThis;

~~Perhaps accessing globalThis.global inside the npm module will enter an infinite loop.~~ I'm not sure, but I debugged with the --inspect flag and it seems to go into an infinite recursion right after executing this line.

ayame113 avatar Feb 07 '23 20:02 ayame113