diff --git a/scripts/indent-linter.js b/scripts/indent-linter.js index c56928d82dd5755c3350e2c0a913862298829517..33a23bcbed300d6dc5e066084745f3116ed61ed0 100644 --- a/scripts/indent-linter.js +++ b/scripts/indent-linter.js @@ -1,22 +1,32 @@ +/* + * indent-linter <glob> <num-spaces> + * Generic, syntax-unaware indentation linter that checks if indentation is even and does not skip indentation levels. + */ + const fs = require("fs"); const glob = require("glob"); -function lintFile(filename) { +function lintFile(filename, spaces) { const file = fs.readFileSync(filename, { encoding: "utf8" }); - const spaces = parseInt(process.argv[3] || "4", 10); const lines = file.split("\n"); + const errors = []; let level = 0; + for (let i = 0; i < lines.length; i++) { const line = lines[i]; const firstNonSpaceIndex = (line.match(/[^ ]/) || { index: 0 }).index; + const indentation = firstNonSpaceIndex; - if (indentation % spaces === 0 && (indentation - level) / spaces <= 1) { + const indentationDividesCleanly = indentation % spaces === 0; + const indentationIsNoMoreThanOneLevelHigher = (indentation - level) / spaces <= 1; + + if (indentationDividesCleanly && indentationIsNoMoreThanOneLevelHigher) { if (indentation !== 0) { level = indentation; } } else { - const expected = level + spaces; + const expected = level; const delta = indentation - expected; const postfix = delta < 0 ? "fewer" : "extra"; errors.push( @@ -24,17 +34,22 @@ function lintFile(filename) { ); } } + if (errors.length) { console.log(filename); console.log(errors.join("\n")); console.log(` ${errors.length} indentation error(s).\n`); } + return errors.length; } glob(process.argv[2], (err, files) => { console.log(""); - const errorCount = files.map(lintFile).reduce((a, c) => a + c, 0); + const spaces = parseInt(process.argv[3] || "4", 10); + + const errorCount = files.map(file => lintFile(file, spaces)).reduce((a, c) => a + c, 0); + console.log(`${errorCount} total indentation error(s).\n`); process.exit(errorCount > 0 ? 1 : 0); });