@puredesktop/create-app 2.1.9 → 2.1.10
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/bin/create-puredesktop-app.mjs +70 -338
- package/package.json +3 -2
- package/template/README.md +3 -3
- package/template/docs/README.md +9 -8
- package/template/docs/howtos/persisting-app-state.md +242 -242
- package/template/docs/howtos/using-document-editor.md +440 -0
- package/template/docs/plugin-manifest.md +1 -1
- package/template/docs/ui-and-components.md +84 -79
- package/template/gitignore.tpl +6 -1
- package/template/package.json +1 -1
- package/template/plugin.json +1 -1
- package/template/scripts/validate-puredesktop-app.mjs +46 -46
- package/template/src/App.tsx +8 -8
- package/template/src/components/AppShell.tsx +11 -11
- package/template/src/components/StarterWorkspace.tsx +154 -154
- package/template/src/constants.ts +2 -2
- package/template/src/lib/starterWorkspace.ts +29 -29
- package/template/vite.config.js +13 -13
|
@@ -1,242 +1,242 @@
|
|
|
1
|
-
# Persisting App State
|
|
2
|
-
|
|
3
|
-
PureDesktop apps persist non-document state through UI bridge helpers. This
|
|
4
|
-
state is app-owned: the app defines the TypeScript type, default value, parser,
|
|
5
|
-
and update commands.
|
|
6
|
-
|
|
7
|
-
## State Surfaces
|
|
8
|
-
|
|
9
|
-
| State | Helper | Permission |
|
|
10
|
-
| --- | --- | --- |
|
|
11
|
-
| Small app preferences | `usePlatformAppSettings` | `settings` |
|
|
12
|
-
| Internal JSON records | `usePlatformJsonStore` | `filesystem` |
|
|
13
|
-
|
|
14
|
-
Use document lifecycle APIs for user-visible documents, drafts, recents, rename,
|
|
15
|
-
duplicate, and open/save workflows.
|
|
16
|
-
|
|
17
|
-
## Generated App Wiring
|
|
18
|
-
|
|
19
|
-
The generated app already has the bridge readiness boundary:
|
|
20
|
-
|
|
21
|
-
- `src/App.tsx` calls `usePlatformBridge()` and receives `ready`.
|
|
22
|
-
- `src/App.tsx` calls `useAppBoot(ready || standaloneDev)`.
|
|
23
|
-
- `src/hooks/useAppBoot.ts` loads startup settings through the app bridge.
|
|
24
|
-
- `src/components/AppShell.tsx` receives boot data as props.
|
|
25
|
-
|
|
26
|
-
Use that structure instead of adding bridge calls inside components.
|
|
27
|
-
|
|
28
|
-
When state is read once at startup, `useAppBoot` can load it and pass it down.
|
|
29
|
-
When state can change while the app is open, create a dedicated hook in
|
|
30
|
-
`src/hooks/` that calls the platform helper and exposes typed commands.
|
|
31
|
-
|
|
32
|
-
## Add Editable App Settings
|
|
33
|
-
|
|
34
|
-
1. Create or reuse the domain folder under `src/lib/<domain>/`.
|
|
35
|
-
2. Define the settings type, default value, and parser in that domain folder.
|
|
36
|
-
3. Create `src/hooks/use<Domain>Settings.ts`.
|
|
37
|
-
4. Inside that hook, call `usePlatformAppSettings`.
|
|
38
|
-
5. Pass `APP_SLUG` and the bridge `ready` value to the hook.
|
|
39
|
-
6. Return typed settings plus app-specific command functions.
|
|
40
|
-
7. Components call those command functions; they do not build settings patches.
|
|
41
|
-
|
|
42
|
-
Hook shape:
|
|
43
|
-
|
|
44
|
-
```text
|
|
45
|
-
use real domain settings type
|
|
46
|
-
call usePlatformAppSettings with APP_SLUG, ready, default settings, parser
|
|
47
|
-
return settings, loading, error
|
|
48
|
-
return field-specific commands that call patchSettings
|
|
49
|
-
```
|
|
50
|
-
|
|
51
|
-
Field-specific commands own the settings patch. Components call the command; they
|
|
52
|
-
do not assemble the patch object.
|
|
53
|
-
|
|
54
|
-
## Add An Internal JSON Store
|
|
55
|
-
|
|
56
|
-
1. Add `filesystem` to `plugin.json`.
|
|
57
|
-
2. Create or reuse the domain folder under `src/lib/<domain>/`.
|
|
58
|
-
3. Define the store type, empty value, parser, and pure update helpers in that
|
|
59
|
-
domain folder.
|
|
60
|
-
4. Create `src/hooks/use<Domain>Store.ts`.
|
|
61
|
-
5. Inside that hook, call `usePlatformJsonStore`.
|
|
62
|
-
6. Use a file name that includes `APP_SLUG` and the real persisted record name.
|
|
63
|
-
7. Return typed store state plus app-specific command functions.
|
|
64
|
-
8. Components call those command functions; they do not edit raw JSON objects.
|
|
65
|
-
|
|
66
|
-
Hook shape:
|
|
67
|
-
|
|
68
|
-
```text
|
|
69
|
-
use real domain store type
|
|
70
|
-
call usePlatformJsonStore with APP_SLUG, ready, file name, empty store, parser
|
|
71
|
-
return store, loading, saving, error
|
|
72
|
-
return domain commands that call updateValue with pure update functions
|
|
73
|
-
```
|
|
74
|
-
|
|
75
|
-
Domain commands own the store update. Components call the command; they do not
|
|
76
|
-
edit raw JSON objects. Store update functions must return new store objects.
|
|
77
|
-
|
|
78
|
-
## App Settings
|
|
79
|
-
|
|
80
|
-
Import:
|
|
81
|
-
|
|
82
|
-
```ts
|
|
83
|
-
import { usePlatformAppSettings } from '@puredesktop/puredesktop-ui-bridge/bridge/react/usePlatformAppSettings'
|
|
84
|
-
```
|
|
85
|
-
|
|
86
|
-
Use for small app preferences such as current mode, sorting, filtering, and
|
|
87
|
-
lightweight options.
|
|
88
|
-
|
|
89
|
-
Options:
|
|
90
|
-
|
|
91
|
-
```ts
|
|
92
|
-
{
|
|
93
|
-
appSlug: string | null
|
|
94
|
-
enabled?: boolean
|
|
95
|
-
initialSettings?: TSettings
|
|
96
|
-
parse?: (value: Record<string, unknown>) => TSettings
|
|
97
|
-
}
|
|
98
|
-
```
|
|
99
|
-
|
|
100
|
-
Returns:
|
|
101
|
-
|
|
102
|
-
```ts
|
|
103
|
-
{
|
|
104
|
-
settings: TSettings
|
|
105
|
-
loading: boolean
|
|
106
|
-
error: Error | null
|
|
107
|
-
patchSettings: (patch: Record<string, unknown>) => Promise<TSettings>
|
|
108
|
-
reload: () => void
|
|
109
|
-
}
|
|
110
|
-
```
|
|
111
|
-
|
|
112
|
-
Behavior:
|
|
113
|
-
|
|
114
|
-
- loads through `settings.app.get`;
|
|
115
|
-
- saves through `settings.app.update`;
|
|
116
|
-
- `patchSettings` shallow-merges the patch in shell preferences;
|
|
117
|
-
- the shell stores app settings under the current app slug;
|
|
118
|
-
- the app parser converts persisted `Record<string, unknown>` into the app's
|
|
119
|
-
typed settings object.
|
|
120
|
-
|
|
121
|
-
App ownership:
|
|
122
|
-
|
|
123
|
-
- keep the settings type in app code;
|
|
124
|
-
- keep defaults and parsing in app code;
|
|
125
|
-
- expose typed settings and typed commands to components;
|
|
126
|
-
- use app settings for preferences, not large record collections.
|
|
127
|
-
|
|
128
|
-
## JSON Store
|
|
129
|
-
|
|
130
|
-
Import:
|
|
131
|
-
|
|
132
|
-
```ts
|
|
133
|
-
import { usePlatformJsonStore } from '@puredesktop/puredesktop-ui-bridge/bridge/react/usePlatformJsonStore'
|
|
134
|
-
```
|
|
135
|
-
|
|
136
|
-
Use for internal app records that are larger than settings and are not
|
|
137
|
-
user-visible documents.
|
|
138
|
-
|
|
139
|
-
Options:
|
|
140
|
-
|
|
141
|
-
```ts
|
|
142
|
-
{
|
|
143
|
-
appSlug: string | null
|
|
144
|
-
fileName: `${string}.json` | null
|
|
145
|
-
initialValue: TValue
|
|
146
|
-
enabled?: boolean
|
|
147
|
-
parse?: (value: unknown) => TValue
|
|
148
|
-
}
|
|
149
|
-
```
|
|
150
|
-
|
|
151
|
-
Returns:
|
|
152
|
-
|
|
153
|
-
```ts
|
|
154
|
-
{
|
|
155
|
-
value: TValue
|
|
156
|
-
path: string | null
|
|
157
|
-
loading: boolean
|
|
158
|
-
saving: boolean
|
|
159
|
-
error: Error | null
|
|
160
|
-
saveValue: (next: TValue) => Promise<TValue>
|
|
161
|
-
updateValue: (updater: (current: TValue) => TValue) => Promise<TValue>
|
|
162
|
-
reload: () => void
|
|
163
|
-
}
|
|
164
|
-
```
|
|
165
|
-
|
|
166
|
-
Behavior:
|
|
167
|
-
|
|
168
|
-
- loads through `storage.readJson`;
|
|
169
|
-
- saves through `storage.writeJson`;
|
|
170
|
-
- missing files load as `initialValue`;
|
|
171
|
-
- saved values replace the full JSON value;
|
|
172
|
-
- `updateValue` queues writes and applies each updater to the latest in-memory
|
|
173
|
-
value;
|
|
174
|
-
- `fileName` must be a single `.json` file name;
|
|
175
|
-
- the JSON file is stored in the shell-managed appdata folder.
|
|
176
|
-
|
|
177
|
-
App ownership:
|
|
178
|
-
|
|
179
|
-
- include `filesystem` in `plugin.json`;
|
|
180
|
-
- keep the store type in app code;
|
|
181
|
-
- keep defaults, parsing, and pure update functions in app code;
|
|
182
|
-
- use an app-prefixed file name with the real persisted record name;
|
|
183
|
-
- expose typed state and typed commands to components;
|
|
184
|
-
- never mutate the current store object in place.
|
|
185
|
-
|
|
186
|
-
## File Shape
|
|
187
|
-
|
|
188
|
-
Use one `src/lib/<domain>/` folder per persisted domain. Do not put types,
|
|
189
|
-
defaults, parsing, pure updates, platform hooks, and UI in one file.
|
|
190
|
-
|
|
191
|
-
```text
|
|
192
|
-
src/
|
|
193
|
-
hooks/
|
|
194
|
-
use<Domain>Settings.ts
|
|
195
|
-
use<Domain>Store.ts
|
|
196
|
-
lib/
|
|
197
|
-
<domain>/
|
|
198
|
-
types.ts
|
|
199
|
-
defaults.ts
|
|
200
|
-
parse.ts
|
|
201
|
-
updates.ts
|
|
202
|
-
index.ts
|
|
203
|
-
components/
|
|
204
|
-
```
|
|
205
|
-
|
|
206
|
-
Responsibilities:
|
|
207
|
-
|
|
208
|
-
- `types.ts` exports the persisted domain types.
|
|
209
|
-
- `defaults.ts` exports default settings or empty store values.
|
|
210
|
-
- `parse.ts` converts unknown persisted values into valid domain state.
|
|
211
|
-
- `updates.ts` contains pure functions that return new state objects.
|
|
212
|
-
- `index.ts` re-exports the domain pieces used outside the folder.
|
|
213
|
-
- `src/hooks/use<Domain>Settings.ts` calls `usePlatformAppSettings`.
|
|
214
|
-
- `src/hooks/use<Domain>Store.ts` calls `usePlatformJsonStore`.
|
|
215
|
-
- components import the app-owned hooks and render state.
|
|
216
|
-
|
|
217
|
-
Split a file when it starts owning more than one responsibility. The hook should
|
|
218
|
-
not define the domain model. Components should not parse persisted data. Pure
|
|
219
|
-
update functions should not call platform helpers.
|
|
220
|
-
|
|
221
|
-
## Verification
|
|
222
|
-
|
|
223
|
-
Run:
|
|
224
|
-
|
|
225
|
-
```bash
|
|
226
|
-
npm run typecheck
|
|
227
|
-
npm run build
|
|
228
|
-
npm run puredesktop:check
|
|
229
|
-
```
|
|
230
|
-
|
|
231
|
-
Source checks:
|
|
232
|
-
|
|
233
|
-
- app settings state has a domain settings type, default value, parser, and
|
|
234
|
-
hook;
|
|
235
|
-
- JSON store state has a domain store type, empty value, parser, pure update
|
|
236
|
-
helpers, and hook;
|
|
237
|
-
- components import the app-owned hooks instead of platform persistence helpers;
|
|
238
|
-
- `usePlatformJsonStore` is only imported from app-owned hooks;
|
|
239
|
-
- apps using `usePlatformJsonStore` include `filesystem` in `plugin.json`;
|
|
240
|
-
- JSON store file names include `APP_SLUG` and the real persisted record name;
|
|
241
|
-
- JSON store update functions return new objects instead of mutating existing
|
|
242
|
-
state.
|
|
1
|
+
# Persisting App State
|
|
2
|
+
|
|
3
|
+
PureDesktop apps persist non-document state through UI bridge helpers. This
|
|
4
|
+
state is app-owned: the app defines the TypeScript type, default value, parser,
|
|
5
|
+
and update commands.
|
|
6
|
+
|
|
7
|
+
## State Surfaces
|
|
8
|
+
|
|
9
|
+
| State | Helper | Permission |
|
|
10
|
+
| --- | --- | --- |
|
|
11
|
+
| Small app preferences | `usePlatformAppSettings` | `settings` |
|
|
12
|
+
| Internal JSON records | `usePlatformJsonStore` | `filesystem` |
|
|
13
|
+
|
|
14
|
+
Use document lifecycle APIs for user-visible documents, drafts, recents, rename,
|
|
15
|
+
duplicate, and open/save workflows.
|
|
16
|
+
|
|
17
|
+
## Generated App Wiring
|
|
18
|
+
|
|
19
|
+
The generated app already has the bridge readiness boundary:
|
|
20
|
+
|
|
21
|
+
- `src/App.tsx` calls `usePlatformBridge()` and receives `ready`.
|
|
22
|
+
- `src/App.tsx` calls `useAppBoot(ready || standaloneDev)`.
|
|
23
|
+
- `src/hooks/useAppBoot.ts` loads startup settings through the app bridge.
|
|
24
|
+
- `src/components/AppShell.tsx` receives boot data as props.
|
|
25
|
+
|
|
26
|
+
Use that structure instead of adding bridge calls inside components.
|
|
27
|
+
|
|
28
|
+
When state is read once at startup, `useAppBoot` can load it and pass it down.
|
|
29
|
+
When state can change while the app is open, create a dedicated hook in
|
|
30
|
+
`src/hooks/` that calls the platform helper and exposes typed commands.
|
|
31
|
+
|
|
32
|
+
## Add Editable App Settings
|
|
33
|
+
|
|
34
|
+
1. Create or reuse the domain folder under `src/lib/<domain>/`.
|
|
35
|
+
2. Define the settings type, default value, and parser in that domain folder.
|
|
36
|
+
3. Create `src/hooks/use<Domain>Settings.ts`.
|
|
37
|
+
4. Inside that hook, call `usePlatformAppSettings`.
|
|
38
|
+
5. Pass `APP_SLUG` and the bridge `ready` value to the hook.
|
|
39
|
+
6. Return typed settings plus app-specific command functions.
|
|
40
|
+
7. Components call those command functions; they do not build settings patches.
|
|
41
|
+
|
|
42
|
+
Hook shape:
|
|
43
|
+
|
|
44
|
+
```text
|
|
45
|
+
use real domain settings type
|
|
46
|
+
call usePlatformAppSettings with APP_SLUG, ready, default settings, parser
|
|
47
|
+
return settings, loading, error
|
|
48
|
+
return field-specific commands that call patchSettings
|
|
49
|
+
```
|
|
50
|
+
|
|
51
|
+
Field-specific commands own the settings patch. Components call the command; they
|
|
52
|
+
do not assemble the patch object.
|
|
53
|
+
|
|
54
|
+
## Add An Internal JSON Store
|
|
55
|
+
|
|
56
|
+
1. Add `filesystem` to `plugin.json`.
|
|
57
|
+
2. Create or reuse the domain folder under `src/lib/<domain>/`.
|
|
58
|
+
3. Define the store type, empty value, parser, and pure update helpers in that
|
|
59
|
+
domain folder.
|
|
60
|
+
4. Create `src/hooks/use<Domain>Store.ts`.
|
|
61
|
+
5. Inside that hook, call `usePlatformJsonStore`.
|
|
62
|
+
6. Use a file name that includes `APP_SLUG` and the real persisted record name.
|
|
63
|
+
7. Return typed store state plus app-specific command functions.
|
|
64
|
+
8. Components call those command functions; they do not edit raw JSON objects.
|
|
65
|
+
|
|
66
|
+
Hook shape:
|
|
67
|
+
|
|
68
|
+
```text
|
|
69
|
+
use real domain store type
|
|
70
|
+
call usePlatformJsonStore with APP_SLUG, ready, file name, empty store, parser
|
|
71
|
+
return store, loading, saving, error
|
|
72
|
+
return domain commands that call updateValue with pure update functions
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
Domain commands own the store update. Components call the command; they do not
|
|
76
|
+
edit raw JSON objects. Store update functions must return new store objects.
|
|
77
|
+
|
|
78
|
+
## App Settings
|
|
79
|
+
|
|
80
|
+
Import:
|
|
81
|
+
|
|
82
|
+
```ts
|
|
83
|
+
import { usePlatformAppSettings } from '@puredesktop/puredesktop-ui-bridge/bridge/react/usePlatformAppSettings'
|
|
84
|
+
```
|
|
85
|
+
|
|
86
|
+
Use for small app preferences such as current mode, sorting, filtering, and
|
|
87
|
+
lightweight options.
|
|
88
|
+
|
|
89
|
+
Options:
|
|
90
|
+
|
|
91
|
+
```ts
|
|
92
|
+
{
|
|
93
|
+
appSlug: string | null
|
|
94
|
+
enabled?: boolean
|
|
95
|
+
initialSettings?: TSettings
|
|
96
|
+
parse?: (value: Record<string, unknown>) => TSettings
|
|
97
|
+
}
|
|
98
|
+
```
|
|
99
|
+
|
|
100
|
+
Returns:
|
|
101
|
+
|
|
102
|
+
```ts
|
|
103
|
+
{
|
|
104
|
+
settings: TSettings
|
|
105
|
+
loading: boolean
|
|
106
|
+
error: Error | null
|
|
107
|
+
patchSettings: (patch: Record<string, unknown>) => Promise<TSettings>
|
|
108
|
+
reload: () => void
|
|
109
|
+
}
|
|
110
|
+
```
|
|
111
|
+
|
|
112
|
+
Behavior:
|
|
113
|
+
|
|
114
|
+
- loads through `settings.app.get`;
|
|
115
|
+
- saves through `settings.app.update`;
|
|
116
|
+
- `patchSettings` shallow-merges the patch in shell preferences;
|
|
117
|
+
- the shell stores app settings under the current app slug;
|
|
118
|
+
- the app parser converts persisted `Record<string, unknown>` into the app's
|
|
119
|
+
typed settings object.
|
|
120
|
+
|
|
121
|
+
App ownership:
|
|
122
|
+
|
|
123
|
+
- keep the settings type in app code;
|
|
124
|
+
- keep defaults and parsing in app code;
|
|
125
|
+
- expose typed settings and typed commands to components;
|
|
126
|
+
- use app settings for preferences, not large record collections.
|
|
127
|
+
|
|
128
|
+
## JSON Store
|
|
129
|
+
|
|
130
|
+
Import:
|
|
131
|
+
|
|
132
|
+
```ts
|
|
133
|
+
import { usePlatformJsonStore } from '@puredesktop/puredesktop-ui-bridge/bridge/react/usePlatformJsonStore'
|
|
134
|
+
```
|
|
135
|
+
|
|
136
|
+
Use for internal app records that are larger than settings and are not
|
|
137
|
+
user-visible documents.
|
|
138
|
+
|
|
139
|
+
Options:
|
|
140
|
+
|
|
141
|
+
```ts
|
|
142
|
+
{
|
|
143
|
+
appSlug: string | null
|
|
144
|
+
fileName: `${string}.json` | null
|
|
145
|
+
initialValue: TValue
|
|
146
|
+
enabled?: boolean
|
|
147
|
+
parse?: (value: unknown) => TValue
|
|
148
|
+
}
|
|
149
|
+
```
|
|
150
|
+
|
|
151
|
+
Returns:
|
|
152
|
+
|
|
153
|
+
```ts
|
|
154
|
+
{
|
|
155
|
+
value: TValue
|
|
156
|
+
path: string | null
|
|
157
|
+
loading: boolean
|
|
158
|
+
saving: boolean
|
|
159
|
+
error: Error | null
|
|
160
|
+
saveValue: (next: TValue) => Promise<TValue>
|
|
161
|
+
updateValue: (updater: (current: TValue) => TValue) => Promise<TValue>
|
|
162
|
+
reload: () => void
|
|
163
|
+
}
|
|
164
|
+
```
|
|
165
|
+
|
|
166
|
+
Behavior:
|
|
167
|
+
|
|
168
|
+
- loads through `storage.readJson`;
|
|
169
|
+
- saves through `storage.writeJson`;
|
|
170
|
+
- missing files load as `initialValue`;
|
|
171
|
+
- saved values replace the full JSON value;
|
|
172
|
+
- `updateValue` queues writes and applies each updater to the latest in-memory
|
|
173
|
+
value;
|
|
174
|
+
- `fileName` must be a single `.json` file name;
|
|
175
|
+
- the JSON file is stored in the shell-managed appdata folder.
|
|
176
|
+
|
|
177
|
+
App ownership:
|
|
178
|
+
|
|
179
|
+
- include `filesystem` in `plugin.json`;
|
|
180
|
+
- keep the store type in app code;
|
|
181
|
+
- keep defaults, parsing, and pure update functions in app code;
|
|
182
|
+
- use an app-prefixed file name with the real persisted record name;
|
|
183
|
+
- expose typed state and typed commands to components;
|
|
184
|
+
- never mutate the current store object in place.
|
|
185
|
+
|
|
186
|
+
## File Shape
|
|
187
|
+
|
|
188
|
+
Use one `src/lib/<domain>/` folder per persisted domain. Do not put types,
|
|
189
|
+
defaults, parsing, pure updates, platform hooks, and UI in one file.
|
|
190
|
+
|
|
191
|
+
```text
|
|
192
|
+
src/
|
|
193
|
+
hooks/
|
|
194
|
+
use<Domain>Settings.ts
|
|
195
|
+
use<Domain>Store.ts
|
|
196
|
+
lib/
|
|
197
|
+
<domain>/
|
|
198
|
+
types.ts
|
|
199
|
+
defaults.ts
|
|
200
|
+
parse.ts
|
|
201
|
+
updates.ts
|
|
202
|
+
index.ts
|
|
203
|
+
components/
|
|
204
|
+
```
|
|
205
|
+
|
|
206
|
+
Responsibilities:
|
|
207
|
+
|
|
208
|
+
- `types.ts` exports the persisted domain types.
|
|
209
|
+
- `defaults.ts` exports default settings or empty store values.
|
|
210
|
+
- `parse.ts` converts unknown persisted values into valid domain state.
|
|
211
|
+
- `updates.ts` contains pure functions that return new state objects.
|
|
212
|
+
- `index.ts` re-exports the domain pieces used outside the folder.
|
|
213
|
+
- `src/hooks/use<Domain>Settings.ts` calls `usePlatformAppSettings`.
|
|
214
|
+
- `src/hooks/use<Domain>Store.ts` calls `usePlatformJsonStore`.
|
|
215
|
+
- components import the app-owned hooks and render state.
|
|
216
|
+
|
|
217
|
+
Split a file when it starts owning more than one responsibility. The hook should
|
|
218
|
+
not define the domain model. Components should not parse persisted data. Pure
|
|
219
|
+
update functions should not call platform helpers.
|
|
220
|
+
|
|
221
|
+
## Verification
|
|
222
|
+
|
|
223
|
+
Run:
|
|
224
|
+
|
|
225
|
+
```bash
|
|
226
|
+
npm run typecheck
|
|
227
|
+
npm run build
|
|
228
|
+
npm run puredesktop:check
|
|
229
|
+
```
|
|
230
|
+
|
|
231
|
+
Source checks:
|
|
232
|
+
|
|
233
|
+
- app settings state has a domain settings type, default value, parser, and
|
|
234
|
+
hook;
|
|
235
|
+
- JSON store state has a domain store type, empty value, parser, pure update
|
|
236
|
+
helpers, and hook;
|
|
237
|
+
- components import the app-owned hooks instead of platform persistence helpers;
|
|
238
|
+
- `usePlatformJsonStore` is only imported from app-owned hooks;
|
|
239
|
+
- apps using `usePlatformJsonStore` include `filesystem` in `plugin.json`;
|
|
240
|
+
- JSON store file names include `APP_SLUG` and the real persisted record name;
|
|
241
|
+
- JSON store update functions return new objects instead of mutating existing
|
|
242
|
+
state.
|