@jskit-ai/agent-docs 0.1.249 → 0.1.251

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.
Files changed (39) hide show
  1. package/guide/agent/app-extras/assistant-conversation.md +307 -59
  2. package/guide/agent/app-extras/assistant.md +6 -1
  3. package/guide/agent/app-extras/realtime.md +48 -0
  4. package/guide/agent/app-setup/existing-application-migration.md +7 -1
  5. package/package.json +1 -1
  6. package/patterns/feature-package/example/booking-engine/package.json +1 -1
  7. package/patterns/minimal-foundation/example/AGENTS.md +6 -0
  8. package/patterns/minimal-foundation/example/package.json +3 -3
  9. package/patterns/shell-foundation/example/AGENTS.md +6 -0
  10. package/patterns/shell-foundation/example/package.json +4 -4
  11. package/patterns/shell-foundation/example/packages/main/package.json +1 -1
  12. package/reference/autogen/KERNEL_MAP.md +6 -0
  13. package/reference/autogen/PATTERN_INDEX.md +37 -37
  14. package/reference/autogen/packages/assistant-core.md +35 -11
  15. package/reference/autogen/packages/crud-core.md +2 -2
  16. package/reference/autogen/packages/http-web.md +29 -0
  17. package/reference/autogen/packages/kernel.md +11 -0
  18. package/reference/autogen/packages/realtime.md +9 -0
  19. package/reference/autogen/packages/shell-web.md +6 -0
  20. package/skills/jskit/references/existing-application-migration.md +7 -1
  21. package/skills/jskit/references/pattern-index.md +37 -37
  22. package/skills/jskit/references/patterns/app/minimal-foundation/example/AGENTS.md +6 -0
  23. package/skills/jskit/references/patterns/app/minimal-foundation/example/package.json +3 -3
  24. package/skills/jskit/references/patterns/app/shell-foundation/example/AGENTS.md +6 -0
  25. package/skills/jskit/references/patterns/app/shell-foundation/example/package.json +4 -4
  26. package/skills/jskit/references/patterns/app/shell-foundation/example/packages/main/package.json +1 -1
  27. package/skills/jskit/references/patterns/auth/accounts-hub/example/package.json +2 -2
  28. package/skills/jskit/references/patterns/auth/oidc-sign-in/example/package.json +2 -2
  29. package/skills/jskit/references/patterns/auth/supabase-auth/example/package.json +1 -1
  30. package/skills/jskit/references/patterns/connectors/calendar-cli/example/package.json +4 -4
  31. package/skills/jskit/references/patterns/crud/crud-screen-set/PATTERN.md +46 -0
  32. package/skills/jskit/references/patterns/crud/json-api-resource-package/PATTERN.md +7 -0
  33. package/skills/jskit/references/patterns/crud/json-api-resource-package/example/packages/books/package.json +2 -2
  34. package/skills/jskit/references/patterns/database/mysql-application/example/package.json +1 -1
  35. package/skills/jskit/references/patterns/database/postgres-application/example/package.json +1 -1
  36. package/skills/jskit/references/patterns/realtime/realtime-application/example/package.json +2 -2
  37. package/skills/jskit/references/patterns/server/feature-package/example/booking-engine/package.json +1 -1
  38. package/skills/jskit/references/patterns/users/user-administration-server/example/packages/users/package.json +2 -2
  39. package/skills/jskit/references/patterns/users/user-administration-server/example/packages/users-workspace/package.json +3 -3
@@ -139,8 +139,10 @@ Local functions
139
139
  - `messageScrollKey(message = null)`
140
140
  - `clearUserScrollIntent()`
141
141
  - `resumePendingTailFollow()`
142
- - `markUserScrollIntent()`
142
+ - `markUserScrollIntent({ upward = false } = {})`
143
143
  - `markKeyboardScrollIntent(event = {})`
144
+ - `rememberTouch(event = {})`
145
+ - `markTouchScrollIntent(event = {})`
144
146
  - `scrollToLatestMessageAfterLayout({ behavior = "auto", force = false } = {})`
145
147
  - `queueInitialBottomScroll()`
146
148
  - `queueLiveBottomScroll({ force = false } = {})`
@@ -355,10 +357,14 @@ Exports
355
357
  - `bindClaudeConversationAccount(entry, { identity, providerId, allowAccountChange = false, stop, save })`
356
358
  - `claudePlanUsage(value)`
357
359
  - `claudeCatalogueModels(initialization)`
358
- - `createClaudeAccountQueries({ createProcess, accountIdentity, processes = () => [], isClosing = () => false })`
360
+ - `createClaudeAccountQueries({ createProcess, accountIdentity, configRoot, processes = () => [], isClosing = () => false })`
359
361
  - `createClaudeCodeProcess({ command = "claude", execution = createLocalConversationExecution(), env = process.env, workdir, onEvent, onControlRequest, onFailure, onStarted, executionLimits, signal, commandWrapper, initializationTimeoutMs = 30_000, onInitializationProgress, ...options } = {})`
360
362
  Local functions
363
+ - `fileRevision(file)`
361
364
  - `readNativeClaudeCodeAuthStatus({ env, credentialHome, command, commandRunner, signal })`
365
+ - `claudeCodeAuthStatus(result)`
366
+ - `claudePlanUsageVerified(value)`
367
+ - `presentPlanUsage(reading)`
362
368
 
363
369
  ### `src/server/conversation/claudeTools.js`
364
370
  Exports
@@ -377,6 +383,8 @@ Local functions
377
383
  - `failure(message, code = "assistant_claude_turn_failed")`
378
384
  - `now()`
379
385
  - `hasPendingClaudeStartup(entry)`
386
+ - `nativeWorkSettled(entry)`
387
+ - `runsNativeWork(entry)`
380
388
 
381
389
  ### `src/server/conversation/codexAuthPreflight.js`
382
390
  Exports
@@ -404,7 +412,7 @@ Exports
404
412
  - `codexAppServerTurnSettings({ effectiveSettings, cwd = "", effort = "", model = "", approvalPolicy, reasoningSummary, sandboxPolicy, externalSandbox = false } = {})`
405
413
  - `codexInteractiveArguments({ command, threadId = "", remoteEndpoint = "", model, effort, disableStartupUpdates = false, bypassApprovalsAndSandbox = false, bypassHookTrust = false } = {})`
406
414
  - `codexAppServerProjectHookTrustConfig(provider, cwd = "", { persist = false } = {})`
407
- - `prepareCodexModelCatalog({ command, runtimeDir, bundled = false, signal, additionalModels = [] })`
415
+ - `prepareCodexModelCatalog({ command, runtimeDir, bundled = false, signal, additionalModels = [], codexHome = process.env.CODEX_HOME || path.join(os.homedir(), ".codex") })`
408
416
  - `readCodexModelContextWindow({ runtimeDir, model } = {})`
409
417
  - `codexAppServerTextHasControlCharacters(value = "")`
410
418
  - `createCodexAppServerIsolation({ clientName = "jskit", minimumVersion = "0.151.0", disabledFeatures = DISABLED_FEATURES, limits: { userAgentMaxLength = 512, mcpServerMaxCount = 128, mcpServerNameMaxLength = 256, configResponseMaxBytes = 256 * 1024, hookMaxCount = 256, hookErrorMaxCount = 256, hookFieldMaxLength = 2048, hookFingerprintMaxLength = 256 * 1024, hookResponseMaxBytes = 512 * 1024 } = {}, createError = codexAppServerIsolationPolicyError } = {})`
@@ -424,6 +432,7 @@ Exports
424
432
  - `codexAuthOutputRequiresReconnect(output = "")`
425
433
  - `CODEX_APP_SERVER_ACCOUNT_ID_MAX_LENGTH`
426
434
  Local functions
435
+ - `codexModelCatalogRevision({ command, codexHome, bundled, additionalModels })`
427
436
  - `isPlainRecord(value)`
428
437
  - `deepFreezeCodexAppServerHelperConfig(value)`
429
438
  - `codexAppServerIsolationPolicyError(message = "", details = {})`
@@ -431,7 +440,7 @@ Local functions
431
440
 
432
441
  ### `src/server/conversation/codexConversations.js`
433
442
  Exports
434
- - `createCodexConversationCommands({ checkpoint, codexAppServerConversationMessageId, codexAppServerStreamMessage, conversationPreparation, ensureCodexAppServerProviderForActiveTurn, errorPrefix, helperLifecycle, helperOwnershipError, interruptFailedCode, namespace, providerSessions, sessionConnection, ensureSessionProvider, steerFailedCode, turnOutcomes })`
443
+ - `createCodexConversationCommands({ checkpoint, codexAppServerConversationMessageId, codexAppServerStreamMessage, conversationPreparation, ensureCodexAppServerProviderForActiveTurn, errorPrefix, helperLifecycle, helperOwnershipError, interruptFailedCode, namespace, providerSessions, ensureSessionProvider, borrowSessionProvider, steerFailedCode, turnOutcomes })`
435
444
 
436
445
  ### `src/server/conversation/codexConversationStore.js`
437
446
  Exports
@@ -485,6 +494,7 @@ Exports
485
494
  - `codexAppServerUserMessageText(item = {})`
486
495
  Local functions
487
496
  - `nonNegativeInteger(value)`
497
+ - `codexAppServerSignedOutText(text = "")`
488
498
  - `codexAppServerTextInputText(input = {})`
489
499
  - `codexAppServerHookPromptText(item = {})`
490
500
  - `codexAppServerFinalEventText(notification = {}, event = null, payload = {})`
@@ -535,6 +545,13 @@ Local functions
535
545
  - `restoreCompactedHistory(body, { destination, historyPath, codexHome, signal, maxRequestBytes })`
536
546
  - `forwardedHeaders(input)`
537
547
 
548
+ ### `src/server/conversation/codexHomeStorage.js`
549
+ Exports
550
+ - `codexDisabledProcessFeatureArguments()`
551
+ - `codexHomeDisposablePaths(codexHome, { retired = false } = {})`
552
+ Local functions
553
+ - `directoryNames(directory)`
554
+
538
555
  ### `src/server/conversation/codexMessageCommands.js`
539
556
  Exports
540
557
  - `createCodexMessageCommands({ output, journal, recovery, threadStatus, selection, observer, delivery, promptDeliveries: codexAppServerPromptDeliveries, createRuntime, debugError, debugLog, errorPrefix, messageIdPrefix, messageMetadata, namespace, providerSessions, recoverAdmission, steerFailedCode, turnAlreadyRunningError, turnState })`
@@ -590,6 +607,7 @@ Exports
590
607
  - `codexAppServerHelperHomeDir(runtimeDir = "")`
591
608
  - `codexAppServerHelperWorkspaceDir(runtimeDir = "")`
592
609
  - `codexAppServerProcessCwd({ executionRoot = "", runtimeDir = "", workdir = "" } = {})`
610
+ - `removeCodexAppServerRuntimeDir(runtimeDir = "")`
593
611
  - `codexAppServerRuntimeIdentity(runtime = {})`
594
612
  - `normalizeCodexAppServerTerminalEnv(terminalEnv = {})`
595
613
  - `codexAppServerCommandBaseEnv({ env = process.env, terminalEnv = {} } = {})`
@@ -617,7 +635,6 @@ Local functions
617
635
  - `codexAppServerUnixEndpoint(socketPath = "")`
618
636
  - `codexAppServerProjectTrustOverride(workdir = "")`
619
637
  - `codexAppServerRuntimeDirIsManaged(runtimeDir = "")`
620
- - `removeCodexAppServerRuntimeDir(runtimeDir = "")`
621
638
  - `removeCodexAppServerMetadataTemps(runtimeDir = "")`
622
639
  - `codexAppServerRuntimeCleanupCanSkip(error)`
623
640
  - `codexHistoryAdapterUrlIsValid(baseUrl, token)`
@@ -667,7 +684,7 @@ Local functions
667
684
  - `codexAppServerThreadRequestParams(params = {}, threadEnv = {})`
668
685
  - `codexControlProbeCommand(keys, marker)`
669
686
  - `codexAppServerThreadInventoryError(errorCode, label, detail)`
670
- - `listBoundedCodexAppServerThreadIds({ ancestorThreadId = "", archived = false, client, cwd = "", errorCode = "", label = "", requestLabel = "", runRequest, signal = null, sourceKinds = ["appServer"], state, verifyCwd = false } = {})`
687
+ - `listBoundedCodexAppServerThreadIds({ ancestorThreadId = "", archived = false, client, cwd = "", errorCode = "", findThreadId = "", label = "", requestLabel = "", runRequest, signal = null, sourceKinds = ["appServer"], state, verifyCwd = false } = {})`
671
688
  - `codexPlanUsage(limits = {})`
672
689
  - `normalizeAgentThread(value = {})`
673
690
  - `normalizeAgentTurn(value = {})`
@@ -675,11 +692,14 @@ Local functions
675
692
  ### `src/server/conversation/codexProviderOwner.js`
676
693
  Exports
677
694
  - `codexAppServerOwnedRuntimeKey(providerKey = "", providerOptions = {})`
695
+ - `releaseSupersededCodexRuntime(runtimeDir = "")`
678
696
  - `codexAppServerRuntimeStopWasVerified(result = {})`
679
697
  - `directoryExists(filePath = "")`
680
- - `createCodexAppServerProviderOwner({ runtimeRoot = "", assertOpen: assertApplicationOpen = () => {}, onRecoveryEvent = () => {}, debugLog = () => {}, debugError = error => error, providerFactory = null, prepareNativeHost = () => ({}), runtimeBusyCode = "codex_app_server_runtime_busy", exitUnverifiedCode = "codex_runtime_exit_unverified", requiredStopCode = "codex_runtime_exit_unverified", runtimeCloseError = "Codex app-server runtime close failed." } = {})`
698
+ - `createCodexAppServerProviderOwner({ runtimeRoot = "", assertOpen: assertApplicationOpen = () => {}, onRecoveryEvent = () => {}, debugLog = () => {}, debugError = error => error, providerFactory = null, prepareNativeHost = () => ({}), runtimeBusyCode = "codex_app_server_runtime_busy", exitUnverifiedCode = "codex_runtime_exit_unverified", requiredStopCode = "codex_runtime_exit_unverified", runtimeCloseError = "Codex app-server runtime close failed.", transientIdleMs = 60_000 } = {})`
681
699
  Local functions
682
700
  - `withRuntimeLifecycle(runtimeKey, operation)`
701
+ - `nativeRequest(client, method, params)`
702
+ - `runningNativeThreads(peers)`
683
703
 
684
704
  ### `src/server/conversation/codexProviderSelection.js`
685
705
  Exports
@@ -716,7 +736,7 @@ Exports
716
736
 
717
737
  ### `src/server/conversation/codexRuntimeLifecycle.js`
718
738
  Exports
719
- - `createCodexRuntimeLifecycle({ pendingWork, observer, checkManagedConnection, providerSessions, helperLifecycle, captureContext, runInContext, debugLog, debugError, closingError = null })`
739
+ - `createCodexRuntimeLifecycle({ pendingWork, observer, checkManagedConnection, providerSessions, helperLifecycle, captureContext, runInContext, continueGoalAfterAccountChange = null, debugLog, debugError, closingError = null })`
720
740
 
721
741
  ### `src/server/conversation/codexSessionCleanup.js`
722
742
  Exports
@@ -736,7 +756,7 @@ Exports
736
756
 
737
757
  ### `src/server/conversation/codexTurn.js`
738
758
  Exports
739
- - `createCodexAppServerRunOwner({ namespace = normalizeCodexRunText, normalizeRunState = normalizeCodexAppServerRunState, debugLog = () => {}, debugError = error => normalizeCodexRunText(error?.message || error), createRuntime, createStore, publish = async () => null, acquireProvider = async () => null, providerSessions = null, serverClosingError = null, helperThreads = null, modelCatalogCacheMs = 30_000, conversationPreparation = null, storeReadError = "The session store does not support agent-run reads.", sessionIdRequiredError = "A session ID is required.", turnClaimsUnsupportedError = "The session runtime does not support Codex turn claims.", turnAlreadyRunningError = "Codex is already working on this session.", messageIdPrefix = "codex:", idlePublishPayload = null, checkpoint = async () => null, messageMetadata = {}, persistCommentary = true, deliveryStateMetadataKey = "assistant_delivery", hasRuntime = () => true, recoverAdmission = null, admissionTaskFinished = () => false, outcomeNotice = async () => null, resultDeliveryFailureMessage = ({ error = "" } = {}) => { const detail = normalizeCodexRunText(error); if (!detail) return "Codex app-server finished this turn, but the assistant result text was not received."; const punctuation = [".", "!", "?"].some(character => detail.endsWith(character)) ? "" : "."; return "Codex completed, but its response could not be processed: " + detail + punctuation; }, orphanedPromptMessage = "The application restarted before Codex confirmed the message. Your message is safe; retry it.", onNotificationSignal = async () => null, captureContext = () => null, runInContext = (_context, operation) => operation(), notificationQueue = null, activeReconcileMs = 2000, finalizingGraceMs = 10000, finalizingGraceAfterHistoryRead = false, failureDetailGraceMs = 0, steerFailedCode = "codex_turn_steer_failed", interruptFailedCode = "codex_turn_interrupt_failed", errorPrefix = "" } = {})`
759
+ - `createCodexAppServerRunOwner({ namespace = normalizeCodexRunText, normalizeRunState = normalizeCodexAppServerRunState, debugLog = () => {}, debugError = error => normalizeCodexRunText(error?.message || error), createRuntime, createStore, publish = async () => null, acquireProvider = async () => null, providerSessions = null, serverClosingError = null, helperThreads = null, modelCatalogCacheMs = 30_000, conversationPreparation = null, storeReadError = "The session store does not support agent-run reads.", sessionIdRequiredError = "A session ID is required.", turnClaimsUnsupportedError = "The session runtime does not support Codex turn claims.", turnAlreadyRunningError = "Codex is already working on this session.", messageIdPrefix = "codex:", idlePublishPayload = null, checkpoint = async () => null, messageMetadata = {}, persistCommentary = true, deliveryStateMetadataKey = "assistant_delivery", hasRuntime = () => true, recoverAdmission = null, admissionTaskFinished = () => false, outcomeNotice = async () => null, resultDeliveryFailureMessage = ({ error = "" } = {}) => { const detail = normalizeCodexRunText(error); if (!detail) return "Codex app-server finished this turn, but the assistant result text was not received."; const punctuation = [".", "!", "?"].some(character => detail.endsWith(character)) ? "" : "."; return "Codex completed, but its response could not be processed: " + detail + punctuation; }, orphanedPromptMessage = "The application restarted before Codex confirmed the message. Your message is safe; retry it.", onNotificationSignal = async () => null, captureContext = () => null, runInContext = (_context, operation) => operation(), // Resumes a goal an account change paused, once the previous account's // runtime has stopped: `(sessionId, { threadId })`. Without it the goal stays // paused for the person to resume. continueGoalAfterAccountChange = null, notificationQueue = null, activeReconcileMs = 2000, finalizingGraceMs = 10000, finalizingGraceAfterHistoryRead = false, failureDetailGraceMs = 0, steerFailedCode = "codex_turn_steer_failed", interruptFailedCode = "codex_turn_interrupt_failed", errorPrefix = "" } = {})`
740
760
  - `CODEX_APP_SERVER_RUN_STATE`
741
761
  - `normalizeCodexAppServerRunState`
742
762
  - `codexAppServerRunStateIsActive`
@@ -940,7 +960,7 @@ Exports
940
960
  - `retireOpenCodeConversationHistory(storageClient, controlClient, binding, options = {})`
941
961
  - `openCodeAssistantMessageText(message = {})`
942
962
  - `OPENCODE_RESPONSE_LIMIT_BYTES`
943
- - `createOpenCodeServerClient({ allowAttachmentDirectories = false, baseUrl = "", directory = "", fetchImpl = globalThis.fetch, password = "", username = "opencode" } = {})`
963
+ - `createOpenCodeServerClient({ allowAttachmentDirectories = false, baseUrl = "", defaultDirectory = "", directory = "", fetchImpl = globalThis.fetch, instances = { addressed: new Map(), sequence: 0 }, password = "", username = "opencode" } = {})`
944
964
  - `readBoundedResponse(response, limitBytes = OPENCODE_RESPONSE_LIMIT_BYTES)`
945
965
  Local functions
946
966
  - `record(value)`
@@ -993,6 +1013,7 @@ Exports
993
1013
  - `createOpenCodeConversationPlugin`
994
1014
  Local functions
995
1015
  - `availableLoopbackPort()`
1016
+ - `openCodeExitReason(logs)`
996
1017
  - `waitForOpenCodeReady({ client, expectedVersion = OPENCODE_EXPECTED_VERSION, processHandle, timeoutMs = OPENCODE_READY_TIMEOUT_MS, signal } = {})`
997
1018
  - `actionPermission(action)`
998
1019
  - `agentPermission(ask, nativeTools, tools)`
@@ -1009,7 +1030,7 @@ Exports
1009
1030
  - `openCodeModel(selection = {}, executionProfile = null)`
1010
1031
  - `sameOpenCodeSelection(left = {}, right = {})`
1011
1032
  - `ensureOpenCodeSession(target, { selection, model, workdir = target.workdir, identity = {}, signal, invalidIdentity = () => new Error("OpenCode did not return a native conversation ID.") })`
1012
- - `createOpenCodeSharedRuntime({ onStop = () => {}, scope } = {})`
1033
+ - `createOpenCodeSharedRuntime({ onStop = () => {}, scope, storageIdleMs = 60_000 } = {})`
1013
1034
  Local functions
1014
1035
  - `openCodeTurnSnapshot(turn = null, threadId = "")`
1015
1036
  - `openCodeCredentialFailure(value = "")`
@@ -1231,6 +1252,8 @@ Exports
1231
1252
  - `createCodexAccountReader`
1232
1253
  - `createCodexAppServerIsolation`
1233
1254
  - `readCodexToolFreeConfiguration`
1255
+ - `codexDisabledProcessFeatureArguments`
1256
+ - `codexHomeDisposablePaths`
1234
1257
 
1235
1258
  ### `src/server/hosts/codexEvents.js`
1236
1259
  Exports
@@ -1839,6 +1862,7 @@ Local functions
1839
1862
  Exports
1840
1863
  - None
1841
1864
  Local functions
1865
+ - `cancelMessage(id)`
1842
1866
  - `accept()`
1843
1867
 
1844
1868
  ### `fixtures/responsive-assistant/main.js`
@@ -45,7 +45,7 @@ Local functions
45
45
 
46
46
  ### `src/server/defineCrudJsonApiFeature.js`
47
47
  Exports
48
- - `defineCrudJsonApiFeature({ resource, id = "", capability = "", surface, ownershipFilter = "", relativePath = "", internal = false, routes = true, listFilterQueryValidator = null, searchSchema = null, permissions = null, scope = {}, requires = {}, decorateRepository = null, decorateService = null, operationLifecycle = {}, operationInputs = {}, actions = {}, operations = undefined } = {})`
48
+ - `defineCrudJsonApiFeature({ resource, id = "", capability = "", surface, ownershipFilter = "", relativePath = "", internal = false, routes = true, listFilterQueryValidator = null, searchSchema = null, permissions = null, scope = {}, requires = {}, decorateRepository = null, decorateService = null, operationLifecycle = {}, operationInputs = {}, actions = {}, operations = undefined, realtimeAudience = "event_scope" } = {})`
49
49
  Local functions
50
50
  - `normalizeAccess(resource = {})`
51
51
  - `normalizeScope(scope = {})`
@@ -74,7 +74,7 @@ Local functions
74
74
  ### `src/server/jsonApiModule/actions.js`
75
75
  Exports
76
76
  - `assertCrudOperationName(operation = "")`
77
- - `createCrudJsonApiActions({ namespace, resource, repository = null, service, surface, permissionForOperation, permissionForAction = permissionForOperation, operations = CRUD_OPERATION_NAMES, scopeInputValidator = null, scopeInputKeys = [], listFilterQueryValidator = null, operationLifecycle = {}, operationInputs = {}, actions: additionalActionDefinitions = {}, dependencies = {} } = {})`
77
+ - `createCrudJsonApiActions({ namespace, resource, repository = null, service, surface, permissionForOperation, permissionForAction = permissionForOperation, operations = CRUD_OPERATION_NAMES, scopeInputValidator = null, scopeInputKeys = [], listFilterQueryValidator = null, operationLifecycle = {}, operationInputs = {}, actions: additionalActionDefinitions = {}, dependencies = {}, realtimeAudience = "event_scope" } = {})`
78
78
  - `normalizeCrudOperationLifecycle(value = {})`
79
79
  Local functions
80
80
  - `isRecord(value)`
@@ -96,6 +96,14 @@ Local functions
96
96
  Exports
97
97
  - None
98
98
 
99
+ ### `src/client/components/SelectField.vue`
100
+ Exports
101
+ - None
102
+ Local functions
103
+ - `titleOf(item)`
104
+ - `valueOf(item)`
105
+ - `update(value)`
106
+
99
107
  ### `src/client/composables/crud/crudBindingSupport.js`
100
108
  Exports
101
109
  - `CRUD_BINDING_MODE_ROUTE`
@@ -598,6 +606,15 @@ Exports
598
606
  - `formatDateOnlyDisplay(value = "", { locale = undefined } = {})`
599
607
  - `formatCrudListDateFilterChipLabel(filter = {}, rawValue, { locale = undefined } = {})`
600
608
 
609
+ ### `src/client/support/selectFieldSupport.js`
610
+ Exports
611
+ - `optionTitle(item, itemTitle)`
612
+ - `optionValue(item, itemTitle, itemValue)`
613
+ - `selectionFieldState(field, seen)`
614
+ Local functions
615
+ - `readOption(item, key, fallback)`
616
+ - `selectedValues(modelValue, multiple)`
617
+
601
618
  ### fixtures
602
619
 
603
620
  ### `fixtures/crud-list-date-filters/App.vue`
@@ -612,6 +629,18 @@ Exports
612
629
  Exports
613
630
  - None
614
631
 
632
+ ### `fixtures/select-field/App.vue`
633
+ Exports
634
+ - None
635
+
636
+ ### `fixtures/select-field/main.js`
637
+ Exports
638
+ - None
639
+
640
+ ### `fixtures/select-field/vite.config.mjs`
641
+ Exports
642
+ - None
643
+
615
644
  ### patterns
616
645
 
617
646
  ### `patterns/crud-screen-set/example/books/BookEditPage.vue`
@@ -60,6 +60,12 @@ Exports
60
60
  - `resolveLinkPath`
61
61
  - `normalizePathname`
62
62
 
63
+ ### `shared/support/clientBuild.js`
64
+ Exports
65
+ - `CLIENT_BUILD_META_NAME`
66
+ - `clientBuildIdFromHtml(html = "")`
67
+ - `pageClientBuildId(documentObject = globalThis.document)`
68
+
63
69
  ### `shared/support/deepFreeze.js`
64
70
  Exports
65
71
  - `deepFreeze(value, seen = new WeakSet())`
@@ -926,6 +932,10 @@ Local functions
926
932
  - `normalizeConfigObject(value)`
927
933
  - `loadConfigModuleAtPath(absolutePath)`
928
934
 
935
+ ### `server/support/clientBuild.js`
936
+ Exports
937
+ - `readServedClientBuildId({ appRoot } = {})`
938
+
929
939
  ### `server/support/defaultMissingHandler.js`
930
940
  Exports
931
941
  - `defaultMissingHandler(_request, reply)`
@@ -960,6 +970,7 @@ Exports
960
970
  - `resolveRequiredAppRoot`
961
971
  - `toPosixPath`
962
972
  - `tryAcquireExclusiveFileLock`
973
+ - `readServedClientBuildId`
963
974
 
964
975
  ### `server/support/path.js`
965
976
  Exports
@@ -44,6 +44,7 @@ Exports
44
44
  - `resolveRealtimeClientConfig({ env = {}, mobile = null } = {})`
45
45
  Local functions
46
46
  - `createRealtimeClient({ config, loggerInput } = {})`
47
+ - `trackServedClientBuild(socket, logger)`
47
48
 
48
49
  ### `src/client/runtime.js`
49
50
  Exports
@@ -108,6 +109,14 @@ Local functions
108
109
  - `resolveHttpServer({ httpServer = null, fastify = null } = {})`
109
110
  - `buildSocketIoRedisAdapterKey(redisNamespace = "")`
110
111
 
112
+ ### `src/server/servedClientBuild.js`
113
+ Exports
114
+ - `announceServedClientBuild({ io, appRoot, logger })`
115
+
116
+ ### `src/shared/servedClientBuild.js`
117
+ Exports
118
+ - `SERVED_CLIENT_BUILD_EVENT`
119
+
111
120
  ### patterns
112
121
 
113
122
  ### `patterns/realtime-application/example/src/placement.js`
@@ -52,6 +52,12 @@ Exports
52
52
  - `normalizeBootstrapPayloadHandler`
53
53
  - `resolveBootstrapErrorStatusCode`
54
54
 
55
+ ### `src/client/clientUpdate/runtime.js`
56
+ Exports
57
+ - `createShellClientUpdateRuntime({ errorRuntime, reload, pageBuildId = pageClientBuildId(), appName = loadedAppName() } = {})`
58
+ Local functions
59
+ - `loadedAppName(documentObject = globalThis.document)`
60
+
55
61
  ### `src/client/components/ShellErrorHost.vue`
56
62
  Exports
57
63
  - None
@@ -62,7 +62,13 @@ or operation boundary. A Feature declares stable named `requires`, optional
62
62
  inputs, and `provides`; `setup()` receives those values directly and returns
63
63
  only the promised outputs. Named actions capture the exact feature APIs they
64
64
  need. Register structural catalogue entries during `setup()` and reserve
65
- `boot()` for long-lived work that starts after composition.
65
+ `boot()` for long-lived work that starts after composition. `shutdown()` stops
66
+ that work. The runtime shuts Features down in reverse order and keeps going
67
+ after one fails; it then rejects with an `AggregateError` holding one error per
68
+ failed Feature, each naming its `providerId`. While shutdown runs,
69
+ `diagnostics().providerShutdowns` lists every shutdown with its status
70
+ (`stopping`, `stopped` or `failed`) and duration, so a host can log which one is
71
+ slow.
66
72
 
67
73
  Capability ids, action ids, routes, events, resources, and placements are
68
74
  stable identities. They are not permission to fetch arbitrary dependencies by