@primafuture/systemd-tasks 1.1.0 → 1.2.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.
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/finalizer.ts","../src/observed-finalization.ts","../src/errors.ts","../src/observed-validation.ts","../src/validation.ts","../src/waiting.ts"],"sourcesContent":["import * as childProcess from 'node:child_process';\nimport * as performance from 'node:perf_hooks';\nimport * as timers from 'node:timers/promises';\nimport * as finalization from './observed-finalization';\nimport * as errors from './errors';\nimport * as runtime from '#runtime';\nimport * as waiting from './waiting';\n\n/** Čte pouze konečný manager-owned stdin; žádná data nepřebírá z task outputu. */\nasync function readBootstrap(): Promise<finalization.Bootstrap> {\n\tconst chunks: Buffer[] = [];\n\tlet bytes = 0;\n\tfor await (const chunk of process.stdin) {\n\t\tconst buffer = Buffer.from(chunk as Uint8Array);\n\t\tbytes += buffer.byteLength;\n\t\tif (bytes > finalization.maximumBootstrapBytes) {\n\t\t\tthrow new errors.TaskError('INVALID_INPUT', 'The finalizer input exceeds its bound.', {\n\t\t\t\treason: 'finalization-bootstrap-limit',\n\t\t\t});\n\t\t}\n\t\tchunks.push(buffer);\n\t}\n\treturn finalization.parse(JSON.parse(Buffer.concat(chunks).toString('utf8')) as unknown);\n}\n\n/** Konečný native callback vlastní standardní Node spawn a cgroup finalizer jednotky. */\nasync function afterRelease(bootstrap: finalization.Bootstrap, timeoutMs: number): Promise<void> {\n\tconst spec = bootstrap.afterRelease.spec;\n\tconst runtimeMs = Math.min(timeoutMs, spec.runtimeLimitMs ?? timeoutMs);\n\tconst control = new waiting.WaitControl({ timeoutMs: runtimeMs });\n\ttry {\n\t\tcontrol.check();\n\t\tawait control.race(new Promise<void>(/** Spawn neposkytuje shell, děděné env ani výstup do veřejné diagnostiky. */ (resolve, reject) => {\n\t\t\tconst child = childProcess.spawn(spec.executable, [...spec.argv], {\n\t\t\t\tcwd: spec.cwd,\n\t\t\t\tenv: { ...spec.env },\n\t\t\t\tstdio: [bootstrap.afterRelease.stdinBase64 === null ? 'ignore' : 'pipe', 'ignore', 'ignore'],\n\t\t\t\tshell: false,\n\t\t\t});\n\t\t\tlet failure: unknown;\n\t\t\tchild.once('error', /** Uchová chybu exec; close uzavře i vlastněné descriptors. */ error => {\n\t\t\t\tfailure = error;\n\t\t\t});\n\t\t\tchild.stdin?.once('error', /** Nedokončený bootstrap se nesmí vydávat za úspěšný callback. */ error => {\n\t\t\t\tfailure = error;\n\t\t\t});\n\t\t\tchild.once('close', /** Výsledek dítěte není výsledek původního payloadu. */ (code, signal) => {\n\t\t\t\tif (failure !== undefined || code !== 0 || signal !== null) {\n\t\t\t\t\treject(new errors.TaskError('RESULT_UNAVAILABLE', 'The after-release command did not complete successfully.', {\n\t\t\t\t\t\treason: 'after-release-failed', taskId: bootstrap.reference.id,\n\t\t\t\t\t}, failure));\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tresolve();\n\t\t\t});\n\t\t\tif (bootstrap.afterRelease.stdinBase64 !== null) {\n\t\t\t\tchild.stdin!.end(Buffer.from(bootstrap.afterRelease.stdinBase64, 'base64'));\n\t\t\t}\n\t\t}));\n\t} finally {\n\t\tcontrol.dispose();\n\t}\n}\n\n/** Po živé fázi uvolní pouze přesný původní task a jednou zavolá konečný cleanup. */\nasync function run(): Promise<void> {\n\tconst bootstrap = await readBootstrap();\n\tconst client = await runtime.connectObserved();\n\t/** Sdílený deadline vzniká až při potvrzení konce, nikdy během živého payloadu. */\n\tconst budget: {\n\t\t/** Absolutní monotonic deadline umožní předat stejný zbývající budget release i callbacku. */\n\t\tdeadline: number | null;\n\t\t/** Jediný lokální cancellation scope pokrývá i asynchronní lookup. */\n\t\tcontrol: waiting.WaitControl | null;\n\t} = { deadline: null, control: null };\n\ttry {\n\t\t/** Deadline začíná po ukončení payloadu a chrání všechny následující fáze. */\n\t\tconst remaining = (): number => {\n\t\t\tif (budget.deadline === null) {\n\t\t\t\tbudget.deadline = performance.performance.now() + bootstrap.timeoutMs;\n\t\t\t\tbudget.control = new waiting.WaitControl({ timeoutMs: bootstrap.timeoutMs });\n\t\t\t}\n\t\t\tbudget.control!.check();\n\t\t\tconst milliseconds = Math.floor(budget.deadline - performance.performance.now());\n\t\t\tif (milliseconds <= 0) {\n\t\t\t\tthrow new errors.TaskError('WAIT_TIMEOUT', 'The finalization deadline expired.', {\n\t\t\t\t\treason: 'finalization-timeout', taskId: bootstrap.reference.id,\n\t\t\t\t});\n\t\t\t}\n\t\t\treturn milliseconds;\n\t\t};\n\t\tfor (;;) {\n\t\t\tbudget.control?.check();\n\t\t\tconst found = await (budget.control === null\n\t\t\t\t? client.lookup(bootstrap.reference)\n\t\t\t\t: budget.control.race(client.lookup(bootstrap.reference)));\n\t\t\tif (found.status === 'not-found') {\n\t\t\t\t// Absence po souběžném release potvrzuje cleanup, nikoli exit status payloadu.\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (found.status === 'incomplete' || found.snapshot.payload.managerTerminal) {\n\t\t\t\tremaining();\n\t\t\t}\n\t\t\tif (found.status === 'found' && found.snapshot.phase === 'completed') {\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (found.status === 'incomplete' || found.snapshot.guardian.managerTerminal) {\n\t\t\t\tconst delayMs = Math.min(remaining(), 50);\n\t\t\t\tawait budget.control!.race(timers.setTimeout(delayMs));\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\ttry {\n\t\t\t\tconst waitOptions = { timeoutMs: budget.deadline === null ? 1000 : Math.min(remaining(), 1000) };\n\t\t\t\tconst snapshot = await (budget.control === null\n\t\t\t\t\t? client.wait(bootstrap.reference, waitOptions)\n\t\t\t\t\t: budget.control.race(client.wait(bootstrap.reference, waitOptions)));\n\t\t\t\tif (snapshot.payload.managerTerminal) {\n\t\t\t\t\tremaining();\n\t\t\t\t}\n\t\t\t\tif (snapshot.phase === 'completed') {\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t} catch (error) {\n\t\t\t\tif (!(error instanceof runtime.TaskError) || (error.code !== 'WAIT_TIMEOUT' && error.code !== 'RESULT_UNAVAILABLE')) {\n\t\t\t\t\tthrow error;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tconst releaseTimeoutMs = remaining();\n\t\tawait budget.control!.race(client.release(bootstrap.reference, { timeoutMs: releaseTimeoutMs }));\n\t\tconst callbackTimeoutMs = remaining();\n\t\tawait budget.control!.race(afterRelease(bootstrap, callbackTimeoutMs));\n\t} finally {\n\t\tbudget.control?.dispose();\n\t\tawait client.disconnect();\n\t}\n}\n\nvoid run().catch(/** Journal dostane pouze vlastní redigovanou chybu, nikdy cizí payload. */ error => {\n\tconst reported = error instanceof errors.TaskError || error instanceof runtime.TaskError\n\t\t? error\n\t\t: new errors.TaskError('RESULT_UNAVAILABLE', 'The observed task finalizer failed.', { reason: 'finalization-failed' });\n\tprocess.stderr.write(`${JSON.stringify(reported.toJSON())}\\n`);\n\t// Tento executable musí skončit i s živým dítětem: jeho cgroup uklidí manager\n\t// přes SIGTERM a TimeoutStopUSec, nikoli Node přímým SIGKILL.\n\tprocess.exit(1);\n});\n","import * as crypto from 'node:crypto';\nimport * as fs from 'node:fs/promises';\nimport * as path from 'node:path';\nimport * as errors from './errors';\nimport * as observedValidation from './observed-validation';\nimport * as systemd from './systemd';\nimport * as validation from './validation';\nimport type * as observedTypes from './observed-types';\nimport type * as transport from './transport';\nimport type * as types from './types';\n\n/** Build banner určuje packaged executable stejně jako u observed guardianu. */\ndeclare const __systemdTasksRuntimeDirectory: string;\n\n/** Zahrnuje bounded stdin po base64 i metadata; limit platí před manager submission. */\nexport const maximumBootstrapBytes = observedValidation.maximumObservedInputBytes * 2;\n\n/** Privátní finite vstup finalizeru bez závislosti na datech jeho konzumenta. */\nexport interface Bootstrap {\n\t/** Exact původní task, jehož běžící fázi finalizer nikdy nepřerušuje. */\n\treadonly reference: observedTypes.ObservedTaskReference;\n\t/** Budget dokončovací fáze, oddělený od neomezeného čekání na konec payloadu. */\n\treadonly timeoutMs: number;\n\t/** Normalizovaný konečný příkaz a jeho stdin bez dalšího task/journal protokolu. */\n\treadonly afterRelease: {\n\t\t/** Native command spuštěný bez shellu po release. */\n\t\treadonly spec: types.TaskSpec;\n\t\t/** Canonical finite stdin snapshot; null znamená /dev/null. */\n\t\treadonly stdinBase64: string | null;\n\t};\n}\n\n/** Vyžaduje kompletní invocation identitu ještě před registrací pomocného procesu. */\nfunction requireCompleteReference(value: unknown): observedTypes.ObservedTaskReference {\n\tconst reference = observedValidation.validateObservedReference(value);\n\tif (!reference.invocationId || !reference.retentionInvocationId || !reference.guardianInvocationId) {\n\t\tvalidation.invalid('finalization-reference-incomplete');\n\t}\n\treturn reference;\n}\n\n/** Kopíruje mutable vstupy, odmítne překlepy a zachová deterministickou registraci. */\nexport function prepare(reference: observedTypes.ObservedTaskReference, value: observedTypes.ObservedFinalizationOptions): Bootstrap {\n\tconst source = validation.record(value, 'finalization-options');\n\tvalidation.keys(source, ['afterRelease', 'timeoutMs'], 'finalization-option-keys');\n\treturn Object.freeze({\n\t\treference: requireCompleteReference(reference),\n\t\ttimeoutMs: validation.duration(source.timeoutMs, validation.maximumLocalTimeoutMs, 'finalization-timeout'),\n\t\tafterRelease: observedValidation.normalizeSpec(source.afterRelease),\n\t});\n}\n\n/** Revaliduje privátní JSON vstup stejnými command a stdin pravidly jako public observed API. */\nexport function parse(value: unknown): Bootstrap {\n\tconst source = validation.record(value, 'finalization-bootstrap');\n\tvalidation.keys(source, ['reference', 'timeoutMs', 'afterRelease'], 'finalization-bootstrap-keys');\n\tconst afterRelease = validation.record(source.afterRelease, 'finalization-after-release');\n\tvalidation.keys(afterRelease, ['spec', 'stdinBase64'], 'finalization-after-release-keys');\n\tconst spec = validation.validateSpec(afterRelease.spec);\n\tlet stdin: Buffer | null = null;\n\tif (afterRelease.stdinBase64 !== null) {\n\t\tconst encoded = validation.string(afterRelease.stdinBase64, 'finalization-stdin');\n\t\tif (encoded.length > 4 * Math.ceil(observedValidation.maximumObservedInputBytes / 3)) {\n\t\t\tvalidation.invalid('finalization-stdin-limit');\n\t\t}\n\t\tstdin = Buffer.from(encoded, 'base64');\n\t\tif (stdin.toString('base64') !== encoded) {\n\t\t\tvalidation.invalid('finalization-stdin-base64');\n\t\t}\n\t}\n\treturn prepare(requireCompleteReference(source.reference), {\n\t\ttimeoutMs: validation.duration(source.timeoutMs, validation.maximumLocalTimeoutMs, 'finalization-timeout'),\n\t\tafterRelease: { ...spec, stdin },\n\t});\n}\n\n/** Jméno je pevně odvozené od původního tasku; caller nemůže vybrat cizí jednotku. */\nexport function unitName(reference: observedTypes.ObservedTaskReference): string {\n\treturn reference.unitName.replace(/\\.service$/u, '-finalizer.service');\n}\n\n/** Marker váže reference i přesný callback, aniž by zveřejnil jeho argv, env nebo stdin. */\nfunction marker(bootstrap: Bootstrap): string {\n\tconst fingerprint = crypto.createHash('sha256').update(JSON.stringify(bootstrap)).digest('hex');\n\treturn `@primafuture/systemd-tasks:observed-finalizer:v1:${bootstrap.reference.id}:${fingerprint}`;\n}\n\n/** Kolize nebo neúspěšný finalizer nejsou potvrzené opakované přijetí. */\nexport function assertRegistered(bootstrap: Bootstrap, unit: transport.RawUnit): void {\n\tconst properties = unit.properties;\n\tif (properties.Transient !== true || properties.Description !== marker(bootstrap)\n\t\t|| properties.Type !== 'exec' || properties.ExitType !== 'main'\n\t\t|| properties.Restart !== 'no' || properties.KillMode !== 'control-group'\n\t\t|| properties.RemainAfterExit !== false || properties.CollectMode !== 'inactive-or-failed') {\n\t\tthrow new errors.TaskError('IDENTITY_CONFLICT', 'The finalizer is not the registered owned instance.', {\n\t\t\treason: 'finalizer-ownership', taskId: bootstrap.reference.id,\n\t\t});\n\t}\n\tif (properties.ActiveState === 'failed') {\n\t\tthrow new errors.TaskError('RESULT_UNAVAILABLE', 'The registered finalizer failed.', {\n\t\t\treason: 'finalizer-failed', taskId: bootstrap.reference.id,\n\t\t});\n\t}\n}\n\n/** Ověří packaged executable před jediným StartTransientUnit pokusem. */\nasync function executablePath(): Promise<string> {\n\tconst directory = typeof __systemdTasksRuntimeDirectory === 'string'\n\t\t? __systemdTasksRuntimeDirectory\n\t\t: path.resolve(process.cwd(), 'src');\n\tconst executable = path.basename(directory) === 'src'\n\t\t? path.resolve(directory, '..', 'dist', 'finalizer.mjs')\n\t\t: path.join(directory, 'finalizer.mjs');\n\ttry {\n\t\tconst stat = await fs.stat(executable);\n\t\tif (!stat.isFile()) {\n\t\t\tthrow new Error('Finalizer is not a regular file.');\n\t\t}\n\t\tawait fs.access(executable, fs.constants.R_OK);\n\t} catch (error) {\n\t\tthrow new errors.TaskError('UNSUPPORTED_ENVIRONMENT', 'The packaged finalizer is unavailable.', {\n\t\t\treason: 'finalizer-unavailable',\n\t\t}, error);\n\t}\n\treturn executable;\n}\n\n/** Samostatná přechodná jednotka nepřebírá lifetime, restart ani output původního tasku. */\nexport async function creationProperties(bootstrap: Bootstrap, inheritedEnvironment: readonly string[]): Promise<readonly transport.Property[]> {\n\tconst input = Buffer.from(JSON.stringify(bootstrap), 'utf8');\n\tif (input.byteLength > maximumBootstrapBytes) {\n\t\tvalidation.invalid('finalization-bootstrap-limit');\n\t}\n\tconst executable = await executablePath();\n\tconst properties = [\n\t\tsystemd.property('Description', 's', marker(bootstrap)),\n\t\tsystemd.property('Type', 's', 'exec'),\n\t\tsystemd.property('ExitType', 's', 'main'),\n\t\tsystemd.property('Restart', 's', 'no'),\n\t\tsystemd.property('RemainAfterExit', 'b', false),\n\t\tsystemd.property('CollectMode', 's', 'inactive-or-failed'),\n\t\tsystemd.property('KillMode', 's', 'control-group'),\n\t\tsystemd.property('TimeoutStopUSec', 't', BigInt(bootstrap.afterRelease.spec.stopGraceMs) * 1000n),\n\t\tsystemd.property('RuntimeMaxUSec', 't', systemd.infinityUsec),\n\t\tsystemd.property('WorkingDirectory', 's', '/'),\n\t\tsystemd.property('Environment', 'as', []),\n\t\tsystemd.property('UnsetEnvironment', 'as', systemd.unsetEnvironment(inheritedEnvironment)),\n\t\tsystemd.property('ExecStartEx', 'a(sasas)', [[process.execPath, [process.execPath, executable], ['no-env-expand']]]),\n\t\tsystemd.property('StandardInput', 's', 'data'),\n\t\tsystemd.property('StandardInputData', 'ay', input),\n\t\tsystemd.property('StandardOutput', 's', 'null'),\n\t\tsystemd.property('StandardError', 's', 'journal'),\n\t];\n\tfor (const resource of bootstrap.afterRelease.spec.systemdProperties ?? []) {\n\t\tproperties.push(systemd.property(resource.name, resource.signature, BigInt(resource.value)));\n\t}\n\treturn Object.freeze(properties);\n}\n","import * as util from 'node:util';\nimport type * as types from './types';\n\n/** A recoverable API error with stable categories and redacted default formatting. */\nexport class TaskError extends Error {\n\t/** Stable category used by applications instead of parsing human-readable messages. */\n\treadonly code: types.ErrorCode;\n\t/** Safe delivery and identity metadata; never contains a command specification. */\n\treadonly details: types.ErrorDetails;\n\n\t/** Preserve the original cause for explicit access while keeping default output redacted. */\n\tconstructor(code: types.ErrorCode, message: string, details: types.ErrorDetails = {}, cause?: unknown) {\n\t\tsuper(message, cause === undefined ? undefined : { cause });\n\t\tthis.name = 'TaskError';\n\t\tthis.code = code;\n\t\tthis.details = Object.freeze({ ...details });\n\t}\n\n\t/** Serialization deliberately excludes raw causes, stack contents, and request payloads. */\n\ttoJSON(): {\n\t\t/** Stable error class name for serialized consumers. */\n\t\tname: string;\n\t\t/** Public recovery category. */\n\t\tcode: types.ErrorCode;\n\t\t/** Redacted explanation safe for default logs. */\n\t\tmessage: string;\n\t\t/** Safe delivery evidence without raw causes. */\n\t\tdetails: types.ErrorDetails;\n\t} {\n\t\treturn { name: this.name, code: this.code, message: this.message, details: this.details };\n\t}\n\n\t/** Console and util.inspect must not expand a transport cause containing request data. */\n\t[util.inspect.custom](): string {\n\t\treturn `${this.name} [${this.code}]: ${this.message}`;\n\t}\n}\n\n/** Extract an OS or transport category without copying its potentially sensitive message. */\nexport function errorCode(error: unknown): string | undefined {\n\tif (typeof error !== 'object' || error === null) return undefined;\n\tif ('code' in error && typeof error.code === 'string') return error.code;\n\treturn undefined;\n}\n\n/** Identify an explicit manager or bus error reply separately from local disconnection. */\nexport function dbusErrorName(error: unknown): string | undefined {\n\tif (typeof error !== 'object' || error === null) return undefined;\n\tif ('type' in error && typeof error.type === 'string') return error.type;\n\treturn undefined;\n}\n","import * as crypto from 'node:crypto';\nimport * as validation from './validation';\nimport type * as observedTypes from './observed-types';\nimport type * as types from './types';\n\n/** Konzervativní strop se vejde i po base64 serializaci do systemd manager state řádku. */\nexport const maximumObservedInputBytes = 512 * 1024;\n\n/** Nejdelší canonical base64 reprezentace povoleného stdin, kontrolovaná před alokací Bufferu. */\nconst maximumObservedInputBase64Characters = 4 * Math.ceil(maximumObservedInputBytes / 3);\n\n/** Samostatný namespace brání kolizi se základními dvoujednotkovými tasky. */\nconst observedUnitPrefix = 'pf-systemd-tasks-observed-';\n\n/** Exact identity klíče zajišťují, že uložený intent nemůže nést skryté policy rozšíření. */\nconst observedIdentityKeys = [\n\t'kind', 'version', 'protocolVersion', 'id', 'unitName', 'retentionUnitName',\n\t'guardianUnitName', 'managerScope', 'fingerprint',\n];\n\n/** Normalizuje příkaz a konečný stdin snapshot bez otevření busu nebo descriptoru. */\nexport function normalizeSpec(value: unknown): { readonly spec: types.TaskSpec; readonly stdinBase64: string | null } {\n\tconst source = validation.record(value, 'observed-spec-object');\n\tvalidation.keys(source, ['executable', 'argv', 'cwd', 'env', 'runtimeLimitMs', 'stopGraceMs', 'systemdProperties', 'stdin'], 'observed-spec-keys');\n\tconst spec = validation.validateSpec({\n\t\texecutable: source.executable,\n\t\targv: source.argv,\n\t\tcwd: source.cwd,\n\t\tenv: source.env,\n\t\truntimeLimitMs: source.runtimeLimitMs,\n\t\tstopGraceMs: source.stopGraceMs,\n\t\t...(source.systemdProperties === undefined ? {} : { systemdProperties: source.systemdProperties }),\n\t});\n\tif (source.stdin === null) return Object.freeze({ spec, stdinBase64: null });\n\tlet bytes: Buffer;\n\tif (typeof source.stdin === 'string') bytes = Buffer.from(source.stdin, 'utf8');\n\telse if (source.stdin instanceof Uint8Array) bytes = Buffer.from(source.stdin);\n\telse return validation.invalid('observed-stdin');\n\tif (bytes.byteLength > maximumObservedInputBytes) validation.invalid('observed-stdin-limit');\n\treturn Object.freeze({ spec, stdinBase64: bytes.toString('base64') });\n}\n\n/** Hash zahrnuje přesný canonical stdin vedle normalizovaného execution kontraktu. */\nfunction fingerprint(spec: types.TaskSpec, stdinBase64: string | null): string {\n\treturn crypto.createHash('sha256').update(JSON.stringify({ spec, stdinBase64 })).digest('hex');\n}\n\n/** Připraví úplný observed intent lokálně a zkopíruje mutable Uint8Array vstup. */\nexport function prepareObserved(spec: observedTypes.ObservedTaskSpec): observedTypes.ObservedTaskIntent {\n\tconst normalized = normalizeSpec(spec);\n\tconst id = crypto.randomUUID();\n\treturn Object.freeze({\n\t\tkind: 'observed', version: 1, protocolVersion: 1, id,\n\t\tunitName: `${observedUnitPrefix}${id}.service`,\n\t\tretentionUnitName: `${observedUnitPrefix}${id}-retention.service`,\n\t\tguardianUnitName: `${observedUnitPrefix}${id}-guardian.service`,\n\t\tmanagerScope: 'user', fingerprint: fingerprint(normalized.spec, normalized.stdinBase64),\n\t\tspec: normalized.spec, stdinBase64: normalized.stdinBase64,\n\t});\n}\n\n/** Ověří odvozená jména a verzovaný identity kontrakt bez důvěry v JSON vstup. */\nfunction identity(source: Record<string, unknown>): observedTypes.ObservedTaskIdentity {\n\tif (source.kind !== 'observed' || source.version !== 1 || source.protocolVersion !== 1 || source.managerScope !== 'user') validation.invalid('observed-identity-version-or-scope');\n\tconst id = validation.uuid(source.id, 'observed-identity-id');\n\tif (source.unitName !== `${observedUnitPrefix}${id}.service`\n\t\t|| source.retentionUnitName !== `${observedUnitPrefix}${id}-retention.service`\n\t\t|| source.guardianUnitName !== `${observedUnitPrefix}${id}-guardian.service`) validation.invalid('observed-identity-unit-name');\n\treturn Object.freeze({\n\t\tkind: 'observed', version: 1, protocolVersion: 1, id,\n\t\tunitName: source.unitName as string,\n\t\tretentionUnitName: source.retentionUnitName as string,\n\t\tguardianUnitName: source.guardianUnitName as string,\n\t\tmanagerScope: 'user', fingerprint: validation.digest(source.fingerprint, 'observed-identity-fingerprint'),\n\t});\n}\n\n/** Ověří canonical base64 v uloženém intentu a vynutí stejný raw stdin limit. */\nfunction validateStdinBase64(value: unknown): string | null {\n\tif (value === null) return null;\n\tconst encoded = validation.string(value, 'observed-stdin-base64');\n\tif (encoded.length > maximumObservedInputBase64Characters || encoded.length % 4 !== 0) validation.invalid('observed-stdin-base64');\n\tconst bytes = Buffer.from(encoded, 'base64');\n\tif (bytes.byteLength > maximumObservedInputBytes || bytes.toString('base64') !== encoded) validation.invalid('observed-stdin-base64');\n\treturn encoded;\n}\n\n/** Revaliduje uložený observed intent a detekuje změnu příkazu nebo stdin. */\nexport function validateObservedIntent(value: unknown): observedTypes.ObservedTaskIntent {\n\tconst source = validation.record(value, 'observed-intent-object');\n\tvalidation.keys(source, [...observedIdentityKeys, 'spec', 'stdinBase64'], 'observed-intent-keys');\n\tconst checkedIdentity = identity(source);\n\tconst spec = validation.validateSpec(source.spec);\n\tconst stdinBase64 = validateStdinBase64(source.stdinBase64);\n\tif (fingerprint(spec, stdinBase64) !== checkedIdentity.fingerprint) validation.invalid('observed-intent-fingerprint-mismatch');\n\treturn Object.freeze({ ...checkedIdentity, spec, stdinBase64 });\n}\n\n/** Ověří exact reference včetně explicitně chybějící guardian invocation evidence. */\nexport function validateObservedReference(value: unknown): observedTypes.ObservedTaskReference {\n\tconst source = validation.record(value, 'observed-reference-object');\n\tvalidation.keys(source, [...observedIdentityKeys, 'manager', 'invocationId', 'retentionInvocationId', 'guardianInvocationId'], 'observed-reference-keys');\n\treturn Object.freeze({\n\t\t...identity(source), manager: validation.validateManagerIdentity(source.manager),\n\t\tinvocationId: validation.validateInvocationId(source.invocationId),\n\t\tretentionInvocationId: validation.validateInvocationId(source.retentionInvocationId),\n\t\tguardianInvocationId: validation.validateInvocationId(source.guardianInvocationId),\n\t});\n}\n\n/** Rozliší persisted intent od exact reference bez načítání command dat do diagnostiky. */\nexport function validateObservedTarget(value: unknown): observedTypes.ObservedTaskIntent | observedTypes.ObservedTaskReference {\n\tconst source = validation.record(value, 'observed-target-object');\n\treturn 'spec' in source ? validateObservedIntent(source) : validateObservedReference(source);\n}\n\n/** Levný discriminator směruje společné client metody ještě před plnou validací. */\nexport function isObservedValue(value: unknown): boolean {\n\treturn typeof value === 'object' && value !== null && !Array.isArray(value) && 'kind' in value && value.kind === 'observed';\n}\n\n/** Vrátí pouze ne-citlivou identitu vhodnou do receiptů a not-found výsledků. */\nexport function identityOnly(value: observedTypes.ObservedTaskIdentity): observedTypes.ObservedTaskIdentity {\n\treturn Object.freeze({\n\t\tkind: 'observed', version: 1, protocolVersion: 1, id: value.id,\n\t\tunitName: value.unitName, retentionUnitName: value.retentionUnitName,\n\t\tguardianUnitName: value.guardianUnitName, managerScope: 'user', fingerprint: value.fingerprint,\n\t});\n}\n\n/** Vytvoří ne-citlivý ownership marker pro jednu roli observed topologie. */\nexport function marker(value: observedTypes.ObservedTaskIdentity, role: 'task' | 'retention' | 'guardian'): string {\n\treturn `@primafuture/systemd-tasks:observed:v1:${value.id}:${value.fingerprint}:${role}`;\n}\n\n/** Dekóduje již validovaný stdin snapshot těsně před sestavením manager properties. */\nexport function stdinBytes(intent: observedTypes.ObservedTaskIntent): Buffer | null {\n\treturn intent.stdinBase64 === null ? null : Buffer.from(intent.stdinBase64, 'base64');\n}\n","import * as crypto from 'node:crypto';\nimport * as path from 'node:path';\nimport * as errors from './errors';\nimport type * as types from './types';\n\n/** Canonical task namespace; a caller cannot supply arbitrary service names. */\nconst unitPrefix = 'pf-systemd-tasks-';\n/** Maximum JavaScript timer delay without Node's overflow-to-one-millisecond behavior. */\nexport const maximumLocalTimeoutMs = 2_147_483_647;\n/** Upper bound that preserves exact millisecond input and uint64 microsecond conversion. */\nconst maximumDurationMs = Number.MAX_SAFE_INTEGER;\n/** Exact keys of serialized ownership evidence, shared by intentions and references. */\nconst identityKeys = ['version', 'id', 'unitName', 'retentionUnitName', 'managerScope', 'fingerprint'];\n\n/** Report validation errors without copying the offending value into the error. */\nexport function invalid(reason: string): never {\n\tthrow new errors.TaskError('INVALID_INPUT', 'The task request is invalid.', { reason, mutationOutcome: 'not-submitted' });\n}\n\n/** Require a plain data object, including JSON objects with a null prototype. */\nexport function record(value: unknown, reason: string): Record<string, unknown> {\n\tif (value === null || typeof value !== 'object' || Array.isArray(value)) invalid(reason);\n\tconst prototype: unknown = Object.getPrototypeOf(value);\n\tif (prototype !== Object.prototype && prototype !== null) invalid(reason);\n\treturn value as Record<string, unknown>;\n}\n\n/** Catch misspellings and unsupported extensions before any I/O or D-Bus mutation. */\nexport function keys(value: Record<string, unknown>, allowed: readonly string[], reason: string): void {\n\tif (Object.keys(value).some(/** Reject keys outside the explicit contract allowlist. */ key => !allowed.includes(key)) || Object.getOwnPropertySymbols(value).length > 0) invalid(reason);\n}\n\n/** D-Bus strings cannot contain NUL; all other characters remain literal. */\nexport function string(value: unknown, reason: string): string {\n\tif (typeof value !== 'string' || value.includes('\\0')) invalid(reason);\n\tfor (const character of value) {\n\t\tconst code = character.codePointAt(0)!;\n\t\tif (code >= 0xd800 && code <= 0xdfff) invalid(reason);\n\t}\n\treturn value;\n}\n\n/** Validate absolute Linux paths without changing symlink-sensitive path semantics. */\nexport function absolutePath(value: unknown, reason: string): string {\n\tconst result = string(value, reason);\n\tif (!path.posix.isAbsolute(result)) invalid(reason);\n\treturn result;\n}\n\n/** Keep zero distinct from unlimited: zero timers are rejected instead of disabling limits. */\nexport function duration(value: unknown, maximum: number, reason: string): number {\n\tif (typeof value !== 'number' || !Number.isSafeInteger(value) || value <= 0 || value > maximum) invalid(reason);\n\treturn value;\n}\n\n/** Normalize and copy public command data into a deterministic JSON representation. */\nexport function validateSpec(value: unknown): types.TaskSpec {\n\tconst source = record(value, 'spec-object');\n\tkeys(source, ['executable', 'argv', 'cwd', 'env', 'runtimeLimitMs', 'stopGraceMs', 'systemdProperties'], 'spec-keys');\n\tconst executable = absolutePath(source.executable, 'executable-path');\n\tconst cwd = absolutePath(source.cwd, 'cwd-path');\n\tif (!Array.isArray(source.argv)) invalid('argv-array');\n\tconst argv = Object.freeze(source.argv.map(/** Validate literal arguments without shell expansion or coercion. */ value => string(value, 'argv-string')));\n\tconst environment = record(source.env, 'environment-object');\n\tconst env: Record<string, string> = Object.create(null) as Record<string, string>;\n\tfor (const key of Object.keys(environment).sort()) {\n\t\tif (!/^[A-Za-z_][A-Za-z0-9_]*$/.test(key)) invalid('environment-name');\n\t\tenv[key] = string(environment[key], 'environment-value');\n\t}\n\tconst runtimeLimitMs = source.runtimeLimitMs === null ? null : duration(source.runtimeLimitMs, maximumDurationMs, 'runtime-limit');\n\tconst stopGraceMs = duration(source.stopGraceMs, maximumDurationMs, 'stop-grace');\n\tconst properties: types.SystemdProperty[] = [];\n\tif (source.systemdProperties !== undefined) {\n\t\tif (!Array.isArray(source.systemdProperties)) invalid('properties-array');\n\t\tconst names = new Set<string>();\n\t\tfor (const value of source.systemdProperties) {\n\t\t\tconst property = record(value, 'property-object');\n\t\t\tkeys(property, ['name', 'signature', 'value'], 'property-keys');\n\t\t\tif (property.name !== 'CPUWeight' && property.name !== 'IOWeight') invalid('reserved-or-unsupported-property');\n\t\t\tif (property.signature !== 't') invalid('property-signature');\n\t\t\tif (names.has(property.name)) invalid('duplicate-property');\n\t\t\tnames.add(property.name);\n\t\t\tproperties.push(Object.freeze({ name: property.name, signature: 't', value: duration(property.value, 10000, 'property-value') }));\n\t\t}\n\t}\n\tproperties.sort(/** Canonicalize resource ordering for a stable specification fingerprint. */ (left, right) => left.name.localeCompare(right.name));\n\treturn Object.freeze({ executable, argv, cwd, env: Object.freeze(env), runtimeLimitMs, stopGraceMs, systemdProperties: Object.freeze(properties) });\n}\n\n/** Hash normalized command data without exposing that data in unit descriptions. */\nexport function specFingerprint(spec: types.TaskSpec): string {\n\treturn crypto.createHash('sha256').update(JSON.stringify(spec)).digest('hex');\n}\n\n/** Ověří canonical random UUID používané ve všech odvozených názvech jednotek. */\nexport function uuid(value: unknown, reason: string): string {\n\tconst result = string(value, reason);\n\tif (!/^[0-9a-f]{8}-[0-9a-f]{4}-4[0-9a-f]{3}-[89ab][0-9a-f]{3}-[0-9a-f]{12}$/.test(result)) invalid(reason);\n\treturn result;\n}\n\n/** Ověří lowercase SHA-256 bez zveřejnění původních fingerprintovaných dat. */\nexport function digest(value: unknown, reason: string): string {\n\tconst result = string(value, reason);\n\tif (!/^[0-9a-f]{64}$/.test(result)) invalid(reason);\n\treturn result;\n}\n\n/** Prepare an intention locally; no connection, file opening, or process start occurs. */\nexport function prepare(spec: types.TaskSpec): types.TaskIntent {\n\tconst normalized = validateSpec(spec);\n\tconst id = crypto.randomUUID();\n\treturn Object.freeze({ version: 1, id, unitName: `${unitPrefix}${id}.service`, retentionUnitName: `${unitPrefix}${id}-retention.service`, managerScope: 'user', fingerprint: specFingerprint(normalized), spec: normalized });\n}\n\n/** Validate derived names and a versioned identity without trusting serialized input. */\nfunction identity(source: Record<string, unknown>): types.TaskIdentity {\n\tif (source.version !== 1 || source.managerScope !== 'user') invalid('identity-version-or-scope');\n\tconst id = uuid(source.id, 'identity-id');\n\tif (source.unitName !== `${unitPrefix}${id}.service` || source.retentionUnitName !== `${unitPrefix}${id}-retention.service`) invalid('identity-unit-name');\n\tconst fingerprint = digest(source.fingerprint, 'identity-fingerprint');\n\treturn Object.freeze({ version: 1, id, unitName: source.unitName as string, retentionUnitName: source.retentionUnitName as string, managerScope: 'user', fingerprint });\n}\n\n/** Revalidate stored intentions and detect changes to their command configuration. */\nexport function validateIntent(value: unknown): types.TaskIntent {\n\tconst source = record(value, 'intent-object');\n\tkeys(source, [...identityKeys, 'spec'], 'intent-keys');\n\tconst validatedIdentity = identity(source);\n\tconst spec = validateSpec(source.spec);\n\tif (specFingerprint(spec) !== validatedIdentity.fingerprint) invalid('intent-fingerprint-mismatch');\n\treturn Object.freeze({ ...validatedIdentity, spec });\n}\n\n/** Null explicitly records missing invocation evidence; present IDs have exact wire length. */\nexport function validateInvocationId(value: unknown): string | null {\n\tif (value === null) return null;\n\tconst result = string(value, 'invocation-id');\n\tif (!/^[0-9a-f]{32}$/.test(result)) invalid('invocation-id');\n\treturn result;\n}\n\n/** Validate the persisted manager binding without contacting another manager. */\nexport function validateManagerIdentity(value: unknown): types.ManagerIdentity {\n\tconst source = record(value, 'manager-identity');\n\tkeys(source, ['scope', 'uid', 'machineId', 'bootId', 'busId', 'owner'], 'manager-keys');\n\tif (source.scope !== 'user' || typeof source.uid !== 'number' || !Number.isSafeInteger(source.uid) || source.uid < 0) invalid('manager-scope-or-uid');\n\tconst machineId = string(source.machineId, 'machine-id');\n\tconst busId = string(source.busId, 'bus-id');\n\tconst bootId = string(source.bootId, 'boot-id');\n\tconst owner = string(source.owner, 'manager-owner');\n\tif (!/^[0-9a-f]{32}$/.test(machineId) || !/^[0-9a-f]{32}$/.test(busId)) invalid('manager-identifiers');\n\tif (!/^[0-9a-f]{8}(?:-[0-9a-f]{4}){3}-[0-9a-f]{12}$/.test(bootId) || !/^:[0-9]+\\.[0-9]+$/.test(owner)) invalid('manager-identifiers');\n\treturn Object.freeze({ scope: 'user', uid: source.uid, machineId, bootId, busId, owner });\n}\n\n/** Reference validation preserves absent evidence rather than silently upgrading it. */\nexport function validateReference(value: unknown): types.TaskReference {\n\tconst source = record(value, 'reference-object');\n\tkeys(source, [...identityKeys, 'manager', 'invocationId', 'retentionInvocationId'], 'reference-keys');\n\treturn Object.freeze({ ...identity(source), manager: validateManagerIdentity(source.manager), invocationId: validateInvocationId(source.invocationId), retentionInvocationId: validateInvocationId(source.retentionInvocationId) });\n}\n\n/** Distinguish an intention from an exact observed reference at API boundaries. */\nexport function validateTarget(value: unknown): types.TaskIntent | types.TaskReference {\n\tconst source = record(value, 'target-object');\n\treturn 'spec' in source ? validateIntent(source) : validateReference(source);\n}\n\n/** Copy only ownership fields when returning receipts or diagnostics. */\nexport function identityOnly(value: types.TaskIdentity): types.TaskIdentity {\n\treturn Object.freeze({ version: value.version, id: value.id, unitName: value.unitName, retentionUnitName: value.retentionUnitName, managerScope: value.managerScope, fingerprint: value.fingerprint });\n}\n\n/** Produce a non-secret ownership marker shared by creation and later lookup. */\nexport function marker(value: types.TaskIdentity, role: 'task' | 'retention'): string {\n\treturn `@primafuture/systemd-tasks:v1:${value.id}:${value.fingerprint}:${role}`;\n}\n\n/** Validate one explicit standard descriptor without opening files. */\nfunction channel(value: unknown, output: boolean): types.TaskInput | types.TaskOutput {\n\tconst source = record(value, 'io-channel');\n\tif (source.type === 'null') {\n\t\tkeys(source, ['type'], 'null-io-keys');\n\t\treturn Object.freeze({ type: 'null' });\n\t}\n\tif (source.type === 'fd') {\n\t\tkeys(source, ['type', 'fd'], 'fd-io-keys');\n\t\tif (typeof source.fd !== 'number' || !Number.isInteger(source.fd) || source.fd < 0 || source.fd > 2_147_483_647) invalid('file-descriptor');\n\t\treturn Object.freeze({ type: 'fd', fd: source.fd });\n\t}\n\tif (source.type === 'file') {\n\t\tkeys(source, output ? ['type', 'path', 'mode'] : ['type', 'path'], 'file-io-keys');\n\t\tconst filePath = absolutePath(source.path, 'io-file-path');\n\t\tif (!output) return Object.freeze({ type: 'file', path: filePath });\n\t\tif (source.mode !== 'append' && source.mode !== 'truncate') invalid('output-mode');\n\t\treturn Object.freeze({ type: 'file', path: filePath, mode: source.mode });\n\t}\n\treturn invalid('io-type');\n}\n\n/** Validate every channel, including obvious shared-path conflicts, before any I/O. */\nexport function validateIO(value: unknown): types.TaskIO {\n\tconst source = record(value, 'io-object');\n\tkeys(source, ['stdin', 'stdout', 'stderr'], 'io-keys');\n\tconst stdin = channel(source.stdin, false) as types.TaskInput;\n\tconst stdout = channel(source.stdout, true) as types.TaskOutput;\n\tconst stderr = channel(source.stderr, true) as types.TaskOutput;\n\tif (stdout.type === 'file' && stderr.type === 'file' && stdout.path === stderr.path && stdout.mode !== stderr.mode) invalid('conflicting-output-modes');\n\treturn Object.freeze({ stdin, stdout, stderr });\n}\n\n/** Validate local cancellation before subscription or mutation starts. */\nexport function validateWaitOptions(value: unknown = {}, stop = false): types.StopOptions {\n\tconst source = record(value, 'wait-options');\n\tkeys(source, stop ? ['signal', 'timeoutMs', 'wait'] : ['signal', 'timeoutMs'], 'wait-option-keys');\n\tif (source.signal !== undefined && !(source.signal instanceof AbortSignal)) invalid('abort-signal');\n\tif (source.wait !== undefined && typeof source.wait !== 'boolean') invalid('stop-wait');\n\treturn {\n\t\t...(source.signal === undefined ? {} : { signal: source.signal as AbortSignal }),\n\t\t...(source.timeoutMs === undefined ? {} : { timeoutMs: duration(source.timeoutMs, maximumLocalTimeoutMs, 'wait-timeout') }),\n\t\t...(source.wait === undefined ? {} : { wait: source.wait as boolean }),\n\t};\n}\n\n/** Validate connection controls without contacting systemd or loading native sockets. */\nexport function validateConnectOptions(value: unknown = {}): Required<Pick<types.ConnectOptions, 'requestTimeoutMs'>> & Pick<types.ConnectOptions, 'onDiagnostic'> {\n\tconst source = record(value, 'connect-options');\n\tkeys(source, ['requestTimeoutMs', 'onDiagnostic'], 'connect-option-keys');\n\tif (source.onDiagnostic !== undefined && typeof source.onDiagnostic !== 'function') invalid('diagnostic-sink');\n\treturn {\n\t\trequestTimeoutMs: source.requestTimeoutMs === undefined ? 5000 : duration(source.requestTimeoutMs, maximumLocalTimeoutMs, 'request-timeout'),\n\t\t...(source.onDiagnostic === undefined ? {} : { onDiagnostic: source.onDiagnostic as (event: types.DiagnosticEvent) => void }),\n\t};\n}\n","import * as errors from './errors';\nimport type * as types from './types';\n\n/** A local deadline and abort scope that never cancels the underlying task or shared read. */\nexport class WaitControl {\n\t/** Internal cancellation combines the caller's abort with a local deadline. */\n\tprivate readonly controller = new AbortController();\n\t/** Local timer, absent for an explicitly unbounded wait. */\n\tprivate readonly timer: ReturnType<typeof setTimeout> | undefined;\n\t/** Caller signal whose listener must be removed at settlement. */\n\tprivate readonly external: AbortSignal | undefined;\n\t/** Captured listener identity allows deterministic cleanup. */\n\tprivate readonly onAbort: () => void;\n\n\t/** A timeout is an observation deadline, never a manager escalation timeout. */\n\tconstructor(options: types.WaitOptions) {\n\t\tthis.external = options.signal;\n\t\tthis.onAbort = /** Propagate caller cancellation into this local wait scope only. */ () => this.controller.abort(new errors.TaskError('WAIT_ABORTED', 'Local waiting was aborted.'));\n\t\tif (options.timeoutMs !== undefined) this.timer = setTimeout(/** Expire local observation without changing systemd execution timers. */ () => this.controller.abort(new errors.TaskError('WAIT_TIMEOUT', 'The local waiting deadline expired.')), options.timeoutMs);\n\t\tif (this.external?.aborted) this.onAbort();\n\t\telse this.external?.addEventListener('abort', this.onAbort, { once: true });\n\t}\n\n\t/** Refuse an already-cancelled operation before it can submit a mutation. */\n\tcheck(): void {\n\t\tif (this.controller.signal.aborted) throw this.controller.signal.reason;\n\t}\n\n\t/** Stop this caller's observation while leaving a shared request or server mutation intact. */\n\tasync race<T>(promise: Promise<T>): Promise<T> {\n\t\tif (this.controller.signal.aborted) {\n\t\t\tvoid promise.catch(/** Consume eventual settlement of work that outlives the cancelled caller. */ () => { /* The underlying shared read or mutation still owns its settlement. */ });\n\t\t\tthis.check();\n\t\t}\n\t\tconst signal = this.controller.signal;\n\t\tlet abort: (() => void) | undefined;\n\t\tconst cancelled = new Promise<never>(/** Bridge local cancellation into the current asynchronous observation. */ (_resolve, reject) => {\n\t\t\tabort = /** Reject with the original local cancellation category. */ () => reject(signal.reason);\n\t\t\tsignal.addEventListener('abort', abort, { once: true });\n\t\t});\n\t\ttry { return await Promise.race([promise, cancelled]); }\n\t\tfinally { if (abort) signal.removeEventListener('abort', abort); }\n\t}\n\n\t/** Remove every local timer and listener without touching a running task. */\n\tdispose(): void {\n\t\tclearTimeout(this.timer);\n\t\tthis.external?.removeEventListener('abort', this.onAbort);\n\t}\n}\n\n/** A subscription token closes the snapshot-to-signal race using a generation counter. */\nexport interface Watch {\n\t/** Current generation, sampled before reading a snapshot. */\n\tversion(): number;\n\t/** Resolve immediately when an event arrived during the preceding snapshot. */\n\tnext(version: number): Promise<void>;\n\t/** Detach this caller without affecting other observers. */\n\tclose(): void;\n}\n\n/** Internal shared watch state: one bounded reconciliation timer per observed task. */\ninterface WatchGroup {\n\t/** Monotonically increasing notification generation. */\n\tgeneration: number;\n\t/** Independent waiting callbacks sharing the same source events. */\n\treadonly callbacks: Set<() => void>;\n\t/** Number of live watch tokens, including callers currently reading. */\n\tusers: number;\n\t/** Periodic reconciliation covers missed or invalidated property notifications. */\n\treadonly timer: ReturnType<typeof setInterval>;\n}\n\n/** Share systemd notifications and low-frequency reconciliation across concurrent waiters. */\nexport class ObservationHub {\n\t/** Entries exist only while a caller is waiting on a unit. */\n\tprivate readonly groups = new Map<string, WatchGroup>();\n\n\t/** Wake one task, or every task after manager disconnection. */\n\tnotify(unitName?: string): void {\n\t\tfor (const [name, group] of this.groups) {\n\t\t\tif (unitName !== undefined && unitName !== name) continue;\n\t\t\tgroup.generation++;\n\t\t\tfor (const callback of [...group.callbacks]) callback();\n\t\t}\n\t}\n\n\t/** Subscribe before the first snapshot, then compare generations before sleeping. */\n\twatch(unitName: string): Watch {\n\t\tlet group = this.groups.get(unitName);\n\t\tif (!group) {\n\t\t\tgroup = { generation: 0, callbacks: new Set(), users: 0, timer: setInterval(/** Reconcile snapshots even if systemd notifications are missed. */ () => this.notify(unitName), 1000) };\n\t\t\tthis.groups.set(unitName, group);\n\t\t}\n\t\tconst state = group;\n\t\tstate.users++;\n\t\tlet closed = false;\n\t\tlet pending: (() => void) | undefined;\n\t\treturn {\n\t\t\t/** Capture notifications already observed by the shared source. */\n\t\t\tversion: () => state.generation,\n\t\t\t/** Retain only one callback per caller, never one callback per event. */\n\t\t\tnext: async version => {\n\t\t\t\tif (closed || version !== state.generation) return;\n\t\t\t\tawait new Promise<void>(/** Retain a single wake callback for this observer. */ resolve => {\n\t\t\t\t\tpending = /** Remove this wake callback before resolving the observer. */ () => {\n\t\t\t\t\t\tif (pending) state.callbacks.delete(pending);\n\t\t\t\t\t\tpending = undefined;\n\t\t\t\t\t\tresolve();\n\t\t\t\t\t};\n\t\t\t\t\tstate.callbacks.add(pending);\n\t\t\t\t});\n\t\t\t},\n\t\t\t/** Cancel one subscription and remove the group's timer after its last user. */\n\t\t\tclose: () => {\n\t\t\t\tif (closed) return;\n\t\t\t\tclosed = true;\n\t\t\t\tpending?.();\n\t\t\t\tstate.users--;\n\t\t\t\tif (state.users === 0) {\n\t\t\t\t\tclearInterval(state.timer);\n\t\t\t\t\tthis.groups.delete(unitName);\n\t\t\t\t}\n\t\t\t},\n\t\t};\n\t}\n\n\t/** Wake pending callers and drop timers after the client is closed. */\n\tdispose(): void {\n\t\tthis.notify();\n\t\tfor (const group of this.groups.values()) clearInterval(group.timer);\n\t\tthis.groups.clear();\n\t}\n}\n"],"mappings":";AAAA,YAAY,kBAAkB;AAC9B,YAAY,iBAAiB;AAC7B,YAAY,YAAY;;;ACFxB,YAAYA,aAAY;AACxB,YAAY,QAAQ;AACpB,YAAYC,WAAU;;;ACFtB,YAAY,UAAU;AAIf,IAAM,YAAN,cAAwB,MAAM;AAAA;AAAA,EAE3B;AAAA;AAAA,EAEA;AAAA;AAAA,EAGT,YAAY,MAAuB,SAAiB,UAA8B,CAAC,GAAG,OAAiB;AACtG,UAAM,SAAS,UAAU,SAAY,SAAY,EAAE,MAAM,CAAC;AAC1D,SAAK,OAAO;AACZ,SAAK,OAAO;AACZ,SAAK,UAAU,OAAO,OAAO,EAAE,GAAG,QAAQ,CAAC;AAAA,EAC5C;AAAA;AAAA,EAGA,SASE;AACD,WAAO,EAAE,MAAM,KAAK,MAAM,MAAM,KAAK,MAAM,SAAS,KAAK,SAAS,SAAS,KAAK,QAAQ;AAAA,EACzF;AAAA;AAAA,EAGA,CAAM,aAAQ,MAAM,IAAY;AAC/B,WAAO,GAAG,KAAK,IAAI,KAAK,KAAK,IAAI,MAAM,KAAK,OAAO;AAAA,EACpD;AACD;;;ACpCA,YAAYC,aAAY;;;ACAxB,YAAY,YAAY;AACxB,YAAY,UAAU;AAOf,IAAM,wBAAwB;AAErC,IAAM,oBAAoB,OAAO;AAK1B,SAAS,QAAQ,QAAuB;AAC9C,QAAM,IAAW,UAAU,iBAAiB,gCAAgC,EAAE,QAAQ,iBAAiB,gBAAgB,CAAC;AACzH;AAGO,SAAS,OAAO,OAAgB,QAAyC;AAC/E,MAAI,UAAU,QAAQ,OAAO,UAAU,YAAY,MAAM,QAAQ,KAAK,EAAG,SAAQ,MAAM;AACvF,QAAM,YAAqB,OAAO,eAAe,KAAK;AACtD,MAAI,cAAc,OAAO,aAAa,cAAc,KAAM,SAAQ,MAAM;AACxE,SAAO;AACR;AAGO,SAAS,KAAK,OAAgC,SAA4B,QAAsB;AACtG,MAAI,OAAO,KAAK,KAAK,EAAE;AAAA;AAAA,IAAiE,SAAO,CAAC,QAAQ,SAAS,GAAG;AAAA,EAAC,KAAK,OAAO,sBAAsB,KAAK,EAAE,SAAS,EAAG,SAAQ,MAAM;AACzL;AAGO,SAAS,OAAO,OAAgB,QAAwB;AAC9D,MAAI,OAAO,UAAU,YAAY,MAAM,SAAS,IAAI,EAAG,SAAQ,MAAM;AACrE,aAAW,aAAa,OAAO;AAC9B,UAAM,OAAO,UAAU,YAAY,CAAC;AACpC,QAAI,QAAQ,SAAU,QAAQ,MAAQ,SAAQ,MAAM;AAAA,EACrD;AACA,SAAO;AACR;AAGO,SAAS,aAAa,OAAgB,QAAwB;AACpE,QAAM,SAAS,OAAO,OAAO,MAAM;AACnC,MAAI,CAAM,WAAM,WAAW,MAAM,EAAG,SAAQ,MAAM;AAClD,SAAO;AACR;AAGO,SAAS,SAAS,OAAgB,SAAiB,QAAwB;AACjF,MAAI,OAAO,UAAU,YAAY,CAAC,OAAO,cAAc,KAAK,KAAK,SAAS,KAAK,QAAQ,QAAS,SAAQ,MAAM;AAC9G,SAAO;AACR;AAGO,SAAS,aAAa,OAAgC;AAC5D,QAAM,SAAS,OAAO,OAAO,aAAa;AAC1C,OAAK,QAAQ,CAAC,cAAc,QAAQ,OAAO,OAAO,kBAAkB,eAAe,mBAAmB,GAAG,WAAW;AACpH,QAAM,aAAa,aAAa,OAAO,YAAY,iBAAiB;AACpE,QAAM,MAAM,aAAa,OAAO,KAAK,UAAU;AAC/C,MAAI,CAAC,MAAM,QAAQ,OAAO,IAAI,EAAG,SAAQ,YAAY;AACrD,QAAM,OAAO,OAAO,OAAO,OAAO,KAAK;AAAA;AAAA,IAA2E,CAAAC,WAAS,OAAOA,QAAO,aAAa;AAAA,EAAC,CAAC;AACxJ,QAAM,cAAc,OAAO,OAAO,KAAK,oBAAoB;AAC3D,QAAM,MAA8B,uBAAO,OAAO,IAAI;AACtD,aAAW,OAAO,OAAO,KAAK,WAAW,EAAE,KAAK,GAAG;AAClD,QAAI,CAAC,2BAA2B,KAAK,GAAG,EAAG,SAAQ,kBAAkB;AACrE,QAAI,GAAG,IAAI,OAAO,YAAY,GAAG,GAAG,mBAAmB;AAAA,EACxD;AACA,QAAM,iBAAiB,OAAO,mBAAmB,OAAO,OAAO,SAAS,OAAO,gBAAgB,mBAAmB,eAAe;AACjI,QAAM,cAAc,SAAS,OAAO,aAAa,mBAAmB,YAAY;AAChF,QAAM,aAAsC,CAAC;AAC7C,MAAI,OAAO,sBAAsB,QAAW;AAC3C,QAAI,CAAC,MAAM,QAAQ,OAAO,iBAAiB,EAAG,SAAQ,kBAAkB;AACxE,UAAM,QAAQ,oBAAI,IAAY;AAC9B,eAAWA,UAAS,OAAO,mBAAmB;AAC7C,YAAM,WAAW,OAAOA,QAAO,iBAAiB;AAChD,WAAK,UAAU,CAAC,QAAQ,aAAa,OAAO,GAAG,eAAe;AAC9D,UAAI,SAAS,SAAS,eAAe,SAAS,SAAS,WAAY,SAAQ,kCAAkC;AAC7G,UAAI,SAAS,cAAc,IAAK,SAAQ,oBAAoB;AAC5D,UAAI,MAAM,IAAI,SAAS,IAAI,EAAG,SAAQ,oBAAoB;AAC1D,YAAM,IAAI,SAAS,IAAI;AACvB,iBAAW,KAAK,OAAO,OAAO,EAAE,MAAM,SAAS,MAAM,WAAW,KAAK,OAAO,SAAS,SAAS,OAAO,KAAO,gBAAgB,EAAE,CAAC,CAAC;AAAA,IACjI;AAAA,EACD;AACA,aAAW;AAAA;AAAA,IAAmF,CAAC,MAAM,UAAU,KAAK,KAAK,cAAc,MAAM,IAAI;AAAA,EAAC;AAClJ,SAAO,OAAO,OAAO,EAAE,YAAY,MAAM,KAAK,KAAK,OAAO,OAAO,GAAG,GAAG,gBAAgB,aAAa,mBAAmB,OAAO,OAAO,UAAU,EAAE,CAAC;AACnJ;AAQO,SAAS,KAAK,OAAgB,QAAwB;AAC5D,QAAM,SAAS,OAAO,OAAO,MAAM;AACnC,MAAI,CAAC,wEAAwE,KAAK,MAAM,EAAG,SAAQ,MAAM;AACzG,SAAO;AACR;AAGO,SAAS,OAAO,OAAgB,QAAwB;AAC9D,QAAM,SAAS,OAAO,OAAO,MAAM;AACnC,MAAI,CAAC,iBAAiB,KAAK,MAAM,EAAG,SAAQ,MAAM;AAClD,SAAO;AACR;AA6BO,SAAS,qBAAqB,OAA+B;AACnE,MAAI,UAAU,KAAM,QAAO;AAC3B,QAAM,SAAS,OAAO,OAAO,eAAe;AAC5C,MAAI,CAAC,iBAAiB,KAAK,MAAM,EAAG,SAAQ,eAAe;AAC3D,SAAO;AACR;AAGO,SAAS,wBAAwB,OAAuC;AAC9E,QAAM,SAAS,OAAO,OAAO,kBAAkB;AAC/C,OAAK,QAAQ,CAAC,SAAS,OAAO,aAAa,UAAU,SAAS,OAAO,GAAG,cAAc;AACtF,MAAI,OAAO,UAAU,UAAU,OAAO,OAAO,QAAQ,YAAY,CAAC,OAAO,cAAc,OAAO,GAAG,KAAK,OAAO,MAAM,EAAG,SAAQ,sBAAsB;AACpJ,QAAM,YAAY,OAAO,OAAO,WAAW,YAAY;AACvD,QAAM,QAAQ,OAAO,OAAO,OAAO,QAAQ;AAC3C,QAAM,SAAS,OAAO,OAAO,QAAQ,SAAS;AAC9C,QAAM,QAAQ,OAAO,OAAO,OAAO,eAAe;AAClD,MAAI,CAAC,iBAAiB,KAAK,SAAS,KAAK,CAAC,iBAAiB,KAAK,KAAK,EAAG,SAAQ,qBAAqB;AACrG,MAAI,CAAC,gDAAgD,KAAK,MAAM,KAAK,CAAC,oBAAoB,KAAK,KAAK,EAAG,SAAQ,qBAAqB;AACpI,SAAO,OAAO,OAAO,EAAE,OAAO,QAAQ,KAAK,OAAO,KAAK,WAAW,QAAQ,OAAO,MAAM,CAAC;AACzF;;;ADpJO,IAAM,4BAA4B,MAAM;AAG/C,IAAM,uCAAuC,IAAI,KAAK,KAAK,4BAA4B,CAAC;AAGxF,IAAM,qBAAqB;AAG3B,IAAM,uBAAuB;AAAA,EAC5B;AAAA,EAAQ;AAAA,EAAW;AAAA,EAAmB;AAAA,EAAM;AAAA,EAAY;AAAA,EACxD;AAAA,EAAoB;AAAA,EAAgB;AACrC;AAGO,SAAS,cAAc,OAAwF;AACrH,QAAM,SAAoB,OAAO,OAAO,sBAAsB;AAC9D,EAAW,KAAK,QAAQ,CAAC,cAAc,QAAQ,OAAO,OAAO,kBAAkB,eAAe,qBAAqB,OAAO,GAAG,oBAAoB;AACjJ,QAAM,OAAkB,aAAa;AAAA,IACpC,YAAY,OAAO;AAAA,IACnB,MAAM,OAAO;AAAA,IACb,KAAK,OAAO;AAAA,IACZ,KAAK,OAAO;AAAA,IACZ,gBAAgB,OAAO;AAAA,IACvB,aAAa,OAAO;AAAA,IACpB,GAAI,OAAO,sBAAsB,SAAY,CAAC,IAAI,EAAE,mBAAmB,OAAO,kBAAkB;AAAA,EACjG,CAAC;AACD,MAAI,OAAO,UAAU,KAAM,QAAO,OAAO,OAAO,EAAE,MAAM,aAAa,KAAK,CAAC;AAC3E,MAAI;AACJ,MAAI,OAAO,OAAO,UAAU,SAAU,SAAQ,OAAO,KAAK,OAAO,OAAO,MAAM;AAAA,WACrE,OAAO,iBAAiB,WAAY,SAAQ,OAAO,KAAK,OAAO,KAAK;AAAA,MACxE,QAAkB,QAAQ,gBAAgB;AAC/C,MAAI,MAAM,aAAa,0BAA2B,CAAW,QAAQ,sBAAsB;AAC3F,SAAO,OAAO,OAAO,EAAE,MAAM,aAAa,MAAM,SAAS,QAAQ,EAAE,CAAC;AACrE;AAsBA,SAAS,SAAS,QAAqE;AACtF,MAAI,OAAO,SAAS,cAAc,OAAO,YAAY,KAAK,OAAO,oBAAoB,KAAK,OAAO,iBAAiB,OAAQ,CAAW,QAAQ,oCAAoC;AACjL,QAAM,KAAgB,KAAK,OAAO,IAAI,sBAAsB;AAC5D,MAAI,OAAO,aAAa,GAAG,kBAAkB,GAAG,EAAE,cAC9C,OAAO,sBAAsB,GAAG,kBAAkB,GAAG,EAAE,wBACvD,OAAO,qBAAqB,GAAG,kBAAkB,GAAG,EAAE,oBAAqB,CAAW,QAAQ,6BAA6B;AAC/H,SAAO,OAAO,OAAO;AAAA,IACpB,MAAM;AAAA,IAAY,SAAS;AAAA,IAAG,iBAAiB;AAAA,IAAG;AAAA,IAClD,UAAU,OAAO;AAAA,IACjB,mBAAmB,OAAO;AAAA,IAC1B,kBAAkB,OAAO;AAAA,IACzB,cAAc;AAAA,IAAQ,aAAwB,OAAO,OAAO,aAAa,+BAA+B;AAAA,EACzG,CAAC;AACF;AAwBO,SAAS,0BAA0B,OAAqD;AAC9F,QAAM,SAAoB,OAAO,OAAO,2BAA2B;AACnE,EAAW,KAAK,QAAQ,CAAC,GAAG,sBAAsB,WAAW,gBAAgB,yBAAyB,sBAAsB,GAAG,yBAAyB;AACxJ,SAAO,OAAO,OAAO;AAAA,IACpB,GAAG,SAAS,MAAM;AAAA,IAAG,SAAoB,wBAAwB,OAAO,OAAO;AAAA,IAC/E,cAAyB,qBAAqB,OAAO,YAAY;AAAA,IACjE,uBAAkC,qBAAqB,OAAO,qBAAqB;AAAA,IACnF,sBAAiC,qBAAqB,OAAO,oBAAoB;AAAA,EAClF,CAAC;AACF;;;AF7FO,IAAM,wBAA2C,4BAA4B;AAkBpF,SAAS,yBAAyB,OAAqD;AACtF,QAAM,YAA+B,0BAA0B,KAAK;AACpE,MAAI,CAAC,UAAU,gBAAgB,CAAC,UAAU,yBAAyB,CAAC,UAAU,sBAAsB;AACnG,IAAW,QAAQ,mCAAmC;AAAA,EACvD;AACA,SAAO;AACR;AAGO,SAAS,QAAQ,WAAgD,OAA6D;AACpI,QAAM,SAAoB,OAAO,OAAO,sBAAsB;AAC9D,EAAW,KAAK,QAAQ,CAAC,gBAAgB,WAAW,GAAG,0BAA0B;AACjF,SAAO,OAAO,OAAO;AAAA,IACpB,WAAW,yBAAyB,SAAS;AAAA,IAC7C,WAAsB,SAAS,OAAO,WAAsB,uBAAuB,sBAAsB;AAAA,IACzG,cAAiC,cAAc,OAAO,YAAY;AAAA,EACnE,CAAC;AACF;AAGO,SAAS,MAAM,OAA2B;AAChD,QAAM,SAAoB,OAAO,OAAO,wBAAwB;AAChE,EAAW,KAAK,QAAQ,CAAC,aAAa,aAAa,cAAc,GAAG,6BAA6B;AACjG,QAAMC,gBAA0B,OAAO,OAAO,cAAc,4BAA4B;AACxF,EAAW,KAAKA,eAAc,CAAC,QAAQ,aAAa,GAAG,iCAAiC;AACxF,QAAM,OAAkB,aAAaA,cAAa,IAAI;AACtD,MAAI,QAAuB;AAC3B,MAAIA,cAAa,gBAAgB,MAAM;AACtC,UAAM,UAAqB,OAAOA,cAAa,aAAa,oBAAoB;AAChF,QAAI,QAAQ,SAAS,IAAI,KAAK,KAAwB,4BAA4B,CAAC,GAAG;AACrF,MAAW,QAAQ,0BAA0B;AAAA,IAC9C;AACA,YAAQ,OAAO,KAAK,SAAS,QAAQ;AACrC,QAAI,MAAM,SAAS,QAAQ,MAAM,SAAS;AACzC,MAAW,QAAQ,2BAA2B;AAAA,IAC/C;AAAA,EACD;AACA,SAAO,QAAQ,yBAAyB,OAAO,SAAS,GAAG;AAAA,IAC1D,WAAsB,SAAS,OAAO,WAAsB,uBAAuB,sBAAsB;AAAA,IACzG,cAAc,EAAE,GAAG,MAAM,MAAM;AAAA,EAChC,CAAC;AACF;;;ADrEA,YAAY,aAAa;;;AKDlB,IAAM,cAAN,MAAkB;AAAA;AAAA,EAEP,aAAa,IAAI,gBAAgB;AAAA;AAAA,EAEjC;AAAA;AAAA,EAEA;AAAA;AAAA,EAEA;AAAA;AAAA,EAGjB,YAAY,SAA4B;AACvC,SAAK,WAAW,QAAQ;AACxB,SAAK;AAAA,IAAgF,MAAM,KAAK,WAAW,MAAM,IAAW,UAAU,gBAAgB,4BAA4B,CAAC;AACnL,QAAI,QAAQ,cAAc,OAAW,MAAK,QAAQ;AAAA;AAAA,MAAsF,MAAM,KAAK,WAAW,MAAM,IAAW,UAAU,gBAAgB,qCAAqC,CAAC;AAAA,MAAG,QAAQ;AAAA,IAAS;AACnQ,QAAI,KAAK,UAAU,QAAS,MAAK,QAAQ;AAAA,QACpC,MAAK,UAAU,iBAAiB,SAAS,KAAK,SAAS,EAAE,MAAM,KAAK,CAAC;AAAA,EAC3E;AAAA;AAAA,EAGA,QAAc;AACb,QAAI,KAAK,WAAW,OAAO,QAAS,OAAM,KAAK,WAAW,OAAO;AAAA,EAClE;AAAA;AAAA,EAGA,MAAM,KAAQ,SAAiC;AAC9C,QAAI,KAAK,WAAW,OAAO,SAAS;AACnC,WAAK,QAAQ;AAAA;AAAA,QAAqF,MAAM;AAAA,QAA0E;AAAA,MAAC;AACnL,WAAK,MAAM;AAAA,IACZ;AACA,UAAM,SAAS,KAAK,WAAW;AAC/B,QAAI;AACJ,UAAM,YAAY,IAAI;AAAA;AAAA,MAA2F,CAAC,UAAU,WAAW;AACtI;AAAA,QAAqE,MAAM,OAAO,OAAO,MAAM;AAC/F,eAAO,iBAAiB,SAAS,OAAO,EAAE,MAAM,KAAK,CAAC;AAAA,MACvD;AAAA,IAAC;AACD,QAAI;AAAE,aAAO,MAAM,QAAQ,KAAK,CAAC,SAAS,SAAS,CAAC;AAAA,IAAG,UACvD;AAAU,UAAI,MAAO,QAAO,oBAAoB,SAAS,KAAK;AAAA,IAAG;AAAA,EAClE;AAAA;AAAA,EAGA,UAAgB;AACf,iBAAa,KAAK,KAAK;AACvB,SAAK,UAAU,oBAAoB,SAAS,KAAK,OAAO;AAAA,EACzD;AACD;;;ALxCA,eAAe,gBAAiD;AAC/D,QAAM,SAAmB,CAAC;AAC1B,MAAI,QAAQ;AACZ,mBAAiB,SAAS,QAAQ,OAAO;AACxC,UAAM,SAAS,OAAO,KAAK,KAAmB;AAC9C,aAAS,OAAO;AAChB,QAAI,QAAqB,uBAAuB;AAC/C,YAAM,IAAW,UAAU,iBAAiB,0CAA0C;AAAA,QACrF,QAAQ;AAAA,MACT,CAAC;AAAA,IACF;AACA,WAAO,KAAK,MAAM;AAAA,EACnB;AACA,SAAoB,MAAM,KAAK,MAAM,OAAO,OAAO,MAAM,EAAE,SAAS,MAAM,CAAC,CAAY;AACxF;AAGA,eAAe,aAAa,WAAmC,WAAkC;AAChG,QAAM,OAAO,UAAU,aAAa;AACpC,QAAM,YAAY,KAAK,IAAI,WAAW,KAAK,kBAAkB,SAAS;AACtE,QAAM,UAAU,IAAY,YAAY,EAAE,WAAW,UAAU,CAAC;AAChE,MAAI;AACH,YAAQ,MAAM;AACd,UAAM,QAAQ,KAAK,IAAI;AAAA;AAAA,MAA4F,CAACC,UAAS,WAAW;AACvI,cAAM,QAAqB,mBAAM,KAAK,YAAY,CAAC,GAAG,KAAK,IAAI,GAAG;AAAA,UACjE,KAAK,KAAK;AAAA,UACV,KAAK,EAAE,GAAG,KAAK,IAAI;AAAA,UACnB,OAAO,CAAC,UAAU,aAAa,gBAAgB,OAAO,WAAW,QAAQ,UAAU,QAAQ;AAAA,UAC3F,OAAO;AAAA,QACR,CAAC;AACD,YAAI;AACJ,cAAM;AAAA,UAAK;AAAA;AAAA,UAAyE,WAAS;AAC5F,sBAAU;AAAA,UACX;AAAA,QAAC;AACD,cAAM,OAAO;AAAA,UAAK;AAAA;AAAA,UAA4E,WAAS;AACtG,sBAAU;AAAA,UACX;AAAA,QAAC;AACD,cAAM;AAAA,UAAK;AAAA;AAAA,UAAkE,CAAC,MAAM,WAAW;AAC9F,gBAAI,YAAY,UAAa,SAAS,KAAK,WAAW,MAAM;AAC3D,qBAAO,IAAW,UAAU,sBAAsB,4DAA4D;AAAA,gBAC7G,QAAQ;AAAA,gBAAwB,QAAQ,UAAU,UAAU;AAAA,cAC7D,GAAG,OAAO,CAAC;AACX;AAAA,YACD;AACA,YAAAA,SAAQ;AAAA,UACT;AAAA,QAAC;AACD,YAAI,UAAU,aAAa,gBAAgB,MAAM;AAChD,gBAAM,MAAO,IAAI,OAAO,KAAK,UAAU,aAAa,aAAa,QAAQ,CAAC;AAAA,QAC3E;AAAA,MACD;AAAA,IAAC,CAAC;AAAA,EACH,UAAE;AACD,YAAQ,QAAQ;AAAA,EACjB;AACD;AAGA,eAAe,MAAqB;AACnC,QAAM,YAAY,MAAM,cAAc;AACtC,QAAM,SAAS,MAAc,wBAAgB;AAE7C,QAAM,SAKF,EAAE,UAAU,MAAM,SAAS,KAAK;AACpC,MAAI;AAEH,UAAM,YAAY,MAAc;AAC/B,UAAI,OAAO,aAAa,MAAM;AAC7B,eAAO,WAAuB,wBAAY,IAAI,IAAI,UAAU;AAC5D,eAAO,UAAU,IAAY,YAAY,EAAE,WAAW,UAAU,UAAU,CAAC;AAAA,MAC5E;AACA,aAAO,QAAS,MAAM;AACtB,YAAM,eAAe,KAAK,MAAM,OAAO,WAAuB,wBAAY,IAAI,CAAC;AAC/E,UAAI,gBAAgB,GAAG;AACtB,cAAM,IAAW,UAAU,gBAAgB,sCAAsC;AAAA,UAChF,QAAQ;AAAA,UAAwB,QAAQ,UAAU,UAAU;AAAA,QAC7D,CAAC;AAAA,MACF;AACA,aAAO;AAAA,IACR;AACA,eAAS;AACR,aAAO,SAAS,MAAM;AACtB,YAAM,QAAQ,OAAO,OAAO,YAAY,OACrC,OAAO,OAAO,UAAU,SAAS,IACjC,OAAO,QAAQ,KAAK,OAAO,OAAO,UAAU,SAAS,CAAC;AACzD,UAAI,MAAM,WAAW,aAAa;AAEjC;AAAA,MACD;AACA,UAAI,MAAM,WAAW,gBAAgB,MAAM,SAAS,QAAQ,iBAAiB;AAC5E,kBAAU;AAAA,MACX;AACA,UAAI,MAAM,WAAW,WAAW,MAAM,SAAS,UAAU,aAAa;AACrE;AAAA,MACD;AACA,UAAI,MAAM,WAAW,gBAAgB,MAAM,SAAS,SAAS,iBAAiB;AAC7E,cAAM,UAAU,KAAK,IAAI,UAAU,GAAG,EAAE;AACxC,cAAM,OAAO,QAAS,KAAY,kBAAW,OAAO,CAAC;AACrD;AAAA,MACD;AACA,UAAI;AACH,cAAM,cAAc,EAAE,WAAW,OAAO,aAAa,OAAO,MAAO,KAAK,IAAI,UAAU,GAAG,GAAI,EAAE;AAC/F,cAAM,WAAW,OAAO,OAAO,YAAY,OACxC,OAAO,KAAK,UAAU,WAAW,WAAW,IAC5C,OAAO,QAAQ,KAAK,OAAO,KAAK,UAAU,WAAW,WAAW,CAAC;AACpE,YAAI,SAAS,QAAQ,iBAAiB;AACrC,oBAAU;AAAA,QACX;AACA,YAAI,SAAS,UAAU,aAAa;AACnC;AAAA,QACD;AAAA,MACD,SAAS,OAAO;AACf,YAAI,EAAE,iBAAyB,sBAAe,MAAM,SAAS,kBAAkB,MAAM,SAAS,sBAAuB;AACpH,gBAAM;AAAA,QACP;AAAA,MACD;AAAA,IACD;AACA,UAAM,mBAAmB,UAAU;AACnC,UAAM,OAAO,QAAS,KAAK,OAAO,QAAQ,UAAU,WAAW,EAAE,WAAW,iBAAiB,CAAC,CAAC;AAC/F,UAAM,oBAAoB,UAAU;AACpC,UAAM,OAAO,QAAS,KAAK,aAAa,WAAW,iBAAiB,CAAC;AAAA,EACtE,UAAE;AACD,WAAO,SAAS,QAAQ;AACxB,UAAM,OAAO,WAAW;AAAA,EACzB;AACD;AAEA,KAAK,IAAI,EAAE;AAAA;AAAA,EAAkF,WAAS;AACrG,UAAM,WAAW,iBAAwB,aAAa,iBAAyB,oBAC5E,QACA,IAAW,UAAU,sBAAsB,uCAAuC,EAAE,QAAQ,sBAAsB,CAAC;AACtH,YAAQ,OAAO,MAAM,GAAG,KAAK,UAAU,SAAS,OAAO,CAAC,CAAC;AAAA,CAAI;AAG7D,YAAQ,KAAK,CAAC;AAAA,EACf;AAAC;","names":["crypto","path","crypto","value","afterRelease","resolve"]}
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/observed.ts"],"sourcesContent":["/** Observed fasáda zpřístupňuje pouze tříjednotkový kontrakt a sdílené lifecycle typy. */\nexport { connectObserved, prepareObserved, TaskError } from '#runtime';\nexport type {\n\tCleanupState, ConnectOptions, DiagnosticEvent, ErrorCode, ErrorDetails, ManagerIdentity,\n\tObservedLookupResult, ObservedOutputEvent, ObservedProcessSnapshot, ObservedStartOptions,\n\tObservedStartReceipt, ObservedStartResult, ObservedStopReceipt, ObservedTaskClient,\n\tObservedTaskIdentity, ObservedTaskIntent, ObservedTaskObservation, ObservedTaskReference,\n\tObservedTaskSnapshot, ObservedTaskSpec, ReleaseOptions, ReleaseReceipt, StopOptions,\n\tSystemdProperty, TaskEvidence, TaskResult, TaskSpec, WaitOptions,\n} from '#runtime';\n"],"mappings":";;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AACA,qBAA4D;","names":[]}
1
+ {"version":3,"sources":["../src/observed.ts"],"sourcesContent":["/** Observed fasáda zpřístupňuje pouze tříjednotkový kontrakt a sdílené lifecycle typy. */\nexport { connectObserved, prepareObserved, TaskError } from '#runtime';\nexport type {\n\tCleanupState, ConnectOptions, DiagnosticEvent, ErrorCode, ErrorDetails, ManagerIdentity,\n\tObservedFinalizationOptions, ObservedFinalizationReceipt,\n\tObservedLookupResult, ObservedOutputEvent, ObservedProcessSnapshot, ObservedStartOptions,\n\tObservedStartReceipt, ObservedStartResult, ObservedStopReceipt, ObservedTaskClient,\n\tObservedTaskIdentity, ObservedTaskIntent, ObservedTaskObservation, ObservedTaskReference,\n\tObservedTaskSnapshot, ObservedTaskSpec, ReleaseOptions, ReleaseReceipt, StopOptions,\n\tSystemdProperty, TaskEvidence, TaskResult, TaskSpec, WaitOptions,\n} from '#runtime';\n"],"mappings":";;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AACA,qBAA4D;","names":[]}
@@ -1 +1 @@
1
- export { CleanupState, ConnectOptions, DiagnosticEvent, ErrorCode, ErrorDetails, ManagerIdentity, ObservedLookupResult, ObservedOutputEvent, ObservedProcessSnapshot, ObservedStartOptions, ObservedStartReceipt, ObservedStartResult, ObservedStopReceipt, ObservedTaskClient, ObservedTaskIdentity, ObservedTaskIntent, ObservedTaskObservation, ObservedTaskReference, ObservedTaskSnapshot, ObservedTaskSpec, ReleaseOptions, ReleaseReceipt, StopOptions, SystemdProperty, TaskError, TaskEvidence, TaskResult, TaskSpec, WaitOptions, connectObserved, prepareObserved } from '#runtime';
1
+ export { CleanupState, ConnectOptions, DiagnosticEvent, ErrorCode, ErrorDetails, ManagerIdentity, ObservedFinalizationOptions, ObservedFinalizationReceipt, ObservedLookupResult, ObservedOutputEvent, ObservedProcessSnapshot, ObservedStartOptions, ObservedStartReceipt, ObservedStartResult, ObservedStopReceipt, ObservedTaskClient, ObservedTaskIdentity, ObservedTaskIntent, ObservedTaskObservation, ObservedTaskReference, ObservedTaskSnapshot, ObservedTaskSpec, ReleaseOptions, ReleaseReceipt, StopOptions, SystemdProperty, TaskError, TaskEvidence, TaskResult, TaskSpec, WaitOptions, connectObserved, prepareObserved } from '#runtime';
@@ -1 +1 @@
1
- export { CleanupState, ConnectOptions, DiagnosticEvent, ErrorCode, ErrorDetails, ManagerIdentity, ObservedLookupResult, ObservedOutputEvent, ObservedProcessSnapshot, ObservedStartOptions, ObservedStartReceipt, ObservedStartResult, ObservedStopReceipt, ObservedTaskClient, ObservedTaskIdentity, ObservedTaskIntent, ObservedTaskObservation, ObservedTaskReference, ObservedTaskSnapshot, ObservedTaskSpec, ReleaseOptions, ReleaseReceipt, StopOptions, SystemdProperty, TaskError, TaskEvidence, TaskResult, TaskSpec, WaitOptions, connectObserved, prepareObserved } from '#runtime';
1
+ export { CleanupState, ConnectOptions, DiagnosticEvent, ErrorCode, ErrorDetails, ManagerIdentity, ObservedFinalizationOptions, ObservedFinalizationReceipt, ObservedLookupResult, ObservedOutputEvent, ObservedProcessSnapshot, ObservedStartOptions, ObservedStartReceipt, ObservedStartResult, ObservedStopReceipt, ObservedTaskClient, ObservedTaskIdentity, ObservedTaskIntent, ObservedTaskObservation, ObservedTaskReference, ObservedTaskSnapshot, ObservedTaskSpec, ReleaseOptions, ReleaseReceipt, StopOptions, SystemdProperty, TaskError, TaskEvidence, TaskResult, TaskSpec, WaitOptions, connectObserved, prepareObserved } from '#runtime';
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/observed.ts"],"sourcesContent":["/** Observed fasáda zpřístupňuje pouze tříjednotkový kontrakt a sdílené lifecycle typy. */\nexport { connectObserved, prepareObserved, TaskError } from '#runtime';\nexport type {\n\tCleanupState, ConnectOptions, DiagnosticEvent, ErrorCode, ErrorDetails, ManagerIdentity,\n\tObservedLookupResult, ObservedOutputEvent, ObservedProcessSnapshot, ObservedStartOptions,\n\tObservedStartReceipt, ObservedStartResult, ObservedStopReceipt, ObservedTaskClient,\n\tObservedTaskIdentity, ObservedTaskIntent, ObservedTaskObservation, ObservedTaskReference,\n\tObservedTaskSnapshot, ObservedTaskSpec, ReleaseOptions, ReleaseReceipt, StopOptions,\n\tSystemdProperty, TaskEvidence, TaskResult, TaskSpec, WaitOptions,\n} from '#runtime';\n"],"mappings":";AACA,SAAS,iBAAiB,iBAAiB,iBAAiB;","names":[]}
1
+ {"version":3,"sources":["../src/observed.ts"],"sourcesContent":["/** Observed fasáda zpřístupňuje pouze tříjednotkový kontrakt a sdílené lifecycle typy. */\nexport { connectObserved, prepareObserved, TaskError } from '#runtime';\nexport type {\n\tCleanupState, ConnectOptions, DiagnosticEvent, ErrorCode, ErrorDetails, ManagerIdentity,\n\tObservedFinalizationOptions, ObservedFinalizationReceipt,\n\tObservedLookupResult, ObservedOutputEvent, ObservedProcessSnapshot, ObservedStartOptions,\n\tObservedStartReceipt, ObservedStartResult, ObservedStopReceipt, ObservedTaskClient,\n\tObservedTaskIdentity, ObservedTaskIntent, ObservedTaskObservation, ObservedTaskReference,\n\tObservedTaskSnapshot, ObservedTaskSpec, ReleaseOptions, ReleaseReceipt, StopOptions,\n\tSystemdProperty, TaskEvidence, TaskResult, TaskSpec, WaitOptions,\n} from '#runtime';\n"],"mappings":";AACA,SAAS,iBAAiB,iBAAiB,iBAAiB;","names":[]}