Skip to content

Repository files navigation

Simple HTML parser

Convert html string into a simple object[]. Handles real world html, and optionally JSX-like syntax.

NuGet

Install-Package NMyVision.HtmlParser

Simple Example

var source = "<div data-field='sample'>Inner Text</div>";
var parser = new HtmlParser();

var nodes = parser.Parse(source);

returns this object.

Simple example

Advance Example

<!DOCTYPE html>
<html lang="en">

<head>
  <title>Jade</title>
  <script type="text/javascript">
    const foo = true;
    let bar = function() {};
    if (foo) {
      bar(1 + 5)
    }
  </script>
</head>

<body>
  <h1>Jade - node template engine</h1>
  <div class="col" id="container">
    <p>You are amazing</p>
    <p>
      Jade is a terse and simple
      templating language with a
      strong focus on performance
      and powerful features.
    </p>
  </div>
</body>

</html>

To

screenshot]

[
  {
    "type": "DocType",
    "content": "DOCTYPE html"
  },
  {
    "tag": "html",
    "type": "Element",
    "attributes": [
      {
        "name": "lang",
        "value": "en"
      }
    ],
    "children": [
      {
        "tag": "head",
        "type": "Element",
        "attributes": [],
        "children": [
          {
            "tag": "title",
            "type": "Element",
            "attributes": [],
            "children": [
              {
                "type": "Text",
                "content": "Jade"
              }
            ]
          },
          {
            "tag": "script",
            "type": "Element",
            "content": "\r\n    const foo = true;\r\n    let bar = function() {};\r\n    if (foo) {\r\n      bar(1 + 5)\r\n    }\r\n    alert('<b>Some html<b>')\r\n  ",
            "attributes": [
              {
                "name": "type",
                "value": "text/javascript"
              }
            ],
            "children": []
          }
        ]
      }
    ]
  },
  {
    "tag": "body",
    "type": "Element",
    "attributes": [],
    "children": [
      {
        "type": "Comment",
        "content": " A simple comment "
      },
      {
        "tag": "h1",
        "type": "Element",
        "attributes": [],
        "children": [
          {
            "type": "Text",
            "content": "Jade - node template engine"
          }
        ]
      },
      {
        "tag": "div",
        "type": "Element",
        "attributes": [
          {
            "name": "class",
            "value": "col"
          },
          {
            "name": "id",
            "value": "container"
          }
        ],
        "children": [
          {
            "tag": "p",
            "type": "Element",
            "attributes": [],
            "children": [
              {
                "type": "Text",
                "content": "You are amazing"
              }
            ]
          },
          {
            "tag": "p",
            "type": "Element",
            "attributes": [],
            "children": [
              {
                "type": "Text",
                "content": "\r\n      Jade is a terse and simple\r\n      templating language with a\r\n      strong focus on performance\r\n      and powerful features.\r\n    "
              }
            ]
          }
        ]
      }
    ]
  }
]

JSX Mode

Version 2.0 adds an opt-in JSX-like syntax mode. Create the parser with ParserOptions.Jsx (or set Mode = SyntaxMode.Jsx); the default Html mode is unchanged.

var parser = new HtmlParser(ParserOptions.Jsx);

var nodes = parser.Parse("<li data-prop={ item.value }>{item.name}</li>");

What JSX mode adds:

  • Expression containers{expr} in child position becomes a node of type Expression with the expression text in Content. Nested braces and braces inside ', ", and ` string literals are handled.
  • Expression attributesattr={ expr } stores the inner text verbatim (spacing preserved) and flags the attribute via Attributes.IsExpression("attr"), so the original { ... } form can be regenerated exactly.
  • Spread attributes<div {...props}> lands in Attributes.Spreads.
  • Fragments<>...</> parses as an element with an empty tag; check with node.IsFragment().
  • Componentsnode.IsComponent() is true for capitalized tags (<MyButton>, <Foo.Bar>).
  • No implicit void tags — in JSX mode <br> is not auto-closed; use <br />.

OuterHTML still returns the exact source slice for each element, so input can be round-tripped.

Releases

2.0.0

  • JSX-like syntax mode (ParserOptions.Jsx): expression containers, expression/spread attributes, fragments, component detection
  • New node type Expression; new members HtmlNode.IsComponent(), HtmlNode.IsFragment(), HtmlAttributeCollection.IsExpression(), HtmlAttributeCollection.Spreads
  • Parser core rewritten to read the source string directly instead of a Queue<char>, removing per-character allocations and string concatenation
  • Extensions.Peek(Queue<char>, int) is obsolete and will be removed in a future release
  • Library now multi-targets netstandard2.0 and net8.0
  • README included in the NuGet package

1.0.8

  • Bug fix name only attribute fix

1.0.2

  • Bug fix index was not reset per Parse call

1.0.1

  • Refactor and code cleanup

1.0.1

  • Initial Release

About

A simple HtmlParser

Resources

Stars

0 stars

Watchers

0 watching

Forks

Releases

Packages

Used by

Contributors

Languages