create-syncular-app 0.15.19 → 0.15.21

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 CHANGED
@@ -62,8 +62,8 @@ scaffolder logic. For each template it:
62
62
 
63
63
  1. scaffolds into a temp dir (`--local`),
64
64
  2. asserts the tree shape + placeholder substitution + package.json rewrite,
65
- 3. runs `syncular generate --check` — proving the committed
66
- `syncular.generated.ts` is byte-fresh,
65
+ 3. runs `syncular generate --check` — proving immutable migration history and
66
+ the committed `syncular.generated.ts` are byte-fresh,
67
67
  4. links a `node_modules` into the temp dir **offline** (see
68
68
  [`test/link-workspace.ts`](./test/link-workspace.ts): `@syncular/*` →
69
69
  the real package dirs, external deps → the workspace `.bun` hoist store),
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "create-syncular-app",
3
- "version": "0.15.19",
3
+ "version": "0.15.21",
4
4
  "description": "Scaffold a new Syncular app: `create-syncular-app`",
5
5
  "license": "Apache-2.0",
6
6
  "author": "Benjamin Kniffler",
@@ -49,6 +49,6 @@
49
49
  "!dist/**/*.test.d.ts"
50
50
  ],
51
51
  "devDependencies": {
52
- "@syncular/typegen": "0.15.19"
52
+ "@syncular/typegen": "0.15.21"
53
53
  }
54
54
  }
@@ -20,6 +20,7 @@ bun run clients # terminal 2 — prints "✓ converged"
20
20
  | File | What it is |
21
21
  |---|---|
22
22
  | `syncular.json` + `migrations/` | The schema manifest and SQL — typegen's input |
23
+ | `syncular.migrations.lock.json` | Immutable checksums/layout evidence for deployed migrations (committed) |
23
24
  | `src/syncular.generated.ts` | Generated by `syncular generate` (committed; regenerate on schema change) |
24
25
  | `src/server.ts` | The whole sync backend in one Bun process |
25
26
  | `src/make-client.ts` | Constructs one `SyncClient` on bun:sqlite + fetch |
@@ -31,11 +32,15 @@ bun run clients # terminal 2 — prints "✓ converged"
31
32
  1. **`src/server.ts` → `resolveScopes`** — the whole authorization story. It
32
33
  runs in your backend next to your auth. The starter returns `['*']` (see
33
34
  everything); a real one returns the scope values the authenticated actor may
34
- see.
35
+ see. Multiple variables are independent, not correlated parent/child tuples:
36
+ test isolation with at least two parents and child IDs, and carry the parent
37
+ scope on every child table before using a child wildcard. See
38
+ [Scopes & authorization](https://syncular.dev/concepts-scopes/).
35
39
  2. **`src/server.ts` → `authenticate`** — plug in your real session/token
36
40
  check; return `{ actorId, partition }` or `null` for a 401.
37
- 3. **`migrations/` + `syncular.json`** — add tables and scopes, then
38
- `bun run generate` to refresh the typed schema.
41
+ 3. **`migrations/` + `syncular.json`** — append migrations and add tables or
42
+ scopes, then `bun run generate` to refresh the lock and typed schema. Never
43
+ edit a migration after deployment.
39
44
 
40
45
  ## Next
41
46
 
@@ -0,0 +1,37 @@
1
+ {
2
+ "formatVersion": 1,
3
+ "migrations": [
4
+ {
5
+ "name": "0001_initial",
6
+ "sha256": "355c1e3c68757f31a3fdd9b640982317df7f44566741e7686e51029e4c4fe4cc",
7
+ "tables": [
8
+ {
9
+ "name": "notes",
10
+ "primaryKey": "id",
11
+ "columns": [
12
+ {
13
+ "name": "id",
14
+ "type": "string",
15
+ "nullable": false
16
+ },
17
+ {
18
+ "name": "list_id",
19
+ "type": "string",
20
+ "nullable": false
21
+ },
22
+ {
23
+ "name": "body",
24
+ "type": "string",
25
+ "nullable": false
26
+ },
27
+ {
28
+ "name": "updated_at_ms",
29
+ "type": "integer",
30
+ "nullable": false
31
+ }
32
+ ]
33
+ }
34
+ ]
35
+ }
36
+ ]
37
+ }
@@ -47,6 +47,7 @@ Prerequisites: [Rust](https://rustup.rs) and the
47
47
  | File | What it is |
48
48
  |---|---|
49
49
  | `syncular.json` + `migrations/` + `queries/` | Schema and named-query inputs |
50
+ | `syncular.migrations.lock.json` | Immutable deployed-migration checksums/layout evidence (committed) |
50
51
  | `src/syncular.generated.ts` + `src/syncular.queries.ts` | Generated descriptors (committed) |
51
52
  | `src/server.ts` | Sync server + WebSocket + the web frontend, one Bun process |
52
53
  | `src/frontend/engine.ts` | **The seam**: picks worker core vs native core |
@@ -76,15 +77,19 @@ On desktop, the plugin owns the database path and the transport — see
76
77
 
77
78
  1. **`src/server.ts` → `resolveScopes`** — the whole authorization story. The
78
79
  starter returns `['*']`; a real one returns the scope values the
79
- authenticated actor may see.
80
+ authenticated actor may see. Multiple variables are independent, not
81
+ correlated parent/child tuples: test isolation with at least two parents and
82
+ child IDs, and carry the parent scope on every child table before using a
83
+ child wildcard. See
84
+ [Scopes & authorization](https://syncular.dev/concepts-scopes/).
80
85
  2. **`src/server.ts` → `authenticate`** — plug in your real session/token
81
86
  check; return `{ actorId, partition }` or `null` for a 401.
82
87
  3. **`src-tauri/src/lib.rs` → `base_url`** — point the native core at your
83
88
  deployed sync endpoint (rotating auth goes through `client.setHeaders`).
84
89
  4. **`src/frontend/main.tsx`** — the UI. Everything under `<SyncProvider>` is
85
90
  shared code; grow it into your app.
86
- 5. **`migrations/` + `syncular.json`** — add tables and scopes, then
87
- `bun run generate`.
91
+ 5. **`migrations/` + `syncular.json`** — append migrations and add tables or
92
+ scopes, then `bun run generate`. Never edit a migration after deployment.
88
93
 
89
94
  ## Next
90
95
 
@@ -21,7 +21,7 @@ tauri = { version = "2", features = [] }
21
21
  # The syncular plugin from crates.io. `native-transport` gives the core its
22
22
  # real HTTP + WebSocket transport (ureq + tungstenite) inside the host
23
23
  # process — the webview never talks to the sync server directly.
24
- tauri-plugin-syncular = { version = "0.15.19", features = ["native-transport"] }
24
+ tauri-plugin-syncular = { version = "0.15.21", features = ["native-transport"] }
25
25
 
26
26
  [features]
27
27
  default = []
@@ -0,0 +1,47 @@
1
+ {
2
+ "formatVersion": 1,
3
+ "migrations": [
4
+ {
5
+ "name": "0001_initial",
6
+ "sha256": "87b23cd0f8e3677ca6fa7ca67eb7c8373a285607b6de10854cc43df1290bb0fa",
7
+ "tables": [
8
+ {
9
+ "name": "todos",
10
+ "primaryKey": "id",
11
+ "columns": [
12
+ {
13
+ "name": "id",
14
+ "type": "string",
15
+ "nullable": false
16
+ },
17
+ {
18
+ "name": "list_id",
19
+ "type": "string",
20
+ "nullable": false
21
+ },
22
+ {
23
+ "name": "title",
24
+ "type": "string",
25
+ "nullable": false
26
+ },
27
+ {
28
+ "name": "done",
29
+ "type": "boolean",
30
+ "nullable": false
31
+ },
32
+ {
33
+ "name": "position",
34
+ "type": "integer",
35
+ "nullable": false
36
+ },
37
+ {
38
+ "name": "updated_at_ms",
39
+ "type": "integer",
40
+ "nullable": false
41
+ }
42
+ ]
43
+ }
44
+ ]
45
+ }
46
+ ]
47
+ }
@@ -30,6 +30,7 @@ covered by `tsc`).
30
30
  | File | What it is |
31
31
  |---|---|
32
32
  | `syncular.json` + `migrations/` | The schema manifest and SQL — typegen's input |
33
+ | `syncular.migrations.lock.json` | Immutable deployed-migration checksums/layout evidence (committed) |
33
34
  | `src/syncular.generated.ts` | Generated by `syncular generate` (committed) |
34
35
  | `src/server.ts` | Sync server + WebSocket + static frontend, one Bun process |
35
36
  | `src/frontend/main.ts` | The single-pane UI, driving a worker core via RPC |
@@ -41,13 +42,17 @@ covered by `tsc`).
41
42
 
42
43
  1. **`src/server.ts` → `resolveScopes`** — the whole authorization story. It
43
44
  runs in your backend next to your auth. The starter returns `['*']`; a real
44
- one returns the scope values the authenticated actor may see.
45
+ one returns the scope values the authenticated actor may see. Multiple
46
+ variables are independent, not correlated parent/child tuples: test
47
+ isolation with at least two parents and child IDs, and carry the parent scope
48
+ on every child table before using a child wildcard. See
49
+ [Scopes & authorization](https://syncular.dev/concepts-scopes/).
45
50
  2. **`src/server.ts` → `authenticate`** — plug in your real session/token
46
51
  check; return `{ actorId, partition }` or `null` for a 401.
47
52
  3. **`src/frontend/main.ts`** — the UI. It queries and mutates through the
48
53
  worker handle; grow it into your app.
49
- 4. **`migrations/` + `syncular.json`** — add tables and scopes, then
50
- `bun run generate`.
54
+ 4. **`migrations/` + `syncular.json`** — append migrations and add tables or
55
+ scopes, then `bun run generate`. Never edit a migration after deployment.
51
56
 
52
57
  ## How the frontend is served
53
58
 
@@ -0,0 +1,47 @@
1
+ {
2
+ "formatVersion": 1,
3
+ "migrations": [
4
+ {
5
+ "name": "0001_initial",
6
+ "sha256": "87b23cd0f8e3677ca6fa7ca67eb7c8373a285607b6de10854cc43df1290bb0fa",
7
+ "tables": [
8
+ {
9
+ "name": "todos",
10
+ "primaryKey": "id",
11
+ "columns": [
12
+ {
13
+ "name": "id",
14
+ "type": "string",
15
+ "nullable": false
16
+ },
17
+ {
18
+ "name": "list_id",
19
+ "type": "string",
20
+ "nullable": false
21
+ },
22
+ {
23
+ "name": "title",
24
+ "type": "string",
25
+ "nullable": false
26
+ },
27
+ {
28
+ "name": "done",
29
+ "type": "boolean",
30
+ "nullable": false
31
+ },
32
+ {
33
+ "name": "position",
34
+ "type": "integer",
35
+ "nullable": false
36
+ },
37
+ {
38
+ "name": "updated_at_ms",
39
+ "type": "integer",
40
+ "nullable": false
41
+ }
42
+ ]
43
+ }
44
+ ]
45
+ }
46
+ ]
47
+ }