simplibs-extractor-html 0.1.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (134) hide show
  1. simplibs_extractor_html-0.1.0/LICENSE +21 -0
  2. simplibs_extractor_html-0.1.0/PKG-INFO +504 -0
  3. simplibs_extractor_html-0.1.0/README.md +464 -0
  4. simplibs_extractor_html-0.1.0/pyproject.toml +94 -0
  5. simplibs_extractor_html-0.1.0/setup.cfg +4 -0
  6. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/__init__.py +82 -0
  7. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/actions/ApplyToHtmlBlocks.py +29 -0
  8. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/actions/CleanupHtmlWhitespace.py +22 -0
  9. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/actions/CompactHtml.py +22 -0
  10. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/actions/HtmlOutline.py +23 -0
  11. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/actions/RemoveTemplateImports.py +22 -0
  12. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/actions/StripHtmlComments.py +23 -0
  13. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/actions/StripTemplateComments.py +27 -0
  14. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/actions/TemplateOutline.py +23 -0
  15. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/actions/__init__.py +57 -0
  16. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/annotations/TemplateEngine.py +26 -0
  17. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/annotations/__init__.py +14 -0
  18. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_ANY_TAG_PATTERN.py +16 -0
  19. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_BLOCK_LANGUAGE_BY_TYPE.py +41 -0
  20. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_COMMENT_END_PATTERN.py +19 -0
  21. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_CONDITIONAL_PATTERN.py +23 -0
  22. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_DEPENDENCY_DIR_NAMES.py +18 -0
  23. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_EXTRA_LANGUAGE_BY_SUFFIX.py +31 -0
  24. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_HEADING_ELEMENTS.py +15 -0
  25. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_ID_ATTRIBUTE_PATTERN.py +21 -0
  26. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_IMPLIED_END.py +34 -0
  27. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_LICENSE_START.py +14 -0
  28. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_LICENSE_TAGS.py +14 -0
  29. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_OUTLINE_ELEMENTS.py +32 -0
  30. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_OUTLINE_TEXT_LIMIT.py +15 -0
  31. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_OUTPUT_DIR_NAMES.py +43 -0
  32. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_PLAIN_SUFFIXES.py +18 -0
  33. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_RAW_TEXT_END_PATTERNS.py +28 -0
  34. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_SUFFIXES.py +22 -0
  35. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_TAG_NAME_PATTERN.py +16 -0
  36. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_TEMPLATE_BLOCKS.py +38 -0
  37. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_TEMPLATE_IMPORT_TAGS.py +29 -0
  38. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_TEMPLATE_OUTLINE_TAGS.py +35 -0
  39. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_TEMPLATE_SUFFIXES.py +19 -0
  40. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_TEMPLATE_TAG_NAME_PATTERN.py +16 -0
  41. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_TEMPLATE_TOKEN_PATTERN.py +16 -0
  42. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_TEXT_ELEMENTS.py +16 -0
  43. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_TOKEN_PATTERN.py +26 -0
  44. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_TYPE_ATTRIBUTE_PATTERN.py +21 -0
  45. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_VOID_ELEMENTS.py +21 -0
  46. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_WRAPPED_STEM_ENDING.py +14 -0
  47. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/HTML_WRAPPED_SUFFIXES.py +15 -0
  48. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/constants/__init__.py +77 -0
  49. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/file_rules/__init__.py +56 -0
  50. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/file_rules/atomic/DEPENDENCY_DIRS.py +17 -0
  51. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/file_rules/atomic/DOT_NAME.py +19 -0
  52. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/file_rules/atomic/OUTPUT_DIRS.py +17 -0
  53. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/file_rules/atomic/VCS_DIRS.py +21 -0
  54. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/file_rules/atomic/WRAPPED_HTML.py +22 -0
  55. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/file_rules/atomic/__init__.py +26 -0
  56. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/file_rules/html/HTML_BASE.py +22 -0
  57. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/file_rules/html/HTML_FILES.py +24 -0
  58. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/file_rules/html/HTML_PLAIN_BASE.py +24 -0
  59. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/file_rules/html/HTML_STRICT_EXCLUDE.py +21 -0
  60. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/file_rules/html/__init__.py +20 -0
  61. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/__init__.py +44 -0
  62. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/HtmlBlock.py +31 -0
  63. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/HtmlOutlineBuilder.py +189 -0
  64. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/HtmlScan.py +50 -0
  65. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/HtmlTag.py +32 -0
  66. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/Ranges.py +48 -0
  67. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/TemplateScan.py +43 -0
  68. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/TemplateTag.py +33 -0
  69. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/__init__.py +68 -0
  70. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/blank_spans.py +40 -0
  71. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/build_html_outline.py +38 -0
  72. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/build_template_outline.py +75 -0
  73. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/find_blanks_start.py +29 -0
  74. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/find_block_language.py +35 -0
  75. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/find_comments.py +60 -0
  76. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/find_protected_spans.py +48 -0
  77. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/find_template_import_spans.py +37 -0
  78. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/fit_removal_span.py +40 -0
  79. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/is_license_comment.py +26 -0
  80. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/line_of.py +23 -0
  81. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/raise_block_result_invalid.py +38 -0
  82. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/replace_spans.py +42 -0
  83. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/scan_checked.py +45 -0
  84. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/scan_html.py +208 -0
  85. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/scan_templates.py +128 -0
  86. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/scan_templates_checked.py +39 -0
  87. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/skip_html_comment.py +41 -0
  88. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/skip_html_tag.py +46 -0
  89. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/tidy_lines.py +86 -0
  90. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/_helpers/warn_problems.py +32 -0
  91. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/apply_to_html_blocks.py +103 -0
  92. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/cleanup_html_whitespace.py +54 -0
  93. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/compact_html.py +44 -0
  94. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/html_comment_spans.py +54 -0
  95. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/html_outline.py +66 -0
  96. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/strip_html_comments.py +63 -0
  97. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/templates/__init__.py +25 -0
  98. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/templates/remove_template_imports.py +51 -0
  99. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/templates/strip_template_comments.py +60 -0
  100. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/templates/template_comment_spans.py +49 -0
  101. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/logic/templates/template_outline.py +62 -0
  102. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/plugin/__init__.py +14 -0
  103. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/plugin/register_all.py +60 -0
  104. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/presets/__init__.py +43 -0
  105. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/presets/html_clean_steps.py +54 -0
  106. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/presets/html_no_imports_steps.py +50 -0
  107. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/presets/html_outline_steps.py +28 -0
  108. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/presets/template_structure_steps.py +27 -0
  109. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/DJANGO_CLEAN.py +36 -0
  110. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/DJANGO_NO_IMPORTS.py +32 -0
  111. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/DJANGO_OUTLINE.py +32 -0
  112. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/DJANGO_STRUCTURE.py +32 -0
  113. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/HTML_CODE_CLEAN.py +32 -0
  114. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/HTML_CODE_NO_IMPORTS.py +30 -0
  115. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/HTML_DATA_ALL.py +26 -0
  116. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/HTML_OUTLINE.py +31 -0
  117. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/HTML_PROFILES.py +42 -0
  118. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/HTML_SRC_CLEAN.py +31 -0
  119. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/JINJA_CLEAN.py +35 -0
  120. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/JINJA_NO_IMPORTS.py +32 -0
  121. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/JINJA_OUTLINE.py +30 -0
  122. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/JINJA_STRUCTURE.py +31 -0
  123. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/__init__.py +86 -0
  124. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/steps_for_engine.py +39 -0
  125. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/profiles/steps_for_pages.py +36 -0
  126. simplibs_extractor_html-0.1.0/src/simplibs/extractor_html/py.typed +1 -0
  127. simplibs_extractor_html-0.1.0/src/simplibs_extractor_html.egg-info/PKG-INFO +504 -0
  128. simplibs_extractor_html-0.1.0/src/simplibs_extractor_html.egg-info/SOURCES.txt +132 -0
  129. simplibs_extractor_html-0.1.0/src/simplibs_extractor_html.egg-info/dependency_links.txt +1 -0
  130. simplibs_extractor_html-0.1.0/src/simplibs_extractor_html.egg-info/entry_points.txt +2 -0
  131. simplibs_extractor_html-0.1.0/src/simplibs_extractor_html.egg-info/requires.txt +14 -0
  132. simplibs_extractor_html-0.1.0/src/simplibs_extractor_html.egg-info/top_level.txt +1 -0
  133. simplibs_extractor_html-0.1.0/tests/test_architecture.py +153 -0
  134. simplibs_extractor_html-0.1.0/tests/test_public_api.py +106 -0
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2025 Dalibor Sova (Sudip2708)
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.
@@ -0,0 +1,504 @@
1
+ Metadata-Version: 2.4
2
+ Name: simplibs-extractor-html
3
+ Version: 0.1.0
4
+ Summary: The HTML add-on of simplibs-extractor: file rules for HTML pages and Django and Jinja templates, steps that remove comments and imports (found by a scanner that knows scripts, styles and template tags), an outline step and thirteen ready profiles.
5
+ Author-email: "Dalibor Sova (Sudip2708)" <daliborsova@seznam.cz>
6
+ License-Expression: MIT
7
+ Project-URL: Homepage, https://github.com/simplibs/simplibs-extractor-html
8
+ Project-URL: Repository, https://github.com/simplibs/simplibs-extractor-html
9
+ Project-URL: Issues, https://github.com/simplibs/simplibs-extractor-html/issues
10
+ Project-URL: Changelog, https://github.com/simplibs/simplibs-extractor-html/blob/main/CHANGELOG.md
11
+ Keywords: extractor,html,django,jinja,templates,code-extractor,project-to-text,comments,imports,outline,markdown,llm,context,plugin,simplibs,simplibs-extractor,developer-tools
12
+ Classifier: Development Status :: 3 - Alpha
13
+ Classifier: Environment :: Console
14
+ Classifier: Intended Audience :: Developers
15
+ Classifier: Programming Language :: Python :: 3
16
+ Classifier: Programming Language :: Python :: 3.11
17
+ Classifier: Programming Language :: Python :: 3.12
18
+ Classifier: Programming Language :: Python :: 3.13
19
+ Classifier: Programming Language :: Python :: 3.14
20
+ Classifier: Topic :: Software Development :: Libraries :: Python Modules
21
+ Classifier: Topic :: Utilities
22
+ Classifier: Typing :: Typed
23
+ Requires-Python: >=3.11
24
+ Description-Content-Type: text/markdown
25
+ License-File: LICENSE
26
+ Requires-Dist: simplibs-extractor>=0.2.0
27
+ Requires-Dist: simplibs-extractor-javascript>=0.1.0
28
+ Requires-Dist: simplibs-extractor-css>=0.1.0
29
+ Requires-Dist: simplibs-text>=0.2.0
30
+ Requires-Dist: simplibs-actions>=0.2.2
31
+ Requires-Dist: simplibs-path>=0.2.0
32
+ Requires-Dist: simplibs-rules>=0.4.0
33
+ Requires-Dist: simplibs-validate>=0.3.2
34
+ Requires-Dist: simplibs-types>=0.2.0
35
+ Requires-Dist: simplibs-exception>=1.0.0
36
+ Provides-Extra: dev
37
+ Requires-Dist: pytest>=9.0; extra == "dev"
38
+ Requires-Dist: pytest-cov>=5.0; extra == "dev"
39
+ Dynamic: license-file
40
+
41
+ # 🌐 `simplibs-extractor-html`
42
+
43
+ [![PyPI](https://img.shields.io/pypi/v/simplibs-extractor-html)](https://pypi.org/project/simplibs-extractor-html/)
44
+ [![Python](https://img.shields.io/badge/python-3.11%2B-blue)](https://www.python.org/downloads/)
45
+ [![Licence](https://img.shields.io/badge/licence-MIT-green)](https://github.com/simplibs/simplibs-extractor-html/blob/main/LICENSE)
46
+ [![tests](https://github.com/simplibs/simplibs-extractor-html/actions/workflows/tests.yml/badge.svg)](https://github.com/simplibs/simplibs-extractor-html/actions)
47
+
48
+ **Pages and templates in one document — Django and Jinja read as the templates they are, the code inside cleaned by the add-on of its own language.**
49
+
50
+ The HTML add-on of [`simplibs-extractor`](https://pypi.org/project/simplibs-extractor/). The extractor gathers the text files of a folder into one document and knows **no language**; this library teaches it pages and templates: which files are worth reading,
51
+ how to take **comments and imports** out of a source, how to tidy its whitespace without touching a `<pre>`, how to hand the JavaScript in `<script>` and the CSS in `<style>` to the steps of their own add-ons, how to write an **outline** of a page and the **skeleton** of
52
+ a template, and **thirteen ready profiles** that put it together. A page is read by a small scanner that knows tags, quoted values and raw text, never by a regex over the whole page — so a `<!--` inside `title="..."` or inside a script is left alone, and
53
+ a `>` inside `{% if a > b %}` does not end a tag.
54
+
55
+ ```bash
56
+ pip install simplibs-extractor-html
57
+ simplibs-extractor html django-clean my_project
58
+ ```
59
+
60
+ ```python
61
+ from simplibs.extractor_html import strip_html_comments, html_outline
62
+
63
+ strip_html_comments("<p>a</p> <!-- note -->\n<p>b</p>\n") # -> '<p>a</p>\n<p>b</p>\n'
64
+ html_outline('<main><h1>Hi</h1><div id="a"></div></main>') # -> 'main\n h1 "Hi"\n div#a\n'
65
+ ```
66
+
67
+ > `pip install` is the whole installation: the library announces itself to the extractor through an entry point, so the profiles show up in `simplibs-extractor --list-profiles html` with nothing to import. It brings the add-ons for JavaScript
68
+ > and CSS with it, because it uses their steps for the code inside a page. The same steps are plain functions (`str -> str`) that you can use without the extractor at all.
69
+
70
+ ---
71
+
72
+ ## 🧭 The Core Philosophy
73
+
74
+ Cleaning a page with a few regular expressions works until the first file where it does not: a `<!--` inside an attribute, a comment-like string in a script, a `>` inside `{% if a > b %}`, a `<pre>` whose spaces are the content, a `.html` file that is a Jinja
75
+ template whose `{# ... #}` spans three lines. `simplibs-extractor-html` takes those traps seriously:
76
+
77
+ * **A scanner, not a parser.** One pass that knows tags with their quoted values and the elements whose content is raw text (`script`, `style`, `textarea`, `title`), and jumps from one stop to the next. It builds no tree and it cannot fail: there is no syntax it refuses.
78
+ * **The curly braces first.** In a template `{{ }}`, `{% %}` and `{# #}` are read before the page and blanked out, so the HTML is read from text that has the same length and the same lines. A construct that is not closed is only text; only a block that is opened and never closed is damage.
79
+ * **Django is not Jinja.** A construct stays on one line in Django and may span lines in Jinja; `{% comment %}` and `{% verbatim %}` exist in Django, `{% raw %}` and `{% macro %}` in Jinja. A page cannot say which engine it is written for, so the steps for templates **require the `engine`**,
80
+ and the profiles come in families: pages, Django, Jinja.
81
+ * **A comment is not always a comment.** A `<!--` inside an attribute or a script is text. An Internet Explorer conditional comment holds real tags and stays by default. With `keep_license=True` the comments that minifiers keep — `<!--! ... -->`, `@license`, `@preserve` — survive.
82
+ * **Whitespace that matters is left alone.** The lines that touch a `<pre>`, a `<textarea>`, a `<script>`, a `<style>` or a verbatim block come out exactly as they went in; everywhere else trailing blanks go and blank runs are reduced.
83
+ * **The code inside a page belongs to its own language.** The step for blocks takes the steps for `<script>` and `<style>` as parameters; the presets give it those of the JavaScript and CSS add-ons. A script that holds JSON or a template of a framework is data, and no step sees it.
84
+ * **A damaged page is left as it is.** A comment, a tag or a `script` that is never closed: the text comes back unchanged, with a warning, and the extractor calls the file `partial`. A step never cuts on a basis it does not trust.
85
+ * **The project's own is its own.** The strict profiles leave out packages of other people and generated output — but `templates/` and `static/` stay, because that is where a Django project keeps its own files, and `public/index.html` of a React project is source.
86
+ * **Functions first, actions on top.** Every step is a plain function; the action is a thin wrapper of the same name, and the presets and profiles are built from the actions. The layers only look left: `constants` ← `annotations` ← `file_rules` ← `logic` ← `actions` ← `presets` ← `profiles` ← `plugin`.
87
+
88
+ ```python
89
+ strip_html_comments("<p>a</p>\n<!-- never closed\n") # -> '<p>a</p>\n<!-- never closed\n' unchanged, with a UserWarning: the comment is never closed
90
+ ```
91
+
92
+ ---
93
+
94
+ ## 📦 Installation
95
+
96
+ ```bash
97
+ pip install simplibs-extractor-html
98
+ ```
99
+
100
+ Requires Python 3.11+. The package brings [`simplibs-extractor`](https://pypi.org/project/simplibs-extractor/) with it, and the command `simplibs-extractor` is available at once. Runtime dependencies (installed automatically):
101
+ [`simplibs-extractor`](https://pypi.org/project/simplibs-extractor/) (the profile, the registry, `by_suffix`),
102
+ [`simplibs-extractor-javascript`](https://pypi.org/project/simplibs-extractor-javascript/) and [`simplibs-extractor-css`](https://pypi.org/project/simplibs-extractor-css/) (the steps for the code inside `<script>` and `<style>`),
103
+ [`simplibs-text`](https://pypi.org/project/simplibs-text/) (cutting the found ranges, the `Span` type, the whitespace presets),
104
+ [`simplibs-actions`](https://pypi.org/project/simplibs-actions/) (the steps as actions),
105
+ [`simplibs-path`](https://pypi.org/project/simplibs-path/) and [`simplibs-rules`](https://pypi.org/project/simplibs-rules/) (the file rules),
106
+ [`simplibs-validate`](https://pypi.org/project/simplibs-validate/) (`@validate_call` on every public function),
107
+ [`simplibs-types`](https://pypi.org/project/simplibs-types/) (`int_positive`, the depth of the outline) and
108
+ [`simplibs-exception`](https://pypi.org/project/simplibs-exception/) (the `ParamError` of the step for blocks).
109
+
110
+ ---
111
+
112
+ ## 🚀 Quick Start in 60 Seconds
113
+
114
+ ### Level 1: The command line
115
+
116
+ ```bash
117
+ simplibs-extractor html src-clean my_project # the project's own pages, cleaned -> my_project/html_src_clean.md
118
+ simplibs-extractor html django-clean my_project # Django templates, read as templates -> my_project/html_django_clean.md
119
+ simplibs-extractor html jinja-structure my_project # the skeleton of Jinja templates: extends, include, macros, blocks
120
+ simplibs-extractor html outline my_project # landmarks, headings and ids — the smallest overview of a page
121
+ simplibs-extractor html django-clean,django-structure my_project # two profiles -> two files, one run
122
+ simplibs-extractor html data-all my_project --dry-run # plan and report, write nothing
123
+ simplibs-extractor --list-profiles html # the thirteen profiles
124
+ ```
125
+
126
+ Which one? For a **plain site**: `data-all` gives the pages as they are, `code-clean` takes the comments away and cleans the code inside, `src-clean` does the same for the project's own pages only, `code-no-imports` takes also the imports away, and `outline` keeps only
127
+ the map. For a **Django** project use the `django-` profiles, for **Jinja** (or Nunjucks) the `jinja-` ones: `-clean`, `-no-imports`, `-outline`, and `-structure` for the skeleton of the templates.
128
+
129
+ ### Level 2: The steps as functions
130
+
131
+ ```python
132
+ from simplibs.extractor_html import (
133
+ strip_html_comments, cleanup_html_whitespace, compact_html, html_outline,
134
+ strip_template_comments, remove_template_imports, template_outline,
135
+ )
136
+
137
+ strip_html_comments("<p>a</p> <!-- n -->\n<p>b</p>\n") # -> '<p>a</p>\n<p>b</p>\n'
138
+ strip_html_comments("<!--[if IE]><p>ie</p><![endif]-->\n<p>a</p>\n", keep_conditional=False) # -> '<p>a</p>\n'
139
+ cleanup_html_whitespace("<div> \n\n\n<p>a</p> \n</div>\n") # -> '<div>\n\n<p>a</p>\n</div>\n'
140
+ compact_html("<ul>\n\n <li>a</li>\n\n</ul>\n") # -> '<ul>\n <li>a</li>\n</ul>\n'
141
+ html_outline('<ul id="menu"><li id="a">x<li id="b">y</ul>\n') # -> 'ul#menu\n li#a\n li#b\n'
142
+
143
+ strip_template_comments("{# note #}\n<p>a</p>\n", engine="django") # -> '<p>a</p>\n'
144
+ remove_template_imports("{% load static %}\n<p>a</p>\n", engine="django") # -> '<p>a</p>\n'
145
+ template_outline("{% extends 'b.html' %}{% block a %}{% endblock %}", engine="jinja") # -> "{% extends 'b.html' %}\n{% block a %}\n"
146
+ ```
147
+
148
+ ### Level 3: The code inside a page, actions and ready-made pipelines
149
+
150
+ ```python
151
+ from simplibs.extractor_html import apply_to_html_blocks
152
+ from simplibs.extractor_html.actions import CleanupHtmlWhitespace, StripHtmlComments
153
+ from simplibs.extractor_html.presets import html_clean_steps
154
+
155
+ apply_to_html_blocks("<style>a{}</style><script>b</script>", style=str.upper) # -> '<style>A{}</style><script>b</script>' any `str -> str` is a step
156
+
157
+ steps = StripHtmlComments() >> CleanupHtmlWhitespace()
158
+ steps("<!-- n -->\n\n\n<p>a</p> \n") # -> '<p>a</p>\n'
159
+
160
+ html_clean_steps("django")("{# n #}\n<!-- c -->\n<p>{{ a }}</p>\n\n\n") # -> '<p>{{ a }}</p>\n'
161
+ ```
162
+
163
+ ### Level 4: Your own profile from the parts
164
+
165
+ File rules combine with `&`, `|` and `~`; the steps are presets; a registered profile is a name for both.
166
+
167
+ ```python
168
+ from simplibs.extractor import Profile, by_suffix, extract, register_profile
169
+ from simplibs.extractor_html.constants import HTML_PLAIN_SUFFIXES
170
+ from simplibs.extractor_html.file_rules import HTML_PLAIN_BASE, OUTPUT_DIRS
171
+ from simplibs.extractor_html.presets import html_clean_steps
172
+
173
+ register_profile(Profile(
174
+ system="html", name="own-django",
175
+ description="Django templates, generated pages left out, comments out",
176
+ include=HTML_PLAIN_BASE,
177
+ exclude=OUTPUT_DIRS,
178
+ steps=by_suffix(html_clean_steps("django"), HTML_PLAIN_SUFFIXES),
179
+ output_name="html_own_django.md",
180
+ ))
181
+
182
+ extract(source="my_project", profile="html/own-django")
183
+ ```
184
+
185
+ A changed copy of a profile of this library is one `dataclasses.replace` away:
186
+
187
+ ```python
188
+ from dataclasses import replace
189
+ from simplibs.extractor_html.profiles import DJANGO_CLEAN
190
+
191
+ mine = replace(DJANGO_CLEAN, name="mine", output_name="mine.md")
192
+ ```
193
+
194
+ ---
195
+
196
+ ## 🛠️ Architecture & Package Structure
197
+
198
+ ```
199
+ src/simplibs/extractor_html/
200
+ ├── constants/ ◄── Suffixes, folder names, licence marks, tables of names, the patterns of the two scanners
201
+ ├── annotations/ ◄── TemplateEngine: "django" or "jinja"
202
+ ├── file_rules/ ◄── Rules on the path inside the source (domain folder)
203
+ │ ├── atomic/ ◄── DOT_NAME, VCS_DIRS, DEPENDENCY_DIRS, OUTPUT_DIRS, WRAPPED_HTML
204
+ │ └── html/ ◄── HTML_FILES, HTML_BASE, HTML_PLAIN_BASE, HTML_STRICT_EXCLUDE
205
+ ├── logic/ ◄── The steps for pages: comments, whitespace, the code inside, the outline
206
+ │ ├── templates/ ◄── The steps for Django and Jinja templates: comments, imports, the skeleton
207
+ │ └── _helpers/ ◄── Private: the two scanners (scan_html, scan_templates) and the small parts they are made of
208
+ ├── actions/ ◄── The steps as Action classes (domain folder)
209
+ ├── presets/ ◄── Ready-made pipelines, functions of the engine (domain folder)
210
+ ├── profiles/ ◄── The thirteen Profile objects and HTML_PROFILES (domain folder)
211
+ ├── plugin/ ◄── register_all: the target of the entry point
212
+ └── py.typed
213
+ ```
214
+
215
+ The folder `_helpers/` is private: it holds the scanners and the parts they are made of, and nothing in it is a public name.
216
+
217
+ The package root exports **the steps**, `TemplateEngine` and `register_all`. The four domain folders have their own `__all__` and are imported through their domain — a function and an action are different kinds of thing and should stay visibly different at the import line:
218
+
219
+ ```python
220
+ from simplibs.extractor_html import strip_html_comments, html_outline, TemplateEngine, register_all # the steps, the type, the entry point
221
+ from simplibs.extractor_html.actions import StripHtmlComments # the steps as actions
222
+ from simplibs.extractor_html.file_rules import HTML_BASE, HTML_STRICT_EXCLUDE # the rules
223
+ from simplibs.extractor_html.presets import html_clean_steps # ready-made pipelines
224
+ from simplibs.extractor_html.profiles import DJANGO_CLEAN # the profiles as objects
225
+ ```
226
+
227
+ The fixed values are imported from `simplibs.extractor_html.constants`. The ranges the steps find are `simplibs.text.Span`; the type is taken from `simplibs-text`, not defined here. The steps themselves know nothing of the JavaScript and CSS add-ons: only the presets use them.
228
+
229
+ ---
230
+
231
+ ## 🔧 `logic/` — The steps that read pages
232
+
233
+ Plain functions: a page as a text in, a text out (one of them gives the positions of the comments). All take their options as keyword-only parameters, and `engine=None` for a page that is only HTML. A page that looks damaged comes back unchanged, with a warning.
234
+
235
+ | Function | Description / Parameters |
236
+ |---------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
237
+ | `html_comment_spans` | Finds the HTML comments; returns a `Span` for each, from the blanks in front to the end (`text`, keyword-only: `engine=None`, `keep_conditional=True`, `keep_license=False`). |
238
+ | `strip_html_comments` | Removes the HTML comments; a line that held only a comment disappears (`text`, keyword-only: `engine=None`, `keep_conditional=True`, `keep_license=False`). |
239
+ | `cleanup_html_whitespace` | Trims line ends, reduces blank runs to one; spares `pre`, `textarea`, `script`, `style` and verbatim blocks (`text`, keyword-only: `engine=None`). |
240
+ | `compact_html` | Drops every blank line; spares the same places (`text`, keyword-only: `engine=None`). |
241
+ | `apply_to_html_blocks` | Runs the steps you give on the code inside `script` and `style` (`text`, keyword-only: `script=None`, `style=None`, `engine=None`). |
242
+ | `html_outline` | Writes the landmarks, the headings and every element with an `id`, indented by nesting (`text`, keyword-only: `engine=None`, `max_depth=None`). |
243
+
244
+ ➡️ [README_EXTRACTOR_HTML_LOGIC](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/logic/README_EXTRACTOR_HTML_LOGIC.md)
245
+
246
+ ---
247
+
248
+ ## 🧾 `logic/templates/` — The steps for Django and Jinja templates
249
+
250
+ Plain functions that read only `{{ }}`, `{% %}` and `{# #}`; the HTML around them is not read. The **`engine` is required** (`"django"` or `"jinja"`): a page cannot say which one it is written for.
251
+
252
+ | Function | Description / Parameters |
253
+ |---------------------------|--------------------------------------------------------------------------------------------------------------------------------------------------|
254
+ | `template_comment_spans` | Finds `{# ... #}` and `{% comment %}`; returns a `Span` for each (`text`, keyword-only: `engine`). |
255
+ | `strip_template_comments` | Removes `{# ... #}` and `{% comment %} ... {% endcomment %}` (`text`, keyword-only: `engine`). |
256
+ | `remove_template_imports` | Removes `{% load %}` (Django), `{% import %}` and `{% from %}` (Jinja); `extends` and `include` stay (`text`, keyword-only: `engine`). |
257
+ | `template_outline` | Writes the skeleton: `extends`, `include`, the blocks, and in Jinja the macros (`text`, keyword-only: `engine`, `max_depth=None`). |
258
+
259
+ ➡️ [README_EXTRACTOR_HTML_TEMPLATES](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/logic/README_EXTRACTOR_HTML_TEMPLATES.md)
260
+
261
+ ---
262
+
263
+ ## 🏷️ `annotations/` — Types for the signatures
264
+
265
+ | Type | Description |
266
+ |------------------|----------------------------------------------------------------------------------------------|
267
+ | `TemplateEngine` | `Literal["django", "jinja"]` — the template language of a page (Nunjucks counts as Jinja). |
268
+
269
+ ➡️ [README_EXTRACTOR_HTML_ANNOTATIONS](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_ANNOTATIONS.md)
270
+
271
+ ---
272
+
273
+ ## ⚙️ `actions/` — Pipeline steps
274
+
275
+ Every step except the two `*_comment_spans` is also an `Action` of [`simplibs-actions`](https://pypi.org/project/simplibs-actions/): configured once, called with the **text** as its main input, chainable with `>>`. The options of the function are the options of the action:
276
+ `StripHtmlComments(engine="django")`. Actions are a separate domain, imported through `simplibs.extractor_html.actions`.
277
+
278
+ | Action | Over | Description |
279
+ |-------------------------|---------------------------|------------------------------------------------------------------|
280
+ | `StripHtmlComments` | `strip_html_comments` | Takes the HTML comments out of the page flowing in. |
281
+ | `StripTemplateComments` | `strip_template_comments` | Takes the template comments out (`engine` required). |
282
+ | `RemoveTemplateImports` | `remove_template_imports` | Takes `{% load %}`, `{% import %}` and `{% from %}` out (`engine` required). |
283
+ | `CleanupHtmlWhitespace` | `cleanup_html_whitespace` | Tidies the whitespace, sparing `pre` and the like. |
284
+ | `CompactHtml` | `compact_html` | Drops every blank line, sparing `pre` and the like. |
285
+ | `ApplyToHtmlBlocks` | `apply_to_html_blocks` | Runs the given steps on the code inside `script` and `style`. |
286
+ | `HtmlOutline` | `html_outline` | Turns the page into the list of its landmarks, headings and ids. |
287
+ | `TemplateOutline` | `template_outline` | Turns the template into the list of its `extends`, `include` and blocks (`engine` required). |
288
+
289
+ ➡️ [README_EXTRACTOR_HTML_ACTIONS](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_ACTIONS.md)
290
+
291
+ ---
292
+
293
+ ## 🧩 `presets/` — Ready-made pipelines
294
+
295
+ The chains of actions that the profiles use. Each is a **function of the engine** (`None` for a page that is only HTML), because the chain is the same for every engine and only the option of its actions differs. The code inside a page is cleaned by `JS_CLEAN` and
296
+ `CSS_PLAIN_CLEAN` of the other add-ons.
297
+
298
+ | Preset | Description / Parameters |
299
+ |----------------------------|------------------------------------------------------------------------------------------------------------------------------------------------|
300
+ | `html_clean_steps` | Comments out, the code inside cleaned, whitespace tidied; imports stay (`engine`). |
301
+ | `html_no_imports_steps` | The same, without imports and without blank lines (`engine`). |
302
+ | `html_outline_steps` | The landmarks, headings and ids of a page (`engine`). |
303
+ | `template_structure_steps` | The `extends`, `include` and blocks of a template (`engine`, never `None`). |
304
+
305
+ ➡️ [README_EXTRACTOR_HTML_PRESETS](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_PRESETS.md)
306
+
307
+ ---
308
+
309
+ ## 📋 `profiles/` — The thirteen profiles
310
+
311
+ Registered in the system `html`; also importable as `Profile` objects. Three families: **pages** (every `.html` is read without an engine; a Jinja suffix as Jinja), **Django** and **Jinja** (every file read with that engine, strict).
312
+
313
+ | Profile | Output | Description |
314
+ |--------------------------|-----------------------------|------------------------------------------------------------------------------------------------------|
315
+ | `html/code-clean` | `html_code_clean.md` | Pages without comments and extra blank lines, the code inside cleaned too (imports stay). |
316
+ | `html/code-no-imports` | `html_code_no_imports.md` | Pure content: no comments, imports (also inside script and style) or blank lines. |
317
+ | `html/data-all` | `html_data_all.md` | Every relevant page, as it is. |
318
+ | `html/outline` | `html_outline.md` | Overview of the pages: landmarks, headings and every element with an id. |
319
+ | `html/src-clean` | `html_src_clean.md` | Like `code-clean`, without packages of other people and generated pages. |
320
+ | `html/django-clean` | `html_django_clean.md` | Django templates without HTML and template comments and extra blank lines (imports stay). |
321
+ | `html/django-no-imports` | `html_django_no_imports.md` | Django templates reduced to their content: no comments, `{% load %}`, imports in script and style, or blank lines. |
322
+ | `html/django-outline` | `html_django_outline.md` | Overview of Django templates as pages: landmarks, headings and every element with an id. |
323
+ | `html/django-structure` | `html_django_structure.md` | Skeleton of Django templates: extends, include and blocks. |
324
+ | `html/jinja-clean` | `html_jinja_clean.md` | Jinja templates without HTML and template comments and extra blank lines (imports stay). |
325
+ | `html/jinja-no-imports` | `html_jinja_no_imports.md` | Jinja templates reduced to their content: no comments, `{% import %}` and `{% from %}`, imports in script and style, or blank lines. |
326
+ | `html/jinja-outline` | `html_jinja_outline.md` | Overview of Jinja templates as pages: landmarks, headings and every element with an id. |
327
+ | `html/jinja-structure` | `html_jinja_structure.md` | Skeleton of Jinja templates: extends, include, macros and blocks. |
328
+
329
+ `HTML_PROFILES` is the tuple of all thirteen, in the order the listings show them.
330
+
331
+ ➡️ [README_EXTRACTOR_HTML_PROFILES](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_PROFILES.md)
332
+
333
+ ---
334
+
335
+ ## 📐 `file_rules/` — Which files are worth reading
336
+
337
+ Rules on the path **inside** the source folder: `Rule` objects of [`simplibs-rules`](https://pypi.org/project/simplibs-rules/), composable with `&`, `|` and `~`.
338
+
339
+ | Rule | Description |
340
+ |-----------------------|---------------------------------------------------------------------------------------------------------------------|
341
+ | `HTML_BASE` | The default choice: every page and template that is not hidden — Jinja suffixes and `.html.j2` included. |
342
+ | `HTML_PLAIN_BASE` | The pages with a `.html`, `.htm` or `.xhtml` suffix, not hidden: the files a Django project keeps its templates in. |
343
+ | `HTML_FILES` | A file with a page or template suffix, or a wrapped page (`index.html.j2`). |
344
+ | `HTML_STRICT_EXCLUDE` | What is not the project's own source: packages of other people, generated output, version control. |
345
+ | `DOT_NAME` | The file name starts with a dot. |
346
+ | `VCS_DIRS` | A folder above the file is a version-control folder (`.git`, `.svn`, `.hg`, `.bzr`). |
347
+ | `DEPENDENCY_DIRS` | A folder above the file holds pages of other people (`node_modules`, `bower_components`, `vendor`). |
348
+ | `OUTPUT_DIRS` | A folder above the file holds generated pages (`dist`, `_build`, `_site`, `staticfiles`, `htmlcov`, …). |
349
+ | `WRAPPED_HTML` | The file is a page behind a wrapper suffix: `index.html.j2`, not `nginx.conf.j2`. |
350
+
351
+ ➡️ [README_EXTRACTOR_HTML_FILE_RULES](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_FILE_RULES.md)
352
+
353
+ ---
354
+
355
+ ## 🔖 `constants/` — Fixed values
356
+
357
+ Thirty fixed values the rules, the scanners, the steps and the profiles are built from.
358
+
359
+ | Constant | Description |
360
+ |----------------------------------|--------------------------------------------------------------------------------------|
361
+ | `HTML_PLAIN_SUFFIXES` | `(".html", ".htm", ".xhtml")` — pages, and Django templates with them. |
362
+ | `HTML_TEMPLATE_SUFFIXES` | `(".jinja", ".jinja2", ".njk")` — templates of the Jinja family. |
363
+ | `HTML_WRAPPED_SUFFIXES` | `(".j2",)` — the wrapper around the real suffix. |
364
+ | `HTML_SUFFIXES` | The three above joined: every suffix the library may read. |
365
+ | `HTML_WRAPPED_STEM_ENDING` | `".html"` — what the stem of a wrapped page ends with. |
366
+ | `HTML_EXTRA_LANGUAGE_BY_SUFFIX` | The code-fence language of the suffixes the extractor does not know. |
367
+ | `HTML_DEPENDENCY_DIR_NAMES` | Folders of pages written by other people. |
368
+ | `HTML_OUTPUT_DIR_NAMES` | Folders of generated pages and reports. |
369
+ | `HTML_LICENSE_START` | `"<!--!"` — how a comment that has to survive minification begins. |
370
+ | `HTML_LICENSE_TAGS` | `("@license", "@preserve")` — words that mark a comment as one to keep. |
371
+ | `HTML_OUTLINE_ELEMENTS` | The landmarks and other big parts that always appear in the outline. |
372
+ | `HTML_HEADING_ELEMENTS` | The six headings. |
373
+ | `HTML_TEXT_ELEMENTS` | The title and the headings: listed with their text. |
374
+ | `HTML_OUTLINE_TEXT_LIMIT` | `80` — the longest heading text in the outline. |
375
+ | `HTML_VOID_ELEMENTS` | The elements that have no content and no end tag. |
376
+ | `HTML_IMPLIED_END` | Which start tags close which open elements (`<li>a<li>b`). |
377
+ | `HTML_BLOCK_LANGUAGE_BY_TYPE` | Which `type` values make a `script` or `style` code, and of what language. |
378
+ | `HTML_TEMPLATE_BLOCKS` | The template tags that swallow everything up to an end tag. |
379
+ | `HTML_TEMPLATE_IMPORT_TAGS` | The template tags that bring in names from elsewhere. |
380
+ | `HTML_TEMPLATE_OUTLINE_TAGS` | The template tags of the skeleton: open, close, standalone. |
381
+ | `HTML_TOKEN_PATTERN` | Where markup begins in a page. |
382
+ | `HTML_COMMENT_END_PATTERN` | `-->` and `--!>`. |
383
+ | `HTML_CONDITIONAL_PATTERN` | The beginning of an Internet Explorer conditional comment. |
384
+ | `HTML_TAG_NAME_PATTERN` | The name of a tag. |
385
+ | `HTML_ID_ATTRIBUTE_PATTERN` | The `id` attribute of a tag. |
386
+ | `HTML_TYPE_ATTRIBUTE_PATTERN` | The `type` attribute of a tag. |
387
+ | `HTML_ANY_TAG_PATTERN` | Anything that looks like a tag (to take the markup out of a heading). |
388
+ | `HTML_RAW_TEXT_END_PATTERNS` | The end tag of each element with raw text: `script`, `style`, `textarea`, `title`. |
389
+ | `HTML_TEMPLATE_TOKEN_PATTERN` | Where a template construct begins: `{#`, `{%`, `{{`. |
390
+ | `HTML_TEMPLATE_TAG_NAME_PATTERN` | The name of a template tag. |
391
+
392
+ ➡️ [README_EXTRACTOR_HTML_CONSTANTS](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_CONSTANTS.md)
393
+
394
+ ---
395
+
396
+ ## 🔌 `plugin/` — The meeting point with the extractor
397
+
398
+ | Function | Description / Parameters |
399
+ |----------------|--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
400
+ | `register_all` | Registers the languages of `.htm`, `.xhtml` and the Jinja suffixes and the thirteen profiles in the extractor's registries and returns the profile keys; the target of the entry point `simplibs.extractor.plugins` (keyword-only: `replace_existing=True`). |
401
+
402
+ The entry point lives in this library's `pyproject.toml`; the extractor's `load_plugins()` finds it, so nothing is imported by name. From Python, call `load_plugins()` of the extractor once before a profile is looked up.
403
+
404
+ ➡️ [README_EXTRACTOR_HTML_PLUGIN](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_PLUGIN.md)
405
+
406
+ ---
407
+
408
+ ## ⚠️ Exceptions
409
+
410
+ **A page is never the cause of an error**: a file that looks damaged is a warning, not an exception. The library raises **one card of its own**, as a structured [`simplibs.exception`](https://pypi.org/project/simplibs-exception/) error; a caller that wants "any error of the
411
+ family" catches `SimpleError`.
412
+
413
+ | Exception | Raised by | Raised when |
414
+ |--------------|------------------------|------------------------------------------------------------------------------------|
415
+ | `ParamError` | `apply_to_html_blocks` | A step for a `script` or `style` block returns something that is not a `str`. |
416
+
417
+ What is an exception and what is not:
418
+
419
+ | Situation | How it is reported |
420
+ |---------------------------------------------------------------------------------------------|---------------------------------------------------------------------------------|
421
+ | A step called directly on a page with a comment, a tag, a `script` or a template block never closed | a `UserWarning`; the text comes back unchanged (the `*_comment_spans`: `[]`) |
422
+ | `template_outline` on a template whose blocks do not pair up | a `UserWarning`; the text comes back unchanged |
423
+ | The same inside an **extraction** | **not raised**: the file stays in the output, marked `partial`, the warning is in the report |
424
+ | A construct that is not closed (`{{` without `}}`) | **nothing**: it is only text |
425
+ | A wrong **type or value** of an argument (`text=5`, `max_depth=0`, `engine="jinja2"`) | a `ValidationError` from `simplibs-validate` |
426
+ | A step of your own that raises inside `apply_to_html_blocks` | its exception, as it was |
427
+ | A profile key that is taken, with `register_all(replace_existing=False)` | the card of the extractor's registry (`EXTRACTOR_PROFILE_EXISTS`) |
428
+
429
+ Each helper README ends with the errors of its own package.
430
+
431
+ ---
432
+
433
+ ## 📚 Documentation
434
+
435
+ The detailed references — every function, rule and profile with its parameters, return value, raised errors, an example and a look under the hood:
436
+
437
+ | Reference | What it describes |
438
+ |-----------|-------------------|
439
+ | [LOGIC](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/logic/README_EXTRACTOR_HTML_LOGIC.md) | the six steps for pages: comments, whitespace, the code inside, the outline — and the scanner under them |
440
+ | [TEMPLATES](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/logic/README_EXTRACTOR_HTML_TEMPLATES.md) | the four steps for Django and Jinja templates — and the scanner of the curly braces |
441
+ | [ANNOTATIONS](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_ANNOTATIONS.md) | `TemplateEngine` |
442
+ | [ACTIONS](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_ACTIONS.md) | the steps as pipeline actions |
443
+ | [PRESETS](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_PRESETS.md) | the four ready-made pipelines, functions of the engine |
444
+ | [PROFILES](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_PROFILES.md) | the thirteen profiles in three families, one page through each, a profile of your own |
445
+ | [FILE_RULES](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_FILE_RULES.md) | which files are worth reading: the atomic pieces and the rules of a page project |
446
+ | [CONSTANTS](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_CONSTANTS.md) | the fixed values: suffixes, folder names, tables of names, the patterns of the scanners |
447
+ | [PLUGIN](https://github.com/simplibs/simplibs-extractor-html/blob/main/docs/README_EXTRACTOR_HTML_PLUGIN.md) | `register_all` and how the extractor finds this add-on |
448
+
449
+ ---
450
+
451
+ ## 🔗 Related libraries
452
+
453
+ * **[`simplibs-extractor`](https://pypi.org/project/simplibs-extractor/)** — the extractor this library is an add-on of: the six phases, the profiles and the command.
454
+ * **[`simplibs-extractor-javascript`](https://pypi.org/project/simplibs-extractor-javascript/)** and **[`simplibs-extractor-css`](https://pypi.org/project/simplibs-extractor-css/)** — the add-ons whose steps clean the code inside `<script>` and `<style>`; `JS_CLEAN`, `JS_NO_IMPORTS`, `CSS_PLAIN_CLEAN` and `CSS_PLAIN_NO_IMPORTS` are used by the presets.
455
+ * **[`simplibs-extractor-python`](https://pypi.org/project/simplibs-extractor-python/)** — the sister add-on for Python projects (a Django project often has both).
456
+ * **[`simplibs-text`](https://pypi.org/project/simplibs-text/)** — `remove_spans` cuts the ranges the steps find, `Span` is their type; `CLEANUP_WHITESPACE` and `COMPACT` are the whitespace presets the code inside a page is closed with.
457
+ * **[`simplibs-actions`](https://pypi.org/project/simplibs-actions/)** — the `Action` the steps are wrapped in.
458
+ * **[`simplibs-path`](https://pypi.org/project/simplibs-path/)** — the path rules (`HasSuffix`, `NameIs`, `StemIs`, `AnyParentNameIs`) and `IGNORE_VCS`.
459
+ * **[`simplibs-rules`](https://pypi.org/project/simplibs-rules/)** — the `Rule` object and its building blocks (`IsIn`, `StartsWith`, `EndsWith`).
460
+ * **[`simplibs-validate`](https://pypi.org/project/simplibs-validate/)** and **[`simplibs-types`](https://pypi.org/project/simplibs-types/)** — the check of every signature, and the `int_positive` type of the outline depth.
461
+ * **[`simplibs-exception`](https://pypi.org/project/simplibs-exception/)** — the structured error cards; `ParamError` of the step for blocks comes from it.
462
+
463
+ ---
464
+
465
+ ## ☯️ About simplibs
466
+
467
+ All libraries in the **simplibs** (Simple Libraries) ecosystem share a common
468
+ engineering philosophy:
469
+
470
+ * **Dyslexia-friendly:**
471
+ We actively minimize cognitive load. Code is atomized into small, self-contained units,
472
+ files are named directly after the logical task they perform, and explanations describe
473
+ *why* something is designed, not just *what* it is.
474
+ * **Programmer's Zen:**
475
+ Nothing should be missing, and nothing should be superfluous. We value clean execution
476
+ paths and robust, understandable code architectures over rushed, messy feature sets.
477
+ * **Defensive Style:**
478
+ We actively anticipate edge cases and failure modes so that only safe operational paths
479
+ remain. Our code is built to degrade gracefully rather than crash unexpectedly.
480
+ * **Minimalism:**
481
+ Find the most direct path to the goal in as few operational steps as possible without
482
+ taking shortcuts on safety, readability, or completeness.
483
+ * **Code as Craft:**
484
+ Code should be pleasant to look at, readable at a glance, and evoke structural harmony.
485
+ We treat software engineering as a precision trade.
486
+
487
+ ---
488
+
489
+ ### 🤝 Contributing & Community
490
+
491
+ This is an **open-source project** built with love and care. We strongly believe in
492
+ community collaboration and welcome any feedback, bug reports, or feature ideas!
493
+
494
+ * **Want to contribute?** Feel free to open an Issue or submit a Pull Request.
495
+ * **Want to get in touch?** If you'd like to discuss the project further, collaborate,
496
+ or just say hello, feel free to open a GitHub Issue or start a Discussion.
497
+
498
+ ---
499
+
500
+ ### 📝 License
501
+
502
+ This library is released under the **MIT License**. Build great things!
503
+
504
+ ---