fastapi-voyager 0.11.11__tar.gz → 0.12.1__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 (54) hide show
  1. fastapi_voyager-0.12.1/PKG-INFO +183 -0
  2. fastapi_voyager-0.12.1/README.md +154 -0
  3. fastapi_voyager-0.12.1/docs/changelog.md +122 -0
  4. fastapi_voyager-0.12.1/docs/idea.md +22 -0
  5. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/server.py +3 -0
  6. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/version.py +1 -1
  7. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/component/schema-code-display.js +1 -0
  8. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/graph-ui.js +3 -8
  9. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/index.html +5 -3
  10. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/vue-main.js +71 -0
  11. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/tests/programatic.py +1 -1
  12. fastapi_voyager-0.11.11/PKG-INFO +0 -350
  13. fastapi_voyager-0.11.11/README.md +0 -321
  14. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/.github/workflows/publish.yml +0 -0
  15. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/.gitignore +0 -0
  16. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/.python-version +0 -0
  17. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/LICENSE +0 -0
  18. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/pyproject.toml +0 -0
  19. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/release.md +0 -0
  20. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/__init__.py +0 -0
  21. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/cli.py +0 -0
  22. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/filter.py +0 -0
  23. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/module.py +0 -0
  24. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/render.py +0 -0
  25. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/type.py +0 -0
  26. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/type_helper.py +0 -0
  27. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/voyager.py +0 -0
  28. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/component/render-graph.js +0 -0
  29. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/component/route-code-display.js +0 -0
  30. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/component/schema-field-filter.js +0 -0
  31. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/graphviz.svg.css +0 -0
  32. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/graphviz.svg.js +0 -0
  33. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/icon/android-chrome-192x192.png +0 -0
  34. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/icon/android-chrome-512x512.png +0 -0
  35. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/icon/apple-touch-icon.png +0 -0
  36. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/icon/favicon-16x16.png +0 -0
  37. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/icon/favicon-32x32.png +0 -0
  38. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/icon/favicon.ico +0 -0
  39. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/icon/site.webmanifest +0 -0
  40. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/quasar.min.css +0 -0
  41. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/src/fastapi_voyager/web/quasar.min.js +0 -0
  42. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/tests/__init__.py +0 -0
  43. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/tests/demo.py +0 -0
  44. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/tests/demo_anno.py +0 -0
  45. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/tests/service/__init__.py +0 -0
  46. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/tests/service/schema.py +0 -0
  47. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/tests/test_analysis.py +0 -0
  48. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/tests/test_filter.py +0 -0
  49. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/tests/test_generic.py +0 -0
  50. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/tests/test_import.py +0 -0
  51. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/tests/test_module.py +0 -0
  52. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/tests/test_type_helper.py +0 -0
  53. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/uv.lock +0 -0
  54. {fastapi_voyager-0.11.11 → fastapi_voyager-0.12.1}/voyager.jpg +0 -0
@@ -0,0 +1,183 @@
1
+ Metadata-Version: 2.4
2
+ Name: fastapi-voyager
3
+ Version: 0.12.1
4
+ Summary: Visualize FastAPI application's routing tree and dependencies
5
+ Project-URL: Homepage, https://github.com/allmonday/fastapi-voyager
6
+ Project-URL: Source, https://github.com/allmonday/fastapi-voyager
7
+ Author-email: Tangkikodo <allmonday@126.com>
8
+ License: MIT
9
+ License-File: LICENSE
10
+ Keywords: fastapi,openapi,routing,visualization
11
+ Classifier: Framework :: FastAPI
12
+ Classifier: Intended Audience :: Developers
13
+ Classifier: License :: OSI Approved :: MIT License
14
+ Classifier: Programming Language :: Python :: 3
15
+ Classifier: Programming Language :: Python :: 3.9
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: Programming Language :: Python :: 3.14
21
+ Requires-Python: >=3.10
22
+ Requires-Dist: fastapi>=0.110
23
+ Requires-Dist: pydantic-resolve>=1.13.2
24
+ Provides-Extra: dev
25
+ Requires-Dist: pytest; extra == 'dev'
26
+ Requires-Dist: ruff; extra == 'dev'
27
+ Requires-Dist: uvicorn; extra == 'dev'
28
+ Description-Content-Type: text/markdown
29
+
30
+ [![pypi](https://img.shields.io/pypi/v/fastapi-voyager.svg)](https://pypi.python.org/pypi/fastapi-voyager)
31
+ ![Python Versions](https://img.shields.io/pypi/pyversions/fastapi-voyager)
32
+ [![PyPI Downloads](https://static.pepy.tech/badge/fastapi-voyager/month)](https://pepy.tech/projects/fastapi-voyager)
33
+
34
+
35
+ > This repo is still in early stage, it supports pydantic v2 only
36
+
37
+ Visualize your FastAPI endpoints, and explore them interactively.
38
+
39
+ [visit online demo](https://www.newsyeah.fun/voyager/) of project: [composition oriented development pattern](https://github.com/allmonday/composition-oriented-development-pattern)
40
+
41
+ <img width="1600" height="986" alt="image" src="https://github.com/user-attachments/assets/8829cda0-f42d-4c84-be2f-b019bb5fe7e1" />
42
+
43
+ ## Installation
44
+
45
+ ```bash
46
+ pip install fastapi-voyager
47
+ # or
48
+ uv add fastapi-voyager
49
+ ```
50
+
51
+ ```shell
52
+ voyager -m path.to.your.app.module --server
53
+ ```
54
+
55
+ > [Sub-Application mounts](https://fastapi.tiangolo.com/advanced/sub-applications/) are not supported yet, but you can specify the name of the FastAPI application used with `--app`. Only a single application (default: 'app') can be selected, but in a scenario where `api` is attached through `app.mount("/api", api)`, you can select `api` like this:
56
+
57
+ ```shell
58
+ voyager -m path.to.your.app.module --server --app api
59
+ ```
60
+
61
+ ## Mount into project
62
+
63
+ ```python
64
+ from fastapi import FastAPI
65
+ from fastapi_voyager import create_voyager
66
+ from tests.demo import app
67
+
68
+ app.mount('/voyager', create_voyager(
69
+ app,
70
+ module_color={"tests.service": "red"},
71
+ module_prefix="tests.service"),
72
+ swagger_url="/docs")
73
+ ```
74
+
75
+ ## Features
76
+
77
+ For scenarios of using FastAPI as internal API integration endpoints, `fastapi-voyager` helps to visualize the dependencies.
78
+
79
+ It is also an architecture inspection tool that can identify issues in data relationships during design phase before turly implemtatioin.
80
+
81
+ If the process of building the view model follows the ER model, the full potential of fastapi-voyager can be realized. It allows for quick identification of APIs that use entities, as well as which entities are used by a specific API
82
+
83
+ ### highlight nodes and links
84
+ click a node to highlight it's upperstream and downstream nodes. figure out the related models of one page, or homw many pages are related with one model.
85
+
86
+
87
+ <img width="1100" height="700" alt="image" src="https://github.com/user-attachments/assets/3e0369ea-5fa4-469a-82c1-ed57d407e53d" />
88
+
89
+ ### focus on nodes
90
+
91
+ Double click a node, and then toggle focus to hide irrelevant nodes.
92
+
93
+ <img width="1061" height="937" alt="image" src="https://github.com/user-attachments/assets/79709b02-7571-43fc-abc9-17a287a97515" />
94
+
95
+ ### view source code
96
+
97
+ double click a node or route to show source code or open file in vscode.
98
+
99
+ <img width="1297" height="940" alt="image" src="https://github.com/user-attachments/assets/c8bb2e7d-b727-42a6-8c9e-64dce297d2d8" />
100
+
101
+ <img width="1132" height="824" alt="image" src="https://github.com/user-attachments/assets/b706e879-e4fc-48dd-ace1-99bf97e3ed6a" />
102
+
103
+
104
+ ## Command Line Usage
105
+
106
+ ### open in browser
107
+
108
+ ```bash
109
+ # open in browser
110
+ voyager -m tests.demo --server
111
+
112
+ voyager -m tests.demo --server --port=8002
113
+ ```
114
+
115
+ ### generate the dot file
116
+ ```bash
117
+ # generate .dot file
118
+ voyager -m tests.demo
119
+
120
+ voyager -m tests.demo --app my_app
121
+
122
+ voyager -m tests.demo --schema Task
123
+
124
+ voyager -m tests.demo --show_fields all
125
+
126
+ voyager -m tests.demo --module_color=tests.demo:red --module_color=tests.service:tomato
127
+
128
+ voyager -m tests.demo -o my_visualization.dot
129
+
130
+ voyager --version
131
+
132
+ voyager --help
133
+ ```
134
+
135
+ ## About pydantic-resolve
136
+
137
+ pydantic-resolve's `@ensure_subset` decorator helps safely pick fields from the 'source class' while **indicating the reference** from the current class to the base class.
138
+
139
+ pydantic-resolve is a lightweight tool designed to build complex, nested data in a simple, declarative way. In version 2.0.0alpha, it will introduce an important feature: ER Diagram, and fastapi-voyager will support this feature, allowing for a clearer understanding of the business relationships between the data.
140
+
141
+ Developers can use fastapi-voyager without needing to know anything about pydantic-resolve, but I still highly recommend everyone to give it a try.
142
+
143
+ ## Dependencies
144
+
145
+ - FastAPI
146
+ - [pydantic-resolve](https://github.com/allmonday/pydantic-resolve)
147
+ - Quasar
148
+
149
+
150
+ ## Credits
151
+
152
+ - https://apis.guru/graphql-voyager/, thanks for inspiration.
153
+ - https://github.com/tintinweb/vscode-interactive-graphviz, thanks for web visualization.
154
+
155
+
156
+ ## How to develop & contribute?
157
+
158
+ fork, clone.
159
+
160
+ install uv.
161
+
162
+ ```shell
163
+ uv venv
164
+ source .venv/bin/activate
165
+ uv pip install ".[dev]"
166
+ uvicorn tests.programatic:app --reload
167
+ ```
168
+
169
+ open `localhost:8000/voyager`
170
+
171
+
172
+ frontend:
173
+ - `src/web/vue-main.js`: main js
174
+
175
+ backend:
176
+ - `voyager.py`: main entry
177
+ - `render.py`: generate dot file
178
+ - `server.py`: serve mode
179
+
180
+
181
+ ## Plan & Raodmap
182
+ - [ideas](./docs/idea.md)
183
+ - [changelog & roadmap](./docs/changelog.md)
@@ -0,0 +1,154 @@
1
+ [![pypi](https://img.shields.io/pypi/v/fastapi-voyager.svg)](https://pypi.python.org/pypi/fastapi-voyager)
2
+ ![Python Versions](https://img.shields.io/pypi/pyversions/fastapi-voyager)
3
+ [![PyPI Downloads](https://static.pepy.tech/badge/fastapi-voyager/month)](https://pepy.tech/projects/fastapi-voyager)
4
+
5
+
6
+ > This repo is still in early stage, it supports pydantic v2 only
7
+
8
+ Visualize your FastAPI endpoints, and explore them interactively.
9
+
10
+ [visit online demo](https://www.newsyeah.fun/voyager/) of project: [composition oriented development pattern](https://github.com/allmonday/composition-oriented-development-pattern)
11
+
12
+ <img width="1600" height="986" alt="image" src="https://github.com/user-attachments/assets/8829cda0-f42d-4c84-be2f-b019bb5fe7e1" />
13
+
14
+ ## Installation
15
+
16
+ ```bash
17
+ pip install fastapi-voyager
18
+ # or
19
+ uv add fastapi-voyager
20
+ ```
21
+
22
+ ```shell
23
+ voyager -m path.to.your.app.module --server
24
+ ```
25
+
26
+ > [Sub-Application mounts](https://fastapi.tiangolo.com/advanced/sub-applications/) are not supported yet, but you can specify the name of the FastAPI application used with `--app`. Only a single application (default: 'app') can be selected, but in a scenario where `api` is attached through `app.mount("/api", api)`, you can select `api` like this:
27
+
28
+ ```shell
29
+ voyager -m path.to.your.app.module --server --app api
30
+ ```
31
+
32
+ ## Mount into project
33
+
34
+ ```python
35
+ from fastapi import FastAPI
36
+ from fastapi_voyager import create_voyager
37
+ from tests.demo import app
38
+
39
+ app.mount('/voyager', create_voyager(
40
+ app,
41
+ module_color={"tests.service": "red"},
42
+ module_prefix="tests.service"),
43
+ swagger_url="/docs")
44
+ ```
45
+
46
+ ## Features
47
+
48
+ For scenarios of using FastAPI as internal API integration endpoints, `fastapi-voyager` helps to visualize the dependencies.
49
+
50
+ It is also an architecture inspection tool that can identify issues in data relationships during design phase before turly implemtatioin.
51
+
52
+ If the process of building the view model follows the ER model, the full potential of fastapi-voyager can be realized. It allows for quick identification of APIs that use entities, as well as which entities are used by a specific API
53
+
54
+ ### highlight nodes and links
55
+ click a node to highlight it's upperstream and downstream nodes. figure out the related models of one page, or homw many pages are related with one model.
56
+
57
+
58
+ <img width="1100" height="700" alt="image" src="https://github.com/user-attachments/assets/3e0369ea-5fa4-469a-82c1-ed57d407e53d" />
59
+
60
+ ### focus on nodes
61
+
62
+ Double click a node, and then toggle focus to hide irrelevant nodes.
63
+
64
+ <img width="1061" height="937" alt="image" src="https://github.com/user-attachments/assets/79709b02-7571-43fc-abc9-17a287a97515" />
65
+
66
+ ### view source code
67
+
68
+ double click a node or route to show source code or open file in vscode.
69
+
70
+ <img width="1297" height="940" alt="image" src="https://github.com/user-attachments/assets/c8bb2e7d-b727-42a6-8c9e-64dce297d2d8" />
71
+
72
+ <img width="1132" height="824" alt="image" src="https://github.com/user-attachments/assets/b706e879-e4fc-48dd-ace1-99bf97e3ed6a" />
73
+
74
+
75
+ ## Command Line Usage
76
+
77
+ ### open in browser
78
+
79
+ ```bash
80
+ # open in browser
81
+ voyager -m tests.demo --server
82
+
83
+ voyager -m tests.demo --server --port=8002
84
+ ```
85
+
86
+ ### generate the dot file
87
+ ```bash
88
+ # generate .dot file
89
+ voyager -m tests.demo
90
+
91
+ voyager -m tests.demo --app my_app
92
+
93
+ voyager -m tests.demo --schema Task
94
+
95
+ voyager -m tests.demo --show_fields all
96
+
97
+ voyager -m tests.demo --module_color=tests.demo:red --module_color=tests.service:tomato
98
+
99
+ voyager -m tests.demo -o my_visualization.dot
100
+
101
+ voyager --version
102
+
103
+ voyager --help
104
+ ```
105
+
106
+ ## About pydantic-resolve
107
+
108
+ pydantic-resolve's `@ensure_subset` decorator helps safely pick fields from the 'source class' while **indicating the reference** from the current class to the base class.
109
+
110
+ pydantic-resolve is a lightweight tool designed to build complex, nested data in a simple, declarative way. In version 2.0.0alpha, it will introduce an important feature: ER Diagram, and fastapi-voyager will support this feature, allowing for a clearer understanding of the business relationships between the data.
111
+
112
+ Developers can use fastapi-voyager without needing to know anything about pydantic-resolve, but I still highly recommend everyone to give it a try.
113
+
114
+ ## Dependencies
115
+
116
+ - FastAPI
117
+ - [pydantic-resolve](https://github.com/allmonday/pydantic-resolve)
118
+ - Quasar
119
+
120
+
121
+ ## Credits
122
+
123
+ - https://apis.guru/graphql-voyager/, thanks for inspiration.
124
+ - https://github.com/tintinweb/vscode-interactive-graphviz, thanks for web visualization.
125
+
126
+
127
+ ## How to develop & contribute?
128
+
129
+ fork, clone.
130
+
131
+ install uv.
132
+
133
+ ```shell
134
+ uv venv
135
+ source .venv/bin/activate
136
+ uv pip install ".[dev]"
137
+ uvicorn tests.programatic:app --reload
138
+ ```
139
+
140
+ open `localhost:8000/voyager`
141
+
142
+
143
+ frontend:
144
+ - `src/web/vue-main.js`: main js
145
+
146
+ backend:
147
+ - `voyager.py`: main entry
148
+ - `render.py`: generate dot file
149
+ - `server.py`: serve mode
150
+
151
+
152
+ ## Plan & Raodmap
153
+ - [ideas](./docs/idea.md)
154
+ - [changelog & roadmap](./docs/changelog.md)
@@ -0,0 +1,122 @@
1
+ # Changelog & roadmap
2
+
3
+ ## <0.9:
4
+ - [x] group schemas by module hierarchy
5
+ - [x] module-based coloring via Analytics(module_color={...})
6
+ - [x] view in web browser
7
+ - [x] config params
8
+ - [x] make a explorer dashboard, provide list of routes, schemas, to make it easy to switch and search
9
+ - [x] support programmatic usage
10
+ - [x] better schema /router node appearance
11
+ - [x] hide fields duplicated with parent's (show `parent fields` instead)
12
+ - [x] refactor the frontend to vue, and tweak the build process
13
+ - [x] find dependency based on picked schema and it's field.
14
+ - [x] optimize static resource (cdn -> local)
15
+ - [x] add configuration for highlight (optional)
16
+ - [x] alt+click to show field details
17
+ - [x] display source code of routes (including response_model)
18
+ - [x] handle excluded field
19
+ - [x] add tooltips
20
+ - [x] route
21
+ - [x] group routes by module hierarchy
22
+ - [x] add response_model in route
23
+ - [x] fixed left bar show tag/ route
24
+ - [x] export voyager core data into json (for better debugging)
25
+ - [x] add api to rebuild core data from json, and render it
26
+ - [x] fix Generic case `test_generic.py`
27
+ - [x] show tips for routes not return pydantic type.
28
+ - [x] fix duplicated link from class and parent class, it also break clicking highlight
29
+ - [x] refactor: abstract render module
30
+
31
+ ## 0.9
32
+ - [x] refactor: server.py
33
+ - [x] rename create_app_with_fastapi -> create_voyager
34
+ - [x] add doc for parameters
35
+ - [x] improve initialization time cost
36
+ - [x] query route / schema info through realtime api
37
+ - [x] adjust fe
38
+ - 0.9.3
39
+ - [x] adjust layout
40
+ - [x] show field detail in right panel
41
+ - [x] show route info in bottom
42
+ - 0.9.4
43
+ - [x] close schema sidebar when switch tag/route
44
+ - [x] schema detail panel show fields by default
45
+ - [x] adjust schema panel's height
46
+ - [x] show from base information in subset case
47
+ - 0.9.5
48
+ - [x] route list should have a max height
49
+
50
+ ## 0.10
51
+ - 0.10.1
52
+ - [x] refactor voyager.py tag -> route structure
53
+ - [x] fix missing route (tag has only one route which return primitive value)
54
+ - [x] make right panel resizable by dragging
55
+ - [x] allow closing tag expansion item
56
+ - [x] hide brief mode if not configured
57
+ - [x] add focus button to only show related nodes under current route/tag graph in dialog
58
+ - 0.10.2
59
+ - [x] fix graph height
60
+ - [x] show version in title
61
+ - 0.10.3
62
+ - [x] fix focus in brief-mode
63
+ - [x] ui: adjust focus position
64
+ - [x] refactor naming
65
+ - [x] fix layout issue when rendering huge graph
66
+ - 0.10.4
67
+ - [x] fix: when focus is on, should ensure changes from other params not broken.
68
+ - 0.10.5
69
+ - [x] double click to show details, and highlight as tomato
70
+
71
+
72
+ ## 0.11
73
+ - 0.11.1
74
+ - [x] support opening route in swagger
75
+ - [x] config docs path
76
+ - [x] provide option to hide routes in brief mode (auto hide in full graph mode)
77
+ - 0.11.2
78
+ - [x] enable/disable module cluster (to save space)
79
+ - 0.11.3
80
+ - [x] support online repo url
81
+ - 0.11.4
82
+ - [x] add loading for field detail panel
83
+ - 0.11.5
84
+ - [x] optimize open in swagger link
85
+ - [x] change jquery cdn
86
+ - 0.11.6
87
+ - [x] flag of loading full graph in first render or not
88
+ - [x] optimize loading static resource
89
+ - 0.11.7
90
+ - [x] fix swagger link
91
+ - 0.11.8
92
+ - [x] fix swagger link in another way
93
+ - 0.11.9
94
+ - [x] replace issubclass with safe_issubclass to prevent exception.
95
+ - 0.11.10
96
+ - [x] fix bug during updating forward refs
97
+ - 0.11.11
98
+ - [x] replace print with logging and add `--log-level` in cli, by default info
99
+ - [x] fill node title color with module color
100
+ - [x] optimize cluster render logic
101
+
102
+ ## 0.12
103
+ - 0.12.1
104
+ - [x] sort tag / route names in left panel
105
+ - [x] display schema name on top of detail panel
106
+ - [x] optimize dbclick style
107
+ - [x] persist the tag/ route in url
108
+ - 0.12.2
109
+ - [ ] search tag/ route
110
+ - [ ] refactor render.py
111
+ - [ ] reorg: move variable into reactive in vue-main.js
112
+
113
+ ## 0.13
114
+ - 0.12.0
115
+ - [ ] integration with pydantic-resolve
116
+ - [ ] show hint for resolve, post fields
117
+ - [ ] display loader as edges
118
+ - [ ] add tests
119
+
120
+ ## 0.13
121
+ todo
122
+
@@ -0,0 +1,22 @@
1
+ # Idea
2
+
3
+ ## backlog
4
+ - [ ] user can generate nodes/edges manually and connect to generated ones
5
+ - [ ] eg: add owner
6
+ - [ ] add extra info for schema
7
+ - [ ] optimize static resource (allow manually config url)
8
+ - [ ] improve search dialog
9
+ - [ ] add route/tag list
10
+ - [ ] type alias should not be kept as node instead of compiling to original type
11
+ - [ ] how to correctly handle the generic type ?
12
+ - [ ] support Google analysis config
13
+ - [ ] sort field name in nodes (only table inside right panel), pending
14
+ - [ ] set max limit for fields in nodes
15
+
16
+ ## in analysis
17
+ - [ ] upgrade network algorithm (optional)
18
+ - [ ] click field to highlight links
19
+ - [ ] animation effect for edges
20
+ - [ ] display standard ER diagram spec. `hard but important`
21
+ - [ ] display potential invalid links
22
+ - [ ] highlight relationship belongs to ER diagram
@@ -57,6 +57,9 @@ def create_voyager(
57
57
 
58
58
  # include tags and their routes
59
59
  tags = voyager.tags
60
+ for t in tags:
61
+ t.routes.sort(key=lambda r: r.name)
62
+ tags.sort(key=lambda t: t.name)
60
63
 
61
64
  schemas = voyager.nodes[:]
62
65
  schemas.sort(key=lambda s: s.name)
@@ -1,2 +1,2 @@
1
1
  __all__ = ["__version__"]
2
- __version__ = "0.11.11"
2
+ __version__ = "0.12.1"
@@ -157,6 +157,7 @@ export default defineComponent({
157
157
  <q-linear-progress indeterminate color="primary" size="2px"/>
158
158
  </div>
159
159
  <div class="q-ml-lg q-mt-md">
160
+ <p style="font-size: 16px;"> {{ schemaName }} </p>
160
161
  <a :href="link" target="_blank" rel="noopener" style="font-size:12px; color:#3b82f6;">
161
162
  Open in VSCode
162
163
  </a>
@@ -58,9 +58,10 @@ export class GraphUI {
58
58
  }
59
59
 
60
60
  highlightSchemaBanner(node) {
61
- const ele = node.querySelector("polygon[fill='#009485']")
61
+ const polygons = node.querySelectorAll("polygon");
62
+ const ele = polygons[2]; // select the second polygon
62
63
  if (ele) {
63
- ele.setAttribute('fill', 'tomato');
64
+ ele.setAttribute('stroke-width', '3.5');
64
65
  }
65
66
  }
66
67
 
@@ -160,12 +161,6 @@ export class GraphUI {
160
161
  }
161
162
  }
162
163
  });
163
-
164
- $(document).on("keydown.graphui", function (evt) {
165
- if (evt.keyCode === 27 && self.gv) {
166
- self.gv.highlight();
167
- }
168
- });
169
164
  },
170
165
  });
171
166
  }
@@ -59,6 +59,9 @@
59
59
  .adjust-fit {
60
60
  height: calc(100vh - 54px);
61
61
  }
62
+
63
+ .github-corner:hover .octo-arm{animation:octocat-wave 560ms ease-in-out}@keyframes octocat-wave{0%,100%{transform:rotate(0)}20%,60%{transform:rotate(-25deg)}40%,80%{transform:rotate(10deg)}}@media (max-width:500px){.github-corner:hover .octo-arm{animation:none}.github-corner .octo-arm{animation:octocat-wave 560ms ease-in-out}}
64
+
62
65
  /* App boot loading overlay & gating */
63
66
  #app-loading-overlay {
64
67
  position: fixed;
@@ -167,9 +170,8 @@
167
170
  </div>
168
171
  </q-tooltip>
169
172
  </q-btn>
170
- <a href="https://github.com/allmonday/fastapi-voyager" target="_blank" class="github-corner" aria-label="View source on GitHub"><svg width="52" height="52" viewBox="0 0 250 250" style="fill:#009485; color:#fff; position: absolute; top: 0; border: 0; right: 0;" aria-hidden="true"><path d="M0,0 L115,115 L130,115 L142,142 L250,250 L250,0 Z"/><path d="M128.3,109.0 C113.8,99.7 119.0,89.6 119.0,89.6 C122.0,82.7 120.5,78.6 120.5,78.6 C119.2,72.0 123.4,76.3 123.4,76.3 C127.3,80.9 125.5,87.3 125.5,87.3 C122.9,97.6 130.6,101.9 134.4,103.2" fill="currentColor" style="transform-origin: 130px 106px;" class="octo-arm"/><path d="M115.0,115.0 C114.9,115.1 118.7,116.5 119.8,115.4 L133.7,101.6 C136.9,99.2 139.9,98.4 142.2,98.6 C133.8,88.0 127.5,74.4 143.8,58.0 C148.5,53.4 154.0,51.2 159.7,51.0 C160.3,49.4 163.2,43.6 171.4,40.1 C171.4,40.1 176.1,42.5 178.8,56.2 C183.1,58.6 187.2,61.8 190.9,65.4 C194.5,69.0 197.7,73.2 200.1,77.6 C213.8,80.2 216.3,84.9 216.3,84.9 C212.7,93.1 206.9,96.0 205.4,96.6 C205.1,102.4 203.0,107.8 198.3,112.5 C181.9,128.9 168.3,122.5 157.7,114.1 C157.9,116.9 156.7,120.9 152.7,124.9 L141.0,136.5 C139.8,137.7 141.6,141.9 141.8,141.8 Z" fill="currentColor" class="octo-body"/></svg></a><style>.github-corner:hover .octo-arm{animation:octocat-wave 560ms ease-in-out}@keyframes octocat-wave{0%,100%{transform:rotate(0)}20%,60%{transform:rotate(-25deg)}40%,80%{transform:rotate(10deg)}}@media (max-width:500px){.github-corner:hover .octo-arm{animation:none}.github-corner .octo-arm{animation:octocat-wave 560ms ease-in-out}}</style></div>
171
- <!-- <q-toolbar-title class="text-primary row">
172
- </q-toolbar-title> -->
173
+ <a href="https://github.com/allmonday/fastapi-voyager" target="_blank" class="github-corner" aria-label="View source on GitHub"><svg width="52" height="52" viewBox="0 0 250 250" style="fill:#009485; color:#fff; position: absolute; top: 0; border: 0; right: 0;" aria-hidden="true"><path d="M0,0 L115,115 L130,115 L142,142 L250,250 L250,0 Z"/><path d="M128.3,109.0 C113.8,99.7 119.0,89.6 119.0,89.6 C122.0,82.7 120.5,78.6 120.5,78.6 C119.2,72.0 123.4,76.3 123.4,76.3 C127.3,80.9 125.5,87.3 125.5,87.3 C122.9,97.6 130.6,101.9 134.4,103.2" fill="currentColor" style="transform-origin: 130px 106px;" class="octo-arm"/><path d="M115.0,115.0 C114.9,115.1 118.7,116.5 119.8,115.4 L133.7,101.6 C136.9,99.2 139.9,98.4 142.2,98.6 C133.8,88.0 127.5,74.4 143.8,58.0 C148.5,53.4 154.0,51.2 159.7,51.0 C160.3,49.4 163.2,43.6 171.4,40.1 C171.4,40.1 176.1,42.5 178.8,56.2 C183.1,58.6 187.2,61.8 190.9,65.4 C194.5,69.0 197.7,73.2 200.1,77.6 C213.8,80.2 216.3,84.9 216.3,84.9 C212.7,93.1 206.9,96.0 205.4,96.6 C205.1,102.4 203.0,107.8 198.3,112.5 C181.9,128.9 168.3,122.5 157.7,114.1 C157.9,116.9 156.7,120.9 152.7,124.9 L141.0,136.5 C139.8,137.7 141.6,141.9 141.8,141.8 Z" fill="currentColor" class="octo-body"/></svg></a>
174
+ </div>
173
175
  </q-toolbar>
174
176
  </q-header>
175
177
 
@@ -59,6 +59,66 @@ const app = createApp({
59
59
  showDetail.value = false;
60
60
  }
61
61
 
62
+ function readQuerySelection() {
63
+ if (typeof window === "undefined") {
64
+ return { tag: null, route: null };
65
+ }
66
+ const params = new URLSearchParams(window.location.search);
67
+ return {
68
+ tag: params.get("tag") || null,
69
+ route: params.get("route") || null,
70
+ };
71
+ }
72
+
73
+ function findTagByRoute(routeId) {
74
+ return (
75
+ state.rawTags.find((tag) =>
76
+ (tag.routes || []).some((route) => route.id === routeId)
77
+ )?.name || null
78
+ );
79
+ }
80
+
81
+ function syncSelectionToUrl() {
82
+ if (typeof window === "undefined") {
83
+ return;
84
+ }
85
+ const params = new URLSearchParams(window.location.search);
86
+ if (state.tag) {
87
+ params.set("tag", state.tag);
88
+ } else {
89
+ params.delete("tag");
90
+ }
91
+ if (state.routeId) {
92
+ params.set("route", state.routeId);
93
+ } else {
94
+ params.delete("route");
95
+ }
96
+ const hash = window.location.hash || "";
97
+ const search = params.toString();
98
+ const base = window.location.pathname;
99
+ const newUrl = search ? `${base}?${search}${hash}` : `${base}${hash}`;
100
+ window.history.replaceState({}, "", newUrl);
101
+ }
102
+
103
+ function applySelectionFromQuery(selection) {
104
+ let applied = false;
105
+ if (selection.tag && state.rawTags.some((tag) => tag.name === selection.tag)) {
106
+ state.tag = selection.tag;
107
+ state._tag = selection.tag;
108
+ applied = true;
109
+ }
110
+ if (selection.route && state.routeItems?.[selection.route]) {
111
+ state.routeId = selection.route;
112
+ applied = true;
113
+ const inferredTag = findTagByRoute(selection.route);
114
+ if (inferredTag) {
115
+ state.tag = inferredTag;
116
+ state._tag = inferredTag;
117
+ }
118
+ }
119
+ return applied;
120
+ }
121
+
62
122
  async function loadInitial() {
63
123
  state.initializing = true;
64
124
  try {
@@ -82,6 +142,14 @@ const app = createApp({
82
142
  state.version = data.version || "";
83
143
  state.swaggerUrl = data.swagger_url || null
84
144
 
145
+ const querySelection = readQuerySelection();
146
+ const restoredFromQuery = applySelectionFromQuery(querySelection);
147
+ if (restoredFromQuery) {
148
+ syncSelectionToUrl();
149
+ onGenerate();
150
+ return;
151
+ }
152
+
85
153
  switch (data.initial_page_policy) {
86
154
  case "full":
87
155
  onGenerate()
@@ -246,6 +314,7 @@ const app = createApp({
246
314
  state.focus = false;
247
315
  schemaCodeName.value = "";
248
316
  onGenerate();
317
+ syncSelectionToUrl();
249
318
  }
250
319
 
251
320
  function toggleTag(tagName, expanded = null) {
@@ -262,6 +331,7 @@ const app = createApp({
262
331
 
263
332
  state.detailDrawer = false;
264
333
  showRouteDetail.value = false;
334
+ syncSelectionToUrl();
265
335
  }
266
336
 
267
337
  function selectRoute(routeId) {
@@ -275,6 +345,7 @@ const app = createApp({
275
345
  state.focus = false;
276
346
  schemaCodeName.value = "";
277
347
  onGenerate();
348
+ syncSelectionToUrl();
278
349
  }
279
350
 
280
351
  function toggleShowModule(val) {
@@ -8,5 +8,5 @@ app.mount(
8
8
  module_color={"tests.service": "purple", "tests.demo": "#ccaa00", "tests": "green"},
9
9
  module_prefix="tests.service",
10
10
  swagger_url="/docs",
11
- initial_page_policy='full',
11
+ initial_page_policy='first',
12
12
  online_repo_url="https://github.com/allmonday/fastapi-voyager/blob/main"))