@bastani/atomic 0.9.32 → 0.9.33-alpha.1
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 +7 -0
- package/dist/builtin/intercom/package.json +1 -1
- package/dist/builtin/mcp/package.json +1 -1
- package/dist/builtin/subagents/package.json +1 -1
- package/dist/builtin/web-access/package.json +1 -1
- package/dist/builtin/workflows/CHANGELOG.md +6 -0
- package/dist/builtin/workflows/builtin/{chunk-bnz4knhy.js → chunk-0d0pd4fz.js} +1 -1
- package/dist/builtin/workflows/builtin/{chunk-v4scsq3y.js → chunk-119gt64q.js} +54 -16
- package/dist/builtin/workflows/builtin/{chunk-9ywkdsa9.js → chunk-s7y3hw0n.js} +1 -1
- package/dist/builtin/workflows/builtin/{chunk-dx5sjaxe.js → chunk-y68758re.js} +1 -1
- package/dist/builtin/workflows/builtin/goal.js +2 -2
- package/dist/builtin/workflows/builtin/index.js +3 -3
- package/dist/builtin/workflows/builtin/ralph.js +2 -2
- package/dist/builtin/workflows/package.json +1 -1
- package/dist/builtin/workflows/src/extension/index.bundle.mjs +78 -20
- package/dist/builtin/workflows/src/index.js +53 -15
- package/dist/modes/interactive/interactive-agent-events.js +9 -1
- package/dist/modes/interactive/interactive-agent-events.js.map +1 -1
- package/dist/modes/interactive/interactive-mode-base.d.ts.map +1 -1
- package/dist/modes/interactive/interactive-mode-base.js +1 -1
- package/dist/modes/interactive/interactive-mode-base.js.map +1 -1
- package/dist/modes/interactive/program-status-reporter.d.ts +14 -0
- package/dist/modes/interactive/program-status-reporter.d.ts.map +1 -1
- package/dist/modes/interactive/program-status-reporter.js +92 -1
- package/dist/modes/interactive/program-status-reporter.js.map +1 -1
- package/dist/modes/interactive-engine/engine-workflow-activity.d.ts +23 -0
- package/dist/modes/interactive-engine/engine-workflow-activity.d.ts.map +1 -0
- package/dist/modes/interactive-engine/engine-workflow-activity.js +80 -0
- package/dist/modes/interactive-engine/engine-workflow-activity.js.map +1 -0
- package/dist/modes/interactive-engine/extension-ui-bridge.d.ts +8 -1
- package/dist/modes/interactive-engine/extension-ui-bridge.d.ts.map +1 -1
- package/dist/modes/interactive-engine/extension-ui-bridge.js +31 -1
- package/dist/modes/interactive-engine/extension-ui-bridge.js.map +1 -1
- package/dist/modes/interactive-engine/isolated-runtime.d.ts +3 -0
- package/dist/modes/interactive-engine/isolated-runtime.d.ts.map +1 -1
- package/dist/modes/interactive-engine/isolated-runtime.js +4 -0
- package/dist/modes/interactive-engine/isolated-runtime.js.map +1 -1
- package/dist/modes/interactive-engine/protocol.d.ts +6 -0
- package/dist/modes/interactive-engine/protocol.d.ts.map +1 -1
- package/dist/modes/interactive-engine/protocol.js +63 -0
- package/dist/modes/interactive-engine/protocol.js.map +1 -1
- package/dist/modes/rpc/rpc-client.d.ts +7 -0
- package/dist/modes/rpc/rpc-client.d.ts.map +1 -1
- package/dist/modes/rpc/rpc-client.js +24 -0
- package/dist/modes/rpc/rpc-client.js.map +1 -1
- package/dist/modes/rpc/rpc-mode.d.ts.map +1 -1
- package/dist/modes/rpc/rpc-mode.js +1 -0
- package/dist/modes/rpc/rpc-mode.js.map +1 -1
- package/dist/modes/rpc/rpc-session-binding.d.ts +5 -1
- package/dist/modes/rpc/rpc-session-binding.d.ts.map +1 -1
- package/dist/modes/rpc/rpc-session-binding.js +10 -1
- package/dist/modes/rpc/rpc-session-binding.js.map +1 -1
- package/docs/terminal-setup.md +6 -4
- package/docs/workflows/operations.md +1 -1
- package/npm-shrinkwrap.json +32 -32
- package/package.json +3 -3
package/CHANGELOG.md
CHANGED
|
@@ -2,6 +2,13 @@
|
|
|
2
2
|
|
|
3
3
|
## [Unreleased]
|
|
4
4
|
|
|
5
|
+
## [0.9.33-alpha.1] - 2026-10-10
|
|
6
|
+
|
|
7
|
+
### Fixed
|
|
8
|
+
|
|
9
|
+
- Fixed workflows falling back to a non-durable in-memory backend after a macOS reboot because the managed PostgreSQL cluster was refused with `Managed Postgres cluster identity mismatch` when only the data volume's device number changed. The cluster now attaches and its ownership record is updated when the data directory inode, path, cluster ID, major version, and PostgreSQL system identifier still match; genuine identity mismatches name the fields that differ ([#3555](https://github.com/bastani-inc/atomic/issues/3555)).
|
|
10
|
+
- Fixed terminal program status (OSC 7501) ignoring workflow runs: it now reports `working` while a workflow run executes, `blocked` while a run or stage waits for your input, `error` when a run fails (held until your next message, even after the run-end notice turn settles), and `done` once the agent and all runs finish ([#3556](https://github.com/bastani-inc/atomic/issues/3556)).
|
|
11
|
+
|
|
5
12
|
## [0.9.32] - 2026-10-10
|
|
6
13
|
|
|
7
14
|
### Fixed
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@bastani/intercom",
|
|
3
|
-
"version": "0.9.
|
|
3
|
+
"version": "0.9.33-alpha.1",
|
|
4
4
|
"private": true,
|
|
5
5
|
"description": "Atomic extension providing a private coordination channel between parent and child agent sessions. Fork of: https://github.com/nicobailon/pi-intercom",
|
|
6
6
|
"contributors": [
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@bastani/subagents",
|
|
3
|
-
"version": "0.9.
|
|
3
|
+
"version": "0.9.33-alpha.1",
|
|
4
4
|
"private": true,
|
|
5
5
|
"description": "Atomic extension for delegating tasks to subagents with parallel execution. Fork of: https://github.com/nicobailon/pi-subagents",
|
|
6
6
|
"contributors": [
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@bastani/web-access",
|
|
3
|
-
"version": "0.9.
|
|
3
|
+
"version": "0.9.33-alpha.1",
|
|
4
4
|
"private": true,
|
|
5
5
|
"description": "Atomic extension for web search, URL fetching, GitHub repo cloning, PDF/video extraction. Fork of: https://github.com/nicobailon/pi-web-access",
|
|
6
6
|
"contributors": [
|
|
@@ -6,6 +6,12 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
|
|
|
6
6
|
|
|
7
7
|
## [Unreleased]
|
|
8
8
|
|
|
9
|
+
## [0.9.33-alpha.1] - 2026-10-10
|
|
10
|
+
|
|
11
|
+
### Fixed
|
|
12
|
+
|
|
13
|
+
- Fixed the managed PostgreSQL cluster being refused with `Managed Postgres cluster identity mismatch` after a macOS reboot changed the data volume's device number. Atomic now attaches the cluster and updates its ownership record when the data directory inode, path, cluster ID, major version, and PostgreSQL system identifier still match, and genuine identity mismatches name the fields that differ ([#3555](https://github.com/bastani-inc/atomic/issues/3555)).
|
|
14
|
+
|
|
9
15
|
## [0.9.32] - 2026-10-10
|
|
10
16
|
|
|
11
17
|
### Fixed
|
|
@@ -6753,7 +6753,6 @@ class PostgresHealth {
|
|
|
6753
6753
|
import { existsSync as existsSync2, lstatSync as lstatSync2, readFileSync as readFileSync2, realpathSync as realpathSync2 } from "node:fs";
|
|
6754
6754
|
import { createRequire as createRequire2 } from "node:module";
|
|
6755
6755
|
import { createServer } from "node:net";
|
|
6756
|
-
import { endianness } from "node:os";
|
|
6757
6756
|
import { dirname as dirname2, isAbsolute as isAbsolute2, join as join3 } from "node:path";
|
|
6758
6757
|
|
|
6759
6758
|
// dist/builtin/workflows/src/durable/dbos-postgres-ownership.ts
|
|
@@ -6768,6 +6767,7 @@ import {
|
|
|
6768
6767
|
rmSync,
|
|
6769
6768
|
writeFileSync
|
|
6770
6769
|
} from "node:fs";
|
|
6770
|
+
import { endianness } from "node:os";
|
|
6771
6771
|
import { join as join2 } from "node:path";
|
|
6772
6772
|
function trustedPath(path, directory = false) {
|
|
6773
6773
|
const stat = lstatSync(path);
|
|
@@ -6778,6 +6778,24 @@ function trustedPath(path, directory = false) {
|
|
|
6778
6778
|
function postgresOwnershipDirectory(baseDir, major) {
|
|
6779
6779
|
return join2(baseDir, `v${major}.shared`);
|
|
6780
6780
|
}
|
|
6781
|
+
function controlFileSystemIdentifier(dataDir) {
|
|
6782
|
+
const controlPath = join2(dataDir, "global", "pg_control");
|
|
6783
|
+
if (!lstatSync(controlPath).isFile())
|
|
6784
|
+
throw new Error("Untrusted managed Postgres control file.");
|
|
6785
|
+
const control = readFileSync(controlPath);
|
|
6786
|
+
return (endianness() === "LE" ? control.readBigUInt64LE(0) : control.readBigUInt64BE(0)).toString();
|
|
6787
|
+
}
|
|
6788
|
+
var directoryInode = (identity) => /^\d+:(\d+)$/.exec(identity)?.[1];
|
|
6789
|
+
function managedPostgresIdentityMismatches(expected, current, compareSystemIdentifier = true) {
|
|
6790
|
+
const inode = directoryInode(expected.directoryIdentity);
|
|
6791
|
+
return [
|
|
6792
|
+
current.clusterId !== expected.clusterId && "clusterId",
|
|
6793
|
+
current.dataDir !== expected.dataDir && "dataDir",
|
|
6794
|
+
(inode === undefined || inode !== directoryInode(current.directoryIdentity)) && "inode",
|
|
6795
|
+
current.major !== expected.major && "major",
|
|
6796
|
+
compareSystemIdentifier && current.server?.systemIdentifier !== expected.server?.systemIdentifier && "systemIdentifier"
|
|
6797
|
+
].filter((field) => field !== false);
|
|
6798
|
+
}
|
|
6781
6799
|
function managedPostgresMetadata(baseDir, major, create) {
|
|
6782
6800
|
if (!lstatSync(join2(baseDir, `v${major}`)).isDirectory()) {
|
|
6783
6801
|
throw new Error("Managed Postgres data must be a real directory, not a link.");
|
|
@@ -6811,10 +6829,30 @@ function managedPostgresMetadata(baseDir, major, create) {
|
|
|
6811
6829
|
}
|
|
6812
6830
|
trustedPath(path);
|
|
6813
6831
|
const record = JSON.parse(readFileSync(path, "utf8"));
|
|
6814
|
-
|
|
6815
|
-
|
|
6832
|
+
const mismatches = [
|
|
6833
|
+
...record?.version !== 1 ? ["version"] : [],
|
|
6834
|
+
...typeof record?.clusterId !== "string" || !/^[0-9a-f-]{36}$/.test(record.clusterId) ? ["clusterId"] : [],
|
|
6835
|
+
...record?.dataDir !== dataDir ? ["dataDir"] : [],
|
|
6836
|
+
...typeof record?.directoryIdentity !== "string" || directoryInode(record.directoryIdentity) !== String(stat.ino) ? ["inode"] : [],
|
|
6837
|
+
...record?.major !== major ? ["major"] : [],
|
|
6838
|
+
...record?.server !== undefined && (!Number.isInteger(record.server?.port) || record.server.port < 1 || record.server.port > 65535 || !Number.isSafeInteger(record.server.pid) || record.server.pid <= 0 || !Number.isSafeInteger(record.server.started) || record.server.started <= 0 || !/^\d+$/.test(record.server.systemIdentifier)) ? ["server"] : []
|
|
6839
|
+
];
|
|
6840
|
+
const mismatch = (fields) => new Error(`Managed Postgres cluster identity mismatch (${fields.join(", ")}): ${path}. Preserve the data and ownership records.`);
|
|
6841
|
+
if (record === null || mismatches.length > 0)
|
|
6842
|
+
throw mismatch(mismatches);
|
|
6843
|
+
if (record.directoryIdentity === directoryIdentity)
|
|
6844
|
+
return record;
|
|
6845
|
+
if (record.server && controlSystemIdentifierOrUndefined(dataDir) !== record.server.systemIdentifier) {
|
|
6846
|
+
throw mismatch(["systemIdentifier"]);
|
|
6847
|
+
}
|
|
6848
|
+
return { ...record, directoryIdentity };
|
|
6849
|
+
}
|
|
6850
|
+
function controlSystemIdentifierOrUndefined(dataDir) {
|
|
6851
|
+
try {
|
|
6852
|
+
return controlFileSystemIdentifier(dataDir);
|
|
6853
|
+
} catch {
|
|
6854
|
+
return;
|
|
6816
6855
|
}
|
|
6817
|
-
return record;
|
|
6818
6856
|
}
|
|
6819
6857
|
function publishPostgresServer(baseDir, metadata, server) {
|
|
6820
6858
|
const current = managedPostgresMetadata(baseDir, metadata.major, false);
|
|
@@ -6965,11 +7003,7 @@ function managedPostmaster(metadata) {
|
|
|
6965
7003
|
return { pid, started, port, systemIdentifier };
|
|
6966
7004
|
}
|
|
6967
7005
|
function managedSystemIdentifier(metadata) {
|
|
6968
|
-
const
|
|
6969
|
-
if (!lstatSync2(controlPath).isFile())
|
|
6970
|
-
throw new Error("Untrusted managed Postgres control file.");
|
|
6971
|
-
const control = readFileSync2(controlPath);
|
|
6972
|
-
const systemIdentifier = (endianness() === "LE" ? control.readBigUInt64LE(0) : control.readBigUInt64BE(0)).toString();
|
|
7006
|
+
const systemIdentifier = controlFileSystemIdentifier(metadata.dataDir);
|
|
6973
7007
|
if (metadata.server && metadata.server.systemIdentifier !== systemIdentifier) {
|
|
6974
7008
|
throw new Error("Managed Postgres system identity mismatch. Preserve the existing data.");
|
|
6975
7009
|
}
|
|
@@ -7179,8 +7213,9 @@ async function ensureCluster(options = {}) {
|
|
|
7179
7213
|
adoptedRegistry = postgresOwnershipDirectory(root, EMBEDDED_PG_MAJOR);
|
|
7180
7214
|
if (options.recovery && !metadata)
|
|
7181
7215
|
throw new Error("Managed Postgres recovery requires existing ownership records.");
|
|
7182
|
-
|
|
7183
|
-
|
|
7216
|
+
const recoveryMismatches = options.recovery && metadata ? managedPostgresIdentityMismatches(options.recovery, metadata) : [];
|
|
7217
|
+
if (recoveryMismatches.length > 0) {
|
|
7218
|
+
throw new Error(`Managed Postgres recovery identity changed (${recoveryMismatches.join(", ")}) while waiting for ownership.`);
|
|
7184
7219
|
}
|
|
7185
7220
|
const existing = metadata && managedPostmaster(metadata);
|
|
7186
7221
|
let port = existing?.port ?? metadata?.server?.port ?? preferredPort;
|
|
@@ -7395,8 +7430,9 @@ async function ensureCluster(options = {}) {
|
|
|
7395
7430
|
};
|
|
7396
7431
|
const inspect = async (probe = options.probeIdentity) => {
|
|
7397
7432
|
const current = managedPostgresMetadata(root, EMBEDDED_PG_MAJOR, false);
|
|
7398
|
-
|
|
7399
|
-
|
|
7433
|
+
const mismatches = managedPostgresIdentityMismatches(pinned, current);
|
|
7434
|
+
if (mismatches.length > 0) {
|
|
7435
|
+
throw new Error(`Managed Postgres health identity mismatch (${mismatches.join(", ")}). Preserve the data and ownership records.`);
|
|
7400
7436
|
}
|
|
7401
7437
|
const server = current.server;
|
|
7402
7438
|
if (!server)
|
|
@@ -7456,8 +7492,9 @@ async function ensureCluster(options = {}) {
|
|
|
7456
7492
|
async function stopBrokenManagedPostmaster(metadata, verified, pgCtl, context, lease, wait = delay, platform = process.platform) {
|
|
7457
7493
|
const check = () => {
|
|
7458
7494
|
const current = managedPostgresMetadata(context.baseDir, metadata.major, false);
|
|
7459
|
-
|
|
7460
|
-
|
|
7495
|
+
const mismatches = managedPostgresIdentityMismatches(metadata, current, false);
|
|
7496
|
+
if (mismatches.length > 0) {
|
|
7497
|
+
throw new Error(`Managed Postgres restart identity changed (${mismatches.join(", ")}). Preserve the server and data directory.`);
|
|
7461
7498
|
}
|
|
7462
7499
|
return { current, process: verifyManagedPostmasterProcess(current, verified) };
|
|
7463
7500
|
};
|
|
@@ -9279,6 +9316,7 @@ function reciprocalWorkflowRootRunId(runById, runId) {
|
|
|
9279
9316
|
function workflowActivityNodeKey(runId, nodeId) {
|
|
9280
9317
|
return `${runId}:${nodeId}`;
|
|
9281
9318
|
}
|
|
9319
|
+
var endedStatuses = new Set(["completed", "cached", "failed", "cancelled"]);
|
|
9282
9320
|
|
|
9283
9321
|
// dist/builtin/workflows/src/shared/workflow-observation-runtime.ts
|
|
9284
9322
|
class WorkflowObservationRuntime {
|
|
@@ -9922,7 +9960,7 @@ function createPendingStageDeliveryStoreMethods(context) {
|
|
|
9922
9960
|
const run = context.findRun(input.runId);
|
|
9923
9961
|
if (run === undefined)
|
|
9924
9962
|
return;
|
|
9925
|
-
const { getAvailableDurableBackend } = await import("./chunk-
|
|
9963
|
+
const { getAvailableDurableBackend } = await import("./chunk-0d0pd4fz.js");
|
|
9926
9964
|
const availableBackend = getAvailableDurableBackend();
|
|
9927
9965
|
const backend = availableBackend === undefined ? undefined : durableBackendForRun(availableBackend, context.state.runs, input.runId);
|
|
9928
9966
|
const receipt = await backend?.readSettledPendingStageMessage?.(input.runId, input.message.id);
|
|
@@ -16,8 +16,8 @@ import {
|
|
|
16
16
|
} from "./chunk-kb7s3gx2.js";
|
|
17
17
|
import {
|
|
18
18
|
goal_default
|
|
19
|
-
} from "./chunk-
|
|
20
|
-
import"./chunk-
|
|
19
|
+
} from "./chunk-s7y3hw0n.js";
|
|
20
|
+
import"./chunk-119gt64q.js";
|
|
21
21
|
import"./chunk-z0d03ktm.js";
|
|
22
22
|
import {
|
|
23
23
|
open_claude_design_default
|
|
@@ -27,7 +27,7 @@ import {
|
|
|
27
27
|
} from "./chunk-94f8zfz1.js";
|
|
28
28
|
import {
|
|
29
29
|
ralph_default
|
|
30
|
-
} from "./chunk-
|
|
30
|
+
} from "./chunk-y68758re.js";
|
|
31
31
|
import {
|
|
32
32
|
tournament_default
|
|
33
33
|
} from "./chunk-wf876n16.js";
|
|
@@ -38545,6 +38545,7 @@ import {
|
|
|
38545
38545
|
rmSync,
|
|
38546
38546
|
writeFileSync
|
|
38547
38547
|
} from "node:fs";
|
|
38548
|
+
import { endianness } from "node:os";
|
|
38548
38549
|
import { join as join3 } from "node:path";
|
|
38549
38550
|
function trustedPath(path, directory = false) {
|
|
38550
38551
|
const stat = lstatSync(path);
|
|
@@ -38555,6 +38556,23 @@ function trustedPath(path, directory = false) {
|
|
|
38555
38556
|
function postgresOwnershipDirectory(baseDir, major) {
|
|
38556
38557
|
return join3(baseDir, `v${major}.shared`);
|
|
38557
38558
|
}
|
|
38559
|
+
function controlFileSystemIdentifier(dataDir) {
|
|
38560
|
+
const controlPath = join3(dataDir, "global", "pg_control");
|
|
38561
|
+
if (!lstatSync(controlPath).isFile())
|
|
38562
|
+
throw new Error("Untrusted managed Postgres control file.");
|
|
38563
|
+
const control = readFileSync2(controlPath);
|
|
38564
|
+
return (endianness() === "LE" ? control.readBigUInt64LE(0) : control.readBigUInt64BE(0)).toString();
|
|
38565
|
+
}
|
|
38566
|
+
function managedPostgresIdentityMismatches(expected, current, compareSystemIdentifier = true) {
|
|
38567
|
+
const inode = directoryInode(expected.directoryIdentity);
|
|
38568
|
+
return [
|
|
38569
|
+
current.clusterId !== expected.clusterId && "clusterId",
|
|
38570
|
+
current.dataDir !== expected.dataDir && "dataDir",
|
|
38571
|
+
(inode === undefined || inode !== directoryInode(current.directoryIdentity)) && "inode",
|
|
38572
|
+
current.major !== expected.major && "major",
|
|
38573
|
+
compareSystemIdentifier && current.server?.systemIdentifier !== expected.server?.systemIdentifier && "systemIdentifier"
|
|
38574
|
+
].filter((field) => field !== false);
|
|
38575
|
+
}
|
|
38558
38576
|
function managedPostgresMetadata(baseDir, major, create) {
|
|
38559
38577
|
if (!lstatSync(join3(baseDir, `v${major}`)).isDirectory()) {
|
|
38560
38578
|
throw new Error("Managed Postgres data must be a real directory, not a link.");
|
|
@@ -38588,10 +38606,30 @@ function managedPostgresMetadata(baseDir, major, create) {
|
|
|
38588
38606
|
}
|
|
38589
38607
|
trustedPath(path);
|
|
38590
38608
|
const record = JSON.parse(readFileSync2(path, "utf8"));
|
|
38591
|
-
|
|
38592
|
-
|
|
38609
|
+
const mismatches = [
|
|
38610
|
+
...record?.version !== 1 ? ["version"] : [],
|
|
38611
|
+
...typeof record?.clusterId !== "string" || !/^[0-9a-f-]{36}$/.test(record.clusterId) ? ["clusterId"] : [],
|
|
38612
|
+
...record?.dataDir !== dataDir ? ["dataDir"] : [],
|
|
38613
|
+
...typeof record?.directoryIdentity !== "string" || directoryInode(record.directoryIdentity) !== String(stat.ino) ? ["inode"] : [],
|
|
38614
|
+
...record?.major !== major ? ["major"] : [],
|
|
38615
|
+
...record?.server !== undefined && (!Number.isInteger(record.server?.port) || record.server.port < 1 || record.server.port > 65535 || !Number.isSafeInteger(record.server.pid) || record.server.pid <= 0 || !Number.isSafeInteger(record.server.started) || record.server.started <= 0 || !/^\d+$/.test(record.server.systemIdentifier)) ? ["server"] : []
|
|
38616
|
+
];
|
|
38617
|
+
const mismatch = (fields) => new Error(`Managed Postgres cluster identity mismatch (${fields.join(", ")}): ${path}. Preserve the data and ownership records.`);
|
|
38618
|
+
if (record === null || mismatches.length > 0)
|
|
38619
|
+
throw mismatch(mismatches);
|
|
38620
|
+
if (record.directoryIdentity === directoryIdentity)
|
|
38621
|
+
return record;
|
|
38622
|
+
if (record.server && controlSystemIdentifierOrUndefined(dataDir) !== record.server.systemIdentifier) {
|
|
38623
|
+
throw mismatch(["systemIdentifier"]);
|
|
38624
|
+
}
|
|
38625
|
+
return { ...record, directoryIdentity };
|
|
38626
|
+
}
|
|
38627
|
+
function controlSystemIdentifierOrUndefined(dataDir) {
|
|
38628
|
+
try {
|
|
38629
|
+
return controlFileSystemIdentifier(dataDir);
|
|
38630
|
+
} catch {
|
|
38631
|
+
return;
|
|
38593
38632
|
}
|
|
38594
|
-
return record;
|
|
38595
38633
|
}
|
|
38596
38634
|
function publishPostgresServer(baseDir, metadata, server) {
|
|
38597
38635
|
const current = managedPostgresMetadata(baseDir, metadata.major, false);
|
|
@@ -38664,13 +38702,13 @@ function assertManagedPostmaster(metadata, port) {
|
|
|
38664
38702
|
throw new Error("Managed Postgres postmaster identity does not match the shared data directory and port.");
|
|
38665
38703
|
}
|
|
38666
38704
|
}
|
|
38705
|
+
var directoryInode = (identity) => /^\d+:(\d+)$/.exec(identity)?.[1];
|
|
38667
38706
|
var init_dbos_postgres_ownership = () => {};
|
|
38668
38707
|
|
|
38669
38708
|
// dist/builtin/workflows/src/durable/dbos-postgres-identity.ts
|
|
38670
38709
|
import { existsSync as existsSync3, lstatSync as lstatSync2, readFileSync as readFileSync3, realpathSync as realpathSync2 } from "node:fs";
|
|
38671
38710
|
import { createRequire as createRequire2 } from "node:module";
|
|
38672
38711
|
import { createServer } from "node:net";
|
|
38673
|
-
import { endianness } from "node:os";
|
|
38674
38712
|
import { dirname as dirname3, isAbsolute as isAbsolute2, join as join4 } from "node:path";
|
|
38675
38713
|
function preferredPostgresPort(value2 = process.env.ATOMIC_POSTGRES_PORT) {
|
|
38676
38714
|
if (value2 === undefined)
|
|
@@ -38748,11 +38786,7 @@ function managedPostmaster(metadata) {
|
|
|
38748
38786
|
return { pid, started, port, systemIdentifier };
|
|
38749
38787
|
}
|
|
38750
38788
|
function managedSystemIdentifier(metadata) {
|
|
38751
|
-
const
|
|
38752
|
-
if (!lstatSync2(controlPath).isFile())
|
|
38753
|
-
throw new Error("Untrusted managed Postgres control file.");
|
|
38754
|
-
const control = readFileSync3(controlPath);
|
|
38755
|
-
const systemIdentifier = (endianness() === "LE" ? control.readBigUInt64LE(0) : control.readBigUInt64BE(0)).toString();
|
|
38789
|
+
const systemIdentifier = controlFileSystemIdentifier(metadata.dataDir);
|
|
38756
38790
|
if (metadata.server && metadata.server.systemIdentifier !== systemIdentifier) {
|
|
38757
38791
|
throw new Error("Managed Postgres system identity mismatch. Preserve the existing data.");
|
|
38758
38792
|
}
|
|
@@ -38963,8 +38997,9 @@ async function ensureCluster(options = {}) {
|
|
|
38963
38997
|
adoptedRegistry = postgresOwnershipDirectory(root, EMBEDDED_PG_MAJOR);
|
|
38964
38998
|
if (options.recovery && !metadata)
|
|
38965
38999
|
throw new Error("Managed Postgres recovery requires existing ownership records.");
|
|
38966
|
-
|
|
38967
|
-
|
|
39000
|
+
const recoveryMismatches = options.recovery && metadata ? managedPostgresIdentityMismatches(options.recovery, metadata) : [];
|
|
39001
|
+
if (recoveryMismatches.length > 0) {
|
|
39002
|
+
throw new Error(`Managed Postgres recovery identity changed (${recoveryMismatches.join(", ")}) while waiting for ownership.`);
|
|
38968
39003
|
}
|
|
38969
39004
|
const existing = metadata && managedPostmaster(metadata);
|
|
38970
39005
|
let port = existing?.port ?? metadata?.server?.port ?? preferredPort;
|
|
@@ -39179,8 +39214,9 @@ async function ensureCluster(options = {}) {
|
|
|
39179
39214
|
};
|
|
39180
39215
|
const inspect = async (probe = options.probeIdentity) => {
|
|
39181
39216
|
const current = managedPostgresMetadata(root, EMBEDDED_PG_MAJOR, false);
|
|
39182
|
-
|
|
39183
|
-
|
|
39217
|
+
const mismatches = managedPostgresIdentityMismatches(pinned, current);
|
|
39218
|
+
if (mismatches.length > 0) {
|
|
39219
|
+
throw new Error(`Managed Postgres health identity mismatch (${mismatches.join(", ")}). Preserve the data and ownership records.`);
|
|
39184
39220
|
}
|
|
39185
39221
|
const server = current.server;
|
|
39186
39222
|
if (!server)
|
|
@@ -39240,8 +39276,9 @@ async function ensureCluster(options = {}) {
|
|
|
39240
39276
|
async function stopBrokenManagedPostmaster(metadata, verified, pgCtl, context, lease, wait = delay, platform = process.platform) {
|
|
39241
39277
|
const check = () => {
|
|
39242
39278
|
const current = managedPostgresMetadata(context.baseDir, metadata.major, false);
|
|
39243
|
-
|
|
39244
|
-
|
|
39279
|
+
const mismatches = managedPostgresIdentityMismatches(metadata, current, false);
|
|
39280
|
+
if (mismatches.length > 0) {
|
|
39281
|
+
throw new Error(`Managed Postgres restart identity changed (${mismatches.join(", ")}). Preserve the server and data directory.`);
|
|
39245
39282
|
}
|
|
39246
39283
|
return { current, process: verifyManagedPostmasterProcess(current, verified) };
|
|
39247
39284
|
};
|
|
@@ -77738,6 +77775,7 @@ function isStoppingRun(run, rootRunId, runs, stoppingRunIds) {
|
|
|
77738
77775
|
}
|
|
77739
77776
|
return stoppingRunIds.has(rootRunId);
|
|
77740
77777
|
}
|
|
77778
|
+
var endedStatuses = new Set(["completed", "cached", "failed", "cancelled"]);
|
|
77741
77779
|
function projectRoot(rootRunId, runs, runById, ownership) {
|
|
77742
77780
|
let activeExecutionCount = 0;
|
|
77743
77781
|
let humanWaits = 0;
|
|
@@ -77748,6 +77786,7 @@ function projectRoot(rootRunId, runs, runById, ownership) {
|
|
|
77748
77786
|
let paused = false;
|
|
77749
77787
|
let stoppingExecutionCount = 0;
|
|
77750
77788
|
let independentContinuation = false;
|
|
77789
|
+
let childContinuation = false;
|
|
77751
77790
|
for (const run of runs) {
|
|
77752
77791
|
const runStopping = isStoppingRun(run, rootRunId, runById, ownership.stoppingRunIds);
|
|
77753
77792
|
let runExecutionCount = (run.toolNodes ?? []).filter((tool) => ownership.executingToolNodeIds.has(workflowActivityNodeKey(run.id, tool.id))).length;
|
|
@@ -77762,7 +77801,17 @@ function projectRoot(rootRunId, runs, runById, ownership) {
|
|
|
77762
77801
|
else
|
|
77763
77802
|
manualWaits++;
|
|
77764
77803
|
}
|
|
77765
|
-
const statuses = new Map([...run.stages, ...run.toolNodes ?? []].map((node) => [
|
|
77804
|
+
const statuses = new Map([...run.stages, ...run.toolNodes ?? []].map((node) => [
|
|
77805
|
+
node.id,
|
|
77806
|
+
endedStatuses.has(node.status) ? "ended" : node.status
|
|
77807
|
+
]));
|
|
77808
|
+
const live = ownership.liveRunIds?.has(run.id) === true;
|
|
77809
|
+
for (const tool of run.toolNodes ?? []) {
|
|
77810
|
+
if (live && run.status === "running" && !runStopping && tool.status === "pending" && tool.parentIds.every((id) => statuses.get(id) === "ended")) {
|
|
77811
|
+
runnable = true;
|
|
77812
|
+
independentContinuation = true;
|
|
77813
|
+
}
|
|
77814
|
+
}
|
|
77766
77815
|
for (const stage of run.stages) {
|
|
77767
77816
|
if (run.status === "running" && stage.status === "paused")
|
|
77768
77817
|
paused = true;
|
|
@@ -77779,20 +77828,29 @@ function projectRoot(rootRunId, runs, runById, ownership) {
|
|
|
77779
77828
|
if (!runStopping)
|
|
77780
77829
|
independentContinuation = true;
|
|
77781
77830
|
}
|
|
77782
|
-
if (run.status === "running" && !runStopping && stage.status === "pending" && stage.parentIds.every((id) => statuses.get(id) === "
|
|
77831
|
+
if (run.status === "running" && !runStopping && stage.status === "pending" && stage.parentIds.every((id) => statuses.get(id) === "ended")) {
|
|
77783
77832
|
runnable = true;
|
|
77784
77833
|
independentContinuation = true;
|
|
77785
77834
|
}
|
|
77786
77835
|
}
|
|
77787
|
-
|
|
77788
|
-
|
|
77789
|
-
|
|
77836
|
+
const childBoundary = (stage) => stage.status === "running" && stage.workflowChildRun !== undefined;
|
|
77837
|
+
if (live && run.status === "running" && !runStopping && !run.pendingPrompt && run.blockedAt === undefined && run.failureDisposition !== "active_blocked" && run.stages.every((stage) => !stage.pendingPrompt && (stage.status === "completed" || stage.status === "failed" || stage.status === "skipped" || childBoundary(stage))) && (run.toolNodes ?? []).every((tool) => endedStatuses.has(tool.status))) {
|
|
77838
|
+
if (run.stages.some(childBoundary))
|
|
77839
|
+
childContinuation = true;
|
|
77840
|
+
else {
|
|
77841
|
+
runnable = true;
|
|
77842
|
+
independentContinuation = true;
|
|
77843
|
+
}
|
|
77790
77844
|
}
|
|
77791
77845
|
activeExecutionCount += runExecutionCount;
|
|
77792
77846
|
if (runStopping)
|
|
77793
77847
|
stoppingExecutionCount += runExecutionCount;
|
|
77794
77848
|
}
|
|
77795
77849
|
const actionableBlockCount = humanWaits + manualWaits;
|
|
77850
|
+
if (childContinuation && actionableBlockCount === 0 && !paused) {
|
|
77851
|
+
runnable = true;
|
|
77852
|
+
independentContinuation = true;
|
|
77853
|
+
}
|
|
77796
77854
|
let state = "idle";
|
|
77797
77855
|
let reason = paused ? "paused" : "quiescent";
|
|
77798
77856
|
if (activeExecutionCount > 0 || retrying || runnable) {
|
|
@@ -37030,6 +37030,7 @@ import {
|
|
|
37030
37030
|
rmSync,
|
|
37031
37031
|
writeFileSync
|
|
37032
37032
|
} from "node:fs";
|
|
37033
|
+
import { endianness } from "node:os";
|
|
37033
37034
|
import { join as join2 } from "node:path";
|
|
37034
37035
|
function trustedPath(path, directory = false) {
|
|
37035
37036
|
const stat = lstatSync(path);
|
|
@@ -37040,6 +37041,23 @@ function trustedPath(path, directory = false) {
|
|
|
37040
37041
|
function postgresOwnershipDirectory(baseDir, major) {
|
|
37041
37042
|
return join2(baseDir, `v${major}.shared`);
|
|
37042
37043
|
}
|
|
37044
|
+
function controlFileSystemIdentifier(dataDir) {
|
|
37045
|
+
const controlPath = join2(dataDir, "global", "pg_control");
|
|
37046
|
+
if (!lstatSync(controlPath).isFile())
|
|
37047
|
+
throw new Error("Untrusted managed Postgres control file.");
|
|
37048
|
+
const control = readFileSync(controlPath);
|
|
37049
|
+
return (endianness() === "LE" ? control.readBigUInt64LE(0) : control.readBigUInt64BE(0)).toString();
|
|
37050
|
+
}
|
|
37051
|
+
function managedPostgresIdentityMismatches(expected, current, compareSystemIdentifier = true) {
|
|
37052
|
+
const inode = directoryInode(expected.directoryIdentity);
|
|
37053
|
+
return [
|
|
37054
|
+
current.clusterId !== expected.clusterId && "clusterId",
|
|
37055
|
+
current.dataDir !== expected.dataDir && "dataDir",
|
|
37056
|
+
(inode === undefined || inode !== directoryInode(current.directoryIdentity)) && "inode",
|
|
37057
|
+
current.major !== expected.major && "major",
|
|
37058
|
+
compareSystemIdentifier && current.server?.systemIdentifier !== expected.server?.systemIdentifier && "systemIdentifier"
|
|
37059
|
+
].filter((field) => field !== false);
|
|
37060
|
+
}
|
|
37043
37061
|
function managedPostgresMetadata(baseDir, major, create) {
|
|
37044
37062
|
if (!lstatSync(join2(baseDir, `v${major}`)).isDirectory()) {
|
|
37045
37063
|
throw new Error("Managed Postgres data must be a real directory, not a link.");
|
|
@@ -37073,10 +37091,30 @@ function managedPostgresMetadata(baseDir, major, create) {
|
|
|
37073
37091
|
}
|
|
37074
37092
|
trustedPath(path);
|
|
37075
37093
|
const record = JSON.parse(readFileSync(path, "utf8"));
|
|
37076
|
-
|
|
37077
|
-
|
|
37094
|
+
const mismatches = [
|
|
37095
|
+
...record?.version !== 1 ? ["version"] : [],
|
|
37096
|
+
...typeof record?.clusterId !== "string" || !/^[0-9a-f-]{36}$/.test(record.clusterId) ? ["clusterId"] : [],
|
|
37097
|
+
...record?.dataDir !== dataDir ? ["dataDir"] : [],
|
|
37098
|
+
...typeof record?.directoryIdentity !== "string" || directoryInode(record.directoryIdentity) !== String(stat.ino) ? ["inode"] : [],
|
|
37099
|
+
...record?.major !== major ? ["major"] : [],
|
|
37100
|
+
...record?.server !== undefined && (!Number.isInteger(record.server?.port) || record.server.port < 1 || record.server.port > 65535 || !Number.isSafeInteger(record.server.pid) || record.server.pid <= 0 || !Number.isSafeInteger(record.server.started) || record.server.started <= 0 || !/^\d+$/.test(record.server.systemIdentifier)) ? ["server"] : []
|
|
37101
|
+
];
|
|
37102
|
+
const mismatch = (fields) => new Error(`Managed Postgres cluster identity mismatch (${fields.join(", ")}): ${path}. Preserve the data and ownership records.`);
|
|
37103
|
+
if (record === null || mismatches.length > 0)
|
|
37104
|
+
throw mismatch(mismatches);
|
|
37105
|
+
if (record.directoryIdentity === directoryIdentity)
|
|
37106
|
+
return record;
|
|
37107
|
+
if (record.server && controlSystemIdentifierOrUndefined(dataDir) !== record.server.systemIdentifier) {
|
|
37108
|
+
throw mismatch(["systemIdentifier"]);
|
|
37109
|
+
}
|
|
37110
|
+
return { ...record, directoryIdentity };
|
|
37111
|
+
}
|
|
37112
|
+
function controlSystemIdentifierOrUndefined(dataDir) {
|
|
37113
|
+
try {
|
|
37114
|
+
return controlFileSystemIdentifier(dataDir);
|
|
37115
|
+
} catch {
|
|
37116
|
+
return;
|
|
37078
37117
|
}
|
|
37079
|
-
return record;
|
|
37080
37118
|
}
|
|
37081
37119
|
function publishPostgresServer(baseDir, metadata, server) {
|
|
37082
37120
|
const current = managedPostgresMetadata(baseDir, metadata.major, false);
|
|
@@ -37149,13 +37187,13 @@ function assertManagedPostmaster(metadata, port) {
|
|
|
37149
37187
|
throw new Error("Managed Postgres postmaster identity does not match the shared data directory and port.");
|
|
37150
37188
|
}
|
|
37151
37189
|
}
|
|
37190
|
+
var directoryInode = (identity) => /^\d+:(\d+)$/.exec(identity)?.[1];
|
|
37152
37191
|
var init_dbos_postgres_ownership = () => {};
|
|
37153
37192
|
|
|
37154
37193
|
// dist/builtin/workflows/src/durable/dbos-postgres-identity.ts
|
|
37155
37194
|
import { existsSync as existsSync2, lstatSync as lstatSync2, readFileSync as readFileSync2, realpathSync as realpathSync2 } from "node:fs";
|
|
37156
37195
|
import { createRequire as createRequire2 } from "node:module";
|
|
37157
37196
|
import { createServer } from "node:net";
|
|
37158
|
-
import { endianness } from "node:os";
|
|
37159
37197
|
import { dirname as dirname2, isAbsolute as isAbsolute2, join as join3 } from "node:path";
|
|
37160
37198
|
function preferredPostgresPort(value = process.env.ATOMIC_POSTGRES_PORT) {
|
|
37161
37199
|
if (value === undefined)
|
|
@@ -37233,11 +37271,7 @@ function managedPostmaster(metadata) {
|
|
|
37233
37271
|
return { pid, started, port, systemIdentifier };
|
|
37234
37272
|
}
|
|
37235
37273
|
function managedSystemIdentifier(metadata) {
|
|
37236
|
-
const
|
|
37237
|
-
if (!lstatSync2(controlPath).isFile())
|
|
37238
|
-
throw new Error("Untrusted managed Postgres control file.");
|
|
37239
|
-
const control = readFileSync2(controlPath);
|
|
37240
|
-
const systemIdentifier = (endianness() === "LE" ? control.readBigUInt64LE(0) : control.readBigUInt64BE(0)).toString();
|
|
37274
|
+
const systemIdentifier = controlFileSystemIdentifier(metadata.dataDir);
|
|
37241
37275
|
if (metadata.server && metadata.server.systemIdentifier !== systemIdentifier) {
|
|
37242
37276
|
throw new Error("Managed Postgres system identity mismatch. Preserve the existing data.");
|
|
37243
37277
|
}
|
|
@@ -37448,8 +37482,9 @@ async function ensureCluster(options = {}) {
|
|
|
37448
37482
|
adoptedRegistry = postgresOwnershipDirectory(root, EMBEDDED_PG_MAJOR);
|
|
37449
37483
|
if (options.recovery && !metadata)
|
|
37450
37484
|
throw new Error("Managed Postgres recovery requires existing ownership records.");
|
|
37451
|
-
|
|
37452
|
-
|
|
37485
|
+
const recoveryMismatches = options.recovery && metadata ? managedPostgresIdentityMismatches(options.recovery, metadata) : [];
|
|
37486
|
+
if (recoveryMismatches.length > 0) {
|
|
37487
|
+
throw new Error(`Managed Postgres recovery identity changed (${recoveryMismatches.join(", ")}) while waiting for ownership.`);
|
|
37453
37488
|
}
|
|
37454
37489
|
const existing = metadata && managedPostmaster(metadata);
|
|
37455
37490
|
let port = existing?.port ?? metadata?.server?.port ?? preferredPort;
|
|
@@ -37664,8 +37699,9 @@ async function ensureCluster(options = {}) {
|
|
|
37664
37699
|
};
|
|
37665
37700
|
const inspect = async (probe = options.probeIdentity) => {
|
|
37666
37701
|
const current = managedPostgresMetadata(root, EMBEDDED_PG_MAJOR, false);
|
|
37667
|
-
|
|
37668
|
-
|
|
37702
|
+
const mismatches = managedPostgresIdentityMismatches(pinned, current);
|
|
37703
|
+
if (mismatches.length > 0) {
|
|
37704
|
+
throw new Error(`Managed Postgres health identity mismatch (${mismatches.join(", ")}). Preserve the data and ownership records.`);
|
|
37669
37705
|
}
|
|
37670
37706
|
const server = current.server;
|
|
37671
37707
|
if (!server)
|
|
@@ -37725,8 +37761,9 @@ async function ensureCluster(options = {}) {
|
|
|
37725
37761
|
async function stopBrokenManagedPostmaster(metadata, verified, pgCtl, context, lease, wait = delay, platform = process.platform) {
|
|
37726
37762
|
const check = () => {
|
|
37727
37763
|
const current = managedPostgresMetadata(context.baseDir, metadata.major, false);
|
|
37728
|
-
|
|
37729
|
-
|
|
37764
|
+
const mismatches = managedPostgresIdentityMismatches(metadata, current, false);
|
|
37765
|
+
if (mismatches.length > 0) {
|
|
37766
|
+
throw new Error(`Managed Postgres restart identity changed (${mismatches.join(", ")}). Preserve the server and data directory.`);
|
|
37730
37767
|
}
|
|
37731
37768
|
return { current, process: verifyManagedPostmasterProcess(current, verified) };
|
|
37732
37769
|
};
|
|
@@ -40069,6 +40106,7 @@ function reciprocalWorkflowRootRunId(runById, runId) {
|
|
|
40069
40106
|
function workflowActivityNodeKey(runId, nodeId) {
|
|
40070
40107
|
return `${runId}:${nodeId}`;
|
|
40071
40108
|
}
|
|
40109
|
+
var endedStatuses = new Set(["completed", "cached", "failed", "cancelled"]);
|
|
40072
40110
|
|
|
40073
40111
|
// dist/builtin/workflows/src/shared/workflow-observation-runtime.ts
|
|
40074
40112
|
class WorkflowObservationRuntime {
|