From bb1884320b3bd3143ca7fd2e4754426af9869b15 Mon Sep 17 00:00:00 2001 From: Simon Lydell Date: Mon, 23 Jan 2017 18:10:51 +0100 Subject: [PATCH] Use babel-code-frame for syntax errors (#367) * Use babel-code-frame for syntax errors * Support the `--color` option more explicitly * Update rollup config to handle babel-code-frame * Use exact dependencies --- bin/prettier.js | 17 ++++++++++++----- docs/rollup.config.js | 2 ++ index.js | 21 ++++++++++++++++++--- package.json | 4 +++- src/parser.js | 17 ++++++++++------- yarn.lock | 33 +++++++++++++++++++++++++++------ 6 files changed, 72 insertions(+), 22 deletions(-) diff --git a/bin/prettier.js b/bin/prettier.js index faff9be4..fccf0749 100755 --- a/bin/prettier.js +++ b/bin/prettier.js @@ -14,13 +14,15 @@ const argv = minimist(process.argv.slice(2), { "single-quote", "trailing-comma", "bracket-spacing", + // See https://github.com/chalk/supports-color/#info + "color", "version", "debug-print-doc", // Deprecated in 0.0.10 "flow-parser" ], string: [ "print-width", "tab-width", "parser" ], - default: { "bracket-spacing": true, parser: "babylon" }, + default: { color: true, "bracket-spacing": true, parser: "babylon" }, unknown: param => { if (param.startsWith("-")) { console.warn("Ignored unknown option: " + param + "\n"); @@ -47,9 +49,14 @@ if (!filepatterns.length && !stdin) { " --tab-width Specify the number of spaces per indentation-level. Defaults to 2.\n" + " --single-quote Use single quotes instead of double.\n" + " --trailing-comma Print trailing commas wherever possible.\n" + - " --bracket-spacing Put spaces between brackets. Defaults to true, set false to turn off.\n" + + " --bracket-spacing Put spaces between brackets. Defaults to true.\n" + " --parser Specify which parse to use. Defaults to babylon.\n" + - " --version Print prettier version." + " --color Colorize error messages. Defaults to true.\n" + + " --version Print prettier version.\n" + + "\n" + + "Boolean options can be turned off like this:\n" + + " --no-bracket-spacing\n" + + " --bracket-spacing=false" ); process.exit(1); } @@ -91,7 +98,7 @@ if (stdin) { console.log(format(input)); } catch (e) { process.exitCode = 2; - console.error(e); + console.error("stdin: " + e); return; } }); @@ -114,7 +121,7 @@ if (stdin) { output = format(input); } catch (e) { process.exitCode = 2; - console.error(e); + console.error(filename + ": " + e); return; } diff --git a/docs/rollup.config.js b/docs/rollup.config.js index 437d8235..ebaacea6 100644 --- a/docs/rollup.config.js +++ b/docs/rollup.config.js @@ -1,6 +1,7 @@ import resolve from 'rollup-plugin-node-resolve'; import commonjs from 'rollup-plugin-commonjs'; import builtins from 'rollup-plugin-node-builtins'; +import globals from 'rollup-plugin-node-globals'; import babili from 'rollup-plugin-real-babili'; import json from 'rollup-plugin-json'; @@ -12,6 +13,7 @@ export default { json(), resolve(), commonjs(), + globals(), builtins(), babili({comments: false, sourceMap: false}), ], diff --git a/index.js b/index.js index fea094df..b4568a1a 100644 --- a/index.js +++ b/index.js @@ -1,4 +1,5 @@ "use strict"; +const codeFrame = require("babel-code-frame"); const comments = require("./src/comments"); const version = require("./package.json").version; const printAstToDoc = require("./src/printer").printAstToDoc; @@ -8,10 +9,24 @@ const parser = require("./src/parser"); const printDocToDebug = require("./src/doc-debug").printDocToDebug; function parse(text, opts) { - if (opts.parser === "flow") { - return parser.parseWithFlow(text, opts.filename); + const parseFunction = opts.parser === "flow" + ? parser.parseWithFlow + : parser.parseWithBabylon; + + try { + return parseFunction(text); + } catch (error) { + const loc = error.loc; + + if (loc) { + error.codeFrame = codeFrame(text, loc.line, loc.column + 1, { + highlightCode: true + }); + error.message += "\n" + error.codeFrame; + } + + throw error; } - return parser.parseWithBabylon(text); } function attachComments(text, ast, opts) { diff --git a/package.json b/package.json index 95d1c7cc..1376cdea 100644 --- a/package.json +++ b/package.json @@ -17,6 +17,7 @@ "main": "./index.js", "dependencies": { "ast-types": "git+https://github.com/jlongster/ast-types.git", + "babel-code-frame": "6.22.0", "babylon": "6.15.0", "esutils": "2.0.2", "flow-parser": "0.38.0", @@ -28,8 +29,9 @@ "jest": "18.0.0", "rollup": "0.41.1", "rollup-plugin-commonjs": "7.0.0", - "rollup-plugin-json": "^2.1.0", + "rollup-plugin-json": "2.1.0", "rollup-plugin-node-builtins": "2.0.0", + "rollup-plugin-node-globals": "1.1.0", "rollup-plugin-node-resolve": "2.0.0", "rollup-plugin-real-babili": "1.0.0-alpha3" }, diff --git a/src/parser.js b/src/parser.js index 77207956..e0d9bd19 100644 --- a/src/parser.js +++ b/src/parser.js @@ -1,5 +1,5 @@ "use strict"; -function parseWithFlow(text, filename) { +function parseWithFlow(text) { // Inline the require to avoid loading all the JS if we don't use it const flowParser = require("flow-parser"); @@ -10,13 +10,16 @@ function parseWithFlow(text, filename) { }); if (ast.errors.length > 0) { - let msg = ast.errors[0].message + - " on line " + - ast.errors[0].loc.start.line; - if (filename) { - msg += " in file " + filename; + // Construct an error similar to the ones thrown by Babylon. + const loc = { + line: ast.errors[0].loc.start.line, + column: ast.errors[0].loc.start.column, } - throw new Error(msg); + const msg = ast.errors[0].message + + " (" + loc.line + ":" + loc.column + ")"; + const error = new SyntaxError(msg); + error.loc = loc; + throw error; } return ast; diff --git a/yarn.lock b/yarn.lock index 3db57606..8d2b2dcf 100644 --- a/yarn.lock +++ b/yarn.lock @@ -138,13 +138,13 @@ aws4@^1.2.1: version "1.5.0" resolved "https://registry.yarnpkg.com/aws4/-/aws4-1.5.0.tgz#0a29ffb79c31c9e712eeb087e8e7a64b4a56d755" -babel-code-frame@^6.20.0: - version "6.20.0" - resolved "https://registry.yarnpkg.com/babel-code-frame/-/babel-code-frame-6.20.0.tgz#b968f839090f9a8bc6d41938fb96cb84f7387b26" +babel-code-frame@^6.20.0, babel-code-frame@^6.22.0: + version "6.22.0" + resolved "https://registry.yarnpkg.com/babel-code-frame/-/babel-code-frame-6.22.0.tgz#027620bee567a88c32561574e7fd0801d33118e4" dependencies: chalk "^1.1.0" esutils "^2.0.2" - js-tokens "^2.0.0" + js-tokens "^3.0.0" babel-core@^6.0.0, babel-core@^6.18.0, babel-core@^6.21.0: version "6.21.0" @@ -520,7 +520,7 @@ bser@^1.0.2: dependencies: node-int64 "^0.4.0" -buffer-es6@^4.9.2: +buffer-es6@^4.9.1, buffer-es6@^4.9.2: version "4.9.3" resolved "https://registry.yarnpkg.com/buffer-es6/-/buffer-es6-4.9.3.tgz#f26347b82df76fd37e18bcb5288c4970cfd5c404" @@ -1457,6 +1457,10 @@ js-tokens@^2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-2.0.0.tgz#79903f5563ee778cc1162e6dcf1a0027c97f9cb5" +js-tokens@^3.0.0: + version "3.0.0" + resolved "https://registry.yarnpkg.com/js-tokens/-/js-tokens-3.0.0.tgz#a2f2a969caae142fb3cd56228358c89366957bd1" + js-yaml@^3.7.0: version "3.7.0" resolved "https://registry.yarnpkg.com/js-yaml/-/js-yaml-3.7.0.tgz#5c967ddd837a9bfdca5f2de84253abe8a1c03b80" @@ -1651,6 +1655,12 @@ loose-envify@^1.0.0: dependencies: js-tokens "^2.0.0" +magic-string@^0.16.0: + version "0.16.0" + resolved "https://registry.yarnpkg.com/magic-string/-/magic-string-0.16.0.tgz#970ebb0da7193301285fb1aa650f39bdd81eb45a" + dependencies: + vlq "^0.2.1" + magic-string@^0.19.0: version "0.19.0" resolved "https://registry.yarnpkg.com/magic-string/-/magic-string-0.19.0.tgz#198948217254e3e0b93080e01146b7c73b2a06b2" @@ -1933,7 +1943,7 @@ private@^0.1.6: version "0.1.6" resolved "https://registry.yarnpkg.com/private/-/private-0.1.6.tgz#55c6a976d0f9bafb9924851350fe47b9b5fbb7c1" -process-es6@^0.11.2: +process-es6@^0.11.2, process-es6@^0.11.3: version "0.11.6" resolved "https://registry.yarnpkg.com/process-es6/-/process-es6-0.11.6.tgz#c6bb389f9a951f82bd4eb169600105bd2ff9c778" @@ -2097,6 +2107,17 @@ rollup-plugin-node-builtins@2.0.0: crypto-browserify "^3.11.0" process-es6 "^0.11.2" +rollup-plugin-node-globals@^1.1.0: + version "1.1.0" + resolved "https://registry.yarnpkg.com/rollup-plugin-node-globals/-/rollup-plugin-node-globals-1.1.0.tgz#7efd8d611d132737829e804e9f51f50962af451f" + dependencies: + acorn "^4.0.1" + buffer-es6 "^4.9.1" + estree-walker "^0.2.1" + magic-string "^0.16.0" + process-es6 "^0.11.3" + rollup-pluginutils "^1.5.2" + rollup-plugin-node-resolve@2.0.0: version "2.0.0" resolved "https://registry.yarnpkg.com/rollup-plugin-node-resolve/-/rollup-plugin-node-resolve-2.0.0.tgz#07e0ae94ac002a3ea36e8f33ca121d9f836b1309"