Metadata-Version: 2.4
Name: pykelet
Version: 2.0.6
Summary: JSON-safe metadata blocks for Python scripts and HTML, parsed by humans and machines alike.
Author: Andrew Kingdom
License: BSD-3-Clause
Project-URL: Homepage, https://github.com/akingdom/pykelet
Project-URL: Repository, https://github.com/akingdom/pykelet
Project-URL: Issues, https://github.com/akingdom/pykelet/issues
Keywords: pykelet,metadata,yaml-frontmatter,html-comment,json,codegen,pipeline,micro-app
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Developers
Classifier: Topic :: Software Development :: Code Generators
Classifier: Topic :: Text Processing :: Markup :: HTML
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.9
Classifier: Programming Language :: Python :: 3.10
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: License :: OSI Approved :: BSD License
Classifier: Operating System :: OS Independent
Requires-Python: >=3.9
Description-Content-Type: text/markdown
License-File: LICENSE.md
Provides-Extra: server
Requires-Dist: fastapi>=0.115.0; extra == "server"
Requires-Dist: uvicorn[standard]>=0.30.0; extra == "server"
Provides-Extra: test
Requires-Dist: pytest>=7.0; extra == "test"
Requires-Dist: pytest-cov>=4.0; extra == "test"
Provides-Extra: dev
Requires-Dist: black; extra == "dev"
Requires-Dist: ruff; extra == "dev"
Requires-Dist: build; extra == "dev"
Requires-Dist: twine; extra == "dev"
Dynamic: license-file

# pykelet

**JSON-safe metadata blocks for Python scripts and HTML — parsed by humans
and machines alike.**

Pykelet gives you one canonical place per file to declare what it is, what it
expects, and what it produces.

- **HTML files** — a `<!--PYKELET ... -->` comment block placed right after
  `<!DOCTYPE html>`. Read by the browser (via `pykelet.js`) *and* by Python.
- **Python scripts** — a module-level `PYKELET = {...}` dict, read via AST
  (the script's main body is never executed during discovery).

---

## Pulling data from an HTML comment

A Pykelet front matter block is essentially the same as that of a YAML
Jekyll/Hugo front matter block except that we encase it in an HTML comment
`<!-- ... -->` rather than YAML `--- ... ---`.

The aim is to be able to pull information from a source-code style comment.
This is not intended for SEO purposes (comments are generally no longer
indexed by search bots), so such data should still be put in the header if
required.

### Example

    <!--PYKELET
      FILENAME:    example.html
      DESCRIPTION: This is a demonstration HTML file showing metadata extraction.
      AUTHOR:      Andrew Kingdom
      LICENSE:     BSD 3-Clause
      -->

*into this:*

> **FILENAME:** example.html
> **DESCRIPTION:** This is a demonstration HTML file showing metadata extraction.
> **AUTHOR:** Andrew Kingdom
> **LICENSE:** BSD 3-Clause

## Browser usage

Include `pykelet.js` **as early as possible** in `<head>`:

```html
<!DOCTYPE html>
<!--PYKELET
TITLE: My Page
AUTHOR: Jane Doe
-->
<html>
<head>
    <script src="js/pykelet.js"></script>
</head>
<body>
    <h1 id="TITLE"></h1>
</body>
</html>
```

`pykelet.js` populates `document.pykelet.comment` and auto-fills any element
whose `id` matches a key. Disable auto-fill by defining
`const disabled_fillDocumentFromPykeletComments = true;` *before* the script
loads.

## Python usage

### Python script with inline PYKELET

```python
from pykelet import true, false, null

PYKELET = {
    "name": "my_op",
    "description": "Adds two numbers.",
    "version": "1.0.0",
    "timeout": 30,
    "active": true,
    "parent": null,
    "input_schema": {"type": "object",
                     "properties": {"a": {"type": "number"},
                                    "b": {"type": "number"}}},
    "output_schema": {"type": "object",
                      "properties": {"sum": {"type": "number"}}},
}
```

### Parse HTML or Python

```python
from pykelet import parse_file

meta = parse_file("example.html")           # → {"FILENAME": ..., ...}
meta = parse_file("my_script.py")           # → {"name": "my_op", ...}
```

### Fill HTML server-side

```python
from pykelet import fill_html

html = open("example.html").read()
filled = fill_html(html, {}, parse=True)   # elements with matching ids filled
```

### Bundled JS

The JS ships inside the package. Extract it with:

```python
from pykelet import copy_js
copy_js("static/")                         # → static/pykelet.js
```

Or from the shell:

```bash
pykelet copy-js static/
pykelet print-js > static/pykelet.js
```

## CLI

```bash
pykelet inspect example.html
pykelet inspect my_script.py
pykelet fill example.html out.html
pykelet copy-js static/
```

## Install

```bash
pip install pykelet
```

## Roadmap

- Pykelet comment blocks are part of a larger yet-to-be-released system.
- **YAML**: For certain file formats (e.g. .llux, etc.) YAML might be used.

## License

BSD 3-Clause. See `LICENSE.md`.
