florajs 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.
- florajs-0.1.0/.gitignore +11 -0
- florajs-0.1.0/PKG-INFO +130 -0
- florajs-0.1.0/README.md +103 -0
- florajs-0.1.0/pyproject.toml +42 -0
- florajs-0.1.0/src/florajs/__init__.py +39 -0
- florajs-0.1.0/src/florajs/_diagram.py +393 -0
- florajs-0.1.0/src/florajs/_engine.py +52 -0
- florajs-0.1.0/src/florajs/_errors.py +41 -0
- florajs-0.1.0/src/florajs/_notebook.py +72 -0
- florajs-0.1.0/src/florajs/_vendor/README.md +5 -0
- florajs-0.1.0/src/florajs/_vendor/flora.iife.js +26 -0
- florajs-0.1.0/tests/test_builder.py +166 -0
- florajs-0.1.0/tests/test_notebook.py +40 -0
- florajs-0.1.0/tests/test_render.py +107 -0
florajs-0.1.0/.gitignore
ADDED
florajs-0.1.0/PKG-INFO
ADDED
|
@@ -0,0 +1,130 @@
|
|
|
1
|
+
Metadata-Version: 2.4
|
|
2
|
+
Name: florajs
|
|
3
|
+
Version: 0.1.0
|
|
4
|
+
Summary: Beautiful, interactive diagrams from Mermaid-compatible syntax — Python interface to the Flora JS library
|
|
5
|
+
Project-URL: Homepage, https://github.com/topspinj/florajs
|
|
6
|
+
Project-URL: Repository, https://github.com/topspinj/florajs
|
|
7
|
+
Project-URL: Issues, https://github.com/topspinj/florajs/issues
|
|
8
|
+
Author: topspinj
|
|
9
|
+
License-Expression: MIT
|
|
10
|
+
Keywords: diagrams,flowchart,jupyter,lineage,mermaid,svg,visualization
|
|
11
|
+
Classifier: Development Status :: 4 - Beta
|
|
12
|
+
Classifier: Framework :: Jupyter
|
|
13
|
+
Classifier: Intended Audience :: Developers
|
|
14
|
+
Classifier: Intended Audience :: Science/Research
|
|
15
|
+
Classifier: Programming Language :: Python :: 3
|
|
16
|
+
Classifier: Programming Language :: Python :: 3.10
|
|
17
|
+
Classifier: Programming Language :: Python :: 3.11
|
|
18
|
+
Classifier: Programming Language :: Python :: 3.12
|
|
19
|
+
Classifier: Programming Language :: Python :: 3.13
|
|
20
|
+
Classifier: Topic :: Multimedia :: Graphics
|
|
21
|
+
Classifier: Topic :: Scientific/Engineering :: Visualization
|
|
22
|
+
Requires-Python: >=3.10
|
|
23
|
+
Requires-Dist: mini-racer>=0.12
|
|
24
|
+
Provides-Extra: dev
|
|
25
|
+
Requires-Dist: pytest>=8; extra == 'dev'
|
|
26
|
+
Description-Content-Type: text/markdown
|
|
27
|
+
|
|
28
|
+
# florajs
|
|
29
|
+
|
|
30
|
+
Beautiful, interactive diagrams from Mermaid-compatible syntax — the Python
|
|
31
|
+
interface to [Flora](https://github.com/topspinj/florajs).
|
|
32
|
+
|
|
33
|
+
- **Jupyter-native**: diagrams display interactively (zoom, pan, hover
|
|
34
|
+
highlighting, click links) right in the notebook.
|
|
35
|
+
- **Headless SVG export**: `to_svg()` runs the Flora renderer in an embedded
|
|
36
|
+
V8 engine — no browser, no Node.js.
|
|
37
|
+
- **Two ways in**: a programmatic builder, or raw Flora/Mermaid syntax.
|
|
38
|
+
|
|
39
|
+
```
|
|
40
|
+
pip install florajs
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
## Quick start
|
|
44
|
+
|
|
45
|
+
```python
|
|
46
|
+
from florajs import Flowchart
|
|
47
|
+
|
|
48
|
+
fc = Flowchart("LR", theme="tufte")
|
|
49
|
+
fc.node("raw", "Raw events", shape="cylinder")
|
|
50
|
+
fc.node("clean", "Cleaned", shape="stadium")
|
|
51
|
+
fc.edge("raw", "clean", "dbt run")
|
|
52
|
+
fc # displays interactively in Jupyter
|
|
53
|
+
```
|
|
54
|
+
|
|
55
|
+
Or from raw Flora/Mermaid syntax:
|
|
56
|
+
|
|
57
|
+
```python
|
|
58
|
+
from florajs import Diagram
|
|
59
|
+
|
|
60
|
+
d = Diagram("""
|
|
61
|
+
flowchart TD
|
|
62
|
+
a[Start] --> b{Decide}
|
|
63
|
+
b -->|yes| c([Done])
|
|
64
|
+
b -->|no| a
|
|
65
|
+
""", theme="sketch")
|
|
66
|
+
d.to_svg_file("decision.svg")
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
## Building diagrams
|
|
70
|
+
|
|
71
|
+
```python
|
|
72
|
+
fc = Flowchart("TD") # TB | TD | BT | LR | RL
|
|
73
|
+
|
|
74
|
+
fc.node("a", "Label", shape="diamond") # rect | rounded | circle | diamond
|
|
75
|
+
# stadium | cylinder | queue
|
|
76
|
+
fc.edge("a", "b", "maybe", # optional edge label
|
|
77
|
+
style="dotted", # solid | dotted | thick
|
|
78
|
+
arrow="bidirectional") # arrow | open | bidirectional
|
|
79
|
+
|
|
80
|
+
with fc.subgraph("Ingest"): # groups nest
|
|
81
|
+
fc.node("api", "API")
|
|
82
|
+
fc.node("queue", "Queue", shape="queue")
|
|
83
|
+
|
|
84
|
+
fc.link("api", "https://example.com/api", # click-through links
|
|
85
|
+
tooltip="API docs", target="_blank")
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
Every builder method chains: `fc.node("a").edge("a", "b")`.
|
|
89
|
+
|
|
90
|
+
## Rendering
|
|
91
|
+
|
|
92
|
+
| Method | Output |
|
|
93
|
+
| --- | --- |
|
|
94
|
+
| `to_svg()` | SVG string (headless, no browser needed) |
|
|
95
|
+
| `to_svg_file(path)` | SVG file |
|
|
96
|
+
| `to_html()` | standalone interactive HTML document |
|
|
97
|
+
| `to_html_file(path)` | standalone interactive HTML file |
|
|
98
|
+
| `_repr_html_` | automatic interactive display in Jupyter |
|
|
99
|
+
| `source` | the generated Flora syntax |
|
|
100
|
+
| `warnings` | parser diagnostics |
|
|
101
|
+
|
|
102
|
+
## Themes
|
|
103
|
+
|
|
104
|
+
Presets: `default`, `tufte`, `digital`, `sketch`. Or pass a dict of
|
|
105
|
+
[theme overrides](https://github.com/topspinj/florajs#theming):
|
|
106
|
+
|
|
107
|
+
```python
|
|
108
|
+
Diagram(src, theme={"background": "#0b1021", "fontSize": 13})
|
|
109
|
+
```
|
|
110
|
+
|
|
111
|
+
## Errors you can trust
|
|
112
|
+
|
|
113
|
+
Flora never renders silently wrong output. Lines that cannot be parsed are
|
|
114
|
+
skipped and reported as a `FloraSyntaxWarning`; pass `strict=True` to raise
|
|
115
|
+
`FloraParseError` instead:
|
|
116
|
+
|
|
117
|
+
```python
|
|
118
|
+
Diagram(src, strict=True).to_svg() # raises FloraParseError on any skipped line
|
|
119
|
+
```
|
|
120
|
+
|
|
121
|
+
## Development
|
|
122
|
+
|
|
123
|
+
The package embeds a JS bundle built from the repository root:
|
|
124
|
+
|
|
125
|
+
```
|
|
126
|
+
npm run build:python # builds and vendors flora.iife.js
|
|
127
|
+
cd python
|
|
128
|
+
pip install -e ".[dev]"
|
|
129
|
+
pytest
|
|
130
|
+
```
|
florajs-0.1.0/README.md
ADDED
|
@@ -0,0 +1,103 @@
|
|
|
1
|
+
# florajs
|
|
2
|
+
|
|
3
|
+
Beautiful, interactive diagrams from Mermaid-compatible syntax — the Python
|
|
4
|
+
interface to [Flora](https://github.com/topspinj/florajs).
|
|
5
|
+
|
|
6
|
+
- **Jupyter-native**: diagrams display interactively (zoom, pan, hover
|
|
7
|
+
highlighting, click links) right in the notebook.
|
|
8
|
+
- **Headless SVG export**: `to_svg()` runs the Flora renderer in an embedded
|
|
9
|
+
V8 engine — no browser, no Node.js.
|
|
10
|
+
- **Two ways in**: a programmatic builder, or raw Flora/Mermaid syntax.
|
|
11
|
+
|
|
12
|
+
```
|
|
13
|
+
pip install florajs
|
|
14
|
+
```
|
|
15
|
+
|
|
16
|
+
## Quick start
|
|
17
|
+
|
|
18
|
+
```python
|
|
19
|
+
from florajs import Flowchart
|
|
20
|
+
|
|
21
|
+
fc = Flowchart("LR", theme="tufte")
|
|
22
|
+
fc.node("raw", "Raw events", shape="cylinder")
|
|
23
|
+
fc.node("clean", "Cleaned", shape="stadium")
|
|
24
|
+
fc.edge("raw", "clean", "dbt run")
|
|
25
|
+
fc # displays interactively in Jupyter
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
Or from raw Flora/Mermaid syntax:
|
|
29
|
+
|
|
30
|
+
```python
|
|
31
|
+
from florajs import Diagram
|
|
32
|
+
|
|
33
|
+
d = Diagram("""
|
|
34
|
+
flowchart TD
|
|
35
|
+
a[Start] --> b{Decide}
|
|
36
|
+
b -->|yes| c([Done])
|
|
37
|
+
b -->|no| a
|
|
38
|
+
""", theme="sketch")
|
|
39
|
+
d.to_svg_file("decision.svg")
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
## Building diagrams
|
|
43
|
+
|
|
44
|
+
```python
|
|
45
|
+
fc = Flowchart("TD") # TB | TD | BT | LR | RL
|
|
46
|
+
|
|
47
|
+
fc.node("a", "Label", shape="diamond") # rect | rounded | circle | diamond
|
|
48
|
+
# stadium | cylinder | queue
|
|
49
|
+
fc.edge("a", "b", "maybe", # optional edge label
|
|
50
|
+
style="dotted", # solid | dotted | thick
|
|
51
|
+
arrow="bidirectional") # arrow | open | bidirectional
|
|
52
|
+
|
|
53
|
+
with fc.subgraph("Ingest"): # groups nest
|
|
54
|
+
fc.node("api", "API")
|
|
55
|
+
fc.node("queue", "Queue", shape="queue")
|
|
56
|
+
|
|
57
|
+
fc.link("api", "https://example.com/api", # click-through links
|
|
58
|
+
tooltip="API docs", target="_blank")
|
|
59
|
+
```
|
|
60
|
+
|
|
61
|
+
Every builder method chains: `fc.node("a").edge("a", "b")`.
|
|
62
|
+
|
|
63
|
+
## Rendering
|
|
64
|
+
|
|
65
|
+
| Method | Output |
|
|
66
|
+
| --- | --- |
|
|
67
|
+
| `to_svg()` | SVG string (headless, no browser needed) |
|
|
68
|
+
| `to_svg_file(path)` | SVG file |
|
|
69
|
+
| `to_html()` | standalone interactive HTML document |
|
|
70
|
+
| `to_html_file(path)` | standalone interactive HTML file |
|
|
71
|
+
| `_repr_html_` | automatic interactive display in Jupyter |
|
|
72
|
+
| `source` | the generated Flora syntax |
|
|
73
|
+
| `warnings` | parser diagnostics |
|
|
74
|
+
|
|
75
|
+
## Themes
|
|
76
|
+
|
|
77
|
+
Presets: `default`, `tufte`, `digital`, `sketch`. Or pass a dict of
|
|
78
|
+
[theme overrides](https://github.com/topspinj/florajs#theming):
|
|
79
|
+
|
|
80
|
+
```python
|
|
81
|
+
Diagram(src, theme={"background": "#0b1021", "fontSize": 13})
|
|
82
|
+
```
|
|
83
|
+
|
|
84
|
+
## Errors you can trust
|
|
85
|
+
|
|
86
|
+
Flora never renders silently wrong output. Lines that cannot be parsed are
|
|
87
|
+
skipped and reported as a `FloraSyntaxWarning`; pass `strict=True` to raise
|
|
88
|
+
`FloraParseError` instead:
|
|
89
|
+
|
|
90
|
+
```python
|
|
91
|
+
Diagram(src, strict=True).to_svg() # raises FloraParseError on any skipped line
|
|
92
|
+
```
|
|
93
|
+
|
|
94
|
+
## Development
|
|
95
|
+
|
|
96
|
+
The package embeds a JS bundle built from the repository root:
|
|
97
|
+
|
|
98
|
+
```
|
|
99
|
+
npm run build:python # builds and vendors flora.iife.js
|
|
100
|
+
cd python
|
|
101
|
+
pip install -e ".[dev]"
|
|
102
|
+
pytest
|
|
103
|
+
```
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
[build-system]
|
|
2
|
+
requires = ["hatchling"]
|
|
3
|
+
build-backend = "hatchling.build"
|
|
4
|
+
|
|
5
|
+
[project]
|
|
6
|
+
name = "florajs"
|
|
7
|
+
version = "0.1.0"
|
|
8
|
+
description = "Beautiful, interactive diagrams from Mermaid-compatible syntax — Python interface to the Flora JS library"
|
|
9
|
+
readme = "README.md"
|
|
10
|
+
license = "MIT"
|
|
11
|
+
authors = [{ name = "topspinj" }]
|
|
12
|
+
requires-python = ">=3.10"
|
|
13
|
+
dependencies = ["mini-racer>=0.12"]
|
|
14
|
+
keywords = ["diagrams", "flowchart", "svg", "mermaid", "visualization", "jupyter", "lineage"]
|
|
15
|
+
classifiers = [
|
|
16
|
+
"Development Status :: 4 - Beta",
|
|
17
|
+
"Intended Audience :: Developers",
|
|
18
|
+
"Intended Audience :: Science/Research",
|
|
19
|
+
"Programming Language :: Python :: 3",
|
|
20
|
+
"Programming Language :: Python :: 3.10",
|
|
21
|
+
"Programming Language :: Python :: 3.11",
|
|
22
|
+
"Programming Language :: Python :: 3.12",
|
|
23
|
+
"Programming Language :: Python :: 3.13",
|
|
24
|
+
"Framework :: Jupyter",
|
|
25
|
+
"Topic :: Multimedia :: Graphics",
|
|
26
|
+
"Topic :: Scientific/Engineering :: Visualization",
|
|
27
|
+
]
|
|
28
|
+
|
|
29
|
+
[project.urls]
|
|
30
|
+
Homepage = "https://github.com/topspinj/florajs"
|
|
31
|
+
Repository = "https://github.com/topspinj/florajs"
|
|
32
|
+
Issues = "https://github.com/topspinj/florajs/issues"
|
|
33
|
+
|
|
34
|
+
[project.optional-dependencies]
|
|
35
|
+
dev = ["pytest>=8"]
|
|
36
|
+
|
|
37
|
+
[tool.hatch.build.targets.wheel]
|
|
38
|
+
packages = ["src/florajs"]
|
|
39
|
+
|
|
40
|
+
[tool.hatch.build]
|
|
41
|
+
# The vendored JS bundle is a build artifact (gitignored); force-include it.
|
|
42
|
+
artifacts = ["src/florajs/_vendor/flora.iife.js"]
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
"""Flora for Python — beautiful, interactive diagrams from Mermaid-compatible
|
|
2
|
+
syntax, rendered by the Flora JS library.
|
|
3
|
+
|
|
4
|
+
Quick start::
|
|
5
|
+
|
|
6
|
+
from florajs import Flowchart
|
|
7
|
+
|
|
8
|
+
fc = Flowchart("LR", theme="tufte")
|
|
9
|
+
fc.node("raw", "Raw events", shape="cylinder")
|
|
10
|
+
fc.node("clean", "Cleaned")
|
|
11
|
+
fc.edge("raw", "clean", "dbt run")
|
|
12
|
+
fc # displays interactively in Jupyter
|
|
13
|
+
fc.to_svg_file("pipeline.svg")
|
|
14
|
+
|
|
15
|
+
Or from raw Flora/Mermaid syntax::
|
|
16
|
+
|
|
17
|
+
from florajs import Diagram
|
|
18
|
+
|
|
19
|
+
Diagram('''
|
|
20
|
+
flowchart TD
|
|
21
|
+
a[Start] --> b{Decide}
|
|
22
|
+
b -->|yes| c([Done])
|
|
23
|
+
''')
|
|
24
|
+
"""
|
|
25
|
+
|
|
26
|
+
from ._diagram import Diagram, Flowchart, THEMES
|
|
27
|
+
from ._errors import FloraParseError, FloraSyntaxWarning, ParseWarning
|
|
28
|
+
|
|
29
|
+
__version__ = "0.1.0"
|
|
30
|
+
|
|
31
|
+
__all__ = [
|
|
32
|
+
"Diagram",
|
|
33
|
+
"Flowchart",
|
|
34
|
+
"THEMES",
|
|
35
|
+
"FloraParseError",
|
|
36
|
+
"FloraSyntaxWarning",
|
|
37
|
+
"ParseWarning",
|
|
38
|
+
"__version__",
|
|
39
|
+
]
|