arcane-os 0.66.0 → 0.68.0
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/CHANGELOG.md +42 -0
- package/README.md +1 -1
- package/browser-runtime/ai/core-image.mjs +84 -34
- package/browser-runtime/ai/core-local.mjs +195 -43
- package/browser-runtime/ai/core-onnx.mjs +71 -12
- package/docs/reference/README.md +6 -0
- package/docs/reference/availability-and-normalization.md +1 -0
- package/docs/reference/core-native-packaging.md +11 -4
- package/docs/reference/core-repositories.md +93 -9
- package/docs/reference/core-runtime.md +46 -5
- package/docs/reference/inventory/package-api.json +62 -20
- package/docs/reference/inventory/runtime-components.json +2 -1
- package/docs/reference/inventory/runtime-modules.json +3 -3
- package/docs/reference/local-ai.md +112 -2
- package/docs/reference/local-image-generation.md +15 -4
- package/docs/reference/model-assets.md +50 -3
- package/docs/reference/native-decisions.md +181 -0
- package/docs/reference/runtime-components.md +62 -5
- package/docs/reference/runtime-modules.md +44 -7
- package/docs/reference/sdk-api.md +229 -19
- package/package.json +5 -2
- package/runtime/arcane/components/theme-switcher.html +112 -13
- package/runtime/arcane/modules/PreferenceStore.js +18 -13
- package/runtime/arcane/modules/SystemAppearance.js +24 -6
- package/src/core/repositories.mjs +27 -8
- package/src/core/runtime.mjs +26 -1
- package/src/core/services/decisions.mjs +144 -0
- package/src/core/services/local-ai.mjs +31 -9
- package/src/core/services/model-assets.mjs +98 -13
- package/src/git-identity.mjs +22 -58
- package/src/local-ai/decision-tokenizer-worker.mjs +31 -0
- package/src/local-ai/decision-tokenizer.mjs +109 -0
- package/src/local-ai/decisions.mjs +273 -0
- package/src/local-ai/dev.mjs +8 -2
- package/src/local-ai/onnx-worker.mjs +67 -7
- package/src/local-ai/onnx.mjs +23 -12
- package/src/native/portable-layout.mjs +8 -3
- package/src/repository.mjs +144 -4
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,47 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## 0.68.0
|
|
4
|
+
|
|
5
|
+
- Add per-instance theme-switcher `configure({modes,labels})` and initial
|
|
6
|
+
`data-modes` / `data-system-label` presentation. Applications can select
|
|
7
|
+
Light / Dark / System with complete readable labels while the default
|
|
8
|
+
Auto / Light / Dark / Skin choices remain unchanged. Preserve selected,
|
|
9
|
+
disabled and keyboard-focus states with wrapping based on component space.
|
|
10
|
+
- Distinguish a wholly absent Core namespace from a missing method in a
|
|
11
|
+
registered service. Retain `METHOD_NOT_ALLOWED` and add exact `method`,
|
|
12
|
+
`namespace` and `reason` lookup metadata; genuine handler errors remain intact.
|
|
13
|
+
- Let the default preference adapter complete single operations through its
|
|
14
|
+
existing app-scoped local store only after an exact absent preferences
|
|
15
|
+
namespace response, retaining cancellation, disposal and full values.
|
|
16
|
+
An advertised rejected atomic batch is never retried as serial writes.
|
|
17
|
+
- Treat an exactly absent optional appearance namespace as unsupported, keeping
|
|
18
|
+
the original diagnostic. Preserve partial-service and genuine errors, the
|
|
19
|
+
existing theme persistence order, native window theming and app-owned host
|
|
20
|
+
preferences. No OS-wide appearance change, migration or dependency is added.
|
|
21
|
+
|
|
22
|
+
## 0.67.0
|
|
23
|
+
|
|
24
|
+
- Add native Laya FP32 typed decisions through `arcane-os/local-ai/decisions`
|
|
25
|
+
and `arcane-os/core/decisions`, using the existing native ONNX and model-assets
|
|
26
|
+
owners plus the approved `@huggingface/tokenizers@0.2.0` Worker dependency.
|
|
27
|
+
Explicit activation preserves complete rows, graph outputs, ordered results,
|
|
28
|
+
current-state replay, cancellation and actual worker-exit file lifetime.
|
|
29
|
+
- Compose selected native services through one Core owner, prepare complete
|
|
30
|
+
model files through the existing asset owner, and expose actual GPU-provider
|
|
31
|
+
attempts with CPU fallback. Accepted configuration does not prove GPU execution.
|
|
32
|
+
- Follow late Core client installation and retirement in default AI accessors.
|
|
33
|
+
Keep explicit clients fixed, model observation non-loading and disposal tied
|
|
34
|
+
to actual retained ownership. Preserve recoverable native inference errors
|
|
35
|
+
without retiring a healthy session or cancelling sibling work; terminal
|
|
36
|
+
stopping revokes readiness while resources remain retained until actual exit.
|
|
37
|
+
- Add repository `configuration()` observations and captured `target:{remote,ref}`
|
|
38
|
+
options for ordinary fast-forward pull, non-force push and write. Preserve
|
|
39
|
+
complete configuration values, payloads and failures without switching branches,
|
|
40
|
+
rewriting Git configuration or changing omitted-target behavior.
|
|
41
|
+
- Keep theme controls, shared same-app host discovery and optional NPU asset
|
|
42
|
+
transport follow-through separate. No app data migration or automatic model
|
|
43
|
+
activation is introduced; applications own their selections and orchestration.
|
|
44
|
+
|
|
3
45
|
## 0.66.0
|
|
4
46
|
|
|
5
47
|
- Add `readGitIdentity` from `arcane-os/core/repositories` for separate global,
|
package/README.md
CHANGED
|
@@ -20,7 +20,7 @@ selected SDK projection or an explicit live SDK source mount. Both profiles
|
|
|
20
20
|
share the theme, packaging, event, cancellation,
|
|
21
21
|
and browser run contracts while retaining their selected application layout.
|
|
22
22
|
|
|
23
|
-
This checkout defines the `0.
|
|
23
|
+
This checkout defines the `0.68.0` SDK contract. Development applications declare
|
|
24
24
|
`arcane-os` as `latest` and retain their lockfile. Exact SDK pins begin when Roshi
|
|
25
25
|
designates a production build. Follow [Consumer updates](docs/consumer-updates.md)
|
|
26
26
|
to refresh and compare the installed SDK and lockfile with the published channel;
|
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import Is from '../dependencies/strong-type/index.js';
|
|
2
|
-
import {
|
|
2
|
+
import {subscribeCoreClient} from '../core/client.mjs';
|
|
3
3
|
import {CoreError, serializeCoreError} from '../core/contracts.mjs';
|
|
4
4
|
import {createArcaneEventSource} from '../event-manager.mjs';
|
|
5
5
|
|
|
@@ -50,7 +50,7 @@ async function encodeImage(image, signal) {
|
|
|
50
50
|
|
|
51
51
|
/** Browser access to the selected native image service; no result persistence. */
|
|
52
52
|
export function createCoreImageRuntime(
|
|
53
|
-
{client
|
|
53
|
+
{client: suppliedClient, signal, onEvent} = {}
|
|
54
54
|
) {
|
|
55
55
|
const owner = {};
|
|
56
56
|
const events = createArcaneEventSource(
|
|
@@ -60,26 +60,37 @@ export function createCoreImageRuntime(
|
|
|
60
60
|
const lifetime = new AbortController();
|
|
61
61
|
const lifetimeSignal = signal ? AbortSignal.any([signal, lifetime.signal]) : lifetime.signal;
|
|
62
62
|
const pending = new Set();
|
|
63
|
-
let
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
selectedModel: null,
|
|
68
|
-
loaded: false,
|
|
69
|
-
state: client ? 'unknown' : 'unavailable',
|
|
70
|
-
backend: null,
|
|
71
|
-
devices: [],
|
|
72
|
-
resources: {},
|
|
73
|
-
progress: null,
|
|
74
|
-
error: null,
|
|
75
|
-
models: []
|
|
76
|
-
};
|
|
63
|
+
let client = null;
|
|
64
|
+
let connection = null;
|
|
65
|
+
let stopInstallation;
|
|
66
|
+
let state = emptyState();
|
|
77
67
|
let revision = 0;
|
|
78
68
|
let closed = false;
|
|
79
69
|
let closing;
|
|
80
70
|
|
|
71
|
+
function emptyState(error = null) {
|
|
72
|
+
return {
|
|
73
|
+
id: 'stable-diffusion.cpp',
|
|
74
|
+
installed: false,
|
|
75
|
+
available: false,
|
|
76
|
+
selectedModel: null,
|
|
77
|
+
loaded: false,
|
|
78
|
+
state: client ? 'unknown' : 'unavailable',
|
|
79
|
+
backend: null,
|
|
80
|
+
devices: [],
|
|
81
|
+
resources: {},
|
|
82
|
+
progress: null,
|
|
83
|
+
error: error ? serializeCoreError(error) : null,
|
|
84
|
+
models: []
|
|
85
|
+
};
|
|
86
|
+
}
|
|
87
|
+
|
|
81
88
|
function current() {
|
|
82
|
-
const requests = [...pending].
|
|
89
|
+
const requests = [...pending].filter(
|
|
90
|
+
function currentConnectionRequest(request) {
|
|
91
|
+
return request.connection === connection && !request.signal.aborted;
|
|
92
|
+
}
|
|
93
|
+
).map(
|
|
83
94
|
function requestState(request) {
|
|
84
95
|
return {
|
|
85
96
|
method: request.method,
|
|
@@ -97,7 +108,7 @@ export function createCoreImageRuntime(
|
|
|
97
108
|
return request.status === 'Thinking';
|
|
98
109
|
}
|
|
99
110
|
) ? 'Thinking' : null,
|
|
100
|
-
busy:
|
|
111
|
+
busy: requests.length > 0,
|
|
101
112
|
closed
|
|
102
113
|
};
|
|
103
114
|
}
|
|
@@ -146,8 +157,38 @@ export function createCoreImageRuntime(
|
|
|
146
157
|
publish();
|
|
147
158
|
}
|
|
148
159
|
|
|
149
|
-
|
|
150
|
-
|
|
160
|
+
function bindClient({client: nextClient, error = null}) {
|
|
161
|
+
if (closed || (connection && nextClient === client)) {
|
|
162
|
+
return;
|
|
163
|
+
}
|
|
164
|
+
const previous = connection;
|
|
165
|
+
client = nextClient;
|
|
166
|
+
const currentConnection = {client, controller: new AbortController(), unsubscribe: null};
|
|
167
|
+
connection = currentConnection;
|
|
168
|
+
revision += 1;
|
|
169
|
+
state = emptyState(error);
|
|
170
|
+
previous?.unsubscribe?.();
|
|
171
|
+
previous?.controller.abort();
|
|
172
|
+
if (client) {
|
|
173
|
+
currentConnection.unsubscribe = client.events.on(
|
|
174
|
+
'image.state',
|
|
175
|
+
function currentImageState(value) {
|
|
176
|
+
if (connection === currentConnection) accept(value);
|
|
177
|
+
}
|
|
178
|
+
);
|
|
179
|
+
}
|
|
180
|
+
publish();
|
|
181
|
+
if (!closed && connection === currentConnection && client) {
|
|
182
|
+
// Observe only; installation never loads an engine or model.
|
|
183
|
+
inspect().catch(
|
|
184
|
+
function initialImageStateUnavailable(error) {
|
|
185
|
+
if (!closed && connection === currentConnection && !currentConnection.controller.signal.aborted) {
|
|
186
|
+
reportObserverFailure(error);
|
|
187
|
+
}
|
|
188
|
+
}
|
|
189
|
+
);
|
|
190
|
+
}
|
|
191
|
+
}
|
|
151
192
|
|
|
152
193
|
function invoke(method, parameters, {signal: requestSignal, onProgress} = {}) {
|
|
153
194
|
if (closed) {
|
|
@@ -156,11 +197,15 @@ export function createCoreImageRuntime(
|
|
|
156
197
|
if (!client) {
|
|
157
198
|
throw unavailable('Local image generation requires an available Core connection.');
|
|
158
199
|
}
|
|
159
|
-
const
|
|
160
|
-
|
|
200
|
+
const currentConnection = connection;
|
|
201
|
+
const operationSignal = AbortSignal.any(
|
|
202
|
+
[lifetimeSignal, currentConnection.controller.signal, ...(requestSignal ? [requestSignal] : [])]
|
|
203
|
+
);
|
|
161
204
|
operationSignal.throwIfAborted();
|
|
162
205
|
const request = {
|
|
163
206
|
method,
|
|
207
|
+
connection: currentConnection,
|
|
208
|
+
signal: operationSignal,
|
|
164
209
|
revision,
|
|
165
210
|
streamId: parameters.streamId,
|
|
166
211
|
status: method === 'image.generate' || method === 'image.edit' ? 'Thinking' : null,
|
|
@@ -169,7 +214,7 @@ export function createCoreImageRuntime(
|
|
|
169
214
|
};
|
|
170
215
|
let stopProgress;
|
|
171
216
|
if (request.streamId) {
|
|
172
|
-
stopProgress = client.events.on(
|
|
217
|
+
stopProgress = currentConnection.client.events.on(
|
|
173
218
|
'image.progress',
|
|
174
219
|
function imageProgress(value) {
|
|
175
220
|
if (closed || operationSignal.aborted || value.streamId !== request.streamId) {
|
|
@@ -202,7 +247,7 @@ export function createCoreImageRuntime(
|
|
|
202
247
|
{type: 'image.request', data: {method, parameters: requestParameters}}
|
|
203
248
|
);
|
|
204
249
|
operationSignal.throwIfAborted();
|
|
205
|
-
const result = await client.invoke(
|
|
250
|
+
const result = await currentConnection.client.invoke(
|
|
206
251
|
method,
|
|
207
252
|
requestParameters,
|
|
208
253
|
{signal: operationSignal, timeoutMs: 0}
|
|
@@ -238,7 +283,7 @@ export function createCoreImageRuntime(
|
|
|
238
283
|
function releaseImageRequest() {
|
|
239
284
|
stopProgress?.();
|
|
240
285
|
pending.delete(request);
|
|
241
|
-
if (!closed) {
|
|
286
|
+
if (!closed && connection === currentConnection) {
|
|
242
287
|
publish();
|
|
243
288
|
}
|
|
244
289
|
}
|
|
@@ -251,12 +296,14 @@ export function createCoreImageRuntime(
|
|
|
251
296
|
|
|
252
297
|
async function inspect({signal: requestSignal} = {}) {
|
|
253
298
|
const before = revision;
|
|
299
|
+
const currentConnection = connection;
|
|
254
300
|
try {
|
|
255
301
|
const result = await invoke(
|
|
256
302
|
'image.status',
|
|
257
303
|
{},
|
|
258
304
|
{signal: requestSignal}
|
|
259
305
|
);
|
|
306
|
+
currentConnection.controller.signal.throwIfAborted();
|
|
260
307
|
if (!closed && revision === before) {
|
|
261
308
|
accept(result);
|
|
262
309
|
}
|
|
@@ -273,11 +320,13 @@ export function createCoreImageRuntime(
|
|
|
273
320
|
|
|
274
321
|
async function load({model, context, assetProjectionId, resourcePaths, signal: requestSignal} = {}) {
|
|
275
322
|
const before = revision;
|
|
323
|
+
const currentConnection = connection;
|
|
276
324
|
const result = await invoke(
|
|
277
325
|
'image.load',
|
|
278
326
|
{model, context, assetProjectionId, resourcePaths},
|
|
279
327
|
{signal: requestSignal}
|
|
280
328
|
);
|
|
329
|
+
currentConnection.controller.signal.throwIfAborted();
|
|
281
330
|
if (!closed && revision === before) {
|
|
282
331
|
accept(result);
|
|
283
332
|
}
|
|
@@ -308,11 +357,13 @@ export function createCoreImageRuntime(
|
|
|
308
357
|
|
|
309
358
|
async function unload({signal: requestSignal} = {}) {
|
|
310
359
|
const before = revision;
|
|
360
|
+
const currentConnection = connection;
|
|
311
361
|
const result = await invoke(
|
|
312
362
|
'image.unload',
|
|
313
363
|
{},
|
|
314
364
|
{signal: requestSignal}
|
|
315
365
|
);
|
|
366
|
+
currentConnection.controller.signal.throwIfAborted();
|
|
316
367
|
if (!closed && revision === before) {
|
|
317
368
|
accept(result);
|
|
318
369
|
}
|
|
@@ -365,8 +416,10 @@ export function createCoreImageRuntime(
|
|
|
365
416
|
);
|
|
366
417
|
lifetime.abort();
|
|
367
418
|
lifetimeSignal.removeEventListener('abort', close);
|
|
368
|
-
|
|
369
|
-
|
|
419
|
+
stopInstallation?.();
|
|
420
|
+
connection?.unsubscribe?.();
|
|
421
|
+
connection?.controller.abort();
|
|
422
|
+
state = {...state, available: false, loaded: false, state: 'closed'};
|
|
370
423
|
publish();
|
|
371
424
|
events.dispose();
|
|
372
425
|
return closing;
|
|
@@ -379,13 +432,10 @@ export function createCoreImageRuntime(
|
|
|
379
432
|
);
|
|
380
433
|
if (lifetimeSignal.aborted) {
|
|
381
434
|
close();
|
|
382
|
-
} else if (
|
|
383
|
-
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
globalThis.console?.error('Core image initial state unavailable.', error);
|
|
387
|
-
}
|
|
388
|
-
);
|
|
435
|
+
} else if (suppliedClient === undefined) {
|
|
436
|
+
stopInstallation = subscribeCoreClient(bindClient, {signal: lifetimeSignal});
|
|
437
|
+
} else {
|
|
438
|
+
bindClient({client: suppliedClient});
|
|
389
439
|
}
|
|
390
440
|
|
|
391
441
|
return {load, generate, edit, unload, inspect, current, subscribe, close};
|