"use strict";
-//------------------------------------------------------------------------------
-// Helper
-//------------------------------------------------------------------------------
-
-/**
- * To make sure this works in both browsers and Node.js
- * @param {string} name Name of the module to require
- * @param {Object} windowName name of the window
- * @returns {Object} Required object
- * @private
- */
-function compatRequire(name, windowName) {
- if (typeof window === "object") { // eslint-disable-line no-undef
- return window[windowName || name]; // eslint-disable-line no-undef
- }
- if (typeof require === "function") {
- return require(name);
- }
- throw new Error(`Cannot find object '${name}'.`);
-}
-
//------------------------------------------------------------------------------
// Requirements
//------------------------------------------------------------------------------
esprima = require("esprima"),
testParsers = require("../../fixtures/parsers/linter-test-parsers");
-const { Linter } = compatRequire("../../../lib/linter", "eslint");
+const { Linter } = require("../../../lib/linter");
//------------------------------------------------------------------------------
// Constants
assert.strictEqual(messages[0].message, filename);
});
+ it("has access to the physicalFilename", () => {
+ linter.defineRule(code, context => ({
+ Literal(node) {
+ context.report(node, context.getPhysicalFilename());
+ }
+ }));
+
+ const config = { rules: {} };
+
+ config.rules[code] = 1;
+
+ const messages = linter.verify("0", config, filename);
+
+ assert.strictEqual(messages[0].message, filename);
+ });
+
it("defaults filename to '<input>'", () => {
linter.defineRule(code, context => ({
Literal(node) {
assert.strictEqual(messages.length, 0);
});
+ // https://github.com/eslint/eslint/issues/14652
+ it("should not report a violation", () => {
+ const codes = [
+ "/*eslint-env es6\n */ new Promise();",
+ "/*eslint-env browser,\nes6 */ window;Promise;",
+ "/*eslint-env\nbrowser,es6 */ window;Promise;"
+ ];
+ const config = { rules: { "no-undef": 1 } };
+
+ for (const code of codes) {
+ const messages = linter.verify(code, config, filename);
+
+ assert.strictEqual(messages.length, 0);
+ }
+
+ });
+
it("should not report a violation", () => {
const code = `/*${ESLINT_ENV} mocha,node */ require();describe();`;
});
});
+ describe("physicalFilenames", () => {
+ it("should be same as `filename` passed on options object, if no processors are used", () => {
+ const physicalFilenameChecker = sinon.spy(context => {
+ assert.strictEqual(context.getPhysicalFilename(), "foo.js");
+ return {};
+ });
+
+ linter.defineRule("checker", physicalFilenameChecker);
+ linter.verify("foo;", { rules: { checker: "error" } }, { filename: "foo.js" });
+ assert(physicalFilenameChecker.calledOnce);
+ });
+
+ it("should default physicalFilename to <input> when options object doesn't have filename", () => {
+ const physicalFilenameChecker = sinon.spy(context => {
+ assert.strictEqual(context.getPhysicalFilename(), "<input>");
+ return {};
+ });
+
+ linter.defineRule("checker", physicalFilenameChecker);
+ linter.verify("foo;", { rules: { checker: "error" } }, {});
+ assert(physicalFilenameChecker.calledOnce);
+ });
+
+ it("should default physicalFilename to <input> when only two arguments are passed", () => {
+ const physicalFilenameChecker = sinon.spy(context => {
+ assert.strictEqual(context.getPhysicalFilename(), "<input>");
+ return {};
+ });
+
+ linter.defineRule("checker", physicalFilenameChecker);
+ linter.verify("foo;", { rules: { checker: "error" } });
+ assert(physicalFilenameChecker.calledOnce);
+ });
+ });
+
it("should report warnings in order by line and column when called", () => {
const code = "foo()\n alert('test')";
describe("processors", () => {
let receivedFilenames = [];
+ let receivedPhysicalFilenames = [];
beforeEach(() => {
receivedFilenames = [];
+ receivedPhysicalFilenames = [];
// A rule that always reports the AST with a message equal to the source text
linter.defineRule("report-original-text", context => ({
Program(ast) {
receivedFilenames.push(context.getFilename());
+ receivedPhysicalFilenames.push(context.getPhysicalFilename());
context.report({ node: ast, message: context.getSourceCode().text });
}
}));
assert.strictEqual(problems.length, 3);
assert.deepStrictEqual(problems.map(problem => problem.message), ["foo", "bar", "baz"]);
+
+ // filename
assert.strictEqual(receivedFilenames.length, 3);
assert(/^filename\.js[/\\]0_block\.js/u.test(receivedFilenames[0]));
assert(/^filename\.js[/\\]1_block\.js/u.test(receivedFilenames[1]));
assert(/^filename\.js[/\\]2_block\.js/u.test(receivedFilenames[2]));
+
+ // physical filename
+ assert.strictEqual(receivedPhysicalFilenames.length, 3);
+ assert.strictEqual(receivedPhysicalFilenames.every(name => name === filename), true);
});
it("should receive text even if a SourceCode object was given.", () => {
let types = [];
let sourceCode;
let scopeManager;
+ let firstChildNodes = [];
beforeEach(() => {
types = [];
+ firstChildNodes = [];
linter.defineRule("collect-node-types", () => ({
"*"(node) {
types.push(node.type);
return {};
});
+ linter.defineRule("esquery-option", () => ({
+ ":first-child"(node) {
+ firstChildNodes.push(node);
+ }
+ }));
linter.defineParser("enhanced-parser2", testParsers.enhancedParser2);
linter.verify("@foo class A {}", {
parser: "enhanced-parser2",
rules: {
"collect-node-types": "error",
- "save-scope-manager": "error"
+ "save-scope-manager": "error",
+ "esquery-option": "error"
}
});
["Program", "ClassDeclaration", "Decorator", "Identifier", "Identifier", "ClassBody"]
);
});
+
+ it("esquery should use the visitorKeys (so 'visitorKeys.ClassDeclaration' includes 'experimentalDecorators')", () => {
+ assert.deepStrictEqual(
+ firstChildNodes,
+ [sourceCode.ast.body[0], sourceCode.ast.body[0].experimentalDecorators[0]]
+ );
+ });
});
describe("if a parser provides 'scope'", () => {