arcane-os 0.5.16 → 0.5.18
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 +44 -0
- package/README.md +42 -19
- package/bin/arcane-test.mjs +16 -13
- package/browser-runtime/ai/browser-speech-artifacts.mjs +41 -38
- package/browser-runtime/ai/browser-speech-providers.mjs +53 -46
- package/browser-runtime/ai/browser-wasm-llm-provider.mjs +127 -124
- package/browser-runtime/ai/browser-wasm.mjs +6 -3
- package/browser-runtime/ai/browser-wllama-runtime.mjs +26 -23
- package/browser-runtime/ai/model-controller.mjs +94 -91
- package/browser-runtime/ai/speech-worker-client.mjs +12 -9
- package/browser-runtime/ai/speech-worker-runtime.mjs +56 -53
- package/browser-runtime/dependencies/strong-type/index.js +207 -82
- package/browser-runtime/dependencies/strong-type/package.json +15 -6
- package/browser-runtime/dom-event-instrumentation.mjs +24 -20
- package/browser-runtime/event-manager.mjs +111 -108
- package/browser-runtime/speech-text.mjs +35 -0
- package/docs/architecture.md +1 -1
- package/docs/reference/README.md +8 -8
- package/docs/reference/ai/browser-speech.md +230 -16
- package/docs/reference/ai/twin-cloud.md +1 -1
- package/docs/reference/availability-and-normalization.md +42 -1
- package/docs/reference/cli.md +1 -1
- package/docs/reference/core/arcane-ai-contracts.md +1 -1
- package/docs/reference/inventory/package-api.json +60 -4
- package/docs/reference/inventory/runtime-components.json +2 -2
- package/docs/reference/inventory/runtime-modules.json +29 -31
- package/docs/reference/protocols.md +17 -13
- package/docs/reference/runtime-components.md +6 -5
- package/docs/reference/runtime-modules.md +212 -70
- package/docs/reference/sdk-api.md +197 -11
- package/examples/wasm-ai-demo/index.html +1 -0
- package/node_modules/event-pubsub/node_modules/strong-type/README.md +408 -0
- package/node_modules/event-pubsub/node_modules/strong-type/assets/strong-type-header.png +0 -0
- package/node_modules/event-pubsub/node_modules/strong-type/index.js +1151 -0
- package/node_modules/event-pubsub/node_modules/strong-type/licence +21 -0
- package/node_modules/event-pubsub/node_modules/strong-type/node.js +125 -0
- package/node_modules/event-pubsub/node_modules/strong-type/package.json +61 -0
- package/node_modules/strong-type/README.md +42 -24
- package/node_modules/strong-type/benchmark/core.js +324 -0
- package/node_modules/strong-type/index.js +207 -82
- package/node_modules/strong-type/package.json +14 -6
- package/package.json +4 -3
- package/runtime/arcane/components/app-bar.html +5 -2
- package/runtime/arcane/components/assistant-panel.html +5 -2
- package/runtime/arcane/components/chart.html +15 -12
- package/runtime/arcane/components/chat.html +118 -141
- package/runtime/arcane/components/dashboard-config.html +6 -3
- package/runtime/arcane/components/data-view.html +4 -1
- package/runtime/arcane/components/directory-picker.html +5 -2
- package/runtime/arcane/components/document-inspector.html +6 -3
- package/runtime/arcane/components/file-drop.html +5 -2
- package/runtime/arcane/components/file-inspector.html +9 -6
- package/runtime/arcane/components/file-manager.html +16 -13
- package/runtime/arcane/components/local-ai-status.html +5 -2
- package/runtime/arcane/components/markdown-document.html +14 -11
- package/runtime/arcane/components/markdown-editor.html +4 -1
- package/runtime/arcane/components/modal.html +4 -1
- package/runtime/arcane/components/output-panel.html +6 -3
- package/runtime/arcane/components/preferences-form.html +4 -1
- package/runtime/arcane/components/record-timeline.html +8 -5
- package/runtime/arcane/components/relationship-board.html +9 -6
- package/runtime/arcane/components/source-code-viewer.html +12 -9
- package/runtime/arcane/components/source-explanation.html +8 -5
- package/runtime/arcane/components/speech.html +24 -21
- package/runtime/arcane/components/summary-strip.html +4 -1
- package/runtime/arcane/components/task-progress.html +6 -3
- package/runtime/arcane/components/terminal-workspace.html +4 -1
- package/runtime/arcane/components/voice-transcription.html +11 -8
- package/runtime/arcane/components/web-navigator.html +5 -2
- package/runtime/arcane/entities/ApiModelRecord.js +5 -2
- package/runtime/arcane/entities/Calculation.js +5 -2
- package/runtime/arcane/entities/Chat.js +33 -33
- package/runtime/arcane/entities/CommunicationMessage.js +4 -1
- package/runtime/arcane/entities/CommunicationThread.js +4 -1
- package/runtime/arcane/entities/File.js +1 -1
- package/runtime/arcane/entities/Image.js +8 -5
- package/runtime/arcane/entities/IntentEnvelope.js +20 -17
- package/runtime/arcane/entities/Preference.js +9 -6
- package/runtime/arcane/entities/Theme.js +5 -2
- package/runtime/arcane/entities/User.js +11 -11
- package/runtime/arcane/entities/Weather.js +5 -2
- package/runtime/arcane/modules/AI.js +503 -187
- package/runtime/arcane/modules/AIPreferenceRuntime.js +5 -2
- package/runtime/arcane/modules/AIPreferenceTuple.js +9 -6
- package/runtime/arcane/modules/AIProviderRuntime.js +117 -92
- package/runtime/arcane/modules/AIResponseURLPolicy.js +148 -62
- package/runtime/arcane/modules/AIRuntimeState.js +29 -26
- package/runtime/arcane/modules/AnsiText.js +4 -1
- package/runtime/arcane/modules/ApiModelDatabase.js +22 -19
- package/runtime/arcane/modules/AppDataScope.js +8 -5
- package/runtime/arcane/modules/ArcaneCommunicationBridge.js +4 -1
- package/runtime/arcane/modules/ArcaneNavigationPolicy.js +8 -5
- package/runtime/arcane/modules/ArcaneNetworkPolicy.js +18 -15
- package/runtime/arcane/modules/AsyncBoundary.js +13 -10
- package/runtime/arcane/modules/BrowserTestSuite.js +19 -16
- package/runtime/arcane/modules/CalculatorEngine.js +5 -2
- package/runtime/arcane/modules/ChatRecords.js +18 -15
- package/runtime/arcane/modules/CommunicationAppController.js +9 -6
- package/runtime/arcane/modules/CommunicationHub.js +9 -6
- package/runtime/arcane/modules/CommunicationPreferences.js +4 -1
- package/runtime/arcane/modules/CommunicationProviderRegistry.js +4 -1
- package/runtime/arcane/modules/ComponentContracts.js +56 -53
- package/runtime/arcane/modules/ConfiguredAIChatSession.js +30 -27
- package/runtime/arcane/modules/ConversationActionItems.js +15 -12
- package/runtime/arcane/modules/ConversationClosingReport.js +11 -8
- package/runtime/arcane/modules/ConversationTimebox.js +28 -25
- package/runtime/arcane/modules/CoreLocalModelCatalog.js +17 -14
- package/runtime/arcane/modules/DBLS.js +7 -4
- package/runtime/arcane/modules/DBOPFS.js +7 -7
- package/runtime/arcane/modules/DBOPFSDocumentLibrary.js +34 -31
- package/runtime/arcane/modules/DevelopmentWorkspace.js +4 -1
- package/runtime/arcane/modules/DirectoryPicker.js +8 -5
- package/runtime/arcane/modules/DocumentLexicalSearch.js +11 -8
- package/runtime/arcane/modules/DocumentNavigation.js +7 -4
- package/runtime/arcane/modules/Errors.js +28 -25
- package/runtime/arcane/modules/HTMLImport.js +7 -4
- package/runtime/arcane/modules/IsolatedModelQuestionRunner.js +15 -12
- package/runtime/arcane/modules/LocalAIReadiness.js +21 -18
- package/runtime/arcane/modules/LocalAIReadinessController.js +6 -3
- package/runtime/arcane/modules/MD.js +1 -1
- package/runtime/arcane/modules/Mail.js +46 -43
- package/runtime/arcane/modules/MailOutbox.mjs +48 -45
- package/runtime/arcane/modules/MailTransport.mjs +29 -26
- package/runtime/arcane/modules/MarkdownSpeech.js +1 -50
- package/runtime/arcane/modules/MemoryRecords.js +7 -4
- package/runtime/arcane/modules/MessageAdvisory.js +6 -3
- package/runtime/arcane/modules/ModelDefinition.js +7 -4
- package/runtime/arcane/modules/Ollama.js +6 -3
- package/runtime/arcane/modules/OllamaModelIdentifier.js +4 -1
- package/runtime/arcane/modules/OpenMeteoWeatherProvider.js +18 -15
- package/runtime/arcane/modules/PersistentAIChatSession.js +33 -30
- package/runtime/arcane/modules/PreferenceStore.js +20 -17
- package/runtime/arcane/modules/PreparedSpeech.js +485 -0
- package/runtime/arcane/modules/Questionnaire.js +6 -3
- package/runtime/arcane/modules/RecordLinkIndex.js +4 -1
- package/runtime/arcane/modules/RecordPassageIndex.js +9 -6
- package/runtime/arcane/modules/RecordReviewStore.js +12 -9
- package/runtime/arcane/modules/RiskSignalAnalyzer.js +4 -1
- package/runtime/arcane/modules/ScopedOPFSCache.js +6 -3
- package/runtime/arcane/modules/ScreenCapture.js +20 -17
- package/runtime/arcane/modules/SpeechPlayback.js +61 -28
- package/runtime/arcane/modules/StaticDocumentCatalog.js +33 -30
- package/runtime/arcane/modules/SystemAppearance.js +5 -2
- package/runtime/arcane/modules/SystemToolRegistry.js +6 -3
- package/runtime/arcane/modules/TerminalClient.js +14 -11
- package/runtime/arcane/modules/TerminalCommandRegistry.js +4 -1
- package/runtime/arcane/modules/ThemeBootstrap.js +9 -6
- package/runtime/arcane/modules/ThemeManager.js +5 -2
- package/runtime/arcane/modules/TimeGuard.js +1 -1
- package/runtime/arcane/modules/ToolCallRouter.js +11 -8
- package/runtime/arcane/modules/WaitForComponent.js +19 -16
- package/runtime/arcane/modules/YouTubeMedia.js +4 -1
- package/runtime/strong-type/index.js +1276 -352
- package/runtime/strong-type/package.json +69 -45
- package/src/app-descriptor.mjs +17 -14
- package/src/application-tests.mjs +4 -1
- package/src/cli/main.mjs +8 -5
- package/src/constants.mjs +4 -1
- package/src/dev-server.mjs +8 -5
- package/src/doctor.mjs +5 -2
- package/src/dom-event-instrumentation.mjs +24 -20
- package/src/errors.mjs +7 -3
- package/src/event-manager.mjs +111 -108
- package/src/event-queue.mjs +8 -5
- package/src/events.mjs +12 -9
- package/src/import-map.mjs +36 -27
- package/src/installed-sdk-runtime.mjs +4 -1
- package/src/integrated-provider-loader.mjs +9 -6
- package/src/mail-credentials.mjs +16 -13
- package/src/mail-server.mjs +53 -50
- package/src/mail.mjs +18 -15
- package/src/native-plan.mjs +12 -9
- package/src/native-provider-loader.mjs +7 -4
- package/src/packager/core.mjs +18 -15
- package/src/process.mjs +6 -3
- package/src/release-bundle.mjs +14 -11
- package/src/runtime.mjs +4 -1
- package/src/scaffold.mjs +9 -6
- package/src/sdk-browser-runtime.mjs +4 -1
- package/src/source-server.mjs +17 -14
- package/src/targets/index.mjs +5 -2
- package/src/templates/workspace-template.mjs +13 -6
- package/src/testing-loader.mjs +7 -4
- package/src/testing.mjs +10 -7
- package/src/toolchain.mjs +13 -10
- package/src/update-check.mjs +9 -6
- package/src/workspace-operation-lock.mjs +14 -11
- package/src/workspace-runtime.mjs +4 -1
- package/src/workspace.mjs +17 -14
- package/runtime/arcane/modules/AIResponseLength.js +0 -32
|
@@ -10,6 +10,9 @@
|
|
|
10
10
|
<html-import id="configModal" class="modal" href="./arcane/components/modal.html?v=13"></html-import>
|
|
11
11
|
|
|
12
12
|
<script type="module">
|
|
13
|
+
const {default:Is}=await import('strong-type');
|
|
14
|
+
const is=new Is(false);
|
|
15
|
+
|
|
13
16
|
const {arcaneLogging}=await import('arcane-os/logging');
|
|
14
17
|
|
|
15
18
|
const host=this;
|
|
@@ -150,7 +153,7 @@
|
|
|
150
153
|
return {
|
|
151
154
|
...definition.chartOptions,
|
|
152
155
|
labels:{...definition.chartOptions.labels},
|
|
153
|
-
chartOptions:
|
|
156
|
+
chartOptions:is.object(definition.chartOptions.chartOptions)
|
|
154
157
|
&&definition.chartOptions.chartOptions!==null
|
|
155
158
|
?{...definition.chartOptions.chartOptions}
|
|
156
159
|
:definition.chartOptions.chartOptions
|
|
@@ -158,7 +161,7 @@
|
|
|
158
161
|
}
|
|
159
162
|
|
|
160
163
|
function isVisible(definition={}){
|
|
161
|
-
return
|
|
164
|
+
return is.boolean(visibility[definition.key])
|
|
162
165
|
?visibility[definition.key]
|
|
163
166
|
:definition.defaultVisible;
|
|
164
167
|
}
|
|
@@ -337,7 +340,7 @@
|
|
|
337
340
|
chartOptions:{
|
|
338
341
|
...definition.chartOptions,
|
|
339
342
|
labels:{...definition.chartOptions.labels},
|
|
340
|
-
chartOptions:
|
|
343
|
+
chartOptions:is.object(definition.chartOptions.chartOptions)
|
|
341
344
|
&&definition.chartOptions.chartOptions!==null
|
|
342
345
|
?{...definition.chartOptions.chartOptions}
|
|
343
346
|
:definition.chartOptions.chartOptions
|
|
@@ -14,6 +14,9 @@
|
|
|
14
14
|
<html-import id="dataModal" class="modal" href="./arcane/components/modal.html?v=13"></html-import>
|
|
15
15
|
|
|
16
16
|
<script type="module">
|
|
17
|
+
const {default:Is}=await import('strong-type');
|
|
18
|
+
const is=new Is(false);
|
|
19
|
+
|
|
17
20
|
const {arcaneLogging}=await import('arcane-os/logging');
|
|
18
21
|
|
|
19
22
|
const host=this;
|
|
@@ -29,7 +32,7 @@
|
|
|
29
32
|
let operationGeneration=0;
|
|
30
33
|
let destroyed=false;
|
|
31
34
|
|
|
32
|
-
host.beforeOpen=
|
|
35
|
+
host.beforeOpen=is.function(host.beforeOpen)
|
|
33
36
|
?host.beforeOpen
|
|
34
37
|
:async function beforeOpen(){};
|
|
35
38
|
host.open=openData;
|
|
@@ -30,6 +30,9 @@
|
|
|
30
30
|
</div>
|
|
31
31
|
|
|
32
32
|
<script type="module">
|
|
33
|
+
const {default:Is}=await import('strong-type');
|
|
34
|
+
const is=new Is(false);
|
|
35
|
+
|
|
33
36
|
const {arcaneLogging}=await import('arcane-os/logging');
|
|
34
37
|
|
|
35
38
|
const host=this;
|
|
@@ -98,7 +101,7 @@
|
|
|
98
101
|
if(destroyed){
|
|
99
102
|
return false;
|
|
100
103
|
}
|
|
101
|
-
if(!input
|
|
104
|
+
if(!input||!is.object(input)||is.array(input)){
|
|
102
105
|
throw new TypeError('Directory picker configuration must be an object.');
|
|
103
106
|
}
|
|
104
107
|
const replacesSelection=Object.prototype.hasOwnProperty.call(input,'picker')
|
|
@@ -109,7 +112,7 @@
|
|
|
109
112
|
:disabled;
|
|
110
113
|
const nextPicker=input.picker===undefined?picker:input.picker;
|
|
111
114
|
if(input.picker!==undefined){
|
|
112
|
-
if(!nextPicker
|
|
115
|
+
if(!nextPicker||!is.function(nextPicker.select)){
|
|
113
116
|
throw new TypeError('picker must expose a select(options) function.');
|
|
114
117
|
}
|
|
115
118
|
}
|
|
@@ -47,6 +47,9 @@
|
|
|
47
47
|
</section>
|
|
48
48
|
|
|
49
49
|
<script type="module">
|
|
50
|
+
const {default:Is}=await import('strong-type');
|
|
51
|
+
const is=new Is(false);
|
|
52
|
+
|
|
50
53
|
const host=this;
|
|
51
54
|
const shadow=host.shadowRoot;
|
|
52
55
|
const tabs=[...shadow.querySelectorAll('[role="tab"]')];
|
|
@@ -117,7 +120,7 @@
|
|
|
117
120
|
const url=new URL(sourceUrl(value));
|
|
118
121
|
if(page===null||page===undefined||page==='') return url.href;
|
|
119
122
|
const resolvedPage=Number(page);
|
|
120
|
-
if(!
|
|
123
|
+
if(!is.safeInteger(resolvedPage)||resolvedPage<1) throw new TypeError('PDF page must be a positive integer.');
|
|
121
124
|
url.searchParams.set('arcane-pdf-page',String(resolvedPage));
|
|
122
125
|
url.hash=`page=${resolvedPage}`;
|
|
123
126
|
return url.href;
|
|
@@ -202,7 +205,7 @@
|
|
|
202
205
|
}));
|
|
203
206
|
reviewStatus.value=String(config.review?.status||'not-reviewed');
|
|
204
207
|
if(!reviewStatus.value&&reviewStatus.options.length) reviewStatus.selectedIndex=0;
|
|
205
|
-
const classificationOptions=
|
|
208
|
+
const classificationOptions=is.array(config.classificationOptions)?config.classificationOptions:[];
|
|
206
209
|
classificationField.hidden=!classificationOptions.length;
|
|
207
210
|
classificationLabel.textContent=String(config.classificationLabel||'Classification');
|
|
208
211
|
reviewClassification.replaceChildren(...classificationOptions.map(option=>{
|
|
@@ -211,7 +214,7 @@
|
|
|
211
214
|
reviewClassification.value=String(config.review?.classification||'unassigned');
|
|
212
215
|
if(!reviewClassification.value&&reviewClassification.options.length) reviewClassification.selectedIndex=0;
|
|
213
216
|
reviewFields.replaceChildren();
|
|
214
|
-
for(const definition of
|
|
217
|
+
for(const definition of is.array(config.reviewFields)?config.reviewFields:[]){
|
|
215
218
|
const key=String(definition.key||'').replace(/[^a-z0-9._-]/gi,'-');
|
|
216
219
|
if(!key) continue;
|
|
217
220
|
const label=document.createElement('label'); const caption=document.createElement('span'); caption.textContent=String(definition.label||key);
|
|
@@ -44,6 +44,9 @@
|
|
|
44
44
|
</section>
|
|
45
45
|
|
|
46
46
|
<script type="module">
|
|
47
|
+
const {default:Is}=await import('strong-type');
|
|
48
|
+
const is=new Is(false);
|
|
49
|
+
|
|
47
50
|
const host=this;
|
|
48
51
|
const root=host.shadowRoot;
|
|
49
52
|
const {createArcaneEventSource,projectArcaneDOMEvent}=await import('arcane-os/event-manager');
|
|
@@ -220,7 +223,7 @@
|
|
|
220
223
|
return progress;
|
|
221
224
|
}
|
|
222
225
|
const numeric=Number(value);
|
|
223
|
-
progress=value===null||value===undefined||!
|
|
226
|
+
progress=value===null||value===undefined||!is.finite(numeric)
|
|
224
227
|
?null
|
|
225
228
|
:Math.min(100,Math.max(0,numeric));
|
|
226
229
|
feedback.hidden=progress===null&&!statusElement.innerText;
|
|
@@ -272,7 +275,7 @@
|
|
|
272
275
|
|
|
273
276
|
function numberOr(value,fallback){
|
|
274
277
|
const numeric=Number(value);
|
|
275
|
-
return
|
|
278
|
+
return is.finite(numeric)&&numeric>=0?numeric:fallback;
|
|
276
279
|
}
|
|
277
280
|
|
|
278
281
|
function destroy(){
|
|
@@ -54,6 +54,9 @@
|
|
|
54
54
|
</section>
|
|
55
55
|
|
|
56
56
|
<script type="module">
|
|
57
|
+
const {default:Is}=await import('strong-type');
|
|
58
|
+
const is=new Is(false);
|
|
59
|
+
|
|
57
60
|
const host=this;
|
|
58
61
|
const root=host.shadowRoot;
|
|
59
62
|
const {createArcaneEventSource,projectArcaneDOMEvent}=await import('arcane-os/event-manager');
|
|
@@ -152,8 +155,8 @@
|
|
|
152
155
|
}
|
|
153
156
|
|
|
154
157
|
function renderMetadata(input=[]){
|
|
155
|
-
const entries=
|
|
156
|
-
?input.map(entry=>
|
|
158
|
+
const entries=is.array(input)
|
|
159
|
+
?input.map(entry=>is.array(entry)?entry:[entry.label,entry.value])
|
|
157
160
|
:Object.entries(input||{});
|
|
158
161
|
const fragment=document.createDocumentFragment();
|
|
159
162
|
for(const [label,value] of entries){
|
|
@@ -177,7 +180,7 @@
|
|
|
177
180
|
return false;
|
|
178
181
|
}
|
|
179
182
|
preview.replaceChildren();
|
|
180
|
-
if(
|
|
183
|
+
if(!is.undefined(globalThis.Node)&&value instanceof Node){
|
|
181
184
|
preview.append(value);
|
|
182
185
|
}else if(`${value??''}`){
|
|
183
186
|
const text=document.createElement('pre');
|
|
@@ -230,7 +233,7 @@
|
|
|
230
233
|
if(destroyed){
|
|
231
234
|
return false;
|
|
232
235
|
}
|
|
233
|
-
const next=
|
|
236
|
+
const next=is.object(value)?value:{label:value,status:value};
|
|
234
237
|
status.innerText=`${next.label||''}`;
|
|
235
238
|
status.dataset.status=`${next.status||''}`;
|
|
236
239
|
status.hidden=!status.innerText;
|
|
@@ -278,7 +281,7 @@
|
|
|
278
281
|
|
|
279
282
|
function formatSize(value){
|
|
280
283
|
const bytes=Number(value);
|
|
281
|
-
if(!
|
|
284
|
+
if(!is.finite(bytes)||bytes<0){
|
|
282
285
|
return '';
|
|
283
286
|
}
|
|
284
287
|
if(bytes<1024){
|
|
@@ -299,7 +302,7 @@
|
|
|
299
302
|
return '';
|
|
300
303
|
}
|
|
301
304
|
const date=new Date(value);
|
|
302
|
-
return
|
|
305
|
+
return is.NaN(date.getTime())?'':date.toLocaleString();
|
|
303
306
|
}
|
|
304
307
|
|
|
305
308
|
function clear(){
|
|
@@ -343,6 +343,9 @@
|
|
|
343
343
|
<html-import id="deleteModal" class="modal" href="./arcane/components/modal.html?v=13"></html-import>
|
|
344
344
|
|
|
345
345
|
<script type="module">
|
|
346
|
+
const {default:Is}=await import('strong-type');
|
|
347
|
+
const is=new Is(false);
|
|
348
|
+
|
|
346
349
|
const {arcaneLogging}=await import('arcane-os/logging');
|
|
347
350
|
|
|
348
351
|
import('../modules/DBOPFS.js');
|
|
@@ -431,12 +434,12 @@
|
|
|
431
434
|
}
|
|
432
435
|
|
|
433
436
|
function isVisibleEntry(entry={}){
|
|
434
|
-
const normalized=
|
|
437
|
+
const normalized=is.string(entry)
|
|
435
438
|
?{name:entry,path:entry,kind:'file'}
|
|
436
439
|
:entry;
|
|
437
440
|
const activeFilter=filter||provider?.filter;
|
|
438
441
|
|
|
439
|
-
if(
|
|
442
|
+
if(is.function(activeFilter)){
|
|
440
443
|
return activeFilter(normalized)!==false;
|
|
441
444
|
}
|
|
442
445
|
|
|
@@ -542,7 +545,7 @@
|
|
|
542
545
|
if(destroyed){
|
|
543
546
|
return null;
|
|
544
547
|
}
|
|
545
|
-
if(nextProvider!==null
|
|
548
|
+
if(nextProvider!==null&&!is.function(nextProvider?.list)){
|
|
546
549
|
throw new TypeError('File manager providers must expose list(path).');
|
|
547
550
|
}
|
|
548
551
|
|
|
@@ -564,7 +567,7 @@
|
|
|
564
567
|
if(destroyed){
|
|
565
568
|
return null;
|
|
566
569
|
}
|
|
567
|
-
if(nextFilter!==null
|
|
570
|
+
if(nextFilter!==null&&!is.function(nextFilter)){
|
|
568
571
|
throw new TypeError('File manager filters must be functions or null.');
|
|
569
572
|
}
|
|
570
573
|
|
|
@@ -593,7 +596,7 @@
|
|
|
593
596
|
}
|
|
594
597
|
|
|
595
598
|
function normalizeProviderEntry(candidate={},parentPath=''){
|
|
596
|
-
if(!candidate
|
|
599
|
+
if(!candidate||!is.object(candidate)){
|
|
597
600
|
return null;
|
|
598
601
|
}
|
|
599
602
|
|
|
@@ -620,7 +623,7 @@
|
|
|
620
623
|
name:name,
|
|
621
624
|
path:path,
|
|
622
625
|
kind:kind,
|
|
623
|
-
size:
|
|
626
|
+
size:is.finite(Number(candidate.size))?Number(candidate.size):0,
|
|
624
627
|
mimeType:String(candidate.mimeType||''),
|
|
625
628
|
lastModified:candidate.lastModified||'',
|
|
626
629
|
status:String(candidate.status||''),
|
|
@@ -629,7 +632,7 @@
|
|
|
629
632
|
}
|
|
630
633
|
|
|
631
634
|
function normalizeProviderEntries(entries=[],parentPath=''){
|
|
632
|
-
if(!
|
|
635
|
+
if(!is.array(entries)){
|
|
633
636
|
throw new TypeError('File manager provider list(path) must return an array.');
|
|
634
637
|
}
|
|
635
638
|
|
|
@@ -833,7 +836,7 @@
|
|
|
833
836
|
name.innerText=entry.name;
|
|
834
837
|
count.className='tree-file-count';
|
|
835
838
|
|
|
836
|
-
if(
|
|
839
|
+
if(is.finite(Number(entry.fileCount))){
|
|
837
840
|
setFileCountLabel(count,Number(entry.fileCount),false);
|
|
838
841
|
item.dataset.fileCount=String(Number(entry.fileCount));
|
|
839
842
|
}
|
|
@@ -900,7 +903,7 @@
|
|
|
900
903
|
const exact=Number(current._fileManagerEntry?.fileCount);
|
|
901
904
|
const countElement=current.querySelector(':scope>.tree-item-row>.tree-file-count');
|
|
902
905
|
|
|
903
|
-
if(
|
|
906
|
+
if(is.finite(exact)){
|
|
904
907
|
current.dataset.fileCount=String(exact);
|
|
905
908
|
setFileCountLabel(countElement,exact,false);
|
|
906
909
|
}else if(current.dataset.loaded==='true'){
|
|
@@ -1188,7 +1191,7 @@
|
|
|
1188
1191
|
return true;
|
|
1189
1192
|
}
|
|
1190
1193
|
|
|
1191
|
-
if(
|
|
1194
|
+
if(is.function(activeTreeProvider().open)){
|
|
1192
1195
|
try{
|
|
1193
1196
|
await activeTreeProvider().open(entry);
|
|
1194
1197
|
if(destroyed||generation!==treeOpenGeneration){
|
|
@@ -1508,7 +1511,7 @@
|
|
|
1508
1511
|
|
|
1509
1512
|
if(
|
|
1510
1513
|
['json','jsonl','ndjson'].includes(fileRef.ext)
|
|
1511
|
-
&&
|
|
1514
|
+
&&is.function(host.previewTransform)
|
|
1512
1515
|
){
|
|
1513
1516
|
preview=await host.previewTransform(
|
|
1514
1517
|
preview,
|
|
@@ -1530,7 +1533,7 @@
|
|
|
1530
1533
|
break;
|
|
1531
1534
|
case 'jsonl':
|
|
1532
1535
|
case 'ndjson':{
|
|
1533
|
-
const records=
|
|
1536
|
+
const records=is.array(preview)?preview:[];
|
|
1534
1537
|
|
|
1535
1538
|
for(let i=0;i<records.length;i++){
|
|
1536
1539
|
rendered.append(
|
|
@@ -1729,7 +1732,7 @@
|
|
|
1729
1732
|
return;
|
|
1730
1733
|
}
|
|
1731
1734
|
|
|
1732
|
-
if(closeFile&&
|
|
1735
|
+
if(closeFile&&is.function(fileModal.close)){
|
|
1733
1736
|
await fileModal.close(undefined,true);
|
|
1734
1737
|
if(destroyed||generation!==deleteGeneration){
|
|
1735
1738
|
return;
|
|
@@ -95,6 +95,9 @@
|
|
|
95
95
|
</section>
|
|
96
96
|
|
|
97
97
|
<script type="module">
|
|
98
|
+
const {default:Is}=await import('strong-type');
|
|
99
|
+
const is=new Is(false);
|
|
100
|
+
|
|
98
101
|
const host=this;
|
|
99
102
|
const root=host.shadowRoot;
|
|
100
103
|
const {createArcaneEventSource,projectArcaneDOMEvent}=await import('arcane-os/event-manager');
|
|
@@ -286,13 +289,13 @@
|
|
|
286
289
|
}
|
|
287
290
|
|
|
288
291
|
function positiveSafeInteger(value){
|
|
289
|
-
return
|
|
292
|
+
return is.safeInteger(value)&&value>0
|
|
290
293
|
?value
|
|
291
294
|
:null;
|
|
292
295
|
}
|
|
293
296
|
|
|
294
297
|
function normalizeResult(value={}){
|
|
295
|
-
if(
|
|
298
|
+
if(is.boolean(value)){
|
|
296
299
|
return {
|
|
297
300
|
required:true,
|
|
298
301
|
ready:value,
|
|
@@ -211,6 +211,9 @@
|
|
|
211
211
|
</section>
|
|
212
212
|
|
|
213
213
|
<script type="module">
|
|
214
|
+
const {default:Is}=await import('strong-type');
|
|
215
|
+
const is=new Is(false);
|
|
216
|
+
|
|
214
217
|
const {arcaneLogging}=await import('arcane-os/logging');
|
|
215
218
|
|
|
216
219
|
const host=this;
|
|
@@ -380,19 +383,19 @@
|
|
|
380
383
|
}
|
|
381
384
|
|
|
382
385
|
function normalizeOptions(input={},previous=defaultOptions){
|
|
383
|
-
if(!input
|
|
386
|
+
if(!input||!is.object(input)||is.array(input)){
|
|
384
387
|
throw new TypeError('Markdown document options must be an object.');
|
|
385
388
|
}
|
|
386
389
|
|
|
387
390
|
const labelInput=input.labels===undefined?{}:input.labels;
|
|
388
|
-
if(!labelInput
|
|
391
|
+
if(!labelInput||!is.object(labelInput)||is.array(labelInput)){
|
|
389
392
|
throw new TypeError('Markdown document labels must be an object.');
|
|
390
393
|
}
|
|
391
394
|
|
|
392
395
|
const labels={...previous.labels};
|
|
393
396
|
for(const name of ['content','empty','error','loading','tableOfContents']){
|
|
394
397
|
if(labelInput[name]!==undefined){
|
|
395
|
-
if(
|
|
398
|
+
if(!is.string(labelInput[name])||!labelInput[name].trim()){
|
|
396
399
|
throw new TypeError(`Markdown document labels.${name} must be a nonempty string.`);
|
|
397
400
|
}
|
|
398
401
|
labels[name]=labelInput[name].trim();
|
|
@@ -412,14 +415,14 @@
|
|
|
412
415
|
const onNavigate=input.onNavigate===undefined
|
|
413
416
|
?previous.onNavigate
|
|
414
417
|
:input.onNavigate;
|
|
415
|
-
if(onNavigate!==null
|
|
418
|
+
if(onNavigate!==null&&!is.function(onNavigate)){
|
|
416
419
|
throw new TypeError('Markdown document onNavigate must be a function or null.');
|
|
417
420
|
}
|
|
418
421
|
|
|
419
422
|
const showTableOfContents=input.showTableOfContents===undefined
|
|
420
423
|
?previous.showTableOfContents
|
|
421
424
|
:input.showTableOfContents;
|
|
422
|
-
if(
|
|
425
|
+
if(!is.boolean(showTableOfContents)){
|
|
423
426
|
throw new TypeError('Markdown document showTableOfContents must be boolean.');
|
|
424
427
|
}
|
|
425
428
|
|
|
@@ -481,7 +484,7 @@
|
|
|
481
484
|
}
|
|
482
485
|
|
|
483
486
|
function sourceURLFrom(input={},fallback=options.sourceURL){
|
|
484
|
-
if(!input
|
|
487
|
+
if(!input||!is.object(input)||is.array(input)){
|
|
485
488
|
throw new TypeError('Markdown document render options must be an object.');
|
|
486
489
|
}
|
|
487
490
|
const candidate=input.sourceURL??input.sourceUrl??fallback;
|
|
@@ -547,7 +550,7 @@
|
|
|
547
550
|
transition('loading',{},operationId);
|
|
548
551
|
|
|
549
552
|
try{
|
|
550
|
-
const pending=
|
|
553
|
+
const pending=is.function(source)
|
|
551
554
|
?source({sourceURL,signal:controller.signal,operationId})
|
|
552
555
|
:source;
|
|
553
556
|
const result=await pending;
|
|
@@ -557,8 +560,8 @@
|
|
|
557
560
|
|
|
558
561
|
if(
|
|
559
562
|
result
|
|
560
|
-
&&
|
|
561
|
-
&&!
|
|
563
|
+
&&is.object(result)
|
|
564
|
+
&&!is.array(result)
|
|
562
565
|
){
|
|
563
566
|
sourceURL=sourceURLFrom(
|
|
564
567
|
result,
|
|
@@ -598,7 +601,7 @@
|
|
|
598
601
|
}
|
|
599
602
|
|
|
600
603
|
function renderMarkdown(markdown='',sourceURL=options.sourceURL,operationId=null){
|
|
601
|
-
if(
|
|
604
|
+
if(!is.string(markdown)){
|
|
602
605
|
throw new TypeError('Markdown document content must be a string.');
|
|
603
606
|
}
|
|
604
607
|
|
|
@@ -783,7 +786,7 @@
|
|
|
783
786
|
};
|
|
784
787
|
const publicDetail={
|
|
785
788
|
characters:Number(detail.characters||currentMarkdown.length||0),
|
|
786
|
-
headingCount:
|
|
789
|
+
headingCount:is.array(detail.headings)?detail.headings.length:tableOfContents.length,
|
|
787
790
|
state
|
|
788
791
|
};
|
|
789
792
|
if(detail.code){
|
|
@@ -74,6 +74,9 @@
|
|
|
74
74
|
</section>
|
|
75
75
|
|
|
76
76
|
<script type="module">
|
|
77
|
+
const {default:Is}=await import('strong-type');
|
|
78
|
+
const is=new Is(false);
|
|
79
|
+
|
|
77
80
|
const {arcaneLogging}=await import('arcane-os/logging');
|
|
78
81
|
|
|
79
82
|
const host=this;
|
|
@@ -300,7 +303,7 @@
|
|
|
300
303
|
}
|
|
301
304
|
|
|
302
305
|
const save=options.onSave||(
|
|
303
|
-
|
|
306
|
+
is.function(host.save)?host.save.bind(host):null
|
|
304
307
|
);
|
|
305
308
|
if(!save){
|
|
306
309
|
status.innerText=options.labels.unavailable;
|
|
@@ -156,6 +156,9 @@
|
|
|
156
156
|
</dialog>
|
|
157
157
|
|
|
158
158
|
<script type="module">
|
|
159
|
+
const {default:Is}=await import('strong-type');
|
|
160
|
+
const is=new Is(false);
|
|
161
|
+
|
|
159
162
|
const {arcaneLogging}=await import('arcane-os/logging');
|
|
160
163
|
|
|
161
164
|
const host=this;
|
|
@@ -339,7 +342,7 @@
|
|
|
339
342
|
}
|
|
340
343
|
|
|
341
344
|
const tasks=jobs.filter(function isRunnableTask(job){
|
|
342
|
-
return job&&
|
|
345
|
+
return job&&is.string(job.name)&&is.function(job.task);
|
|
343
346
|
});
|
|
344
347
|
if(!tasks.length){
|
|
345
348
|
return [];
|
|
@@ -41,6 +41,9 @@
|
|
|
41
41
|
</section>
|
|
42
42
|
|
|
43
43
|
<script type="module">
|
|
44
|
+
const {default:Is}=await import('strong-type');
|
|
45
|
+
const is=new Is(false);
|
|
46
|
+
|
|
44
47
|
const host=this;
|
|
45
48
|
const root=host.shadowRoot;
|
|
46
49
|
const {createArcaneEventSource,projectArcaneDOMEvent}=await import('arcane-os/event-manager');
|
|
@@ -131,7 +134,7 @@
|
|
|
131
134
|
|
|
132
135
|
function setBody(value=''){
|
|
133
136
|
bodyContent.replaceChildren();
|
|
134
|
-
if(
|
|
137
|
+
if(!is.undefined(globalThis.Node)&&value instanceof Node){
|
|
135
138
|
bodyContent.append(value);
|
|
136
139
|
}else if(`${value??''}`){
|
|
137
140
|
const text=document.createElement('pre');
|
|
@@ -145,14 +148,14 @@
|
|
|
145
148
|
}
|
|
146
149
|
|
|
147
150
|
function setCoverage(value=''){
|
|
148
|
-
const next=
|
|
151
|
+
const next=is.object(value)?value:{label:value};
|
|
149
152
|
coverage.innerText=`${next.label??next.text??''}`;
|
|
150
153
|
coverage.hidden=!coverage.innerText;
|
|
151
154
|
return coverage.innerText;
|
|
152
155
|
}
|
|
153
156
|
|
|
154
157
|
function setStatus(value=''){
|
|
155
|
-
const next=
|
|
158
|
+
const next=is.object(value)?value:{label:value,status:value};
|
|
156
159
|
status.innerText=`${next.label||''}`;
|
|
157
160
|
status.dataset.status=`${next.status||''}`;
|
|
158
161
|
status.hidden=!status.innerText;
|
|
@@ -29,6 +29,9 @@
|
|
|
29
29
|
</form>
|
|
30
30
|
|
|
31
31
|
<script type="module">
|
|
32
|
+
const {default:Is}=await import('strong-type');
|
|
33
|
+
const is=new Is(false);
|
|
34
|
+
|
|
32
35
|
const host=this;
|
|
33
36
|
const root=host.shadowRoot;
|
|
34
37
|
const form=root.querySelector('form');
|
|
@@ -68,7 +71,7 @@
|
|
|
68
71
|
reset.addEventListener('click',()=>emit('preferences-reset'));
|
|
69
72
|
|
|
70
73
|
function configure(options={}){
|
|
71
|
-
schema=Array.from(options.schema||[]).map(item=>
|
|
74
|
+
schema=Array.from(options.schema||[]).map(item=>is.function(item.toJSON)?item.toJSON():{...item});
|
|
72
75
|
title.innerText=String(options.title||'Preferences');
|
|
73
76
|
description.innerText=String(options.description||'');
|
|
74
77
|
description.hidden=!description.innerText;
|
|
@@ -25,6 +25,9 @@
|
|
|
25
25
|
<p class="empty" data-empty>No dated events match this view.</p>
|
|
26
26
|
|
|
27
27
|
<script type="module">
|
|
28
|
+
const {default:Is}=await import('strong-type');
|
|
29
|
+
const is=new Is(false);
|
|
30
|
+
|
|
28
31
|
const host=this;
|
|
29
32
|
const list=host.shadowRoot.querySelector('[data-list]');
|
|
30
33
|
const empty=host.shadowRoot.querySelector('[data-empty]');
|
|
@@ -49,7 +52,7 @@
|
|
|
49
52
|
});
|
|
50
53
|
|
|
51
54
|
function normalizeItem(item,index){
|
|
52
|
-
const source=item&&
|
|
55
|
+
const source=item&&is.object(item)?item:{};
|
|
53
56
|
const date=String(source.date||source.isoDate||'');
|
|
54
57
|
if(!source.id||!date) return null;
|
|
55
58
|
return {
|
|
@@ -63,7 +66,7 @@
|
|
|
63
66
|
sourceLabel:String(source.sourceLabel||''),
|
|
64
67
|
status:String(source.status||''),
|
|
65
68
|
factualPosture:String(source.factualPosture||''),
|
|
66
|
-
sourceCount:
|
|
69
|
+
sourceCount:is.finite(Number(source.sourceCount))&&Number(source.sourceCount)>=0
|
|
67
70
|
?Number(source.sourceCount)
|
|
68
71
|
:0,
|
|
69
72
|
order:index
|
|
@@ -71,8 +74,8 @@
|
|
|
71
74
|
}
|
|
72
75
|
|
|
73
76
|
function setItems(value=[],input={}){
|
|
74
|
-
options={...options,...(input&&
|
|
75
|
-
items=(
|
|
77
|
+
options={...options,...(input&&is.object(input)?input:{})};
|
|
78
|
+
items=(is.array(value)?value:[]).map(normalizeItem).filter(Boolean)
|
|
76
79
|
.sort((left,right)=>left.date.localeCompare(right.date)||left.order-right.order);
|
|
77
80
|
render();
|
|
78
81
|
return items.map(item=>({...item}));
|
|
@@ -80,7 +83,7 @@
|
|
|
80
83
|
|
|
81
84
|
function displayDate(value=''){
|
|
82
85
|
const parsed=new Date(`${value.slice(0,10)}T00:00:00Z`);
|
|
83
|
-
return
|
|
86
|
+
return is.finite(parsed.getTime())
|
|
84
87
|
?new Intl.DateTimeFormat(undefined,{year:'numeric',month:'short',day:'numeric',timeZone:'UTC'}).format(parsed)
|
|
85
88
|
:value;
|
|
86
89
|
}
|
|
@@ -29,6 +29,9 @@
|
|
|
29
29
|
</section>
|
|
30
30
|
|
|
31
31
|
<script type="module">
|
|
32
|
+
const {default:Is}=await import('strong-type');
|
|
33
|
+
const is=new Is(false);
|
|
34
|
+
|
|
32
35
|
const host=this;
|
|
33
36
|
const board=host.shadowRoot.querySelector('[data-board]');
|
|
34
37
|
const selectedTitle=host.shadowRoot.querySelector('[data-selected-title]');
|
|
@@ -64,22 +67,22 @@
|
|
|
64
67
|
});
|
|
65
68
|
|
|
66
69
|
function normalizeNode(value,index){
|
|
67
|
-
const item=value&&
|
|
70
|
+
const item=value&&is.object(value)?value:{};
|
|
68
71
|
if(!item.id) return null;
|
|
69
|
-
return {...item,id:String(item.id),label:String(item.label||item.title||item.id),summary:String(item.summary||''),lane:String(item.lane||item.kind||'Other'),order:
|
|
72
|
+
return {...item,id:String(item.id),label:String(item.label||item.title||item.id),summary:String(item.summary||''),lane:String(item.lane||item.kind||'Other'),order:is.finite(Number(item.order))?Number(item.order):index};
|
|
70
73
|
}
|
|
71
74
|
function normalizeEdge(value,index,known){
|
|
72
|
-
const item=value&&
|
|
75
|
+
const item=value&&is.object(value)?value:{};
|
|
73
76
|
const from=String(item.from||''); const to=String(item.to||'');
|
|
74
77
|
if(!from||!to||!known.has(from)||!known.has(to)) return null;
|
|
75
78
|
return {...item,id:String(item.id||`edge-${index+1}`),from,to,label:String(item.label||'related to'),summary:String(item.summary||'')};
|
|
76
79
|
}
|
|
77
80
|
|
|
78
81
|
function setGraph(graph={},options={}){
|
|
79
|
-
nodes=(
|
|
82
|
+
nodes=(is.array(graph.nodes)?graph.nodes:[]).map(normalizeNode).filter(Boolean);
|
|
80
83
|
const known=new Set(nodes.map(item=>item.id));
|
|
81
|
-
edges=(
|
|
82
|
-
const supplied=
|
|
84
|
+
edges=(is.array(graph.edges)?graph.edges:[]).map((item,index)=>normalizeEdge(item,index,known)).filter(Boolean);
|
|
85
|
+
const supplied=is.array(options.lanes)?options.lanes:is.array(graph.lanes)?graph.lanes:[];
|
|
83
86
|
lanes=[...new Set([...supplied.map(String),...nodes.map(item=>item.lane)])];
|
|
84
87
|
board.style.setProperty('--lane-count',String(Math.max(1,Math.min(6,lanes.length))));
|
|
85
88
|
if(selectedId&&!known.has(selectedId)) selectedId='';
|