@syncular/typegen 0.15.12 → 0.15.14
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.
- package/README.md +41 -7
- package/dist/emit-queries-rust.d.ts +2 -0
- package/dist/emit-queries-rust.js +748 -0
- package/dist/emit-queries.js +47 -3
- package/dist/generate.js +12 -2
- package/dist/index.d.ts +1 -0
- package/dist/index.js +1 -0
- package/dist/lsp.js +2 -0
- package/dist/manifest.d.ts +9 -1
- package/dist/manifest.js +24 -3
- package/dist/naming.d.ts +11 -1
- package/dist/naming.js +126 -2
- package/package.json +3 -3
- package/src/emit-queries-rust.ts +975 -0
- package/src/emit-queries.ts +57 -2
- package/src/generate.ts +16 -1
- package/src/index.ts +1 -0
- package/src/lsp.ts +1 -0
- package/src/manifest.ts +37 -4
- package/src/naming.ts +153 -3
package/README.md
CHANGED
|
@@ -77,6 +77,7 @@ schema guide and suggests `syncular init`.
|
|
|
77
77
|
| `output.swift` | no | Opt-in Swift emitter (see §5). A path string, or `{ "path", "enumName", "queriesPath" }` (default `enumName` `SyncularSchema`; `queriesPath` opts into §6 Swift named queries). |
|
|
78
78
|
| `output.kotlin` | no | Opt-in Kotlin emitter (see §5). A path string, or `{ "path", "package", "objectName", "queriesPath" }` (defaults `syncular.generated` / `SyncularSchema`). |
|
|
79
79
|
| `output.dart` | no | Opt-in Dart emitter (see §5). A path string, or `{ "path", "queriesPath" }`. |
|
|
80
|
+
| `output.rust` | no | Opt-in Rust named-query emitter (see §6). An object `{ "queriesPath", "clientCrate"? }`; `clientCrate` defaults to `syncular_client`. Rust consumes neutral schema IR rather than a generated schema source file. |
|
|
80
81
|
| `schemaVersions` | yes, non-empty | The §1.5 version history. See below. |
|
|
81
82
|
| `tables` | yes, non-empty | Synced tables. **Array order is the handler-declared bootstrap order (§4.7)** and flows unchanged into the IR and `schema.tables`. |
|
|
82
83
|
| `tables[].name` | yes | Must be created by a migration. |
|
|
@@ -410,14 +411,15 @@ present-null, and present-value remain distinct. A group is one optional host
|
|
|
410
411
|
object whose members are all required. A `bool = false` flag activates on
|
|
411
412
|
true. Sort is a generated enum/union of complete checked profiles; limit is validated as a
|
|
412
413
|
positive bounded integer before execution. `integer` inputs are exact signed
|
|
413
|
-
64-bit values in the SYQL API (`bigint` in TypeScript,
|
|
414
|
-
|
|
414
|
+
64-bit values in the SYQL API (`bigint` in TypeScript,
|
|
415
|
+
`Int64`/`Long`/`int` on Swift/Kotlin/Dart, and `i64` on Rust).
|
|
415
416
|
|
|
416
417
|
**File & naming convention.** Named queries live in a `queries/` directory
|
|
417
418
|
next to `migrations/` (override with the top-level `"queries"` manifest key).
|
|
418
419
|
The directory is **walked recursively** — subfolders are pure organization.
|
|
419
420
|
Each language's queries file is a **separate output** (`output.queries` for TS,
|
|
420
|
-
and `queriesPath` on `output.swift`/`output.kotlin`/`output.dart`
|
|
421
|
+
and `queriesPath` on `output.swift`/`output.kotlin`/`output.dart` plus
|
|
422
|
+
`output.rust.queriesPath`), so
|
|
421
423
|
schema-only consumers never churn when a query changes. A queries output is
|
|
422
424
|
opt-in per language; when none is requested the `queries/` dir is not even
|
|
423
425
|
read.
|
|
@@ -577,7 +579,7 @@ required, non-null, exactly typed binds are allowed. Result identity is inferred
|
|
|
577
579
|
from schema keys and the projection. Without constructive proof the compiler
|
|
578
580
|
falls back to table-wide dependency, no coverage, and/or unkeyed reconciliation.
|
|
579
581
|
|
|
580
|
-
**Emitted shape, per language** (
|
|
582
|
+
**Emitted shape, per language** (abbreviated):
|
|
581
583
|
|
|
582
584
|
| | Output |
|
|
583
585
|
|---|---|
|
|
@@ -585,13 +587,45 @@ falls back to table-wide dependency, no coverage, and/or unkeyed reconciliation.
|
|
|
585
587
|
| Swift | `struct ListTodosRow` + `init?(row:)` and `<Enum>Queries.listTodos(client:listId:) throws -> [ListTodosRow]` + `listTodosTables` |
|
|
586
588
|
| Kotlin | `data class ListTodosRow` + `fromRow` and `<Object>Queries.listTodos(client, listId): List<ListTodosRow>` + `listTodosTables` |
|
|
587
589
|
| Dart | `class ListTodosRow` + `fromRow` and `syncularListTodosQuery(client, listId): List<ListTodosRow>` + `syncularListTodosQueryTables` |
|
|
590
|
+
| Rust | `list_todos::{Row, Params, DESCRIPTOR, select, run, snapshot}` with strict decoding, `i64` fidelity, reactive dependencies, `WindowCoverage`, and proven `row_key` |
|
|
588
591
|
|
|
589
592
|
Each projection row is its **own** generated type per query (the drift-kill:
|
|
590
|
-
the row shape is exactly what the SELECT returns).
|
|
591
|
-
|
|
592
|
-
|
|
593
|
+
the row shape is exactly what the SELECT returns). Swift/Kotlin/Dart rows use
|
|
594
|
+
their wrapper `fromRow` mapping. Rust returns a query/column-specific error for
|
|
595
|
+
missing or malformed values and accepts the client's lossless `$bigint` and
|
|
596
|
+
`$bytes` envelopes. `--check` gates every queries file byte-exactly, like the
|
|
593
597
|
schema files; each carries the DO-NOT-EDIT header + IR hash.
|
|
594
598
|
|
|
599
|
+
Rust is object-only in the manifest:
|
|
600
|
+
|
|
601
|
+
```json
|
|
602
|
+
{
|
|
603
|
+
"output": {
|
|
604
|
+
"rust": {
|
|
605
|
+
"queriesPath": "./src/syncular_queries.rs",
|
|
606
|
+
"clientCrate": "syncular_client"
|
|
607
|
+
}
|
|
608
|
+
}
|
|
609
|
+
}
|
|
610
|
+
```
|
|
611
|
+
|
|
612
|
+
Each query is a snake-case module. Required inputs go through `Params::new`;
|
|
613
|
+
optional nullable inputs use `SyqlPresence<Option<T>>`; sort profiles are
|
|
614
|
+
closed enums; and `select(¶ms)` exposes the exact checked SQL and binds for
|
|
615
|
+
diagnostics. `run` executes a typed local read. `snapshot` returns typed rows,
|
|
616
|
+
the local revision, and coverage from one SQLite read snapshot. The generated
|
|
617
|
+
`DESCRIPTOR` contains the QueryIR hash identity, tables, dependencies,
|
|
618
|
+
coverage, plan selector, and optional proven row-key function. It deliberately
|
|
619
|
+
does not prescribe a Rust UI observer.
|
|
620
|
+
|
|
621
|
+
TypeScript named queries also emit one `mapRow` decoder per projection. The
|
|
622
|
+
direct async runner and the React descriptor share that decoder, so a boolean
|
|
623
|
+
field is always a JavaScript boolean on the first read and every reactive
|
|
624
|
+
re-read (`0` → false, finite non-zero → true, an existing boolean is
|
|
625
|
+
preserved, and nullable booleans preserve `null`). A value that does not match
|
|
626
|
+
the analyzed result type throws `QueryResultDecodeError`; raw `client.query()`
|
|
627
|
+
and `useRawSql()` remain storage-shaped unless the caller supplies a mapper.
|
|
628
|
+
|
|
595
629
|
**React helper.** `@syncular/react` exports `useQuery(query, params?)`,
|
|
596
630
|
which takes the TS `NamedQuery` descriptor and observes the client-scoped
|
|
597
631
|
revisioned store:
|