├── .editorconfig ├── .gitattributes ├── .github └── workflows │ ├── bb.yml │ └── main.yml ├── .gitignore ├── .npmrc ├── .prettierignore ├── changelog.md ├── doc ├── getting-started.md └── plugins.md ├── license ├── logo-square.svg ├── logo.svg ├── package.json ├── packages ├── rehype-cli │ ├── .npmrc │ ├── cli.js │ ├── license │ ├── package.json │ ├── readme.md │ └── tsconfig.json ├── rehype-parse │ ├── .npmrc │ ├── index.d.ts │ ├── index.js │ ├── lib │ │ └── index.js │ ├── license │ ├── package.json │ ├── readme.md │ └── tsconfig.json ├── rehype-stringify │ ├── .npmrc │ ├── index.d.ts │ ├── index.js │ ├── lib │ │ └── index.js │ ├── license │ ├── package.json │ ├── readme.md │ └── tsconfig.json └── rehype │ ├── .npmrc │ ├── index.d.ts │ ├── index.js │ ├── license │ ├── package.json │ ├── readme.md │ └── tsconfig.json ├── readme.md ├── test ├── api.js ├── cli.js ├── fixtures │ ├── adoption │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── aria │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── body-body-attributes │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── body-html-attributes │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── character-data │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── comment │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── comments │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── directive-in-fragment │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── doctype-almost-standards │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── doctype-legacy-double │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── doctype-legacy-single │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── doctype-nameless │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── doctype-quirksmode-ibm │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── doctype-quirksmode-xml │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── doctype-quotes-double │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── doctype-quotes-single │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── doctype │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-attributes-names │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-attributes │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-auto-close-document │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-auto-close-fragment │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-broken-close │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-children │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-closing-attributes │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-closing │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-empty │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-loose-close-document │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-loose-close-fragment │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-opening │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-void-close │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element-void │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── element │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── empty-document │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── empty-fragment │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── entities-in-literals │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── entities │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── html-in-svg-in-html │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── mathml │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── noscript │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── processing-instruction │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── quirksmode-off │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── quirksmode-on │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── svg-in-html │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── svg │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ ├── verbose │ │ ├── config.json │ │ ├── index.html │ │ ├── index.json │ │ └── result.html │ └── xhtml │ │ ├── index.html │ │ ├── index.json │ │ └── result.html ├── index.js ├── parse-error.js └── parse-error │ ├── abandoned-head-element-child │ ├── index.html │ └── messages.json │ ├── abrupt-closing-of-empty-comment │ ├── index.html │ └── messages.json │ ├── abrupt-doctype-public-identifier │ ├── index.html │ └── messages.json │ ├── abrupt-doctype-system-identifier │ ├── index.html │ └── messages.json │ ├── absence-of-digits-in-numeric-character-reference │ ├── index.html │ └── messages.json │ ├── cdata-in-html-content │ ├── index.html │ └── messages.json │ ├── character-reference-outside-unicode-range │ ├── index.html │ └── messages.json │ ├── closing-of-element-with-open-child-elements │ ├── index.html │ └── messages.json │ ├── control-character-in-input-stream │ ├── index.html │ └── messages.json │ ├── control-character-reference │ ├── index.html │ └── messages.json │ ├── disallowed-content-in-noscript-in-head │ ├── index.html │ └── messages.json │ ├── duplicate-attribute │ ├── index.html │ └── messages.json │ ├── end-tag-with-attributes │ ├── index.html │ └── messages.json │ ├── end-tag-with-trailing-solidus │ ├── index.html │ └── messages.json │ ├── end-tag-without-matching-open-element │ ├── index.html │ └── messages.json │ ├── eof-before-tag-name │ ├── index.html │ └── messages.json │ ├── eof-in-cdata │ ├── index.html │ └── messages.json │ ├── eof-in-comment │ ├── index.html │ └── messages.json │ ├── eof-in-doctype │ ├── index.html │ └── messages.json │ ├── eof-in-element-that-can-contain-only-text │ ├── index.html │ └── messages.json │ ├── eof-in-script-html-comment-like-text │ ├── index.html │ └── messages.json │ ├── eof-in-tag │ ├── index.html │ └── messages.json │ ├── incorrectly-closed-comment │ ├── index.html │ └── messages.json │ ├── incorrectly-opened-comment │ ├── index.html │ └── messages.json │ ├── invalid-character-sequence-after-doctype-name │ ├── index.html │ └── messages.json │ ├── invalid-first-character-of-tag-name │ ├── index.html │ └── messages.json │ ├── misplaced-doctype │ ├── index.html │ └── messages.json │ ├── misplaced-start-tag-for-head-element │ ├── index.html │ └── messages.json │ ├── missing-attribute-value │ ├── index.html │ └── messages.json │ ├── missing-doctype-name │ ├── index.html │ └── messages.json │ ├── missing-doctype-public-identifier │ ├── index.html │ └── messages.json │ ├── missing-doctype-system-identifier │ ├── index.html │ └── messages.json │ ├── missing-doctype │ ├── index.html │ └── messages.json │ ├── missing-end-tag-name │ ├── index.html │ └── messages.json │ ├── missing-quote-before-doctype-public-identifier │ ├── index.html │ └── messages.json │ ├── missing-quote-before-doctype-system-identifier │ ├── index.html │ └── messages.json │ ├── missing-semicolon-after-character-reference │ ├── index.html │ └── messages.json │ ├── missing-whitespace-after-doctype-public-keyword │ ├── index.html │ └── messages.json │ ├── missing-whitespace-after-doctype-system-keyword │ ├── index.html │ └── messages.json │ ├── missing-whitespace-before-doctype-name │ ├── index.html │ └── messages.json │ ├── missing-whitespace-between-attributes │ ├── index.html │ └── messages.json │ ├── missing-whitespace-between-doctype-public-and-system-identifiers │ ├── index.html │ └── messages.json │ ├── nested-comment │ ├── index.html │ └── messages.json │ ├── nested-noscript-in-head │ ├── index.html │ └── messages.json │ ├── non-conforming-doctype │ ├── index.html │ └── messages.json │ ├── non-void-html-element-start-tag-with-trailing-solidus │ ├── index.html │ └── messages.json │ ├── noncharacter-character-reference │ ├── index.html │ └── messages.json │ ├── noncharacter-in-input-stream │ ├── index.html │ └── messages.json │ ├── null-character-reference │ ├── index.html │ └── messages.json │ ├── open-elements-left-after-eof │ ├── index.html │ └── messages.json │ ├── surrogate-character-reference │ ├── index.html │ └── messages.json │ ├── unexpected-character-after-doctype-system-identifier │ ├── index.html │ └── messages.json │ ├── unexpected-character-in-attribute-name │ ├── index.html │ └── messages.json │ ├── unexpected-character-in-unquoted-attribute-value │ ├── index.html │ └── messages.json │ ├── unexpected-equals-sign-before-attribute-name │ ├── index.html │ └── messages.json │ ├── unexpected-null-character │ ├── index.html │ └── messages.json │ ├── unexpected-question-mark-instead-of-tag-name │ ├── index.html │ └── messages.json │ ├── unexpected-solidus-in-tag │ ├── index.html │ └── messages.json │ └── unknown-named-character-reference │ ├── index.html │ └── messages.json └── tsconfig.json /.editorconfig: -------------------------------------------------------------------------------- 1 | root = true 2 | 3 | [*] 4 | charset = utf-8 5 | end_of_line = lf 6 | indent_size = 2 7 | indent_style = space 8 | insert_final_newline = true 9 | trim_trailing_whitespace = true 10 | -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | # https://github.com/github/linguist/blob/HEAD/docs/overrides.md 2 | test/**/*.html linguist-vendored 3 | -------------------------------------------------------------------------------- /.github/workflows/bb.yml: -------------------------------------------------------------------------------- 1 | jobs: 2 | main: 3 | runs-on: ubuntu-latest 4 | steps: 5 | - uses: unifiedjs/beep-boop-beta@main 6 | with: 7 | repo-token: ${{secrets.GITHUB_TOKEN}} 8 | name: bb 9 | on: 10 | issues: 11 | types: [closed, edited, labeled, opened, reopened, unlabeled] 12 | pull_request_target: 13 | types: [closed, edited, labeled, opened, reopened, unlabeled] 14 | -------------------------------------------------------------------------------- /.github/workflows/main.yml: -------------------------------------------------------------------------------- 1 | jobs: 2 | main: 3 | name: ${{matrix.node}} 4 | runs-on: ubuntu-latest 5 | steps: 6 | - uses: actions/checkout@v4 7 | - uses: actions/setup-node@v4 8 | with: 9 | node-version: ${{matrix.node}} 10 | - run: npm install 11 | - run: npm test 12 | - uses: codecov/codecov-action@v4 13 | strategy: 14 | matrix: 15 | node: 16 | - lts/hydrogen 17 | - node 18 | name: main 19 | on: 20 | - pull_request 21 | - push 22 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | coverage/ 2 | node_modules/ 3 | *.d.ts.map 4 | *.d.ts 5 | *.tsbuildinfo 6 | *.log 7 | .DS_Store 8 | yarn.lock 9 | !packages/rehype/index.d.ts 10 | !packages/rehype-parse/index.d.ts 11 | !packages/rehype-stringify/index.d.ts 12 | -------------------------------------------------------------------------------- /.npmrc: -------------------------------------------------------------------------------- 1 | ignore-scripts=true 2 | package-lock=false 3 | -------------------------------------------------------------------------------- /.prettierignore: -------------------------------------------------------------------------------- 1 | coverage/ 2 | *.html 3 | *.md 4 | -------------------------------------------------------------------------------- /changelog.md: -------------------------------------------------------------------------------- 1 | # Changelog 2 | 3 | See [GitHub Releases][releases] for the changelog. 4 | 5 | [releases]: https://github.com/rehypejs/rehype/releases 6 | -------------------------------------------------------------------------------- /doc/getting-started.md: -------------------------------------------------------------------------------- 1 | # Getting started 2 | 3 | See [the monorepo readme][rehype] for what the rehype ecosystem is and examples 4 | of how to get started. 5 | 6 | [rehype]: https://github.com/rehypejs/rehype 7 | -------------------------------------------------------------------------------- /license: -------------------------------------------------------------------------------- 1 | (The MIT License) 2 | 3 | Copyright (c) Titus Wormer 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /logo-square.svg: -------------------------------------------------------------------------------- 1 | 2 | 10 | 11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /logo.svg: -------------------------------------------------------------------------------- 1 | 2 | 10 | 11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "rehype", 3 | "private": true, 4 | "license": "MIT", 5 | "homepage": "https://github.com/rehypejs/rehype", 6 | "repository": "rehypejs/rehype", 7 | "bugs": "https://github.com/rehypejs/rehype/issues", 8 | "funding": { 9 | "type": "opencollective", 10 | "url": "https://opencollective.com/unified" 11 | }, 12 | "type": "module", 13 | "workspaces": [ 14 | "packages/rehype-parse", 15 | "packages/rehype-stringify", 16 | "packages/rehype", 17 | "packages/rehype-cli" 18 | ], 19 | "devDependencies": { 20 | "@types/node": "^22.0.0", 21 | "c8": "^10.0.0", 22 | "hast-util-assert": "^4.0.0", 23 | "prettier": "^3.0.0", 24 | "remark-cli": "^12.0.0", 25 | "remark-preset-wooorm": "^10.0.0", 26 | "type-coverage": "^2.0.0", 27 | "typescript": "^5.0.0", 28 | "unified": "^11.0.0", 29 | "unist-util-remove-position": "^5.0.0", 30 | "vfile": "^6.0.0", 31 | "xo": "^0.59.0" 32 | }, 33 | "scripts": { 34 | "build": "tsc --build --clean && tsc --build && type-coverage", 35 | "format": "remark . --frail --output --quiet && prettier . --log-level warn --write && xo --fix", 36 | "test": "npm run build && npm run format && npm run test-coverage", 37 | "test-api": "node --conditions development test/index.js", 38 | "test-coverage": "c8 --100 --check-coverage --reporter lcov npm run test-api" 39 | }, 40 | "prettier": { 41 | "bracketSpacing": false, 42 | "singleQuote": true, 43 | "semi": false, 44 | "tabWidth": 2, 45 | "trailingComma": "none", 46 | "useTabs": false 47 | }, 48 | "remarkConfig": { 49 | "plugins": [ 50 | "remark-preset-wooorm", 51 | [ 52 | "remark-lint-no-html", 53 | false 54 | ] 55 | ] 56 | }, 57 | "typeCoverage": { 58 | "atLeast": 100, 59 | "detail": true, 60 | "ignoreCatch": true, 61 | "strict": true 62 | }, 63 | "xo": { 64 | "overrides": [ 65 | { 66 | "files": [ 67 | "test/**/*.js" 68 | ], 69 | "rules": { 70 | "no-await-in-loop": "off" 71 | } 72 | }, 73 | { 74 | "files": [ 75 | "**/*.ts" 76 | ], 77 | "rules": { 78 | "@typescript-eslint/ban-types": "off", 79 | "@typescript-eslint/consistent-type-definitions": "off", 80 | "@typescript-eslint/triple-slash-reference": "off" 81 | } 82 | } 83 | ], 84 | "prettier": true, 85 | "rules": { 86 | "unicorn/no-this-assignment": "off", 87 | "unicorn/prefer-code-point": "off", 88 | "unicorn/prefer-string-replace-all": "off" 89 | } 90 | } 91 | } 92 | -------------------------------------------------------------------------------- /packages/rehype-cli/.npmrc: -------------------------------------------------------------------------------- 1 | ignore-scripts=true 2 | package-lock=false 3 | -------------------------------------------------------------------------------- /packages/rehype-cli/cli.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | /** 4 | * @typedef Pack 5 | * Minimum `package.json`. 6 | * @property {string} name 7 | * Name. 8 | * @property {string} version 9 | * Version. 10 | * @property {string} description 11 | * Description. 12 | */ 13 | 14 | import fs from 'node:fs/promises' 15 | import {resolve} from 'import-meta-resolve' 16 | import {rehype} from 'rehype' 17 | import {args} from 'unified-args' 18 | 19 | /** @type {Pack} */ 20 | const rehypePackage = JSON.parse( 21 | String( 22 | await fs.readFile( 23 | new URL('package.json', resolve('rehype', import.meta.url)) 24 | ) 25 | ) 26 | ) 27 | 28 | /** @type {Pack} */ 29 | const cliPackage = JSON.parse( 30 | String(await fs.readFile(new URL('package.json', import.meta.url))) 31 | ) 32 | 33 | args({ 34 | description: cliPackage.description, 35 | extensions: ['html', 'htm', 'xht', 'xhtml'], 36 | ignoreName: '.' + rehypePackage.name + 'ignore', 37 | name: rehypePackage.name, 38 | packageField: rehypePackage.name, 39 | pluginPrefix: rehypePackage.name, 40 | processor: rehype, 41 | rcName: '.' + rehypePackage.name + 'rc', 42 | version: [ 43 | rehypePackage.name + ': ' + rehypePackage.version, 44 | cliPackage.name + ': ' + cliPackage.version 45 | ].join(', ') 46 | }) 47 | -------------------------------------------------------------------------------- /packages/rehype-cli/license: -------------------------------------------------------------------------------- 1 | (The MIT License) 2 | 3 | Copyright (c) Titus Wormer 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /packages/rehype-cli/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "rehype-cli", 3 | "version": "12.0.1", 4 | "description": "CLI to process HTML with rehype", 5 | "license": "MIT", 6 | "keywords": [ 7 | "bin", 8 | "cli", 9 | "html", 10 | "rehype", 11 | "unified" 12 | ], 13 | "repository": "https://github.com/rehypejs/rehype/tree/main/packages/rehype-cli", 14 | "bugs": "https://github.com/rehypejs/rehype/issues", 15 | "funding": { 16 | "type": "opencollective", 17 | "url": "https://opencollective.com/unified" 18 | }, 19 | "author": "Titus Wormer (https://wooorm.com)", 20 | "contributors": [ 21 | "Titus Wormer (https://wooorm.com)" 22 | ], 23 | "type": "module", 24 | "exports": [], 25 | "bin": { 26 | "rehype": "cli.js" 27 | }, 28 | "files": [ 29 | "cli.js" 30 | ], 31 | "dependencies": { 32 | "import-meta-resolve": "^4.0.0", 33 | "rehype": "^13.0.0", 34 | "unified-args": "^11.0.0" 35 | }, 36 | "scripts": {}, 37 | "typeCoverage": { 38 | "atLeast": 100, 39 | "detail": true, 40 | "strict": true, 41 | "ignoreCatch": true 42 | } 43 | } 44 | -------------------------------------------------------------------------------- /packages/rehype-cli/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "../../tsconfig.json", 3 | "references": [{"path": "../rehype/"}] 4 | } 5 | -------------------------------------------------------------------------------- /packages/rehype-parse/.npmrc: -------------------------------------------------------------------------------- 1 | ignore-scripts=true 2 | package-lock=false 3 | -------------------------------------------------------------------------------- /packages/rehype-parse/index.d.ts: -------------------------------------------------------------------------------- 1 | import type {Root} from 'hast' 2 | import type {Plugin} from 'unified' 3 | import type {Options} from './lib/index.js' 4 | 5 | export type {ErrorCode, ErrorSeverity} from 'hast-util-from-html' 6 | export type {Options} from './lib/index.js' 7 | 8 | // Note: we have to use manual types here, 9 | // instead of getting them from `lib/index.js`, 10 | // because TS generates wrong types for functions that use `this`. 11 | // TS makes them into classes which is incorrect. 12 | /** 13 | * Plugin to add support for parsing from HTML. 14 | * 15 | * @this 16 | * Unified processor. 17 | * @param 18 | * Configuration (optional). 19 | * @returns 20 | * Nothing. 21 | */ 22 | declare const rehypeParse: Plugin<[(Options | null | undefined)?], string, Root> 23 | export default rehypeParse 24 | 25 | // Add custom settings supported when `rehype-parse` is added. 26 | declare module 'unified' { 27 | interface Settings extends Options {} 28 | } 29 | -------------------------------------------------------------------------------- /packages/rehype-parse/index.js: -------------------------------------------------------------------------------- 1 | // Note: types exposed from `index.d.ts`. 2 | export {default} from './lib/index.js' 3 | -------------------------------------------------------------------------------- /packages/rehype-parse/lib/index.js: -------------------------------------------------------------------------------- 1 | /** 2 | * @import {Root} from 'hast' 3 | * @import {Options as FromHtmlOptions} from 'hast-util-from-html' 4 | * @import {Processor} from 'unified' 5 | * @import {VFile} from 'vfile' 6 | */ 7 | 8 | /** 9 | * @typedef {Omit & RehypeParseFields} Options 10 | * Configuration. 11 | * 12 | * @typedef RehypeParseFields 13 | * Extra fields. 14 | * @property {boolean | null | undefined} [emitParseErrors=false] 15 | * Whether to emit parse errors while parsing (default: `false`). 16 | * 17 | * > 👉 **Note**: parse errors are currently being added to HTML. 18 | * > Not all errors emitted by parse5 (or us) are specced yet. 19 | * > Some documentation may still be missing. 20 | */ 21 | 22 | import {fromHtml} from 'hast-util-from-html' 23 | 24 | /** 25 | * Plugin to add support for parsing from HTML. 26 | * 27 | * > 👉 **Note**: this is not an XML parser. 28 | * > It supports SVG as embedded in HTML. 29 | * > It does not support the features available in XML. 30 | * > Passing SVG files might break but fragments of modern SVG should be fine. 31 | * > Use [`xast-util-from-xml`][xast-util-from-xml] to parse XML. 32 | * 33 | * @this {Processor} 34 | * Processor instance. 35 | * @param {Options | null | undefined} [options] 36 | * Configuration (optional). 37 | * @returns {undefined} 38 | * Nothing. 39 | */ 40 | export default function rehypeParse(options) { 41 | const self = this 42 | const {emitParseErrors, ...settings} = {...self.data('settings'), ...options} 43 | 44 | self.parser = parser 45 | 46 | /** 47 | * @param {string} document 48 | * Document. 49 | * @param {VFile} file 50 | * File. 51 | * @returns {Root} 52 | * Tree. 53 | */ 54 | function parser(document, file) { 55 | return fromHtml(document, { 56 | ...settings, 57 | onerror: emitParseErrors 58 | ? function (message) { 59 | if (file.path) { 60 | message.name = file.path + ':' + message.name 61 | message.file = file.path 62 | } 63 | 64 | file.messages.push(message) 65 | } 66 | : undefined 67 | }) 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /packages/rehype-parse/license: -------------------------------------------------------------------------------- 1 | (The MIT License) 2 | 3 | Copyright (c) Titus Wormer 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /packages/rehype-parse/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "rehype-parse", 3 | "version": "9.0.1", 4 | "description": "rehype plugin to parse HTML", 5 | "license": "MIT", 6 | "keywords": [ 7 | "abstract", 8 | "ast", 9 | "html", 10 | "parse", 11 | "plugin", 12 | "rehype", 13 | "rehype-plugin", 14 | "syntax", 15 | "tree", 16 | "unified" 17 | ], 18 | "homepage": "https://github.com/rehypejs/rehype", 19 | "repository": "https://github.com/rehypejs/rehype/tree/main/packages/rehype-parse", 20 | "bugs": "https://github.com/rehypejs/rehype/issues", 21 | "funding": { 22 | "type": "opencollective", 23 | "url": "https://opencollective.com/unified" 24 | }, 25 | "author": "Titus Wormer (https://wooorm.com)", 26 | "contributors": [ 27 | "Titus Wormer (https://wooorm.com)" 28 | ], 29 | "sideEffects": false, 30 | "type": "module", 31 | "exports": "./index.js", 32 | "files": [ 33 | "lib/", 34 | "index.d.ts", 35 | "index.js" 36 | ], 37 | "dependencies": { 38 | "@types/hast": "^3.0.0", 39 | "hast-util-from-html": "^2.0.0", 40 | "unified": "^11.0.0", 41 | "vfile": "^6.0.0" 42 | }, 43 | "scripts": {}, 44 | "typeCoverage": { 45 | "atLeast": 100, 46 | "detail": true, 47 | "strict": true, 48 | "ignoreCatch": true 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /packages/rehype-parse/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "../../tsconfig.json" 3 | } 4 | -------------------------------------------------------------------------------- /packages/rehype-stringify/.npmrc: -------------------------------------------------------------------------------- 1 | ignore-scripts=true 2 | package-lock=false 3 | -------------------------------------------------------------------------------- /packages/rehype-stringify/index.d.ts: -------------------------------------------------------------------------------- 1 | import type {Root} from 'hast' 2 | import type {Plugin} from 'unified' 3 | import type {Options} from 'hast-util-to-html' 4 | 5 | export type {CharacterReferences, Options} from 'hast-util-to-html' 6 | 7 | // Note: we have to use manual types here, 8 | // instead of getting them from `lib/index.js`, 9 | // because TS generates wrong types for functions that use `this`. 10 | // TS makes them into classes which is incorrect. 11 | /** 12 | * Plugin to add support for serializing as HTML. 13 | * 14 | * @this 15 | * Unified processor. 16 | * @param 17 | * Configuration (optional). 18 | * @returns 19 | * Nothing. 20 | */ 21 | declare const rehypeStringify: Plugin< 22 | [(Options | null | undefined)?], 23 | Root, 24 | string 25 | > 26 | export default rehypeStringify 27 | 28 | // Add custom settings supported when `rehype-stringify` is added. 29 | declare module 'unified' { 30 | interface Settings extends Options {} 31 | } 32 | -------------------------------------------------------------------------------- /packages/rehype-stringify/index.js: -------------------------------------------------------------------------------- 1 | // Note: types exposed from `index.d.ts`. 2 | export {default} from './lib/index.js' 3 | -------------------------------------------------------------------------------- /packages/rehype-stringify/lib/index.js: -------------------------------------------------------------------------------- 1 | /** 2 | * @import {Root} from 'hast' 3 | * @import {Options} from 'hast-util-to-html' 4 | * @import {Processor} from 'unified' 5 | */ 6 | 7 | import {toHtml} from 'hast-util-to-html' 8 | 9 | /** 10 | * Plugin to add support for serializing as HTML. 11 | * 12 | * @this {Processor} 13 | * Processor instance. 14 | * @param {Options | null | undefined} [options] 15 | * Configuration (optional). 16 | * @returns {undefined} 17 | * Nothing. 18 | */ 19 | export default function rehypeStringify(options) { 20 | const self = this 21 | const settings = {...self.data('settings'), ...options} 22 | 23 | self.compiler = compiler 24 | 25 | /** 26 | * @param {Root} tree 27 | * Tree. 28 | * @returns {string} 29 | * Document. 30 | */ 31 | function compiler(tree) { 32 | return toHtml(tree, settings) 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /packages/rehype-stringify/license: -------------------------------------------------------------------------------- 1 | (The MIT License) 2 | 3 | Copyright (c) Titus Wormer 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /packages/rehype-stringify/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "rehype-stringify", 3 | "version": "10.0.1", 4 | "description": "rehype plugin to serialize HTML", 5 | "license": "MIT", 6 | "keywords": [ 7 | "abstract", 8 | "ast", 9 | "compile", 10 | "html", 11 | "plugin", 12 | "rehype", 13 | "rehype-plugin", 14 | "serialize", 15 | "stringify", 16 | "syntax", 17 | "tree", 18 | "unified" 19 | ], 20 | "homepage": "https://github.com/rehypejs/rehype", 21 | "repository": "https://github.com/rehypejs/rehype/tree/main/packages/rehype-stringify", 22 | "bugs": "https://github.com/rehypejs/rehype/issues", 23 | "funding": { 24 | "type": "opencollective", 25 | "url": "https://opencollective.com/unified" 26 | }, 27 | "author": "Titus Wormer (https://wooorm.com)", 28 | "contributors": [ 29 | "Titus Wormer (https://wooorm.com)" 30 | ], 31 | "sideEffects": false, 32 | "type": "module", 33 | "exports": "./index.js", 34 | "files": [ 35 | "lib/", 36 | "index.d.ts", 37 | "index.js" 38 | ], 39 | "dependencies": { 40 | "@types/hast": "^3.0.0", 41 | "hast-util-to-html": "^9.0.0", 42 | "unified": "^11.0.0" 43 | }, 44 | "scripts": {}, 45 | "typeCoverage": { 46 | "atLeast": 100, 47 | "detail": true, 48 | "strict": true, 49 | "ignoreCatch": true 50 | } 51 | } 52 | -------------------------------------------------------------------------------- /packages/rehype-stringify/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "../../tsconfig.json" 3 | } 4 | -------------------------------------------------------------------------------- /packages/rehype/.npmrc: -------------------------------------------------------------------------------- 1 | ignore-scripts=true 2 | package-lock=false 3 | -------------------------------------------------------------------------------- /packages/rehype/index.d.ts: -------------------------------------------------------------------------------- 1 | /// 2 | /// 3 | 4 | import type {Root} from 'hast' 5 | import type {Processor} from 'unified' 6 | 7 | /** 8 | * Create a new unified processor that already uses `rehype-parse` and 9 | * `rehype-stringify`. 10 | */ 11 | export const rehype: Processor 12 | -------------------------------------------------------------------------------- /packages/rehype/index.js: -------------------------------------------------------------------------------- 1 | // Note: types exposed from `index.d.ts` 2 | import rehypeParse from 'rehype-parse' 3 | import rehypeStringify from 'rehype-stringify' 4 | import {unified} from 'unified' 5 | 6 | /** 7 | * Create a new unified processor that already uses `rehype-parse` and 8 | * `rehype-stringify`. 9 | */ 10 | export const rehype = unified().use(rehypeParse).use(rehypeStringify).freeze() 11 | -------------------------------------------------------------------------------- /packages/rehype/license: -------------------------------------------------------------------------------- 1 | (The MIT License) 2 | 3 | Copyright (c) Titus Wormer 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | -------------------------------------------------------------------------------- /packages/rehype/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "rehype", 3 | "version": "13.0.2", 4 | "description": "HTML processor powered by plugins part of the unified collective", 5 | "license": "MIT", 6 | "keywords": [ 7 | "abstract", 8 | "ast", 9 | "html", 10 | "parse", 11 | "process", 12 | "rehype", 13 | "serialize", 14 | "stringify", 15 | "syntax", 16 | "tree", 17 | "unified" 18 | ], 19 | "dependencies": { 20 | "@types/hast": "^3.0.0", 21 | "rehype-parse": "^9.0.0", 22 | "rehype-stringify": "^10.0.0", 23 | "unified": "^11.0.0" 24 | }, 25 | "homepage": "https://github.com/rehypejs/rehype", 26 | "repository": "https://github.com/rehypejs/rehype/tree/main/packages/rehype", 27 | "bugs": "https://github.com/rehypejs/rehype/issues", 28 | "funding": { 29 | "type": "opencollective", 30 | "url": "https://opencollective.com/unified" 31 | }, 32 | "author": "Titus Wormer (https://wooorm.com)", 33 | "contributors": [ 34 | "Titus Wormer (https://wooorm.com)" 35 | ], 36 | "sideEffects": false, 37 | "type": "module", 38 | "exports": "./index.js", 39 | "files": [ 40 | "index.d.ts", 41 | "index.js" 42 | ], 43 | "scripts": {}, 44 | "typeCoverage": { 45 | "atLeast": 100, 46 | "detail": true, 47 | "strict": true, 48 | "ignoreCatch": true 49 | } 50 | } 51 | -------------------------------------------------------------------------------- /packages/rehype/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "../../tsconfig.json", 3 | "references": [{"path": "../rehype-parse/"}, {"path": "../rehype-stringify/"}] 4 | } 5 | -------------------------------------------------------------------------------- /test/cli.js: -------------------------------------------------------------------------------- 1 | import assert from 'node:assert/strict' 2 | import childProcess from 'node:child_process' 3 | import test from 'node:test' 4 | import {promisify} from 'node:util' 5 | import {fileURLToPath} from 'node:url' 6 | 7 | const exec = promisify(childProcess.exec) 8 | 9 | test('rehype-cli', async function (t) { 10 | const binary = fileURLToPath( 11 | new URL('../packages/rehype-cli/cli.js', import.meta.url) 12 | ) 13 | 14 | await t.test('should show help on `--help`', async function () { 15 | const result = await exec(binary + ' --help') 16 | 17 | assert.equal( 18 | result.stdout, 19 | [ 20 | 'Usage: rehype [options] [path | glob ...]', 21 | '', 22 | ' CLI to process HTML with rehype', 23 | '', 24 | 'Options:', 25 | '', 26 | ' --[no-]color specify color in report (on by default)', 27 | ' --[no-]config search for configuration files (on by default)', 28 | ' -e --ext specify extensions', 29 | ' --file-path specify path to process as', 30 | ' -f --frail exit with 1 on warnings', 31 | ' -h --help output usage information', 32 | ' --[no-]ignore search for ignore files (on by default)', 33 | ' -i --ignore-path specify ignore file', 34 | ' --ignore-path-resolve-from cwd|dir resolve patterns in `ignore-path` from its directory or cwd', 35 | ' --ignore-pattern specify ignore patterns', 36 | ' --inspect output formatted syntax tree', 37 | ' -o --output [path] specify output location', 38 | ' -q --quiet output only warnings and errors', 39 | ' -r --rc-path specify configuration file', 40 | ' --report specify reporter', 41 | ' -s --setting specify settings', 42 | ' -S --silent output only errors', 43 | ' --silently-ignore do not fail when given ignored files', 44 | ' --[no-]stdout specify writing to stdout (on by default)', 45 | ' -t --tree specify input and output as syntax tree', 46 | ' --tree-in specify input as syntax tree', 47 | ' --tree-out output syntax tree', 48 | ' -u --use use plugins', 49 | ' --verbose report extra info for messages', 50 | ' -v --version output version number', 51 | ' -w --watch watch for changes and reprocess', 52 | '', 53 | 'Examples:', 54 | '', 55 | ' # Process `input.html`', 56 | ' $ rehype input.html -o output.html', 57 | '', 58 | ' # Pipe', 59 | ' $ rehype < input.html > output.html', 60 | '', 61 | ' # Rewrite all applicable files', 62 | ' $ rehype . -o', 63 | '' 64 | ].join('\n') 65 | ) 66 | }) 67 | 68 | await t.test('should show version on `--version`', async function () { 69 | const result = await exec(binary + ' --version') 70 | 71 | assert.match(result.stdout, /rehype: \d+\.\d+\.\d+/) 72 | assert.match(result.stdout, /rehype-cli: \d+\.\d+\.\d+/) 73 | }) 74 | }) 75 | -------------------------------------------------------------------------------- /test/fixtures/adoption/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/adoption/index.html: -------------------------------------------------------------------------------- 1 |

2 | -------------------------------------------------------------------------------- /test/fixtures/adoption/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "element", 6 | "tagName": "a", 7 | "properties": {}, 8 | "children": [ 9 | { 10 | "type": "element", 11 | "tagName": "b", 12 | "properties": {}, 13 | "children": [ 14 | { 15 | "type": "element", 16 | "tagName": "b", 17 | "properties": {}, 18 | "children": [], 19 | "position": { 20 | "start": { 21 | "line": 1, 22 | "column": 7, 23 | "offset": 6 24 | }, 25 | "end": { 26 | "line": 1, 27 | "column": 10, 28 | "offset": 9 29 | } 30 | } 31 | } 32 | ], 33 | "position": { 34 | "start": { 35 | "line": 1, 36 | "column": 4, 37 | "offset": 3 38 | }, 39 | "end": { 40 | "line": 1, 41 | "column": 10, 42 | "offset": 9 43 | } 44 | } 45 | } 46 | ], 47 | "position": { 48 | "start": { 49 | "line": 1, 50 | "column": 1, 51 | "offset": 0 52 | }, 53 | "end": { 54 | "line": 1, 55 | "column": 17, 56 | "offset": 16 57 | } 58 | } 59 | }, 60 | { 61 | "type": "element", 62 | "tagName": "b", 63 | "properties": {}, 64 | "children": [ 65 | { 66 | "type": "element", 67 | "tagName": "b", 68 | "properties": {}, 69 | "children": [ 70 | { 71 | "type": "element", 72 | "tagName": "p", 73 | "properties": {}, 74 | "children": [ 75 | { 76 | "type": "element", 77 | "tagName": "a", 78 | "properties": {}, 79 | "children": [] 80 | }, 81 | { 82 | "type": "text", 83 | "value": "\n", 84 | "position": { 85 | "start": { 86 | "line": 1, 87 | "column": 17, 88 | "offset": 16 89 | }, 90 | "end": { 91 | "line": 2, 92 | "column": 1, 93 | "offset": 17 94 | } 95 | } 96 | } 97 | ], 98 | "position": { 99 | "start": { 100 | "line": 1, 101 | "column": 10, 102 | "offset": 9 103 | }, 104 | "end": { 105 | "line": 2, 106 | "column": 1, 107 | "offset": 17 108 | } 109 | } 110 | } 111 | ] 112 | } 113 | ] 114 | } 115 | ], 116 | "data": { 117 | "quirksMode": false 118 | }, 119 | "position": { 120 | "start": { 121 | "line": 1, 122 | "column": 1, 123 | "offset": 0 124 | }, 125 | "end": { 126 | "line": 2, 127 | "column": 1, 128 | "offset": 17 129 | } 130 | } 131 | } 132 | -------------------------------------------------------------------------------- /test/fixtures/adoption/result.html: -------------------------------------------------------------------------------- 1 |

2 |

-------------------------------------------------------------------------------- /test/fixtures/aria/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/aria/index.html: -------------------------------------------------------------------------------- 1 |
2 | 3 | 16 |
17 | Login 18 |
19 | 20 | 21 | 22 |
23 |
24 | 25 | 26 | 27 |
28 |
29 |
30 | -------------------------------------------------------------------------------- /test/fixtures/aria/result.html: -------------------------------------------------------------------------------- 1 |
2 | 3 | 16 |
17 | Login 18 |
19 | 20 | 21 | 22 |
23 |
24 | 25 | 26 | 27 |
28 |
29 |
30 | -------------------------------------------------------------------------------- /test/fixtures/body-body-attributes/config.json: -------------------------------------------------------------------------------- 1 | {} 2 | -------------------------------------------------------------------------------- /test/fixtures/body-body-attributes/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /test/fixtures/body-body-attributes/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "element", 6 | "tagName": "html", 7 | "properties": {}, 8 | "children": [ 9 | { 10 | "type": "element", 11 | "tagName": "head", 12 | "properties": {}, 13 | "children": [] 14 | }, 15 | { 16 | "type": "element", 17 | "tagName": "body", 18 | "properties": { 19 | "id": "a", 20 | "title": "b", 21 | "className": ["c"], 22 | "onClick": "e" 23 | }, 24 | "children": [ 25 | { 26 | "type": "text", 27 | "value": "\n\n", 28 | "position": { 29 | "start": { 30 | "line": 2, 31 | "column": 34, 32 | "offset": 40 33 | }, 34 | "end": { 35 | "line": 4, 36 | "column": 1, 37 | "offset": 70 38 | } 39 | } 40 | } 41 | ], 42 | "position": { 43 | "start": { 44 | "line": 2, 45 | "column": 1, 46 | "offset": 7 47 | }, 48 | "end": { 49 | "line": 4, 50 | "column": 1, 51 | "offset": 70 52 | } 53 | } 54 | } 55 | ], 56 | "position": { 57 | "start": { 58 | "line": 1, 59 | "column": 1, 60 | "offset": 0 61 | }, 62 | "end": { 63 | "line": 4, 64 | "column": 1, 65 | "offset": 70 66 | } 67 | } 68 | } 69 | ], 70 | "data": { 71 | "quirksMode": true 72 | }, 73 | "position": { 74 | "start": { 75 | "line": 1, 76 | "column": 1, 77 | "offset": 0 78 | }, 79 | "end": { 80 | "line": 4, 81 | "column": 1, 82 | "offset": 70 83 | } 84 | } 85 | } 86 | -------------------------------------------------------------------------------- /test/fixtures/body-body-attributes/result.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | -------------------------------------------------------------------------------- /test/fixtures/body-html-attributes/config.json: -------------------------------------------------------------------------------- 1 | {} 2 | -------------------------------------------------------------------------------- /test/fixtures/body-html-attributes/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /test/fixtures/body-html-attributes/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "element", 6 | "tagName": "html", 7 | "properties": { 8 | "className": ["d"], 9 | "onClick": "e" 10 | }, 11 | "children": [ 12 | { 13 | "type": "element", 14 | "tagName": "head", 15 | "properties": {}, 16 | "children": [] 17 | }, 18 | { 19 | "type": "element", 20 | "tagName": "body", 21 | "properties": { 22 | "id": "a", 23 | "title": "b", 24 | "className": ["c"] 25 | }, 26 | "children": [ 27 | { 28 | "type": "text", 29 | "value": "\n\n", 30 | "position": { 31 | "start": { 32 | "line": 2, 33 | "column": 34, 34 | "offset": 40 35 | }, 36 | "end": { 37 | "line": 4, 38 | "column": 1, 39 | "offset": 70 40 | } 41 | } 42 | } 43 | ], 44 | "position": { 45 | "start": { 46 | "line": 2, 47 | "column": 1, 48 | "offset": 7 49 | }, 50 | "end": { 51 | "line": 4, 52 | "column": 1, 53 | "offset": 70 54 | } 55 | } 56 | } 57 | ], 58 | "position": { 59 | "start": { 60 | "line": 1, 61 | "column": 1, 62 | "offset": 0 63 | }, 64 | "end": { 65 | "line": 4, 66 | "column": 1, 67 | "offset": 70 68 | } 69 | } 70 | } 71 | ], 72 | "data": { 73 | "quirksMode": true 74 | }, 75 | "position": { 76 | "start": { 77 | "line": 1, 78 | "column": 1, 79 | "offset": 0 80 | }, 81 | "end": { 82 | "line": 4, 83 | "column": 1, 84 | "offset": 70 85 | } 86 | } 87 | } 88 | -------------------------------------------------------------------------------- /test/fixtures/body-html-attributes/result.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | -------------------------------------------------------------------------------- /test/fixtures/character-data/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/character-data/index.html: -------------------------------------------------------------------------------- 1 | 9 | 10 | Echo]]> 11 | 12 | 13 | 14 |

You can add a string to a number, but this stringifies the number:

15 | 16 | x<y 17 | + 18 | 3 19 | = 20 | x>y3 21 | 22 | -------------------------------------------------------------------------------- /test/fixtures/character-data/result.html: -------------------------------------------------------------------------------- 1 | 9 | 10 | Echo]]> 11 | 12 | 13 | 14 |

You can add a string to a number, but this stringifies the number:

15 | 16 | 17 | + 18 | 3 19 | = 20 | y3]]> 21 | 22 | -------------------------------------------------------------------------------- /test/fixtures/comment/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/comment/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /test/fixtures/comment/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "comment", 6 | "value": "This is a comment", 7 | "position": { 8 | "start": { 9 | "line": 1, 10 | "column": 1, 11 | "offset": 0 12 | }, 13 | "end": { 14 | "line": 1, 15 | "column": 25, 16 | "offset": 24 17 | } 18 | } 19 | }, 20 | { 21 | "type": "text", 22 | "value": "\n\n", 23 | "position": { 24 | "start": { 25 | "line": 1, 26 | "column": 25, 27 | "offset": 24 28 | }, 29 | "end": { 30 | "line": 3, 31 | "column": 1, 32 | "offset": 26 33 | } 34 | } 35 | }, 36 | { 37 | "type": "comment", 38 | "value": "", 39 | "position": { 40 | "start": { 41 | "line": 3, 42 | "column": 1, 43 | "offset": 26 44 | }, 45 | "end": { 46 | "line": 3, 47 | "column": 8, 48 | "offset": 33 49 | } 50 | } 51 | }, 52 | { 53 | "type": "text", 54 | "value": "\n", 55 | "position": { 56 | "start": { 57 | "line": 3, 58 | "column": 8, 59 | "offset": 33 60 | }, 61 | "end": { 62 | "line": 4, 63 | "column": 1, 64 | "offset": 34 65 | } 66 | } 67 | } 68 | ], 69 | "data": { 70 | "quirksMode": false 71 | }, 72 | "position": { 73 | "start": { 74 | "line": 1, 75 | "column": 1, 76 | "offset": 0 77 | }, 78 | "end": { 79 | "line": 4, 80 | "column": 1, 81 | "offset": 34 82 | } 83 | } 84 | } 85 | -------------------------------------------------------------------------------- /test/fixtures/comment/result.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /test/fixtures/comments/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true, 3 | "reprocess": false 4 | } 5 | -------------------------------------------------------------------------------- /test/fixtures/comments/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | Valid: 8 | 9 | Invalid: . 10 | Invalid: . 11 | Invalid: . 12 | Invalid: . 13 | -------------------------------------------------------------------------------- /test/fixtures/comments/result.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | Valid: 8 | 9 | Invalid: . 10 | Invalid: . 11 | Invalid: . 12 | Invalid: . 13 | -------------------------------------------------------------------------------- /test/fixtures/directive-in-fragment/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/directive-in-fragment/index.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/directive-in-fragment/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "text", 6 | "value": "\n", 7 | "position": { 8 | "start": { 9 | "line": 1, 10 | "column": 11, 11 | "offset": 10 12 | }, 13 | "end": { 14 | "line": 2, 15 | "column": 1, 16 | "offset": 11 17 | } 18 | } 19 | } 20 | ], 21 | "data": { 22 | "quirksMode": false 23 | }, 24 | "position": { 25 | "start": { 26 | "line": 1, 27 | "column": 1, 28 | "offset": 0 29 | }, 30 | "end": { 31 | "line": 2, 32 | "column": 1, 33 | "offset": 11 34 | } 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /test/fixtures/directive-in-fragment/result.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/doctype-almost-standards/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "reprocess": false 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/doctype-almost-standards/index.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/doctype-almost-standards/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "doctype", 6 | "position": { 7 | "start": { 8 | "line": 1, 9 | "column": 1, 10 | "offset": 0 11 | }, 12 | "end": { 13 | "line": 1, 14 | "column": 64, 15 | "offset": 63 16 | } 17 | } 18 | }, 19 | { 20 | "type": "element", 21 | "tagName": "html", 22 | "properties": {}, 23 | "children": [ 24 | { 25 | "type": "element", 26 | "tagName": "head", 27 | "properties": {}, 28 | "children": [] 29 | }, 30 | { 31 | "type": "element", 32 | "tagName": "body", 33 | "properties": {}, 34 | "children": [] 35 | } 36 | ] 37 | } 38 | ], 39 | "data": { 40 | "quirksMode": true 41 | }, 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 1, 46 | "offset": 0 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 64 52 | } 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /test/fixtures/doctype-almost-standards/result.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /test/fixtures/doctype-legacy-double/index.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/doctype-legacy-double/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "doctype", 6 | "position": { 7 | "start": { 8 | "line": 1, 9 | "column": 1, 10 | "offset": 0 11 | }, 12 | "end": { 13 | "line": 1, 14 | "column": 45, 15 | "offset": 44 16 | } 17 | } 18 | }, 19 | { 20 | "type": "element", 21 | "tagName": "html", 22 | "properties": {}, 23 | "children": [ 24 | { 25 | "type": "element", 26 | "tagName": "head", 27 | "properties": {}, 28 | "children": [] 29 | }, 30 | { 31 | "type": "element", 32 | "tagName": "body", 33 | "properties": {}, 34 | "children": [] 35 | } 36 | ] 37 | } 38 | ], 39 | "data": { 40 | "quirksMode": false 41 | }, 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 1, 46 | "offset": 0 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 45 52 | } 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /test/fixtures/doctype-legacy-double/result.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /test/fixtures/doctype-legacy-single/index.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/doctype-legacy-single/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "doctype", 6 | "position": { 7 | "start": { 8 | "line": 1, 9 | "column": 1, 10 | "offset": 0 11 | }, 12 | "end": { 13 | "line": 1, 14 | "column": 45, 15 | "offset": 44 16 | } 17 | } 18 | }, 19 | { 20 | "type": "element", 21 | "tagName": "html", 22 | "properties": {}, 23 | "children": [ 24 | { 25 | "type": "element", 26 | "tagName": "head", 27 | "properties": {}, 28 | "children": [] 29 | }, 30 | { 31 | "type": "element", 32 | "tagName": "body", 33 | "properties": {}, 34 | "children": [] 35 | } 36 | ] 37 | } 38 | ], 39 | "data": { 40 | "quirksMode": false 41 | }, 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 1, 46 | "offset": 0 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 45 52 | } 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /test/fixtures/doctype-legacy-single/result.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /test/fixtures/doctype-nameless/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "reprocess": false 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/doctype-nameless/index.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/doctype-nameless/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "doctype", 6 | "position": { 7 | "start": { 8 | "line": 1, 9 | "column": 1, 10 | "offset": 0 11 | }, 12 | "end": { 13 | "line": 1, 14 | "column": 11, 15 | "offset": 10 16 | } 17 | } 18 | }, 19 | { 20 | "type": "element", 21 | "tagName": "html", 22 | "properties": {}, 23 | "children": [ 24 | { 25 | "type": "element", 26 | "tagName": "head", 27 | "properties": {}, 28 | "children": [] 29 | }, 30 | { 31 | "type": "element", 32 | "tagName": "body", 33 | "properties": {}, 34 | "children": [] 35 | } 36 | ] 37 | } 38 | ], 39 | "data": { 40 | "quirksMode": true 41 | }, 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 1, 46 | "offset": 0 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 11 52 | } 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /test/fixtures/doctype-nameless/result.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quirksmode-ibm/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "reprocess": false 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quirksmode-ibm/index.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quirksmode-ibm/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "doctype", 6 | "position": { 7 | "start": { 8 | "line": 1, 9 | "column": 1, 10 | "offset": 0 11 | }, 12 | "end": { 13 | "line": 1, 14 | "column": 84, 15 | "offset": 83 16 | } 17 | } 18 | }, 19 | { 20 | "type": "element", 21 | "tagName": "html", 22 | "properties": {}, 23 | "children": [ 24 | { 25 | "type": "element", 26 | "tagName": "head", 27 | "properties": {}, 28 | "children": [] 29 | }, 30 | { 31 | "type": "element", 32 | "tagName": "body", 33 | "properties": {}, 34 | "children": [] 35 | } 36 | ] 37 | } 38 | ], 39 | "data": { 40 | "quirksMode": true 41 | }, 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 1, 46 | "offset": 0 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 84 52 | } 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quirksmode-ibm/result.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quirksmode-xml/index.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quirksmode-xml/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "comment", 6 | "value": "?xml version=\"1.0\"?", 7 | "position": { 8 | "start": { 9 | "line": 1, 10 | "column": 1, 11 | "offset": 0 12 | }, 13 | "end": { 14 | "line": 1, 15 | "column": 22, 16 | "offset": 21 17 | } 18 | } 19 | }, 20 | { 21 | "type": "element", 22 | "tagName": "html", 23 | "properties": {}, 24 | "children": [ 25 | { 26 | "type": "element", 27 | "tagName": "head", 28 | "properties": {}, 29 | "children": [] 30 | }, 31 | { 32 | "type": "element", 33 | "tagName": "body", 34 | "properties": {}, 35 | "children": [] 36 | } 37 | ] 38 | } 39 | ], 40 | "data": { 41 | "quirksMode": true 42 | }, 43 | "position": { 44 | "start": { 45 | "line": 1, 46 | "column": 1, 47 | "offset": 0 48 | }, 49 | "end": { 50 | "line": 2, 51 | "column": 1, 52 | "offset": 22 53 | } 54 | } 55 | } 56 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quirksmode-xml/result.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quotes-double/index.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quotes-double/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "doctype", 6 | "position": { 7 | "start": { 8 | "line": 1, 9 | "column": 1, 10 | "offset": 0 11 | }, 12 | "end": { 13 | "line": 1, 14 | "column": 77, 15 | "offset": 76 16 | } 17 | } 18 | }, 19 | { 20 | "type": "element", 21 | "tagName": "html", 22 | "properties": {}, 23 | "children": [ 24 | { 25 | "type": "element", 26 | "tagName": "head", 27 | "properties": {}, 28 | "children": [] 29 | }, 30 | { 31 | "type": "element", 32 | "tagName": "body", 33 | "properties": {}, 34 | "children": [] 35 | } 36 | ] 37 | } 38 | ], 39 | "data": { 40 | "quirksMode": false 41 | }, 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 1, 46 | "offset": 0 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 77 52 | } 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quotes-double/result.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quotes-single/index.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quotes-single/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "doctype", 6 | "position": { 7 | "start": { 8 | "line": 1, 9 | "column": 1, 10 | "offset": 0 11 | }, 12 | "end": { 13 | "line": 1, 14 | "column": 77, 15 | "offset": 76 16 | } 17 | } 18 | }, 19 | { 20 | "type": "element", 21 | "tagName": "html", 22 | "properties": {}, 23 | "children": [ 24 | { 25 | "type": "element", 26 | "tagName": "head", 27 | "properties": {}, 28 | "children": [] 29 | }, 30 | { 31 | "type": "element", 32 | "tagName": "body", 33 | "properties": {}, 34 | "children": [] 35 | } 36 | ] 37 | } 38 | ], 39 | "data": { 40 | "quirksMode": false 41 | }, 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 1, 46 | "offset": 0 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 77 52 | } 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /test/fixtures/doctype-quotes-single/result.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /test/fixtures/doctype/index.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/doctype/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "doctype", 6 | "position": { 7 | "start": { 8 | "line": 1, 9 | "column": 1, 10 | "offset": 0 11 | }, 12 | "end": { 13 | "line": 1, 14 | "column": 16, 15 | "offset": 15 16 | } 17 | } 18 | }, 19 | { 20 | "type": "element", 21 | "tagName": "html", 22 | "properties": {}, 23 | "children": [ 24 | { 25 | "type": "element", 26 | "tagName": "head", 27 | "properties": {}, 28 | "children": [] 29 | }, 30 | { 31 | "type": "element", 32 | "tagName": "body", 33 | "properties": {}, 34 | "children": [] 35 | } 36 | ] 37 | } 38 | ], 39 | "data": { 40 | "quirksMode": false 41 | }, 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 1, 46 | "offset": 0 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 16 52 | } 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /test/fixtures/doctype/result.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /test/fixtures/element-attributes-names/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/element-attributes-names/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /test/fixtures/element-attributes-names/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "element", 6 | "tagName": "a", 7 | "properties": { 8 | "foo": "" 9 | }, 10 | "children": [], 11 | "position": { 12 | "start": { 13 | "line": 1, 14 | "column": 1, 15 | "offset": 0 16 | }, 17 | "end": { 18 | "line": 1, 19 | "column": 12, 20 | "offset": 11 21 | } 22 | } 23 | }, 24 | { 25 | "type": "text", 26 | "value": "\n", 27 | "position": { 28 | "start": { 29 | "line": 1, 30 | "column": 12, 31 | "offset": 11 32 | }, 33 | "end": { 34 | "line": 2, 35 | "column": 1, 36 | "offset": 12 37 | } 38 | } 39 | }, 40 | { 41 | "type": "element", 42 | "tagName": "a", 43 | "properties": { 44 | "foo": "" 45 | }, 46 | "children": [], 47 | "position": { 48 | "start": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 12 52 | }, 53 | "end": { 54 | "line": 2, 55 | "column": 12, 56 | "offset": 23 57 | } 58 | } 59 | }, 60 | { 61 | "type": "text", 62 | "value": "\n", 63 | "position": { 64 | "start": { 65 | "line": 2, 66 | "column": 12, 67 | "offset": 23 68 | }, 69 | "end": { 70 | "line": 3, 71 | "column": 1, 72 | "offset": 24 73 | } 74 | } 75 | }, 76 | { 77 | "type": "element", 78 | "tagName": "a", 79 | "properties": { 80 | "foo": "" 81 | }, 82 | "children": [], 83 | "position": { 84 | "start": { 85 | "line": 3, 86 | "column": 1, 87 | "offset": 24 88 | }, 89 | "end": { 90 | "line": 3, 91 | "column": 12, 92 | "offset": 35 93 | } 94 | } 95 | }, 96 | { 97 | "type": "text", 98 | "value": "\n", 99 | "position": { 100 | "start": { 101 | "line": 3, 102 | "column": 12, 103 | "offset": 35 104 | }, 105 | "end": { 106 | "line": 4, 107 | "column": 1, 108 | "offset": 36 109 | } 110 | } 111 | }, 112 | { 113 | "type": "element", 114 | "tagName": "a", 115 | "properties": { 116 | "foo": "" 117 | }, 118 | "children": [], 119 | "position": { 120 | "start": { 121 | "line": 4, 122 | "column": 1, 123 | "offset": 36 124 | }, 125 | "end": { 126 | "line": 4, 127 | "column": 20, 128 | "offset": 55 129 | } 130 | } 131 | }, 132 | { 133 | "type": "text", 134 | "value": "\n", 135 | "position": { 136 | "start": { 137 | "line": 4, 138 | "column": 20, 139 | "offset": 55 140 | }, 141 | "end": { 142 | "line": 5, 143 | "column": 1, 144 | "offset": 56 145 | } 146 | } 147 | } 148 | ], 149 | "data": { 150 | "quirksMode": false 151 | }, 152 | "position": { 153 | "start": { 154 | "line": 1, 155 | "column": 1, 156 | "offset": 0 157 | }, 158 | "end": { 159 | "line": 5, 160 | "column": 1, 161 | "offset": 56 162 | } 163 | } 164 | } 165 | -------------------------------------------------------------------------------- /test/fixtures/element-attributes-names/result.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /test/fixtures/element-attributes/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/element-attributes/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 |
8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | ng-whatevs. 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 |
54 | 55 |
56 | 57 |
58 | 59 |
60 | 61 |
62 | 63 |
64 | 65 |
66 | 67 |
68 | 69 |
70 | 71 |
72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | -------------------------------------------------------------------------------- /test/fixtures/element-attributes/result.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 |
8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | ng-whatevs. 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 |
54 | 55 |
56 | 57 |
58 | 59 |
60 | 61 |
62 | 63 |
64 | 65 |
66 | 67 |
68 | 69 |
70 | 71 |
72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | 92 | 93 | 94 | 95 | 96 | -------------------------------------------------------------------------------- /test/fixtures/element-auto-close-document/index.html: -------------------------------------------------------------------------------- 1 | 2 | Alpha 3 | 4 |

bravo 5 |

charlie

6 |
    7 |
  1. delta 8 |
  2. echo 9 | -------------------------------------------------------------------------------- /test/fixtures/element-auto-close-document/result.html: -------------------------------------------------------------------------------- 1 | 2 | Alpha 3 | 4 |

    bravo 5 |

    charlie

    6 |
      7 |
    1. delta 8 |
    2. echo 9 |
    -------------------------------------------------------------------------------- /test/fixtures/element-auto-close-fragment/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/element-auto-close-fragment/index.html: -------------------------------------------------------------------------------- 1 | 2 | Alpha 3 | 4 |

    bravo 5 |

    charlie

    6 |
      7 |
    1. delta 8 |
    2. echo 9 | -------------------------------------------------------------------------------- /test/fixtures/element-auto-close-fragment/result.html: -------------------------------------------------------------------------------- 1 | 2 | Alpha 3 | 4 |

      bravo 5 |

      charlie

      6 |
        7 |
      1. delta 8 |
      2. echo 9 |
      -------------------------------------------------------------------------------- /test/fixtures/element-broken-close/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/element-broken-close/index.html: -------------------------------------------------------------------------------- 1 | fooStrong, emphasis, and code. 2 | -------------------------------------------------------------------------------- /test/fixtures/element-children/result.html: -------------------------------------------------------------------------------- 1 |
      Strong, emphasis, and code.
      2 | -------------------------------------------------------------------------------- /test/fixtures/element-closing-attributes/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/element-closing-attributes/index.html: -------------------------------------------------------------------------------- 1 | bar 2 | bar 3 | bar 4 | -------------------------------------------------------------------------------- /test/fixtures/element-closing-attributes/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "element", 6 | "tagName": "foo", 7 | "properties": {}, 8 | "children": [ 9 | { 10 | "type": "text", 11 | "value": "bar", 12 | "position": { 13 | "start": { 14 | "line": 1, 15 | "column": 6, 16 | "offset": 5 17 | }, 18 | "end": { 19 | "line": 1, 20 | "column": 9, 21 | "offset": 8 22 | } 23 | } 24 | } 25 | ], 26 | "position": { 27 | "start": { 28 | "line": 1, 29 | "column": 1, 30 | "offset": 0 31 | }, 32 | "end": { 33 | "line": 1, 34 | "column": 15, 35 | "offset": 14 36 | } 37 | } 38 | }, 39 | { 40 | "type": "text", 41 | "value": "\n", 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 15, 46 | "offset": 14 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 15 52 | } 53 | } 54 | }, 55 | { 56 | "type": "element", 57 | "tagName": "foo", 58 | "properties": {}, 59 | "children": [ 60 | { 61 | "type": "text", 62 | "value": "bar", 63 | "position": { 64 | "start": { 65 | "line": 2, 66 | "column": 6, 67 | "offset": 20 68 | }, 69 | "end": { 70 | "line": 2, 71 | "column": 9, 72 | "offset": 23 73 | } 74 | } 75 | } 76 | ], 77 | "position": { 78 | "start": { 79 | "line": 2, 80 | "column": 1, 81 | "offset": 15 82 | }, 83 | "end": { 84 | "line": 2, 85 | "column": 19, 86 | "offset": 33 87 | } 88 | } 89 | }, 90 | { 91 | "type": "text", 92 | "value": "\n", 93 | "position": { 94 | "start": { 95 | "line": 2, 96 | "column": 19, 97 | "offset": 33 98 | }, 99 | "end": { 100 | "line": 3, 101 | "column": 1, 102 | "offset": 34 103 | } 104 | } 105 | }, 106 | { 107 | "type": "element", 108 | "tagName": "foo", 109 | "properties": {}, 110 | "children": [ 111 | { 112 | "type": "text", 113 | "value": "bar", 114 | "position": { 115 | "start": { 116 | "line": 3, 117 | "column": 6, 118 | "offset": 39 119 | }, 120 | "end": { 121 | "line": 3, 122 | "column": 9, 123 | "offset": 42 124 | } 125 | } 126 | } 127 | ], 128 | "position": { 129 | "start": { 130 | "line": 3, 131 | "column": 1, 132 | "offset": 34 133 | }, 134 | "end": { 135 | "line": 3, 136 | "column": 25, 137 | "offset": 58 138 | } 139 | } 140 | }, 141 | { 142 | "type": "text", 143 | "value": "\n", 144 | "position": { 145 | "start": { 146 | "line": 3, 147 | "column": 25, 148 | "offset": 58 149 | }, 150 | "end": { 151 | "line": 4, 152 | "column": 1, 153 | "offset": 59 154 | } 155 | } 156 | } 157 | ], 158 | "data": { 159 | "quirksMode": false 160 | }, 161 | "position": { 162 | "start": { 163 | "line": 1, 164 | "column": 1, 165 | "offset": 0 166 | }, 167 | "end": { 168 | "line": 4, 169 | "column": 1, 170 | "offset": 59 171 | } 172 | } 173 | } 174 | -------------------------------------------------------------------------------- /test/fixtures/element-closing-attributes/result.html: -------------------------------------------------------------------------------- 1 | bar 2 | bar 3 | bar 4 | -------------------------------------------------------------------------------- /test/fixtures/element-closing/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/element-closing/index.html: -------------------------------------------------------------------------------- 1 | bar 2 | bar 3 | bar 4 | -------------------------------------------------------------------------------- /test/fixtures/element-closing/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "element", 6 | "tagName": "foo", 7 | "properties": {}, 8 | "children": [ 9 | { 10 | "type": "text", 11 | "value": "bar", 12 | "position": { 13 | "start": { 14 | "line": 1, 15 | "column": 6, 16 | "offset": 5 17 | }, 18 | "end": { 19 | "line": 1, 20 | "column": 9, 21 | "offset": 8 22 | } 23 | } 24 | } 25 | ], 26 | "position": { 27 | "start": { 28 | "line": 1, 29 | "column": 1, 30 | "offset": 0 31 | }, 32 | "end": { 33 | "line": 1, 34 | "column": 15, 35 | "offset": 14 36 | } 37 | } 38 | }, 39 | { 40 | "type": "text", 41 | "value": "\n", 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 15, 46 | "offset": 14 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 15 52 | } 53 | } 54 | }, 55 | { 56 | "type": "element", 57 | "tagName": "foo", 58 | "properties": {}, 59 | "children": [ 60 | { 61 | "type": "text", 62 | "value": "bar", 63 | "position": { 64 | "start": { 65 | "line": 2, 66 | "column": 6, 67 | "offset": 20 68 | }, 69 | "end": { 70 | "line": 2, 71 | "column": 9, 72 | "offset": 23 73 | } 74 | } 75 | } 76 | ], 77 | "position": { 78 | "start": { 79 | "line": 2, 80 | "column": 1, 81 | "offset": 15 82 | }, 83 | "end": { 84 | "line": 2, 85 | "column": 15, 86 | "offset": 29 87 | } 88 | } 89 | }, 90 | { 91 | "type": "text", 92 | "value": "\n", 93 | "position": { 94 | "start": { 95 | "line": 2, 96 | "column": 15, 97 | "offset": 29 98 | }, 99 | "end": { 100 | "line": 3, 101 | "column": 1, 102 | "offset": 30 103 | } 104 | } 105 | }, 106 | { 107 | "type": "element", 108 | "tagName": "foo", 109 | "properties": {}, 110 | "children": [ 111 | { 112 | "type": "text", 113 | "value": "bar", 114 | "position": { 115 | "start": { 116 | "line": 3, 117 | "column": 6, 118 | "offset": 35 119 | }, 120 | "end": { 121 | "line": 3, 122 | "column": 9, 123 | "offset": 38 124 | } 125 | } 126 | } 127 | ], 128 | "position": { 129 | "start": { 130 | "line": 3, 131 | "column": 1, 132 | "offset": 30 133 | }, 134 | "end": { 135 | "line": 3, 136 | "column": 15, 137 | "offset": 44 138 | } 139 | } 140 | }, 141 | { 142 | "type": "text", 143 | "value": "\n", 144 | "position": { 145 | "start": { 146 | "line": 3, 147 | "column": 15, 148 | "offset": 44 149 | }, 150 | "end": { 151 | "line": 4, 152 | "column": 1, 153 | "offset": 45 154 | } 155 | } 156 | } 157 | ], 158 | "data": { 159 | "quirksMode": false 160 | }, 161 | "position": { 162 | "start": { 163 | "line": 1, 164 | "column": 1, 165 | "offset": 0 166 | }, 167 | "end": { 168 | "line": 4, 169 | "column": 1, 170 | "offset": 45 171 | } 172 | } 173 | } 174 | -------------------------------------------------------------------------------- /test/fixtures/element-closing/result.html: -------------------------------------------------------------------------------- 1 | bar 2 | bar 3 | bar 4 | -------------------------------------------------------------------------------- /test/fixtures/element-empty/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/element-empty/index.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/element-empty/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "element", 6 | "tagName": "span", 7 | "properties": {}, 8 | "children": [], 9 | "position": { 10 | "start": { 11 | "line": 1, 12 | "column": 1, 13 | "offset": 0 14 | }, 15 | "end": { 16 | "line": 1, 17 | "column": 14, 18 | "offset": 13 19 | } 20 | } 21 | }, 22 | { 23 | "type": "text", 24 | "value": "\n", 25 | "position": { 26 | "start": { 27 | "line": 1, 28 | "column": 14, 29 | "offset": 13 30 | }, 31 | "end": { 32 | "line": 2, 33 | "column": 1, 34 | "offset": 14 35 | } 36 | } 37 | } 38 | ], 39 | "data": { 40 | "quirksMode": false 41 | }, 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 1, 46 | "offset": 0 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 14 52 | } 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /test/fixtures/element-empty/result.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/element-loose-close-document/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |

      5 | 6 |

      7 | -------------------------------------------------------------------------------- /test/fixtures/element-loose-close-document/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "element", 6 | "tagName": "html", 7 | "properties": {}, 8 | "children": [ 9 | { 10 | "type": "element", 11 | "tagName": "head", 12 | "properties": {}, 13 | "children": [] 14 | }, 15 | { 16 | "type": "element", 17 | "tagName": "body", 18 | "properties": {}, 19 | "children": [ 20 | { 21 | "type": "text", 22 | "value": "\n\n\n", 23 | "position": { 24 | "start": { 25 | "line": 1, 26 | "column": 27, 27 | "offset": 26 28 | }, 29 | "end": { 30 | "line": 4, 31 | "column": 1, 32 | "offset": 29 33 | } 34 | } 35 | }, 36 | { 37 | "type": "element", 38 | "tagName": "p", 39 | "properties": {}, 40 | "children": [] 41 | }, 42 | { 43 | "type": "text", 44 | "value": "\n\n", 45 | "position": { 46 | "start": { 47 | "line": 4, 48 | "column": 5, 49 | "offset": 33 50 | }, 51 | "end": { 52 | "line": 6, 53 | "column": 1, 54 | "offset": 35 55 | } 56 | } 57 | }, 58 | { 59 | "type": "element", 60 | "tagName": "div", 61 | "properties": {}, 62 | "children": [ 63 | { 64 | "type": "element", 65 | "tagName": "p", 66 | "properties": {}, 67 | "children": [] 68 | } 69 | ], 70 | "position": { 71 | "start": { 72 | "line": 6, 73 | "column": 1, 74 | "offset": 35 75 | }, 76 | "end": { 77 | "line": 6, 78 | "column": 16, 79 | "offset": 50 80 | } 81 | } 82 | }, 83 | { 84 | "type": "text", 85 | "value": "\n", 86 | "position": { 87 | "start": { 88 | "line": 6, 89 | "column": 16, 90 | "offset": 50 91 | }, 92 | "end": { 93 | "line": 7, 94 | "column": 1, 95 | "offset": 51 96 | } 97 | } 98 | } 99 | ], 100 | "position": { 101 | "start": { 102 | "line": 1, 103 | "column": 1, 104 | "offset": 0 105 | }, 106 | "end": { 107 | "line": 1, 108 | "column": 20, 109 | "offset": 19 110 | } 111 | } 112 | } 113 | ] 114 | } 115 | ], 116 | "data": { 117 | "quirksMode": true 118 | }, 119 | "position": { 120 | "start": { 121 | "line": 1, 122 | "column": 1, 123 | "offset": 0 124 | }, 125 | "end": { 126 | "line": 7, 127 | "column": 1, 128 | "offset": 51 129 | } 130 | } 131 | } 132 | -------------------------------------------------------------------------------- /test/fixtures/element-loose-close-document/result.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |

      5 | 6 |

      7 | -------------------------------------------------------------------------------- /test/fixtures/element-loose-close-fragment/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/element-loose-close-fragment/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |

      5 | 6 |

      7 | -------------------------------------------------------------------------------- /test/fixtures/element-loose-close-fragment/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "text", 6 | "value": "\n\n\n", 7 | "position": { 8 | "start": { 9 | "line": 1, 10 | "column": 27, 11 | "offset": 26 12 | }, 13 | "end": { 14 | "line": 4, 15 | "column": 1, 16 | "offset": 29 17 | } 18 | } 19 | }, 20 | { 21 | "type": "element", 22 | "tagName": "p", 23 | "properties": {}, 24 | "children": [] 25 | }, 26 | { 27 | "type": "text", 28 | "value": "\n\n", 29 | "position": { 30 | "start": { 31 | "line": 4, 32 | "column": 5, 33 | "offset": 33 34 | }, 35 | "end": { 36 | "line": 6, 37 | "column": 1, 38 | "offset": 35 39 | } 40 | } 41 | }, 42 | { 43 | "type": "element", 44 | "tagName": "div", 45 | "properties": {}, 46 | "children": [ 47 | { 48 | "type": "element", 49 | "tagName": "p", 50 | "properties": {}, 51 | "children": [] 52 | } 53 | ], 54 | "position": { 55 | "start": { 56 | "line": 6, 57 | "column": 1, 58 | "offset": 35 59 | }, 60 | "end": { 61 | "line": 6, 62 | "column": 16, 63 | "offset": 50 64 | } 65 | } 66 | }, 67 | { 68 | "type": "text", 69 | "value": "\n", 70 | "position": { 71 | "start": { 72 | "line": 6, 73 | "column": 16, 74 | "offset": 50 75 | }, 76 | "end": { 77 | "line": 7, 78 | "column": 1, 79 | "offset": 51 80 | } 81 | } 82 | } 83 | ], 84 | "data": { 85 | "quirksMode": false 86 | }, 87 | "position": { 88 | "start": { 89 | "line": 1, 90 | "column": 1, 91 | "offset": 0 92 | }, 93 | "end": { 94 | "line": 7, 95 | "column": 1, 96 | "offset": 51 97 | } 98 | } 99 | } 100 | -------------------------------------------------------------------------------- /test/fixtures/element-loose-close-fragment/result.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |

      5 | 6 |

      7 | -------------------------------------------------------------------------------- /test/fixtures/element-opening/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/element-opening/index.html: -------------------------------------------------------------------------------- 1 | bar 2 | bar 3 | bar 4 | -------------------------------------------------------------------------------- /test/fixtures/element-opening/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "element", 6 | "tagName": "foo", 7 | "properties": {}, 8 | "children": [ 9 | { 10 | "type": "text", 11 | "value": "bar", 12 | "position": { 13 | "start": { 14 | "line": 1, 15 | "column": 6, 16 | "offset": 5 17 | }, 18 | "end": { 19 | "line": 1, 20 | "column": 9, 21 | "offset": 8 22 | } 23 | } 24 | } 25 | ], 26 | "position": { 27 | "start": { 28 | "line": 1, 29 | "column": 1, 30 | "offset": 0 31 | }, 32 | "end": { 33 | "line": 1, 34 | "column": 15, 35 | "offset": 14 36 | } 37 | } 38 | }, 39 | { 40 | "type": "text", 41 | "value": "\n", 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 15, 46 | "offset": 14 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 15 52 | } 53 | } 54 | }, 55 | { 56 | "type": "element", 57 | "tagName": "foo", 58 | "properties": {}, 59 | "children": [ 60 | { 61 | "type": "text", 62 | "value": "bar", 63 | "position": { 64 | "start": { 65 | "line": 2, 66 | "column": 6, 67 | "offset": 20 68 | }, 69 | "end": { 70 | "line": 2, 71 | "column": 9, 72 | "offset": 23 73 | } 74 | } 75 | } 76 | ], 77 | "position": { 78 | "start": { 79 | "line": 2, 80 | "column": 1, 81 | "offset": 15 82 | }, 83 | "end": { 84 | "line": 2, 85 | "column": 15, 86 | "offset": 29 87 | } 88 | } 89 | }, 90 | { 91 | "type": "text", 92 | "value": "\n", 93 | "position": { 94 | "start": { 95 | "line": 2, 96 | "column": 15, 97 | "offset": 29 98 | }, 99 | "end": { 100 | "line": 3, 101 | "column": 1, 102 | "offset": 30 103 | } 104 | } 105 | }, 106 | { 107 | "type": "element", 108 | "tagName": "foo", 109 | "properties": {}, 110 | "children": [ 111 | { 112 | "type": "text", 113 | "value": "bar", 114 | "position": { 115 | "start": { 116 | "line": 3, 117 | "column": 6, 118 | "offset": 35 119 | }, 120 | "end": { 121 | "line": 3, 122 | "column": 9, 123 | "offset": 38 124 | } 125 | } 126 | } 127 | ], 128 | "position": { 129 | "start": { 130 | "line": 3, 131 | "column": 1, 132 | "offset": 30 133 | }, 134 | "end": { 135 | "line": 3, 136 | "column": 15, 137 | "offset": 44 138 | } 139 | } 140 | }, 141 | { 142 | "type": "text", 143 | "value": "\n", 144 | "position": { 145 | "start": { 146 | "line": 3, 147 | "column": 15, 148 | "offset": 44 149 | }, 150 | "end": { 151 | "line": 4, 152 | "column": 1, 153 | "offset": 45 154 | } 155 | } 156 | } 157 | ], 158 | "data": { 159 | "quirksMode": false 160 | }, 161 | "position": { 162 | "start": { 163 | "line": 1, 164 | "column": 1, 165 | "offset": 0 166 | }, 167 | "end": { 168 | "line": 4, 169 | "column": 1, 170 | "offset": 45 171 | } 172 | } 173 | } 174 | -------------------------------------------------------------------------------- /test/fixtures/element-opening/result.html: -------------------------------------------------------------------------------- 1 | bar 2 | bar 3 | bar 4 | -------------------------------------------------------------------------------- /test/fixtures/element-void-close/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/element-void-close/index.html: -------------------------------------------------------------------------------- 1 |
      text
      2 | text 3 | -------------------------------------------------------------------------------- /test/fixtures/element-void-close/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "element", 6 | "tagName": "br", 7 | "properties": {}, 8 | "children": [], 9 | "position": { 10 | "start": { 11 | "line": 1, 12 | "column": 1, 13 | "offset": 0 14 | }, 15 | "end": { 16 | "line": 1, 17 | "column": 5, 18 | "offset": 4 19 | } 20 | } 21 | }, 22 | { 23 | "type": "text", 24 | "value": "text", 25 | "position": { 26 | "start": { 27 | "line": 1, 28 | "column": 5, 29 | "offset": 4 30 | }, 31 | "end": { 32 | "line": 1, 33 | "column": 9, 34 | "offset": 8 35 | } 36 | } 37 | }, 38 | { 39 | "type": "element", 40 | "tagName": "br", 41 | "properties": {}, 42 | "children": [] 43 | }, 44 | { 45 | "type": "text", 46 | "value": "\n", 47 | "position": { 48 | "start": { 49 | "line": 1, 50 | "column": 14, 51 | "offset": 13 52 | }, 53 | "end": { 54 | "line": 2, 55 | "column": 1, 56 | "offset": 14 57 | } 58 | } 59 | }, 60 | { 61 | "type": "element", 62 | "tagName": "img", 63 | "properties": {}, 64 | "children": [], 65 | "position": { 66 | "start": { 67 | "line": 2, 68 | "column": 1, 69 | "offset": 14 70 | }, 71 | "end": { 72 | "line": 2, 73 | "column": 6, 74 | "offset": 19 75 | } 76 | } 77 | }, 78 | { 79 | "type": "text", 80 | "value": "text\n", 81 | "position": { 82 | "start": { 83 | "line": 2, 84 | "column": 6, 85 | "offset": 19 86 | }, 87 | "end": { 88 | "line": 3, 89 | "column": 1, 90 | "offset": 30 91 | } 92 | } 93 | } 94 | ], 95 | "data": { 96 | "quirksMode": false 97 | }, 98 | "position": { 99 | "start": { 100 | "line": 1, 101 | "column": 1, 102 | "offset": 0 103 | }, 104 | "end": { 105 | "line": 3, 106 | "column": 1, 107 | "offset": 30 108 | } 109 | } 110 | } 111 | -------------------------------------------------------------------------------- /test/fixtures/element-void-close/result.html: -------------------------------------------------------------------------------- 1 |
      text
      2 | text 3 | -------------------------------------------------------------------------------- /test/fixtures/element-void/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/element-void/index.html: -------------------------------------------------------------------------------- 1 | foo 2 | 3 |
      4 | 5 |

      this
      and that

      6 | 7 |

      this
      and that

      8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | -------------------------------------------------------------------------------- /test/fixtures/element-void/result.html: -------------------------------------------------------------------------------- 1 | foo 2 | 3 |
      4 | 5 |

      this
      and that

      6 | 7 |

      this
      and that

      8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | -------------------------------------------------------------------------------- /test/fixtures/element/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/element/index.html: -------------------------------------------------------------------------------- 1 | Hello World. 2 | -------------------------------------------------------------------------------- /test/fixtures/element/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "element", 6 | "tagName": "strong", 7 | "properties": {}, 8 | "children": [ 9 | { 10 | "type": "text", 11 | "value": "Hello World.", 12 | "position": { 13 | "start": { 14 | "line": 1, 15 | "column": 9, 16 | "offset": 8 17 | }, 18 | "end": { 19 | "line": 1, 20 | "column": 21, 21 | "offset": 20 22 | } 23 | } 24 | } 25 | ], 26 | "position": { 27 | "start": { 28 | "line": 1, 29 | "column": 1, 30 | "offset": 0 31 | }, 32 | "end": { 33 | "line": 1, 34 | "column": 30, 35 | "offset": 29 36 | } 37 | } 38 | }, 39 | { 40 | "type": "text", 41 | "value": "\n", 42 | "position": { 43 | "start": { 44 | "line": 1, 45 | "column": 30, 46 | "offset": 29 47 | }, 48 | "end": { 49 | "line": 2, 50 | "column": 1, 51 | "offset": 30 52 | } 53 | } 54 | } 55 | ], 56 | "data": { 57 | "quirksMode": false 58 | }, 59 | "position": { 60 | "start": { 61 | "line": 1, 62 | "column": 1, 63 | "offset": 0 64 | }, 65 | "end": { 66 | "line": 2, 67 | "column": 1, 68 | "offset": 30 69 | } 70 | } 71 | } 72 | -------------------------------------------------------------------------------- /test/fixtures/element/result.html: -------------------------------------------------------------------------------- 1 | Hello World. 2 | -------------------------------------------------------------------------------- /test/fixtures/empty-document/index.html: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rehypejs/rehype/f946e55cd03a10d3bf27afb49a38557caf920f59/test/fixtures/empty-document/index.html -------------------------------------------------------------------------------- /test/fixtures/empty-document/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "element", 6 | "tagName": "html", 7 | "properties": {}, 8 | "children": [ 9 | { 10 | "type": "element", 11 | "tagName": "head", 12 | "properties": {}, 13 | "children": [] 14 | }, 15 | { 16 | "type": "element", 17 | "tagName": "body", 18 | "properties": {}, 19 | "children": [] 20 | } 21 | ] 22 | } 23 | ], 24 | "data": { 25 | "quirksMode": true 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /test/fixtures/empty-document/result.html: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /test/fixtures/empty-fragment/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/empty-fragment/index.html: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rehypejs/rehype/f946e55cd03a10d3bf27afb49a38557caf920f59/test/fixtures/empty-fragment/index.html -------------------------------------------------------------------------------- /test/fixtures/empty-fragment/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [], 4 | "data": { 5 | "quirksMode": false 6 | } 7 | } 8 | -------------------------------------------------------------------------------- /test/fixtures/empty-fragment/result.html: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rehypejs/rehype/f946e55cd03a10d3bf27afb49a38557caf920f59/test/fixtures/empty-fragment/result.html -------------------------------------------------------------------------------- /test/fixtures/entities-in-literals/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/entities-in-literals/index.html: -------------------------------------------------------------------------------- 1 | 6 | 7 | 12 | 13 | 18 | -------------------------------------------------------------------------------- /test/fixtures/entities-in-literals/result.html: -------------------------------------------------------------------------------- 1 | 6 | 7 | 12 | 13 | 18 | -------------------------------------------------------------------------------- /test/fixtures/entities/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/entities/index.html: -------------------------------------------------------------------------------- 1 | © & baz. AT&T. 2 | alpha < bravo ' charlie > delta. 3 | -------------------------------------------------------------------------------- /test/fixtures/entities/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "text", 6 | "value": "© & baz. AT&T.\nalpha < bravo ' charlie > delta.\n", 7 | "position": { 8 | "start": { 9 | "line": 1, 10 | "column": 1, 11 | "offset": 0 12 | }, 13 | "end": { 14 | "line": 3, 15 | "column": 1, 16 | "offset": 67 17 | } 18 | } 19 | } 20 | ], 21 | "data": { 22 | "quirksMode": false 23 | }, 24 | "position": { 25 | "start": { 26 | "line": 1, 27 | "column": 1, 28 | "offset": 0 29 | }, 30 | "end": { 31 | "line": 3, 32 | "column": 1, 33 | "offset": 67 34 | } 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /test/fixtures/entities/result.html: -------------------------------------------------------------------------------- 1 | © & baz. AT&T. 2 | alpha < bravo ' charlie > delta. 3 | -------------------------------------------------------------------------------- /test/fixtures/html-in-svg-in-html/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/html-in-svg-in-html/index.html: -------------------------------------------------------------------------------- 1 |

      HTML in SVG in HTML

      2 | 3 | 4 | This example uses the `<switch>` element to provide a fallback 5 | graphical representation of a paragraph, if HTML is not supported. 6 | The element will process the first child whose testing attributes 7 | evaluate to true. 8 | `[requiredExtensions]` is such a test to check if the user agent 9 | supports an extensions. 10 | The first child without tests is the default. 11 | 12 | 13 | 14 |

      Here is an HTML paragraph that requires word wrap

      15 |
      16 | 17 | Here is an SVG paragraph 18 | that requires word wrap. 19 | 20 |
      21 |
      22 | -------------------------------------------------------------------------------- /test/fixtures/html-in-svg-in-html/result.html: -------------------------------------------------------------------------------- 1 |

      HTML in SVG in HTML

      2 | 3 | 4 | This example uses the `<switch>` element to provide a fallback 5 | graphical representation of a paragraph, if HTML is not supported. 6 | The element will process the first child whose testing attributes 7 | evaluate to true. 8 | `[requiredExtensions]` is such a test to check if the user agent 9 | supports an extensions. 10 | The first child without tests is the default. 11 | 12 | 13 | 14 |

      Here is an HTML paragraph that requires word wrap

      15 |
      16 | 17 | Here is an SVG paragraph 18 | that requires word wrap. 19 | 20 |
      21 |
      22 | -------------------------------------------------------------------------------- /test/fixtures/mathml/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/mathml/index.html: -------------------------------------------------------------------------------- 1 |

      The quadratic formula

      2 |

      3 | 4 | x 5 | = 6 | 7 | 8 | b 9 | ± 10 | 11 | b 2 12 | 13 | 4 a c 14 | 15 | 16 | 17 | 2 a 18 | 19 | 20 | 21 |

      22 | -------------------------------------------------------------------------------- /test/fixtures/mathml/result.html: -------------------------------------------------------------------------------- 1 |

      The quadratic formula

      2 |

      3 | 4 | x 5 | = 6 | 7 | 8 | b 9 | ± 10 | 11 | b 2 12 | 13 | 4 a c 14 | 15 | 16 | 17 | 2 a 18 | 19 | 20 | 21 |

      22 | -------------------------------------------------------------------------------- /test/fixtures/noscript/index.html: -------------------------------------------------------------------------------- 1 | 2 |

      noscript!

      3 | 4 | 5 | -------------------------------------------------------------------------------- /test/fixtures/noscript/result.html: -------------------------------------------------------------------------------- 1 |

      noscript!

      2 | 3 | 4 | -------------------------------------------------------------------------------- /test/fixtures/processing-instruction/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true 3 | } 4 | -------------------------------------------------------------------------------- /test/fixtures/processing-instruction/index.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/processing-instruction/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "type": "root", 3 | "children": [ 4 | { 5 | "type": "comment", 6 | "value": "?xml version=\"1.0\" encoding=\"UTF-8\"?", 7 | "position": { 8 | "start": { 9 | "line": 1, 10 | "column": 1, 11 | "offset": 0 12 | }, 13 | "end": { 14 | "line": 1, 15 | "column": 39, 16 | "offset": 38 17 | } 18 | } 19 | }, 20 | { 21 | "type": "text", 22 | "value": "\n", 23 | "position": { 24 | "start": { 25 | "line": 1, 26 | "column": 39, 27 | "offset": 38 28 | }, 29 | "end": { 30 | "line": 2, 31 | "column": 1, 32 | "offset": 39 33 | } 34 | } 35 | } 36 | ], 37 | "data": { 38 | "quirksMode": false 39 | }, 40 | "position": { 41 | "start": { 42 | "line": 1, 43 | "column": 1, 44 | "offset": 0 45 | }, 46 | "end": { 47 | "line": 2, 48 | "column": 1, 49 | "offset": 39 50 | } 51 | } 52 | } 53 | -------------------------------------------------------------------------------- /test/fixtures/processing-instruction/result.html: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /test/fixtures/quirksmode-off/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | Not-Quirksmode 4 |

      Outside of quirksmode, the following table is outside this paragraph: 5 | !
      6 | -------------------------------------------------------------------------------- /test/fixtures/quirksmode-off/result.html: -------------------------------------------------------------------------------- 1 | Not-Quirksmode 2 |

      Outside of quirksmode, the following table is outside this paragraph: 3 |

      !
      4 | -------------------------------------------------------------------------------- /test/fixtures/quirksmode-on/index.html: -------------------------------------------------------------------------------- 1 | 2 | Quirksmode 3 |

      In quirksmode, the following table is in this paragraph: 4 | !
      5 | -------------------------------------------------------------------------------- /test/fixtures/quirksmode-on/result.html: -------------------------------------------------------------------------------- 1 | Quirksmode 2 |

      In quirksmode, the following table is in this paragraph: 3 | !
      4 |

      -------------------------------------------------------------------------------- /test/fixtures/svg-in-html/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | The SVG `<circle>` element 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | -------------------------------------------------------------------------------- /test/fixtures/svg-in-html/result.html: -------------------------------------------------------------------------------- 1 | 2 | The SVG `<circle>` element 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | -------------------------------------------------------------------------------- /test/fixtures/svg/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "fragment": true, 3 | "closeEmptyElements": true, 4 | "tightSelfClosing": true 5 | } 6 | -------------------------------------------------------------------------------- /test/fixtures/svg/index.html: -------------------------------------------------------------------------------- 1 | 2 | Variable: shape 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /test/fixtures/svg/result.html: -------------------------------------------------------------------------------- 1 | 2 | Variable: shape 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /test/fixtures/verbose/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "verbose": true, 3 | "reprocess": false 4 | } 5 | -------------------------------------------------------------------------------- /test/fixtures/verbose/index.html: -------------------------------------------------------------------------------- 1 | 2 |

      3 |

      4 |
      5 | -------------------------------------------------------------------------------- /test/fixtures/verbose/result.html: -------------------------------------------------------------------------------- 1 | 2 |

      3 |

      4 |
      5 | -------------------------------------------------------------------------------- /test/fixtures/xhtml/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Example document 5 | 6 | 7 |

      Example paragraph

      8 | 9 | 10 | -------------------------------------------------------------------------------- /test/fixtures/xhtml/result.html: -------------------------------------------------------------------------------- 1 | 2 | Example document 3 | 4 | 5 |

      Example paragraph

      6 | 7 | 8 | -------------------------------------------------------------------------------- /test/index.js: -------------------------------------------------------------------------------- 1 | /* eslint-disable import/no-unassigned-import */ 2 | import './api.js' 3 | import './cli.js' 4 | import './parse-error.js' 5 | /* eslint-enable import/no-unassigned-import */ 6 | -------------------------------------------------------------------------------- /test/parse-error.js: -------------------------------------------------------------------------------- 1 | import assert from 'node:assert/strict' 2 | import fs from 'node:fs/promises' 3 | import process from 'node:process' 4 | import test from 'node:test' 5 | import rehypeParse from 'rehype-parse' 6 | import {unified} from 'unified' 7 | import {VFile} from 'vfile' 8 | 9 | test('parse errors', async function (t) { 10 | let index = -1 11 | const root = new URL('parse-error/', import.meta.url) 12 | const folders = await fs.readdir(root) 13 | 14 | while (++index < folders.length) { 15 | const folder = folders[index] 16 | 17 | if (folder.charAt(0) === '.') { 18 | continue 19 | } 20 | 21 | await t.test(folder, async function () { 22 | const base = new URL(folder + '/', root) 23 | const inputUrl = new URL('index.html', base) 24 | const expectedUrl = new URL('messages.json', base) 25 | 26 | const input = new VFile({ 27 | basename: 'index.html', 28 | value: await fs.readFile(inputUrl) 29 | }) 30 | 31 | unified().use(rehypeParse, {emitParseErrors: true}).parse(input) 32 | 33 | /** @type {Array} */ 34 | // eslint-disable-next-line unicorn/prefer-structured-clone -- cast to plain JSON. 35 | const actual = JSON.parse(JSON.stringify(input.messages)) 36 | 37 | /** @type {Array} */ 38 | let expected 39 | 40 | try { 41 | expected = JSON.parse(String(await fs.readFile(expectedUrl))) 42 | if ('UPDATE' in process.env) throw new Error('Update') 43 | } catch { 44 | expected = actual 45 | await fs.writeFile( 46 | expectedUrl, 47 | JSON.stringify(expected, undefined, 2) + '\n' 48 | ) 49 | } 50 | 51 | assert.deepEqual(actual, expected) 52 | }) 53 | } 54 | 55 | // This one has to be manual as it’s lone surrogates which editors/tools will 56 | // typically fix. 57 | await t.test('surrogate-in-input-stream', function () { 58 | const file = new VFile({ 59 | path: 'index.html', 60 | value: '\n' + String.fromCharCode(0xd8_00) 61 | }) 62 | 63 | unified().use(rehypeParse, {emitParseErrors: true}).parse(file) 64 | 65 | /** @type {Array} */ 66 | // eslint-disable-next-line unicorn/prefer-structured-clone -- cast to plain JSON. 67 | const actual = JSON.parse(JSON.stringify(file.messages)) 68 | 69 | assert.deepEqual(actual, [ 70 | { 71 | column: 1, 72 | fatal: false, 73 | message: 'Unexpected surrogate character', 74 | line: 2, 75 | name: 'index.html:2:1-2:1', 76 | place: { 77 | start: {line: 2, column: 1, offset: 16}, 78 | end: {line: 2, column: 1, offset: 16} 79 | }, 80 | reason: 'Unexpected surrogate character', 81 | ruleId: 'surrogate-in-input-stream', 82 | source: 'hast-util-from-html', 83 | note: 'Unexpected code point `0xD800`. Do not use lone surrogate characters in HTML', 84 | url: 'https://html.spec.whatwg.org/multipage/parsing.html#parse-error-surrogate-in-input-stream', 85 | file: 'index.html' 86 | } 87 | ]) 88 | }) 89 | }) 90 | -------------------------------------------------------------------------------- /test/parse-error/abandoned-head-element-child/index.html: -------------------------------------------------------------------------------- 1 | 2 | abandoned-head-element-child 3 | 4 | 5 | -------------------------------------------------------------------------------- /test/parse-error/abandoned-head-element-child/messages.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "column": 1, 4 | "fatal": false, 5 | "message": "Unexpected metadata element after head", 6 | "line": 4, 7 | "name": "index.html:4:1-4:9", 8 | "place": { 9 | "start": { 10 | "line": 4, 11 | "column": 1, 12 | "offset": 68 13 | }, 14 | "end": { 15 | "line": 4, 16 | "column": 9, 17 | "offset": 76 18 | } 19 | }, 20 | "reason": "Unexpected metadata element after head", 21 | "ruleId": "abandoned-head-element-child", 22 | "source": "hast-util-from-html", 23 | "note": "Unexpected element after head. Expected the element before ``", 24 | "file": "index.html" 25 | } 26 | ] 27 | -------------------------------------------------------------------------------- /test/parse-error/abrupt-closing-of-empty-comment/index.html: -------------------------------------------------------------------------------- 1 | 2 | abrupt closing of empty comment 3 | This one: . 4 | And this one: . 5 | -------------------------------------------------------------------------------- /test/parse-error/abrupt-closing-of-empty-comment/messages.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "column": 15, 4 | "fatal": false, 5 | "message": "Unexpected abruptly closed empty comment", 6 | "line": 3, 7 | "name": "index.html:3:15-3:15", 8 | "place": { 9 | "start": { 10 | "line": 3, 11 | "column": 15, 12 | "offset": 77 13 | }, 14 | "end": { 15 | "line": 3, 16 | "column": 15, 17 | "offset": 77 18 | } 19 | }, 20 | "reason": "Unexpected abruptly closed empty comment", 21 | "ruleId": "abrupt-closing-of-empty-comment", 22 | "source": "hast-util-from-html", 23 | "note": "Unexpected `>` or `->`. Expected `-->` to close comments", 24 | "url": "https://html.spec.whatwg.org/multipage/parsing.html#parse-error-abrupt-closing-of-empty-comment", 25 | "file": "index.html" 26 | }, 27 | { 28 | "column": 20, 29 | "fatal": false, 30 | "message": "Unexpected abruptly closed empty comment", 31 | "line": 4, 32 | "name": "index.html:4:20-4:20", 33 | "place": { 34 | "start": { 35 | "line": 4, 36 | "column": 20, 37 | "offset": 99 38 | }, 39 | "end": { 40 | "line": 4, 41 | "column": 20, 42 | "offset": 99 43 | } 44 | }, 45 | "reason": "Unexpected abruptly closed empty comment", 46 | "ruleId": "abrupt-closing-of-empty-comment", 47 | "source": "hast-util-from-html", 48 | "note": "Unexpected `>` or `->`. Expected `-->` to close comments", 49 | "url": "https://html.spec.whatwg.org/multipage/parsing.html#parse-error-abrupt-closing-of-empty-comment", 50 | "file": "index.html" 51 | } 52 | ] 53 | -------------------------------------------------------------------------------- /test/parse-error/abrupt-doctype-public-identifier/index.html: -------------------------------------------------------------------------------- 1 | 2 | abrupt doctype public identifier 3 | -------------------------------------------------------------------------------- /test/parse-error/abrupt-doctype-public-identifier/messages.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "column": 27, 4 | "fatal": false, 5 | "message": "Unexpected abruptly closed public identifier", 6 | "line": 1, 7 | "name": "index.html:1:27-1:27", 8 | "place": { 9 | "start": { 10 | "line": 1, 11 | "column": 27, 12 | "offset": 26 13 | }, 14 | "end": { 15 | "line": 1, 16 | "column": 27, 17 | "offset": 26 18 | } 19 | }, 20 | "reason": "Unexpected abruptly closed public identifier", 21 | "ruleId": "abrupt-doctype-public-identifier", 22 | "source": "hast-util-from-html", 23 | "note": "Unexpected `>`. Expected a closing `\"` or `'` after the public identifier", 24 | "url": "https://html.spec.whatwg.org/multipage/parsing.html#parse-error-abrupt-doctype-public-identifier", 25 | "file": "index.html" 26 | }, 27 | { 28 | "column": 1, 29 | "fatal": false, 30 | "message": "Unexpected non-conforming doctype declaration", 31 | "line": 1, 32 | "name": "index.html:1:1-1:28", 33 | "place": { 34 | "start": { 35 | "line": 1, 36 | "column": 1, 37 | "offset": 0 38 | }, 39 | "end": { 40 | "line": 1, 41 | "column": 28, 42 | "offset": 27 43 | } 44 | }, 45 | "reason": "Unexpected non-conforming doctype declaration", 46 | "ruleId": "non-conforming-doctype", 47 | "source": "hast-util-from-html", 48 | "note": "Expected `` or ``", 49 | "file": "index.html" 50 | } 51 | ] 52 | -------------------------------------------------------------------------------- /test/parse-error/abrupt-doctype-system-identifier/index.html: -------------------------------------------------------------------------------- 1 | 2 | abrupt doctype system identifier 3 | -------------------------------------------------------------------------------- /test/parse-error/abrupt-doctype-system-identifier/messages.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "column": 55, 4 | "fatal": false, 5 | "message": "Unexpected abruptly closed system identifier", 6 | "line": 1, 7 | "name": "index.html:1:55-1:55", 8 | "place": { 9 | "start": { 10 | "line": 1, 11 | "column": 55, 12 | "offset": 54 13 | }, 14 | "end": { 15 | "line": 1, 16 | "column": 55, 17 | "offset": 54 18 | } 19 | }, 20 | "reason": "Unexpected abruptly closed system identifier", 21 | "ruleId": "abrupt-doctype-system-identifier", 22 | "source": "hast-util-from-html", 23 | "note": "Unexpected `>`. Expected a closing `\"` or `'` after the identifier identifier", 24 | "url": "https://html.spec.whatwg.org/multipage/parsing.html#parse-error-abrupt-doctype-system-identifier", 25 | "file": "index.html" 26 | }, 27 | { 28 | "column": 1, 29 | "fatal": false, 30 | "message": "Unexpected non-conforming doctype declaration", 31 | "line": 1, 32 | "name": "index.html:1:1-1:56", 33 | "place": { 34 | "start": { 35 | "line": 1, 36 | "column": 1, 37 | "offset": 0 38 | }, 39 | "end": { 40 | "line": 1, 41 | "column": 56, 42 | "offset": 55 43 | } 44 | }, 45 | "reason": "Unexpected non-conforming doctype declaration", 46 | "ruleId": "non-conforming-doctype", 47 | "source": "hast-util-from-html", 48 | "note": "Expected `` or ``", 49 | "file": "index.html" 50 | } 51 | ] 52 | -------------------------------------------------------------------------------- /test/parse-error/absence-of-digits-in-numeric-character-reference/index.html: -------------------------------------------------------------------------------- 1 | 2 | absence-of-digits-in-numeric-character-reference 3 | &#abc; 4 | &#xghi; 5 | -------------------------------------------------------------------------------- /test/parse-error/absence-of-digits-in-numeric-character-reference/messages.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "column": 3, 4 | "fatal": false, 5 | "message": "Unexpected non-digit at start of numeric character reference", 6 | "line": 3, 7 | "name": "index.html:3:3-3:3", 8 | "place": { 9 | "start": { 10 | "line": 3, 11 | "column": 3, 12 | "offset": 82 13 | }, 14 | "end": { 15 | "line": 3, 16 | "column": 3, 17 | "offset": 82 18 | } 19 | }, 20 | "reason": "Unexpected non-digit at start of numeric character reference", 21 | "ruleId": "absence-of-digits-in-numeric-character-reference", 22 | "source": "hast-util-from-html", 23 | "note": "Unexpected `a`. Expected `[0-9]` for decimal references or `[0-9a-fA-F]` for hexadecimal references", 24 | "url": "https://html.spec.whatwg.org/multipage/parsing.html#parse-error-absence-of-digits-in-numeric-character-reference", 25 | "file": "index.html" 26 | }, 27 | { 28 | "column": 4, 29 | "fatal": false, 30 | "message": "Unexpected non-digit at start of numeric character reference", 31 | "line": 4, 32 | "name": "index.html:4:4-4:4", 33 | "place": { 34 | "start": { 35 | "line": 4, 36 | "column": 4, 37 | "offset": 90 38 | }, 39 | "end": { 40 | "line": 4, 41 | "column": 4, 42 | "offset": 90 43 | } 44 | }, 45 | "reason": "Unexpected non-digit at start of numeric character reference", 46 | "ruleId": "absence-of-digits-in-numeric-character-reference", 47 | "source": "hast-util-from-html", 48 | "note": "Unexpected `g`. Expected `[0-9]` for decimal references or `[0-9a-fA-F]` for hexadecimal references", 49 | "url": "https://html.spec.whatwg.org/multipage/parsing.html#parse-error-absence-of-digits-in-numeric-character-reference", 50 | "file": "index.html" 51 | } 52 | ] 53 | -------------------------------------------------------------------------------- /test/parse-error/cdata-in-html-content/index.html: -------------------------------------------------------------------------------- 1 | 2 | cdata-in-html-content 3 | 4 | but it’s fine in foreign content 5 | -------------------------------------------------------------------------------- /test/parse-error/cdata-in-html-content/messages.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "column": 9, 4 | "fatal": false, 5 | "message": "Unexpected CDATA section in HTML", 6 | "line": 3, 7 | "name": "index.html:3:9-3:9", 8 | "place": { 9 | "start": { 10 | "line": 3, 11 | "column": 9, 12 | "offset": 61 13 | }, 14 | "end": { 15 | "line": 3, 16 | "column": 9, 17 | "offset": 61 18 | } 19 | }, 20 | "reason": "Unexpected CDATA section in HTML", 21 | "ruleId": "cdata-in-html-content", 22 | "source": "hast-util-from-html", 23 | "note": "Unexpected ` 2 | character-reference-outside-unicode-range 3 | � 4 | � 5 | -------------------------------------------------------------------------------- /test/parse-error/character-reference-outside-unicode-range/messages.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "column": 11, 4 | "fatal": false, 5 | "message": "Unexpected too big numeric character reference", 6 | "line": 3, 7 | "name": "index.html:3:11-3:11", 8 | "place": { 9 | "start": { 10 | "line": 3, 11 | "column": 11, 12 | "offset": 83 13 | }, 14 | "end": { 15 | "line": 3, 16 | "column": 11, 17 | "offset": 83 18 | } 19 | }, 20 | "reason": "Unexpected too big numeric character reference", 21 | "ruleId": "character-reference-outside-unicode-range", 22 | "source": "hast-util-from-html", 23 | "note": "Unexpectedly high character reference. Expected character references to be at most hexadecimal 10ffff (or decimal 1114111)", 24 | "url": "https://html.spec.whatwg.org/multipage/parsing.html#parse-error-character-reference-outside-unicode-range", 25 | "file": "index.html" 26 | }, 27 | { 28 | "column": 11, 29 | "fatal": false, 30 | "message": "Unexpected too big numeric character reference", 31 | "line": 4, 32 | "name": "index.html:4:11-4:11", 33 | "place": { 34 | "start": { 35 | "line": 4, 36 | "column": 11, 37 | "offset": 94 38 | }, 39 | "end": { 40 | "line": 4, 41 | "column": 11, 42 | "offset": 94 43 | } 44 | }, 45 | "reason": "Unexpected too big numeric character reference", 46 | "ruleId": "character-reference-outside-unicode-range", 47 | "source": "hast-util-from-html", 48 | "note": "Unexpectedly high character reference. Expected character references to be at most hexadecimal 10ffff (or decimal 1114111)", 49 | "url": "https://html.spec.whatwg.org/multipage/parsing.html#parse-error-character-reference-outside-unicode-range", 50 | "file": "index.html" 51 | } 52 | ] 53 | -------------------------------------------------------------------------------- /test/parse-error/closing-of-element-with-open-child-elements/index.html: -------------------------------------------------------------------------------- 1 | 2 | closing-of-element-with-open-child-elements 3 | 4 | -------------------------------------------------------------------------------- /test/parse-error/closing-of-element-with-open-child-elements/messages.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "column": 19, 4 | "fatal": false, 5 | "message": "Unexpected closing tag with open child elements", 6 | "line": 3, 7 | "name": "index.html:3:19-3:30", 8 | "place": { 9 | "start": { 10 | "line": 3, 11 | "column": 19, 12 | "offset": 93 13 | }, 14 | "end": { 15 | "line": 3, 16 | "column": 30, 17 | "offset": 104 18 | } 19 | }, 20 | "reason": "Unexpected closing tag with open child elements", 21 | "ruleId": "closing-of-element-with-open-child-elements", 22 | "source": "hast-util-from-html", 23 | "note": "Unexpectedly closing tag. Expected other tags to be closed first", 24 | "file": "index.html" 25 | } 26 | ] 27 | -------------------------------------------------------------------------------- /test/parse-error/control-character-in-input-stream/index.html: -------------------------------------------------------------------------------- 1 | 2 | control-character-in-input-stream 3 | 4 |  5 | -------------------------------------------------------------------------------- /test/parse-error/control-character-in-input-stream/messages.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "column": 1, 4 | "fatal": false, 5 | "message": "Unexpected control character", 6 | "line": 4, 7 | "name": "index.html:4:1-4:1", 8 | "place": { 9 | "start": { 10 | "line": 4, 11 | "column": 1, 12 | "offset": 111 13 | }, 14 | "end": { 15 | "line": 4, 16 | "column": 1, 17 | "offset": 111 18 | } 19 | }, 20 | "reason": "Unexpected control character", 21 | "ruleId": "control-character-in-input-stream", 22 | "source": "hast-util-from-html", 23 | "note": "Unexpected control character `0x7F`. Expected a non-control code point, 0x00, or ASCII whitespace", 24 | "url": "https://html.spec.whatwg.org/multipage/parsing.html#parse-error-control-character-in-input-stream", 25 | "file": "index.html" 26 | } 27 | ] 28 | -------------------------------------------------------------------------------- /test/parse-error/control-character-reference/index.html: -------------------------------------------------------------------------------- 1 | 2 | control-character-reference 3 |  4 | -------------------------------------------------------------------------------- /test/parse-error/control-character-reference/messages.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "column": 7, 4 | "fatal": false, 5 | "message": "Unexpected control character reference", 6 | "line": 3, 7 | "name": "index.html:3:7-3:7", 8 | "place": { 9 | "start": { 10 | "line": 3, 11 | "column": 7, 12 | "offset": 65 13 | }, 14 | "end": { 15 | "line": 3, 16 | "column": 7, 17 | "offset": 65 18 | } 19 | }, 20 | "reason": "Unexpected control character reference", 21 | "ruleId": "control-character-reference", 22 | "source": "hast-util-from-html", 23 | "note": "Unexpectedly control character in reference. Expected a non-control code point, 0x00, or ASCII whitespace", 24 | "url": "https://html.spec.whatwg.org/multipage/parsing.html#parse-error-control-character-reference", 25 | "file": "index.html" 26 | } 27 | ] 28 | -------------------------------------------------------------------------------- /test/parse-error/disallowed-content-in-noscript-in-head/index.html: -------------------------------------------------------------------------------- 1 | 2 | disallowed-content-in-noscript-in-head 3 | 4 | -------------------------------------------------------------------------------- /test/parse-error/disallowed-content-in-noscript-in-head/messages.json: -------------------------------------------------------------------------------- 1 | [ 2 | { 3 | "column": 11, 4 | "fatal": false, 5 | "message": "Disallowed content inside `