From c8a74bd72cc38838a4b1ed435a5e5cc8900f9c33 Mon Sep 17 00:00:00 2001 From: David Anson Date: Fri, 6 Sep 2019 22:35:33 -0700 Subject: [PATCH] Update MD037/MD038/MD039 to report fixInfo for violations. --- lib/md037.js | 46 ++++++++++++++++++++++++++++++---------------- lib/md038.js | 22 ++++++++++++++++------ lib/md039.js | 27 ++++++++++++++++++++------- 3 files changed, 66 insertions(+), 29 deletions(-) diff --git a/lib/md037.js b/lib/md037.js index 3f94d252..1e4b77c3 100644 --- a/lib/md037.js +++ b/lib/md037.js @@ -4,29 +4,43 @@ const { addErrorContext, forEachInlineChild } = require("../helpers"); +const leftSpaceRe = /(?:^|\s)(\*\*?|__?)\s.*[^\\]\1/g; +const rightSpaceRe = /(?:^|[^\\])(\*\*?|__?).+\s\1(?:\s|$)/g; + module.exports = { "names": [ "MD037", "no-space-in-emphasis" ], "description": "Spaces inside emphasis markers", "tags": [ "whitespace", "emphasis" ], "function": function MD037(params, onError) { forEachInlineChild(params, "text", (token) => { - let left = true; - let match = /(?:^|\s)(\*\*?|__?)\s.*[^\\]\1/.exec(token.content); - if (!match) { - left = false; - match = /(?:^|[^\\])(\*\*?|__?).+\s\1(?:\s|$)/.exec(token.content); - } - if (match) { - const fullText = match[0]; - const line = params.lines[token.lineNumber - 1]; - if (line.includes(fullText)) { - const text = fullText.trim(); - const column = line.indexOf(text) + 1; - const length = text.length; - addErrorContext(onError, token.lineNumber, - text, left, !left, [ column, length ]); + [ leftSpaceRe, rightSpaceRe ].forEach((spaceRe, index) => { + let match = null; + while ((match = spaceRe.exec(token.content)) !== null) { + const [ fullText, marker ] = match; + const line = params.lines[token.lineNumber - 1]; + if (line.includes(fullText)) { + const text = fullText.trim(); + const column = line.indexOf(text) + 1; + const length = text.length; + const markerLength = marker.length; + const emphasized = text.slice(markerLength, length - markerLength); + const fixedText = `${marker}${emphasized.trim()}${marker}`; + addErrorContext( + onError, + token.lineNumber, + text, + index === 0, + index !== 0, + [ column, length ], + { + "editColumn": column, + "deleteCount": length, + "insertText": fixedText + } + ); + } } - } + }); }); } }; diff --git a/lib/md038.js b/lib/md038.js index c8bbfab2..424623a2 100644 --- a/lib/md038.js +++ b/lib/md038.js @@ -5,8 +5,8 @@ const { addErrorContext, filterTokens, forEachInlineCodeSpan, newLineRe } = require("../helpers"); -const startRe = /^\s([^`]|$)/; -const endRe = /[^`]\s$/; +const leftSpaceRe = /^\s([^`]|$)/; +const rightSpaceRe = /[^`]\s$/; module.exports = { "names": [ "MD038", "no-space-in-code" ], @@ -23,8 +23,8 @@ module.exports = { let rangeLength = code.length + (2 * tickCount); let rangeLineOffset = 0; const codeLines = code.split(newLineRe); - const left = startRe.test(code); - const right = !left && endRe.test(code); + const left = leftSpaceRe.test(code); + const right = !left && rightSpaceRe.test(code); if (right && (codeLines.length > 1)) { rangeIndex = 0; rangeLineOffset = codeLines.length - 1; @@ -36,8 +36,18 @@ module.exports = { const context = tokenLines[lineIndex + rangeLineOffset] .substring(rangeIndex, rangeIndex + rangeLength); addErrorContext( - onError, token.lineNumber + lineIndex + rangeLineOffset, - context, left, right, [ rangeIndex + 1, rangeLength ]); + onError, + token.lineNumber + lineIndex + rangeLineOffset, + context, + left, + right, + [ rangeIndex + 1, rangeLength ], + { + "editColumn": rangeIndex + (left ? tickCount : 0) + 1, + "deleteCount": rangeLength - (right ? tickCount : 0), + "insertText": code.trim() + } + ); } }); } diff --git a/lib/md039.js b/lib/md039.js index fb59d67f..146ebd90 100644 --- a/lib/md039.js +++ b/lib/md039.js @@ -2,8 +2,7 @@ "use strict"; -const { addErrorContext, filterTokens, rangeFromRegExp } = - require("../helpers"); +const { addErrorContext, filterTokens } = require("../helpers"); const spaceInLinkRe = /\[(?:\s+(?:[^\]]*?)\s*|(?:[^\]]*?)\s+)](?=\(\S*\))/; @@ -12,10 +11,11 @@ module.exports = { "description": "Spaces inside link text", "tags": [ "whitespace", "links" ], "function": function MD039(params, onError) { - filterTokens(params, "inline", function forToken(token) { + filterTokens(params, "inline", (token) => { + const { line, lineNumber, children } = token; let inLink = false; let linkText = ""; - token.children.forEach(function forChild(child) { + children.forEach((child) => { if (child.type === "link_open") { inLink = true; linkText = ""; @@ -24,9 +24,22 @@ module.exports = { const left = linkText.trimLeft().length !== linkText.length; const right = linkText.trimRight().length !== linkText.length; if (left || right) { - addErrorContext(onError, token.lineNumber, - "[" + linkText + "]", left, right, - rangeFromRegExp(token.line, spaceInLinkRe)); + const match = line.match(spaceInLinkRe); + const column = match.index + 1; + const length = match[0].length; + addErrorContext( + onError, + lineNumber, + `[${linkText}]`, + left, + right, + [ column, length ], + { + "editColumn": column + 1, + "deleteCount": length - 2, + "insertText": linkText.trim() + } + ); } } else if (inLink) { linkText += child.content;