Skip to content

Commit aa34884

Browse files
authored
Separate schema registry and TypeScript code generation responsibilities, add docs (#807)
* Separate schema registry and Typescript type generation responsibilities Improve inline documentation * Create new explanation dir in contributor guide Move architecture documentation in * Re-organize contributor how-tos into how-tos subdir * Create interface directory before attempting to write to it * Fix broken link * Update toctree glob expressions to include files in same dir * Fix link * More consistent how-to titles * Add code generation documentation * Add more specificity about code generation commands * Lint 🔔 * Fix doc build "misc.highlighting_failure" failure * Adjust extension order to fix rendering If the extension is loaded after sphinx_tabs, it doesn't work! :o * Switch flowchart to top-down It was rendering too small in left-to-right mode * Fix mermaid rendering issues Some lines are too long. Handle special characters with quotes.
1 parent 65516e6 commit aa34884

File tree

15 files changed

+152
-29
lines changed

15 files changed

+152
-29
lines changed

docs/conf.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
"sphinx_autodoc_typehints",
1717
"sphinx.ext.intersphinx",
1818
"sphinx.ext.napoleon",
19+
"sphinxcontrib.mermaid",
1920
"sphinx_tabs.tabs",
2021
"sphinx_exercise",
2122
"sphinx_togglebutton",
@@ -25,6 +26,7 @@
2526
myst_enable_extensions = [
2627
"colon_fence",
2728
]
29+
myst_fence_as_directive = ["mermaid"]
2830

2931
master_doc = "index"
3032
project = "JupyterGIS"
File renamed without changes.
Lines changed: 105 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,105 @@
1+
# Code generation
2+
3+
JupyterGIS leverages code generation to share information about data structures across
4+
Python and TypeScript packages.
5+
6+
## Overview
7+
8+
There are 3 code generation targets: the schema registry, TypeScript types, and Python
9+
types.
10+
11+
Code generation tasks are defined in `packages/schema/package.json`.
12+
You can run all code generation tasks with `jlpm run build:schema`, or run them
13+
individually using the commands in the diagram below.
14+
15+
```mermaid
16+
flowchart TD
17+
package-manifest["package.json"]
18+
npm-script-schema-registry{{"build:schema:registry"}}
19+
npm-script-schema-js{{"build:schema:js"}}
20+
npm-script-schema-py{{"build:schema:py"}}
21+
22+
combined-schema[("Combined schema<br/>(forms.json)")]
23+
schema-registry[["schemaregistry.ts"]]
24+
react-forms[["React forms"]]
25+
26+
ts-types[("TypeScript type definitions")]
27+
28+
tmp-schema[("Temporary schema<br/>(rewritten $ref paths)")]
29+
py-types[("Python type definitions")]
30+
31+
package-manifest -->|jlpm run| npm-script-schema-registry
32+
package-manifest -->|jlpm run| npm-script-schema-js
33+
package-manifest -->|jlpm run| npm-script-schema-py
34+
35+
npm-script-schema-registry -->|scripts/dereference-and-combine-schemas-for-registry.js| combined-schema
36+
-->|read| schema-registry
37+
-->|react-jsonschema-form| react-forms
38+
39+
npm-script-schema-js -->|json-schema-to-typescript| ts-types
40+
npm-script-schema-js -->|scripts/add-schema-version.ts| ts-types
41+
42+
npm-script-schema-py -->|scripts/preprocess-schemas-for-python-type-generation.js| tmp-schema
43+
--> |datamodel-code-generator| py-types
44+
```
45+
46+
## Schema registry
47+
48+
The schema registry is built for use in TypeScript code.
49+
It's used by [`react-jsonschema-form` (RJSF)](https://github.com/rjsf-team/react-jsonschema-form)
50+
to generate forms (React components) from JSONSchema.
51+
52+
Prior to generating the schema registry, we dereference (i.e. inline `$ref`s) our
53+
schemas and combine them into one JSON file which contains a mapping from schema names
54+
to schema data for each schema.
55+
56+
:::{note}
57+
Combining the schemas into `forms.json` is vestigial.
58+
Before we had a schema registry, we would directly index into this data to find a
59+
schema.
60+
Now that we're building a schema registry for interfacing with schemas, perhaps we don't
61+
need a combined `forms.json` schema.
62+
:::
63+
64+
## TypeScript types
65+
66+
TypeScript types are generated from the JSONSchema files using
67+
[`json-schema-to-typescript`](https://github.com/bcherny/json-schema-to-typescript).
68+
69+
We additionally run a custom script (`scripts/add-schema-version.ts`) to generate a
70+
version number variable.
71+
72+
## Python types
73+
74+
Python types are generated from the JSONSchema files using
75+
[`datamodel-code-generator`](https://github.com/koxudaxi/datamodel-code-generator).
76+
77+
### Weirdness with `$ref` paths
78+
79+
Unfortunately, `datamodel-code-generator` expects `$ref` paths to be expressed
80+
differently from `json-schema-to-typescript`.
81+
The former expects "relative" paths, and the latter expects "absolute" paths.
82+
83+
For example, if we have two schema files:
84+
85+
```text
86+
├── referent.json
87+
└── subdir
88+
└── referrer.json
89+
```
90+
91+
...`json-schema-to-typescript` would expect `referrer.json` to contain a reference like:
92+
93+
```json
94+
"$ref": "referent.json",
95+
```
96+
97+
...and `datamodel-code-generator` would expect the reference in `referrer.json` to look like:
98+
99+
```json
100+
"$ref": "../referent.json",
101+
```
102+
103+
**For this reason, we chose to write our schema files in the way
104+
`json-schema-to-typescript` expects, and pre-process them into a temp directory so they
105+
look the way `datamodel-code-generator` expects before generating Python types.**
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
# Explanation
2+
3+
```{toctree}
4+
:maxdepth: 1
5+
:glob:
6+
7+
*
8+
```

docs/contributor_guide/docs.md renamed to docs/contributor_guide/how-tos/build-docs-locally.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
# Building JupyterGIS documentation locally
1+
# Build JupyterGIS documentation locally
22

33
:::{tip}
44
You can use `conda` or `mamba` as drop-in replacements for `micromamba` in the steps
@@ -7,7 +7,7 @@ below, but they will not be as fast.
77

88
## 0. Build JupyterGIS JavaScript packages
99

10-
Follow the [development environment setup instructions](./development_setup.md) through running `jlpm run build` from the **root of the repo**.
10+
Follow the [development environment setup instructions](../development_setup.md) through running `jlpm run build` from the **root of the repo**.
1111

1212
:::{important}
1313
Navigate to the `docs/` directory before starting any of the following steps!

docs/contributor_guide/code_quality.md renamed to docs/contributor_guide/how-tos/code_quality.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
1-
# Code quality
1+
# Check code quality
22

33
```{seealso}
4-
Complete [dev install](./development_setup) instructions before continuing.
4+
Complete [dev install](../development_setup) instructions before continuing.
55
```
66

77
We have several tools configured for checking code quality:

docs/contributor_guide/how-tos/index.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,4 +5,5 @@
55
:glob:
66
77
*/*
8+
*
89
```

docs/contributor_guide/releasing.md renamed to docs/contributor_guide/how-tos/release.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
# Releasing
1+
# Release JupyterGIS packages
22

33
## Automated Releases with `jupyter_releaser`
44

docs/contributor_guide/testing.md renamed to docs/contributor_guide/how-tos/test.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
# Testing
1+
# Test JupyterGIS
22

33
## Python unit tests
44

docs/contributor_guide/tutorial_writing_guide.md renamed to docs/contributor_guide/how-tos/write-tutorials.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
# Tutorial Writing Guide
1+
# Write tutorials
22

33
This guide provides best practices for writing tutorials for JupyterGIS. To keep tutorials consistent and easy to follow, please follow the guidelines below.
44

0 commit comments

Comments
 (0)