From d7e319a06e9dc3db86ea29f82506cefcaa7b841f Mon Sep 17 00:00:00 2001 From: Simon Date: Wed, 6 Nov 2024 23:38:46 +0000 Subject: [PATCH 1/7] chore: ignore built cjs file --- .gitignore | 1 + 1 file changed, 1 insertion(+) diff --git a/.gitignore b/.gitignore index 2a77a84..b9a859a 100644 --- a/.gitignore +++ b/.gitignore @@ -2,3 +2,4 @@ node_modules/ npm-debug.log coverage/ .idea +index.cjs From f3dc0a5e084063a3bbe8e9e844f8067eeb14f020 Mon Sep 17 00:00:00 2001 From: Simon Date: Thu, 7 Nov 2024 00:03:28 +0000 Subject: [PATCH 2/7] feat(#53): add test for markdown parser ignoring wikilink within code blocks --- tests/fixtures/within-code.html | 3 +++ tests/fixtures/within-code.md | 7 ++++++ tests/markdown-wikilink-renderer.test.js | 27 ++++++++++++++++++++++++ 3 files changed, 37 insertions(+) create mode 100644 tests/fixtures/within-code.html create mode 100644 tests/fixtures/within-code.md diff --git a/tests/fixtures/within-code.html b/tests/fixtures/within-code.html new file mode 100644 index 0000000..3c5e69b --- /dev/null +++ b/tests/fixtures/within-code.html @@ -0,0 +1,3 @@ +

Test Markdown File

+
[[wiki link]]
+

This contains a wiki link [[wiki link]] within an inline code element. This sentance does not: Wiki Link.

diff --git a/tests/fixtures/within-code.md b/tests/fixtures/within-code.md new file mode 100644 index 0000000..1511178 --- /dev/null +++ b/tests/fixtures/within-code.md @@ -0,0 +1,7 @@ +# Test Markdown File + +``` +[[wiki link]] +``` + +This contains a wiki link `[[wiki link]]` within an inline code element. This sentance does not: [[wiki link]]. diff --git a/tests/markdown-wikilink-renderer.test.js b/tests/markdown-wikilink-renderer.test.js index b514b78..0426c0a 100644 --- a/tests/markdown-wikilink-renderer.test.js +++ b/tests/markdown-wikilink-renderer.test.js @@ -91,6 +91,33 @@ test('inline rule correctly parses single embed', t => { ); }); +test('inline rule ignores wikilink within code and pre tags', t => { + const wikilinkParser = new WikilinkParser(opts, new Set(), new Map()); + + wikilinkParser.linkCache.set('[[wiki link]]', { + title: 'Wiki Link', + link: '[[wiki link]]', + href: '/wiki-link/', + content: 'Wiki Link', + isEmbed: false, + }); + + const md = MarkdownIt({html: true}); + md.inline.ruler.push('inline_wikilink', wikilinkInlineRule( + wikilinkParser + )); + + md.renderer.rules.inline_wikilink = wikilinkRenderRule(); + + const markdown = fs.readFileSync(__dirname + '/fixtures/within-code.md', {encoding:'utf8', flag:'r'}); + const html = fs.readFileSync(__dirname + '/fixtures/within-code.html', {encoding:'utf8', flag:'r'}); + + t.is( + normalize(md.render(markdown)), + normalize(html) + ); +}); + test('inline rule correctly parses mixed wikilink and embed in multiline input', t => { const wikilinkParser = new WikilinkParser(opts, new Set(), new Map()); From f22cb1b53ee53f695eea1315f27da0f45c503480 Mon Sep 17 00:00:00 2001 From: Simon Date: Thu, 7 Nov 2024 00:06:55 +0000 Subject: [PATCH 3/7] TDD(#53): add failing test for feature --- tests/html-internal-link-parser.test.js | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/tests/html-internal-link-parser.test.js b/tests/html-internal-link-parser.test.js index 9547c39..a5a8255 100644 --- a/tests/html-internal-link-parser.test.js +++ b/tests/html-internal-link-parser.test.js @@ -23,3 +23,10 @@ test('html link parser grabs multiple href, ignoring external links', t => { t.is(0, expectedLinks.length); }); + +test('html link parser ignores href within code blocks', t => { + const parser = new HTMLLinkParser(new DeadLinks()); + const links = parser.find('this is a link home', pageDirectory); + + t.is(0, links.length); +}); From 4fec5dbbe9124a724d351752f3784aafd8472101 Mon Sep 17 00:00:00 2001 From: Simon Date: Thu, 7 Nov 2024 00:26:08 +0000 Subject: [PATCH 4/7] chore(#53): require jsdom --- package-lock.json | 346 +++++++++++++++++++++++++++++++++++++++++++++- package.json | 1 + 2 files changed, 341 insertions(+), 6 deletions(-) diff --git a/package-lock.json b/package-lock.json index 259ce72..d730f96 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,16 +1,17 @@ { "name": "@photogabble/eleventy-plugin-interlinker", - "version": "1.1.0-rc4", + "version": "1.1.0-rc5", "lockfileVersion": 3, "requires": true, "packages": { "": { "name": "@photogabble/eleventy-plugin-interlinker", - "version": "1.1.0-rc4", + "version": "1.1.0-rc5", "license": "MIT", "dependencies": { "chalk": "^4.1.1", "entities": "^4.5.0", + "jsdom": "^25.0.1", "markdown-it": "^14.1.0" }, "devDependencies": { @@ -659,6 +660,17 @@ "node": ">=0.4.0" } }, + "node_modules/agent-base": { + "version": "7.1.1", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-7.1.1.tgz", + "integrity": "sha512-H0TSyFNDMomMNJQBn8wFV5YC/2eJ+VXECwOadZJT554xP6cODZHPX3H9QMQECxvrgiSOP1pHjy1sMWQVYJOUOA==", + "dependencies": { + "debug": "^4.3.4" + }, + "engines": { + "node": ">= 14" + } + }, "node_modules/aggregate-error": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/aggregate-error/-/aggregate-error-4.0.1.tgz", @@ -783,6 +795,11 @@ "integrity": "sha512-BSHWgDSAiKs50o2Re8ppvp3seVHXSRM44cdSsT9FfNEUUZLOGWVCsiWaRPWM1Znn+mqZ1OfVZ3z3DWEzSp7hRA==", "dev": true }, + "node_modules/asynckit": { + "version": "0.4.0", + "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", + "integrity": "sha512-Oei9OH4tRh0YqU3GxhX79dM/mwVgvbZJaSNaRk+bshkj0S5cfHcgYakreBjrHwatXKbz+IoIdYLxrKim2MjW0Q==" + }, "node_modules/ava": { "version": "5.3.1", "resolved": "https://registry.npmjs.org/ava/-/ava-5.3.1.tgz", @@ -1412,6 +1429,17 @@ "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz", "integrity": "sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==" }, + "node_modules/combined-stream": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", + "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", + "dependencies": { + "delayed-stream": "~1.0.0" + }, + "engines": { + "node": ">= 0.8" + } + }, "node_modules/commander": { "version": "10.0.1", "resolved": "https://registry.npmjs.org/commander/-/commander-10.0.1.tgz", @@ -1481,6 +1509,17 @@ "node": ">= 8" } }, + "node_modules/cssstyle": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/cssstyle/-/cssstyle-4.1.0.tgz", + "integrity": "sha512-h66W1URKpBS5YMI/V8PyXvTMFT8SupJ1IzoIV8IeBC/ji8WVmrO8dGlTi+2dh6whmdk6BiKJLD/ZBkhWbcg6nA==", + "dependencies": { + "rrweb-cssom": "^0.7.1" + }, + "engines": { + "node": ">=18" + } + }, "node_modules/currently-unhandled": { "version": "0.4.1", "resolved": "https://registry.npmjs.org/currently-unhandled/-/currently-unhandled-0.4.1.tgz", @@ -1493,6 +1532,18 @@ "node": ">=0.10.0" } }, + "node_modules/data-urls": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/data-urls/-/data-urls-5.0.0.tgz", + "integrity": "sha512-ZYP5VBHshaDAiVZxjbRVcFJpc+4xGgT0bK3vzy1HLN8jTO975HEbuYzZJcHoQEY5K1a0z8YayJkyVETa08eNTg==", + "dependencies": { + "whatwg-mimetype": "^4.0.0", + "whatwg-url": "^14.0.0" + }, + "engines": { + "node": ">=18" + } + }, "node_modules/date-time": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/date-time/-/date-time-3.1.0.tgz", @@ -1509,7 +1560,6 @@ "version": "4.3.7", "resolved": "https://registry.npmjs.org/debug/-/debug-4.3.7.tgz", "integrity": "sha512-Er2nc/H7RrMXZBFCEim6TCmMk02Z8vLC2Rbi1KEBggpo0fS6l0S1nnapwmIi3yW/+GOJap1Krg4w0Hg80oCqgQ==", - "dev": true, "dependencies": { "ms": "^2.1.3" }, @@ -1522,6 +1572,11 @@ } } }, + "node_modules/decimal.js": { + "version": "10.4.3", + "resolved": "https://registry.npmjs.org/decimal.js/-/decimal.js-10.4.3.tgz", + "integrity": "sha512-VBBaLc1MgL5XpzgIP7ny5Z6Nx3UrRkIViUkPUdtl9aya5amy3De1gsUUSB1g3+3sExYNjCAsAznmukyxCb1GRA==" + }, "node_modules/define-data-property": { "version": "1.1.4", "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", @@ -1556,6 +1611,14 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/delayed-stream": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", + "integrity": "sha512-ZySD7Nf91aLB0RxL4KGrKHBXl7Eds1DAmEdcoVawXnLD7SDhpNgtuII2aAkg7a7QS41jxPSZ17p4VdGnMHk3MQ==", + "engines": { + "node": ">=0.4.0" + } + }, "node_modules/depd": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/depd/-/depd-2.0.0.tgz", @@ -1994,6 +2057,19 @@ "node": ">=8.0.0" } }, + "node_modules/form-data": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/form-data/-/form-data-4.0.1.tgz", + "integrity": "sha512-tzN8e4TX8+kkxGPK8D5u0FNmjPUjw3lwC9lSLxxoB/+GtsJG91CO8bSWy73APlgAZzZbXEYZJuxjkHH2w+Ezhw==", + "dependencies": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + }, + "engines": { + "node": ">= 6" + } + }, "node_modules/fresh": { "version": "0.5.2", "resolved": "https://registry.npmjs.org/fresh/-/fresh-0.5.2.tgz", @@ -2286,6 +2362,17 @@ "node": ">= 0.4" } }, + "node_modules/html-encoding-sniffer": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/html-encoding-sniffer/-/html-encoding-sniffer-4.0.0.tgz", + "integrity": "sha512-Y22oTqIU4uuPgEemfz7NDJz6OeKf12Lsu+QC+s3BVpda64lTiMYCyGwg5ki4vFxkMwQdeZDl2adZoqUgdFuTgQ==", + "dependencies": { + "whatwg-encoding": "^3.1.1" + }, + "engines": { + "node": ">=18" + } + }, "node_modules/html-escaper": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/html-escaper/-/html-escaper-2.0.2.tgz", @@ -2348,6 +2435,41 @@ "node": ">= 0.8" } }, + "node_modules/http-proxy-agent": { + "version": "7.0.2", + "resolved": "https://registry.npmjs.org/http-proxy-agent/-/http-proxy-agent-7.0.2.tgz", + "integrity": "sha512-T1gkAiYYDWYx3V5Bmyu7HcfcvL7mUrTWiM6yOfa3PIphViJ/gFPbvidQ+veqSOHci/PxBcDabeUNCzpOODJZig==", + "dependencies": { + "agent-base": "^7.1.0", + "debug": "^4.3.4" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/https-proxy-agent": { + "version": "7.0.5", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-7.0.5.tgz", + "integrity": "sha512-1e4Wqeblerz+tMKPIq2EMGiiWW1dIjZOksyHWSUm1rmuvw/how9hBHZ38lAGj5ID4Ik6EdkOw7NmWPy6LAwalw==", + "dependencies": { + "agent-base": "^7.0.2", + "debug": "4" + }, + "engines": { + "node": ">= 14" + } + }, + "node_modules/iconv-lite": { + "version": "0.6.3", + "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz", + "integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==", + "dependencies": { + "safer-buffer": ">= 2.1.2 < 3.0.0" + }, + "engines": { + "node": ">=0.10.0" + } + }, "node_modules/ignore": { "version": "5.3.2", "resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.2.tgz", @@ -2531,6 +2653,11 @@ "node": ">=0.10.0" } }, + "node_modules/is-potential-custom-element-name": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/is-potential-custom-element-name/-/is-potential-custom-element-name-1.0.1.tgz", + "integrity": "sha512-bCYeRA2rVibKZd+s2625gGnGF/t7DSqDs4dP7CrLA1m7jKWz6pps0LpYLJN8Q64HtmPKJ1hrN3nzPNKFEKOUiQ==" + }, "node_modules/is-promise": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-4.0.0.tgz", @@ -2636,6 +2763,45 @@ "js-yaml": "bin/js-yaml.js" } }, + "node_modules/jsdom": { + "version": "25.0.1", + "resolved": "https://registry.npmjs.org/jsdom/-/jsdom-25.0.1.tgz", + "integrity": "sha512-8i7LzZj7BF8uplX+ZyOlIz86V6TAsSs+np6m1kpW9u0JWi4z/1t+FzcK1aek+ybTnAC4KhBL4uXCNT0wcUIeCw==", + "dependencies": { + "cssstyle": "^4.1.0", + "data-urls": "^5.0.0", + "decimal.js": "^10.4.3", + "form-data": "^4.0.0", + "html-encoding-sniffer": "^4.0.0", + "http-proxy-agent": "^7.0.2", + "https-proxy-agent": "^7.0.5", + "is-potential-custom-element-name": "^1.0.1", + "nwsapi": "^2.2.12", + "parse5": "^7.1.2", + "rrweb-cssom": "^0.7.1", + "saxes": "^6.0.0", + "symbol-tree": "^3.2.4", + "tough-cookie": "^5.0.0", + "w3c-xmlserializer": "^5.0.0", + "webidl-conversions": "^7.0.0", + "whatwg-encoding": "^3.1.1", + "whatwg-mimetype": "^4.0.0", + "whatwg-url": "^14.0.0", + "ws": "^8.18.0", + "xml-name-validator": "^5.0.0" + }, + "engines": { + "node": ">=18" + }, + "peerDependencies": { + "canvas": "^2.11.2" + }, + "peerDependenciesMeta": { + "canvas": { + "optional": true + } + } + }, "node_modules/junk": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/junk/-/junk-1.0.3.tgz", @@ -2906,6 +3072,25 @@ "node": ">=10.0.0" } }, + "node_modules/mime-db": { + "version": "1.52.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.52.0.tgz", + "integrity": "sha512-sPU4uV7dYlvtWJxwwxHD0PuihVNiE7TyAbQ5SWxDCB9mUYvOgroQOwYQQOKPJ8CIbE+1ETVlOoK1UC2nU3gYvg==", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/mime-types": { + "version": "2.1.35", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.35.tgz", + "integrity": "sha512-ZDY+bPm5zTTF+YpCrAU9nK0UgICYPT0QtT1NZWFv4s++TNkcgVaT0g6+4R2uI4MjQjzysHB1zxuWL50hzaeXiw==", + "dependencies": { + "mime-db": "1.52.0" + }, + "engines": { + "node": ">= 0.6" + } + }, "node_modules/mimic-fn": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-4.0.0.tgz", @@ -2978,8 +3163,7 @@ "node_modules/ms": { "version": "2.1.3", "resolved": "https://registry.npmjs.org/ms/-/ms-2.1.3.tgz", - "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==", - "dev": true + "integrity": "sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==" }, "node_modules/nise": { "version": "5.1.9", @@ -3057,6 +3241,11 @@ "node": ">= 6" } }, + "node_modules/nwsapi": { + "version": "2.2.13", + "resolved": "https://registry.npmjs.org/nwsapi/-/nwsapi-2.2.13.tgz", + "integrity": "sha512-cTGB9ptp9dY9A5VbMSe7fQBcl/tt22Vcqdq8+eN93rblOuE0aCFu4aZ2vMwct/2t+lFnosm8RkQW1I0Omb1UtQ==" + }, "node_modules/object-keys": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/object-keys/-/object-keys-1.1.1.tgz", @@ -3206,6 +3395,17 @@ "integrity": "sha512-/2qh0lav6CmI15FzA3i/2Bzk2zCgQhGMkvhOhKNcBVQ1ldgpbfiNTVslmooUmWJcADi1f1kIeynbDRVzNlfR6Q==", "dev": true }, + "node_modules/parse5": { + "version": "7.2.1", + "resolved": "https://registry.npmjs.org/parse5/-/parse5-7.2.1.tgz", + "integrity": "sha512-BuBYQYlv1ckiPdQi/ohiivi9Sagc9JG+Ozs0r7b/0iK3sKmrb0b9FdWdBbOdx6hBCM/F9Ir82ofnBhtZOjCRPQ==", + "dependencies": { + "entities": "^4.5.0" + }, + "funding": { + "url": "https://github.com/inikulin/parse5?sponsor=1" + } + }, "node_modules/parseurl": { "version": "1.3.3", "resolved": "https://registry.npmjs.org/parseurl/-/parseurl-1.3.3.tgz", @@ -3495,6 +3695,14 @@ "integrity": "sha512-yPw4Sng1gWghHQWj0B3ZggWUm4qVbPwPFcRG8KyxiU7J2OHFSoEHKS+EZ3fv5l1t9CyCiop6l/ZYeWbrgoQejw==", "dev": true }, + "node_modules/punycode": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/punycode/-/punycode-2.3.1.tgz", + "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==", + "engines": { + "node": ">=6" + } + }, "node_modules/punycode.js": { "version": "2.3.1", "resolved": "https://registry.npmjs.org/punycode.js/-/punycode.js-2.3.1.tgz", @@ -3634,6 +3842,11 @@ "fsevents": "~2.3.2" } }, + "node_modules/rrweb-cssom": { + "version": "0.7.1", + "resolved": "https://registry.npmjs.org/rrweb-cssom/-/rrweb-cssom-0.7.1.tgz", + "integrity": "sha512-TrEMa7JGdVm0UThDJSx7ddw5nVm3UJS9o9CCIZ72B1vSyEZoziDqBYP3XIoi/12lKrJR8rE3jeFHMok2F/Mnsg==" + }, "node_modules/run-parallel": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/run-parallel/-/run-parallel-1.2.0.tgz", @@ -3657,6 +3870,22 @@ "queue-microtask": "^1.2.2" } }, + "node_modules/safer-buffer": { + "version": "2.1.2", + "resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz", + "integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==" + }, + "node_modules/saxes": { + "version": "6.0.0", + "resolved": "https://registry.npmjs.org/saxes/-/saxes-6.0.0.tgz", + "integrity": "sha512-xAg7SOnEhrm5zI3puOOKyy1OMcMlIJZYNJY7xLBwSze0UjhPLnWfj2GF2EpT0jmzaJKIWKHLsaSSajf35bcYnA==", + "dependencies": { + "xmlchars": "^2.2.0" + }, + "engines": { + "node": ">=v12.22.7" + } + }, "node_modules/section-matter": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/section-matter/-/section-matter-1.0.0.tgz", @@ -4066,6 +4295,11 @@ "node": ">=8" } }, + "node_modules/symbol-tree": { + "version": "3.2.4", + "resolved": "https://registry.npmjs.org/symbol-tree/-/symbol-tree-3.2.4.tgz", + "integrity": "sha512-9QNk5KwDF+Bvz+PyObkmSYjI5ksVUYtjW7AU22r2NKcfLJcXp96hkDWU3+XndOsUb+AQ9QhfzfCT2O+CNWT5Tw==" + }, "node_modules/temp-dir": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/temp-dir/-/temp-dir-3.0.0.tgz", @@ -4119,6 +4353,22 @@ "node": ">=4" } }, + "node_modules/tldts": { + "version": "6.1.58", + "resolved": "https://registry.npmjs.org/tldts/-/tldts-6.1.58.tgz", + "integrity": "sha512-MQJrJhjHOYGYb8DobR6Y4AdDbd4TYkyQ+KBDVc5ODzs1cbrvPpfN1IemYi9jfipJ/vR1YWvrDli0hg1y19VRoA==", + "dependencies": { + "tldts-core": "^6.1.58" + }, + "bin": { + "tldts": "bin/cli.js" + } + }, + "node_modules/tldts-core": { + "version": "6.1.58", + "resolved": "https://registry.npmjs.org/tldts-core/-/tldts-core-6.1.58.tgz", + "integrity": "sha512-dR936xmhBm7AeqHIhCWwK765gZ7dFyL+IqLSFAjJbFlUXGMLCb8i2PzlzaOuWBuplBTaBYseSb565nk/ZEM0Bg==" + }, "node_modules/to-regex-range": { "version": "5.0.1", "resolved": "https://registry.npmjs.org/to-regex-range/-/to-regex-range-5.0.1.tgz", @@ -4140,6 +4390,28 @@ "node": ">=0.6" } }, + "node_modules/tough-cookie": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-5.0.0.tgz", + "integrity": "sha512-FRKsF7cz96xIIeMZ82ehjC3xW2E+O2+v11udrDYewUbszngYhsGa8z6YUMMzO9QJZzzyd0nGGXnML/TReX6W8Q==", + "dependencies": { + "tldts": "^6.1.32" + }, + "engines": { + "node": ">=16" + } + }, + "node_modules/tr46": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/tr46/-/tr46-5.0.0.tgz", + "integrity": "sha512-tk2G5R2KRwBd+ZN0zaEXpmzdKyOYksXwywulIX95MBODjSzMIuQnQ3m8JxgbhnL1LeVo7lqQKsYa1O3Htl7K5g==", + "dependencies": { + "punycode": "^2.3.1" + }, + "engines": { + "node": ">=18" + } + }, "node_modules/type-detect": { "version": "4.0.8", "resolved": "https://registry.npmjs.org/type-detect/-/type-detect-4.0.8.tgz", @@ -4195,6 +4467,25 @@ "node": ">=10.12.0" } }, + "node_modules/w3c-xmlserializer": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/w3c-xmlserializer/-/w3c-xmlserializer-5.0.0.tgz", + "integrity": "sha512-o8qghlI8NZHU1lLPrpi2+Uq7abh4GGPpYANlalzWxyWteJOCsr/P+oPBA49TOLu5FTZO4d3F9MnWJfiMo4BkmA==", + "dependencies": { + "xml-name-validator": "^5.0.0" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/webidl-conversions": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-7.0.0.tgz", + "integrity": "sha512-VwddBukDzu71offAQR975unBIGqfKZpM+8ZX6ySk8nYhVoo5CYaZyzt3YBvYtRtO+aoGlqxPg/B87NGVZ/fu6g==", + "engines": { + "node": ">=12" + } + }, "node_modules/well-known-symbols": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/well-known-symbols/-/well-known-symbols-2.0.0.tgz", @@ -4204,6 +4495,37 @@ "node": ">=6" } }, + "node_modules/whatwg-encoding": { + "version": "3.1.1", + "resolved": "https://registry.npmjs.org/whatwg-encoding/-/whatwg-encoding-3.1.1.tgz", + "integrity": "sha512-6qN4hJdMwfYBtE3YBTTHhoeuUrDBPZmbQaxWAqSALV/MeEnR5z1xd8UKud2RAkFoPkmB+hli1TZSnyi84xz1vQ==", + "dependencies": { + "iconv-lite": "0.6.3" + }, + "engines": { + "node": ">=18" + } + }, + "node_modules/whatwg-mimetype": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/whatwg-mimetype/-/whatwg-mimetype-4.0.0.tgz", + "integrity": "sha512-QaKxh0eNIi2mE9p2vEdzfagOKHCcj1pJ56EEHGQOVxp8r9/iszLUUV7v89x9O1p/T+NlTM5W7jW6+cz4Fq1YVg==", + "engines": { + "node": ">=18" + } + }, + "node_modules/whatwg-url": { + "version": "14.0.0", + "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-14.0.0.tgz", + "integrity": "sha512-1lfMEm2IEr7RIV+f4lUNPOqfFL+pO+Xw3fJSqmjX9AbXcXcYOkCe1P6+9VBZB6n94af16NfZf+sSk0JCBZC9aw==", + "dependencies": { + "tr46": "^5.0.0", + "webidl-conversions": "^7.0.0" + }, + "engines": { + "node": ">=18" + } + }, "node_modules/which": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", @@ -4354,7 +4676,6 @@ "version": "8.18.0", "resolved": "https://registry.npmjs.org/ws/-/ws-8.18.0.tgz", "integrity": "sha512-8VbfWfHLbbwu3+N6OKsOMpBdT4kXPDDB9cJk2bJ6mh9ucxdlnNvH1e+roYkKmN9Nxw2yjz7VzeO9oOz2zJ04Pw==", - "dev": true, "engines": { "node": ">=10.0.0" }, @@ -4371,6 +4692,19 @@ } } }, + "node_modules/xml-name-validator": { + "version": "5.0.0", + "resolved": "https://registry.npmjs.org/xml-name-validator/-/xml-name-validator-5.0.0.tgz", + "integrity": "sha512-EvGK8EJ3DhaHfbRlETOWAS5pO9MZITeauHKJyb8wyajUfQUenkIg2MvLDTZ4T/TgIcm3HU0TFBgWWboAZ30UHg==", + "engines": { + "node": ">=18" + } + }, + "node_modules/xmlchars": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/xmlchars/-/xmlchars-2.2.0.tgz", + "integrity": "sha512-JZnDKK8B0RCDw84FNdDAIpZK+JuJw+s7Lz8nksI7SIuU3UXJJslUthsi+uWBUYOwPFwW7W7PRLRfUKpxjtjFCw==" + }, "node_modules/y18n": { "version": "5.0.8", "resolved": "https://registry.npmjs.org/y18n/-/y18n-5.0.8.tgz", diff --git a/package.json b/package.json index 6d5f619..fdf5b67 100644 --- a/package.json +++ b/package.json @@ -53,6 +53,7 @@ "dependencies": { "chalk": "^4.1.1", "entities": "^4.5.0", + "jsdom": "^25.0.1", "markdown-it": "^14.1.0" }, "devDependencies": { From 81589a0e137dff2bfeee0321776b5c9fa19af5ad Mon Sep 17 00:00:00 2001 From: Simon Date: Thu, 7 Nov 2024 00:37:04 +0000 Subject: [PATCH 5/7] chore(#53): fix typo --- tests/fixtures/within-code.html | 2 +- tests/fixtures/within-code.md | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/fixtures/within-code.html b/tests/fixtures/within-code.html index 3c5e69b..7b399e9 100644 --- a/tests/fixtures/within-code.html +++ b/tests/fixtures/within-code.html @@ -1,3 +1,3 @@

Test Markdown File

[[wiki link]]
-

This contains a wiki link [[wiki link]] within an inline code element. This sentance does not: Wiki Link.

+

This contains a wiki link [[wiki link]] within an inline code element. This sentence does not: Wiki Link.

diff --git a/tests/fixtures/within-code.md b/tests/fixtures/within-code.md index 1511178..9a74dbb 100644 --- a/tests/fixtures/within-code.md +++ b/tests/fixtures/within-code.md @@ -4,4 +4,4 @@ [[wiki link]] ``` -This contains a wiki link `[[wiki link]]` within an inline code element. This sentance does not: [[wiki link]]. +This contains a wiki link `[[wiki link]]` within an inline code element. This sentence does not: [[wiki link]]. From 4254a186557f43b752ad09329a9969b51620b05a Mon Sep 17 00:00:00 2001 From: Simon Date: Thu, 7 Nov 2024 00:49:59 +0000 Subject: [PATCH 6/7] bugfix: correct expected and actual values --- tests/html-internal-link-parser.test.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/html-internal-link-parser.test.js b/tests/html-internal-link-parser.test.js index a5a8255..a2abacd 100644 --- a/tests/html-internal-link-parser.test.js +++ b/tests/html-internal-link-parser.test.js @@ -9,7 +9,7 @@ test('html link parser grabs multiple href, ignoring external links', t => { const parser = new HTMLLinkParser(new DeadLinks()); const links = parser.find('

Hello world this is a link home and this is a link somewhere

The following link should be ignored example.com.

', pageDirectory); - t.is(2, links.length); + t.is(links.length, 2); const expectedLinks = ['/home', '/somewhere']; for (const link of links) { @@ -21,7 +21,7 @@ test('html link parser grabs multiple href, ignoring external links', t => { expectedLinks.splice(idx, 1); } - t.is(0, expectedLinks.length); + t.is(expectedLinks.length, 0); }); test('html link parser ignores href within code blocks', t => { From 939e15136709f79bfb4e2aaeabd3cd3bcd03819b Mon Sep 17 00:00:00 2001 From: Simon Date: Thu, 7 Nov 2024 00:51:03 +0000 Subject: [PATCH 7/7] feat(#53): use JSDOM to parse internal anchor tags --- src/html-link-parser.js | 16 ++++++++++++++-- tests/html-internal-link-parser.test.js | 10 +++++++--- 2 files changed, 21 insertions(+), 5 deletions(-) diff --git a/src/html-link-parser.js b/src/html-link-parser.js index 1027a3f..5c98846 100644 --- a/src/html-link-parser.js +++ b/src/html-link-parser.js @@ -1,3 +1,4 @@ +import {JSDOM} from 'jsdom'; export default class HTMLLinkParser { /** @@ -24,7 +25,7 @@ export default class HTMLLinkParser { */ parseSingle(link, pageDirectory) { const meta = { - href: link.slice(6, -1) + href: link .replace(/.(md|markdown)\s?$/i, "") .replace("\\", "") .trim() @@ -61,8 +62,19 @@ export default class HTMLLinkParser { * @return {Array} */ find(document, pageDirectory) { + const dom = new JSDOM(document); + const anchors = dom.window.document.getElementsByTagName('a'); + const toParse = []; + + for (const anchor of anchors) { + // Ignore any anchor tags within either code or pre tags + if (anchor.closest('code,pre')) continue; + // Ignore any links that don't begin with / denoting internal links + if (anchor.href.startsWith('/')) toParse.push(anchor.href); + } + return this.parseMultiple( - (document.match(this.internalLinkRegex) || []), + toParse, pageDirectory ) } diff --git a/tests/html-internal-link-parser.test.js b/tests/html-internal-link-parser.test.js index a2abacd..54bde61 100644 --- a/tests/html-internal-link-parser.test.js +++ b/tests/html-internal-link-parser.test.js @@ -2,8 +2,12 @@ import HTMLLinkParser from '../src/html-link-parser.js' import DeadLinks from '../src/dead-links.js'; import {pageLookup} from '../src/find-page.js'; import test from 'ava'; +import fs from "node:fs"; +import path from "node:path"; +import {fileURLToPath} from "node:url"; const pageDirectory = pageLookup([]); +const __dirname = path.dirname(fileURLToPath(import.meta.url)); test('html link parser grabs multiple href, ignoring external links', t => { const parser = new HTMLLinkParser(new DeadLinks()); @@ -25,8 +29,8 @@ test('html link parser grabs multiple href, ignoring external links', t => { }); test('html link parser ignores href within code blocks', t => { - const parser = new HTMLLinkParser(new DeadLinks()); - const links = parser.find('this is a link home', pageDirectory); + t.is(0, ((new HTMLLinkParser(new DeadLinks())).find('this is a link home', pageDirectory)).length); - t.is(0, links.length); + const html = fs.readFileSync(__dirname + '/fixtures/within-code.html', {encoding:'utf8', flag:'r'}); + t.is(1, ((new HTMLLinkParser(new DeadLinks())).find(html, pageDirectory)).length); });