agenticros 0.1.16 → 0.1.18
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/commands/down.d.ts.map +1 -1
- package/dist/commands/down.js +55 -3
- package/dist/commands/down.js.map +1 -1
- package/dist/menu.d.ts +12 -3
- package/dist/menu.d.ts.map +1 -1
- package/dist/menu.js +104 -51
- package/dist/menu.js.map +1 -1
- package/package.json +1 -1
- package/runtime/BUNDLE.json +1 -1
- package/runtime/scripts/start_demo.sh +26 -3
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"down.d.ts","sourceRoot":"","sources":["../../src/commands/down.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAOH,MAAM,WAAW,WAAW;IAC1B,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,qEAAqE;IACrE,WAAW,CAAC,EAAE,OAAO,CAAC;CACvB;AAID,wBAAsB,WAAW,CAAC,IAAI,EAAE,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC,
|
|
1
|
+
{"version":3,"file":"down.d.ts","sourceRoot":"","sources":["../../src/commands/down.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAOH,MAAM,WAAW,WAAW;IAC1B,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,qEAAqE;IACrE,WAAW,CAAC,EAAE,OAAO,CAAC;CACvB;AAID,wBAAsB,WAAW,CAAC,IAAI,EAAE,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC,CAgDlE"}
|
package/dist/commands/down.js
CHANGED
|
@@ -29,9 +29,24 @@ export async function downCommand(opts) {
|
|
|
29
29
|
clearPid(name);
|
|
30
30
|
});
|
|
31
31
|
}
|
|
32
|
-
// Mop up
|
|
33
|
-
//
|
|
34
|
-
|
|
32
|
+
// Mop up stray subprocesses that don't have a pidfile we own. Two common
|
|
33
|
+
// sources of orphans:
|
|
34
|
+
// - `ros2 launch realsense2_camera rs_launch.py` writes the launch parent's
|
|
35
|
+
// PID to the pidfile, but the actual `realsense2_camera_node` is a
|
|
36
|
+
// detached child. If the launch parent dies (or start_demo.sh's "already
|
|
37
|
+
// running, skipping" path runs), the node keeps running with its IR
|
|
38
|
+
// projector lit and is invisible to our pidfile bookkeeping.
|
|
39
|
+
// - Sim children (gz sim, rviz, parameter_bridge) inherit termination from
|
|
40
|
+
// ros2 launch in most cases but not always.
|
|
41
|
+
// We pkill them all by name. -f matches the full command line; SIGTERM first,
|
|
42
|
+
// then a brief grace period, then SIGKILL anything still hanging on.
|
|
43
|
+
if (!opts.keepCamera) {
|
|
44
|
+
await pkillAndWait([
|
|
45
|
+
"realsense2_camera_node",
|
|
46
|
+
"ros2 launch realsense2_camera",
|
|
47
|
+
]);
|
|
48
|
+
}
|
|
49
|
+
await pkillAndWait(["gz sim", "ign gazebo", "rviz2", "parameter_bridge"]);
|
|
35
50
|
if (opts.stopGateway) {
|
|
36
51
|
await stopGatewayService();
|
|
37
52
|
}
|
|
@@ -72,6 +87,43 @@ async function tryKill(patterns) {
|
|
|
72
87
|
}
|
|
73
88
|
}
|
|
74
89
|
}
|
|
90
|
+
/**
|
|
91
|
+
* Send SIGTERM to anything matching `patterns`, wait for the kernel to schedule
|
|
92
|
+
* the exits, then SIGKILL any survivors. Crucially, this is what actually turns
|
|
93
|
+
* the RealSense IR projector off: SIGTERM gives the realsense2_camera_node a
|
|
94
|
+
* chance to release the USB device cleanly, and the SIGKILL fallback handles
|
|
95
|
+
* the case where it's wedged.
|
|
96
|
+
*/
|
|
97
|
+
async function pkillAndWait(patterns, termGraceMs = 1500) {
|
|
98
|
+
// Phase 1: gentle termination.
|
|
99
|
+
let matchedAny = false;
|
|
100
|
+
for (const pattern of patterns) {
|
|
101
|
+
try {
|
|
102
|
+
const { exitCode } = await execa("pkill", ["-TERM", "-f", pattern], {
|
|
103
|
+
reject: false,
|
|
104
|
+
});
|
|
105
|
+
// pkill exits 0 when at least one process matched, 1 when nothing did.
|
|
106
|
+
if (exitCode === 0)
|
|
107
|
+
matchedAny = true;
|
|
108
|
+
}
|
|
109
|
+
catch {
|
|
110
|
+
// pkill missing — nothing to do.
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
if (!matchedAny)
|
|
114
|
+
return;
|
|
115
|
+
// Phase 2: brief wait so well-behaved processes can exit cleanly.
|
|
116
|
+
await new Promise((r) => setTimeout(r, termGraceMs));
|
|
117
|
+
// Phase 3: SIGKILL anything that's still around.
|
|
118
|
+
for (const pattern of patterns) {
|
|
119
|
+
try {
|
|
120
|
+
await execa("pkill", ["-KILL", "-f", pattern], { reject: false });
|
|
121
|
+
}
|
|
122
|
+
catch {
|
|
123
|
+
// ignore
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
}
|
|
75
127
|
async function stopGatewayService() {
|
|
76
128
|
try {
|
|
77
129
|
const { exitCode } = await execa("systemctl", ["--user", "is-active", "openclaw-gateway.service"], { reject: false });
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"down.js","sourceRoot":"","sources":["../../src/commands/down.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,KAAK,EAAE,MAAM,OAAO,CAAC;AAE9B,OAAO,EAAE,QAAQ,EAAE,UAAU,EAAE,OAAO,EAAuB,MAAM,oBAAoB,CAAC;AACxF,OAAO,EAAE,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE,EAAE,EAAE,IAAI,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAQ7E,MAAM,SAAS,GAAqB,CAAC,KAAK,EAAE,KAAK,EAAE,WAAW,EAAE,QAAQ,CAAC,CAAC;AAE1E,MAAM,CAAC,KAAK,UAAU,WAAW,CAAC,IAAiB;IACjD,MAAM,CAAC,4BAA4B,CAAC,CAAC;IAErC,IAAI,UAAU,GAAG,KAAK,CAAC;IACvB,KAAK,MAAM,IAAI,IAAI,SAAS,EAAE,CAAC;QAC7B,IAAI,IAAI,KAAK,QAAQ,IAAI,IAAI,CAAC,UAAU,EAAE,CAAC;YACzC,IAAI,CAAC,kCAAkC,CAAC,CAAC;YACzC,SAAS;QACX,CAAC;QACD,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC;YAAE,SAAS;QAChC,UAAU,GAAG,IAAI,CAAC;QAClB,MAAM,WAAW,CAAC,YAAY,IAAI,EAAE,EAAE,KAAK,IAAI,EAAE;YAC/C,MAAM,GAAG,GAAG,OAAO,CAAC,IAAI,EAAE,SAAS,CAAC,CAAC;YACrC,IAAI,GAAG,KAAK,SAAS;gBAAE,OAAO;YAC9B,MAAM,WAAW,CAAC,GAAG,CAAC,CAAC;YACvB,QAAQ,CAAC,IAAI,CAAC,CAAC;QACjB,CAAC,CAAC,CAAC;IACL,CAAC;IAED,8EAA8E;IAC9E,
|
|
1
|
+
{"version":3,"file":"down.js","sourceRoot":"","sources":["../../src/commands/down.ts"],"names":[],"mappings":"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"}
|
package/dist/menu.d.ts
CHANGED
|
@@ -1,9 +1,18 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Interactive top-level menu for `agenticros` (invoked with no subcommand).
|
|
3
3
|
*
|
|
4
|
-
*
|
|
5
|
-
*
|
|
6
|
-
*
|
|
4
|
+
* Behavior:
|
|
5
|
+
* - Looping: the menu redisplays after every non-launch action (doctor, config,
|
|
6
|
+
* skills, etc.) so the user keeps a stable home base. Only the real-robot and
|
|
7
|
+
* simulation launches hand off the terminal to a long-running process and
|
|
8
|
+
* therefore terminate the menu.
|
|
9
|
+
* - Every sub-prompt offers an explicit "Back to main menu" option so users
|
|
10
|
+
* never get trapped on a path they accidentally entered (notably the sim
|
|
11
|
+
* robot picker, which previously had no escape hatch).
|
|
12
|
+
* - Adaptive: when doctor reports a red check (workspace not built, no API key,
|
|
13
|
+
* etc.) the first option becomes "First-time setup" so brand-new users land
|
|
14
|
+
* naturally on `agenticros init`. Otherwise we lead with "Launch with real
|
|
15
|
+
* robot".
|
|
7
16
|
*/
|
|
8
17
|
export declare function runMenu(): Promise<void>;
|
|
9
18
|
//# sourceMappingURL=menu.d.ts.map
|
package/dist/menu.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"menu.d.ts","sourceRoot":"","sources":["../src/menu.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"menu.d.ts","sourceRoot":"","sources":["../src/menu.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAyBH,wBAAsB,OAAO,IAAI,OAAO,CAAC,IAAI,CAAC,CAc7C"}
|
package/dist/menu.js
CHANGED
|
@@ -1,11 +1,20 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Interactive top-level menu for `agenticros` (invoked with no subcommand).
|
|
3
3
|
*
|
|
4
|
-
*
|
|
5
|
-
*
|
|
6
|
-
*
|
|
4
|
+
* Behavior:
|
|
5
|
+
* - Looping: the menu redisplays after every non-launch action (doctor, config,
|
|
6
|
+
* skills, etc.) so the user keeps a stable home base. Only the real-robot and
|
|
7
|
+
* simulation launches hand off the terminal to a long-running process and
|
|
8
|
+
* therefore terminate the menu.
|
|
9
|
+
* - Every sub-prompt offers an explicit "Back to main menu" option so users
|
|
10
|
+
* never get trapped on a path they accidentally entered (notably the sim
|
|
11
|
+
* robot picker, which previously had no escape hatch).
|
|
12
|
+
* - Adaptive: when doctor reports a red check (workspace not built, no API key,
|
|
13
|
+
* etc.) the first option becomes "First-time setup" so brand-new users land
|
|
14
|
+
* naturally on `agenticros init`. Otherwise we lead with "Launch with real
|
|
15
|
+
* robot".
|
|
7
16
|
*/
|
|
8
|
-
import { select
|
|
17
|
+
import { select } from "@inquirer/prompts";
|
|
9
18
|
import { upCommand } from "./commands/up.js";
|
|
10
19
|
import { downCommand } from "./commands/down.js";
|
|
11
20
|
import { initCommand } from "./commands/init.js";
|
|
@@ -17,18 +26,31 @@ import { skillsCommand } from "./commands/skills.js";
|
|
|
17
26
|
import { header, info, isTty, dim } from "./util/logger.js";
|
|
18
27
|
import { readState, formatAge } from "./util/state.js";
|
|
19
28
|
import { listSkills } from "./util/skills.js";
|
|
29
|
+
/** Sentinel used by sub-prompts to ask the main loop to redraw without acting. */
|
|
30
|
+
const BACK = "__back__";
|
|
20
31
|
export async function runMenu() {
|
|
21
32
|
if (!isTty) {
|
|
22
33
|
info("Interactive menu requires a TTY. Use a subcommand (e.g. `agenticros up real`) or `agenticros --help`.");
|
|
23
34
|
return;
|
|
24
35
|
}
|
|
25
36
|
header("AgenticROS - agentic AI for ROS-powered robots");
|
|
37
|
+
while (true) {
|
|
38
|
+
const shouldExit = await runMenuOnce();
|
|
39
|
+
if (shouldExit)
|
|
40
|
+
return;
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* Render the main menu once and dispatch the chosen action.
|
|
45
|
+
* @returns true if the menu should exit (the action either launched a
|
|
46
|
+
* long-running process or the user asked to quit).
|
|
47
|
+
*/
|
|
48
|
+
async function runMenuOnce() {
|
|
26
49
|
const state = readState();
|
|
27
50
|
if (state.lastMode) {
|
|
28
51
|
const age = formatAge(state.lastUpAt);
|
|
29
52
|
dim(`Last mode: ${state.lastMode}${age ? ` (${age})` : ""}`);
|
|
30
53
|
}
|
|
31
|
-
// Need-setup detection. Doctor returns a count; we use that to reorder.
|
|
32
54
|
const setupNeeded = await hasRedChecks();
|
|
33
55
|
const skillsListing = safeListSkills();
|
|
34
56
|
const skillsSuffix = formatSkillsSuffix(skillsListing);
|
|
@@ -53,83 +75,114 @@ export async function runMenu() {
|
|
|
53
75
|
const choice = await select({
|
|
54
76
|
message: "What would you like to do?",
|
|
55
77
|
choices,
|
|
56
|
-
default: setupNeeded
|
|
78
|
+
default: setupNeeded
|
|
79
|
+
? "init"
|
|
80
|
+
: state.lastMode === "sim-amr" || state.lastMode === "sim-arm"
|
|
81
|
+
? "sim"
|
|
82
|
+
: "real",
|
|
57
83
|
});
|
|
58
84
|
switch (choice) {
|
|
59
85
|
case "real":
|
|
60
86
|
await upCommand({ target: "real" });
|
|
61
|
-
|
|
87
|
+
// Hands control to the foreground launcher; menu is done.
|
|
88
|
+
return true;
|
|
62
89
|
case "sim": {
|
|
63
|
-
const
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
{ name: "2-wheel AMR (camera + depth + LiDAR)", value: "sim-amr" },
|
|
67
|
-
{
|
|
68
|
-
name: "6-DOF arm (UR5e-shaped, per-joint position control)",
|
|
69
|
-
value: "sim-arm",
|
|
70
|
-
},
|
|
71
|
-
],
|
|
72
|
-
default: "sim-amr",
|
|
73
|
-
});
|
|
74
|
-
const rviz = await confirm({ message: "Show RViz?", default: false });
|
|
75
|
-
await upCommand({ target: sub, rviz });
|
|
76
|
-
break;
|
|
90
|
+
const launched = await runSimFlow();
|
|
91
|
+
// launched === true ⇒ upCommand has taken over; otherwise back to main.
|
|
92
|
+
return launched;
|
|
77
93
|
}
|
|
78
94
|
case "init":
|
|
79
95
|
await initCommand({});
|
|
80
|
-
|
|
96
|
+
return false;
|
|
81
97
|
case "down":
|
|
82
98
|
await downCommand({});
|
|
83
|
-
|
|
99
|
+
return false;
|
|
84
100
|
case "doctor":
|
|
85
101
|
await doctorCommand({});
|
|
86
|
-
|
|
102
|
+
return false;
|
|
87
103
|
case "config":
|
|
88
104
|
await configCommand({ action: "show" });
|
|
89
|
-
|
|
105
|
+
return false;
|
|
90
106
|
case "skills":
|
|
91
107
|
await skillsSubmenu();
|
|
92
|
-
|
|
108
|
+
return false;
|
|
93
109
|
case "logs":
|
|
94
110
|
await logsCommand({ target: undefined });
|
|
95
|
-
|
|
111
|
+
return false;
|
|
96
112
|
case "status":
|
|
97
113
|
await statusCommand({});
|
|
98
|
-
|
|
114
|
+
return false;
|
|
99
115
|
case "quit":
|
|
100
116
|
default:
|
|
101
|
-
|
|
117
|
+
return true;
|
|
102
118
|
}
|
|
103
119
|
}
|
|
104
120
|
/**
|
|
105
|
-
*
|
|
106
|
-
*
|
|
107
|
-
*
|
|
121
|
+
* Simulation launch flow. Two prompts (which robot, then RViz?) — both expose
|
|
122
|
+
* "Back to main menu" so the user can bail out at any step without launching.
|
|
123
|
+
* @returns true if a simulation was launched (caller should exit the menu),
|
|
124
|
+
* false if the user backed out.
|
|
108
125
|
*/
|
|
109
|
-
async function
|
|
110
|
-
const
|
|
111
|
-
|
|
112
|
-
const hasRegistered = listing && listing.registered.length > 0;
|
|
113
|
-
const action = await select({
|
|
114
|
-
message: "Skills:",
|
|
126
|
+
async function runSimFlow() {
|
|
127
|
+
const target = await select({
|
|
128
|
+
message: "Which simulated robot?",
|
|
115
129
|
choices: [
|
|
116
|
-
{ name: "
|
|
130
|
+
{ name: "2-wheel AMR (camera + depth + LiDAR)", value: "sim-amr" },
|
|
117
131
|
{
|
|
118
|
-
name:
|
|
119
|
-
|
|
120
|
-
: "Discover & register (interactive picker)",
|
|
121
|
-
value: "discover",
|
|
132
|
+
name: "6-DOF arm (UR5e-shaped, per-joint position control)",
|
|
133
|
+
value: "sim-arm",
|
|
122
134
|
},
|
|
123
|
-
{ name: "
|
|
124
|
-
{ name: "Remove a skill", value: "remove" },
|
|
125
|
-
{ name: "Sync OpenClaw contracts.tools allowlist", value: "sync" },
|
|
126
|
-
{ name: "Back", value: "back" },
|
|
135
|
+
{ name: "Back to main menu", value: BACK },
|
|
127
136
|
],
|
|
128
|
-
default:
|
|
137
|
+
default: "sim-amr",
|
|
129
138
|
});
|
|
130
|
-
if (
|
|
131
|
-
return;
|
|
132
|
-
await
|
|
139
|
+
if (target === BACK)
|
|
140
|
+
return false;
|
|
141
|
+
const rvizChoice = await select({
|
|
142
|
+
message: "Show RViz?",
|
|
143
|
+
choices: [
|
|
144
|
+
{ name: "No", value: "no" },
|
|
145
|
+
{ name: "Yes", value: "yes" },
|
|
146
|
+
{ name: "Back to main menu", value: BACK },
|
|
147
|
+
],
|
|
148
|
+
default: "no",
|
|
149
|
+
});
|
|
150
|
+
if (rvizChoice === BACK)
|
|
151
|
+
return false;
|
|
152
|
+
await upCommand({ target, rviz: rvizChoice === "yes" });
|
|
153
|
+
return true;
|
|
154
|
+
}
|
|
155
|
+
/**
|
|
156
|
+
* Skills sub-menu. Loops until the user picks "Back to main menu" so the user
|
|
157
|
+
* can run several skill actions (list, then discover, then sync, …) without
|
|
158
|
+
* round-tripping through the top-level menu each time.
|
|
159
|
+
*/
|
|
160
|
+
async function skillsSubmenu() {
|
|
161
|
+
while (true) {
|
|
162
|
+
const listing = safeListSkills();
|
|
163
|
+
const hasAvailable = listing && listing.available.length > 0;
|
|
164
|
+
const hasRegistered = listing && listing.registered.length > 0;
|
|
165
|
+
const action = await select({
|
|
166
|
+
message: "Skills:",
|
|
167
|
+
choices: [
|
|
168
|
+
{ name: "List registered + available", value: "list" },
|
|
169
|
+
{
|
|
170
|
+
name: hasAvailable
|
|
171
|
+
? `Discover & register (${listing.available.length} unregistered found)`
|
|
172
|
+
: "Discover & register (interactive picker)",
|
|
173
|
+
value: "discover",
|
|
174
|
+
},
|
|
175
|
+
{ name: "Add a skill by path or package name", value: "add" },
|
|
176
|
+
{ name: "Remove a skill", value: "remove" },
|
|
177
|
+
{ name: "Sync OpenClaw contracts.tools allowlist", value: "sync" },
|
|
178
|
+
{ name: "Back to main menu", value: BACK },
|
|
179
|
+
],
|
|
180
|
+
default: hasRegistered ? "list" : "discover",
|
|
181
|
+
});
|
|
182
|
+
if (action === BACK)
|
|
183
|
+
return;
|
|
184
|
+
await skillsCommand({ action });
|
|
185
|
+
}
|
|
133
186
|
}
|
|
134
187
|
/** Read skills without throwing; the menu must keep working even if the config is broken. */
|
|
135
188
|
function safeListSkills() {
|
package/dist/menu.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"menu.js","sourceRoot":"","sources":["../src/menu.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"menu.js","sourceRoot":"","sources":["../src/menu.ts"],"names":[],"mappings":"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"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "agenticros",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.18",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "AgenticROS - agentic AI for ROS-powered robots. Single CLI to launch real-robot or simulated demos, manage configuration, and inspect status.",
|
|
6
6
|
"keywords": [
|
package/runtime/BUNDLE.json
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
{
|
|
2
|
-
"packedAt": "2026-06-
|
|
2
|
+
"packedAt": "2026-06-09T22:12:21.081Z",
|
|
3
3
|
"repo": "https://github.com/PlaiPin/agenticros",
|
|
4
4
|
"note": "This directory is a snapshot of the agenticros monorepo source. `agenticros init` will copy it to ~/agenticros and run pnpm install + colcon build there.",
|
|
5
5
|
"layout": {
|
|
@@ -36,11 +36,34 @@ echo "==> Starting RealSense camera (logs: $CAMERA_LOG)"
|
|
|
36
36
|
if [[ -f "$CAMERA_PID_FILE" ]] && kill -0 "$(cat "$CAMERA_PID_FILE")" 2>/dev/null; then
|
|
37
37
|
echo " Already running (pid $(cat "$CAMERA_PID_FILE")) — skipping"
|
|
38
38
|
elif pgrep -f "realsense2_camera_node" >/dev/null; then
|
|
39
|
-
|
|
39
|
+
# Camera node from a prior session is still running but our pidfile is gone.
|
|
40
|
+
# Re-adopt it so `agenticros down` can find and stop it (turning off the IR
|
|
41
|
+
# projector). We point the pidfile at the actual node, not a launch parent,
|
|
42
|
+
# because that's what's holding the USB device.
|
|
43
|
+
existing_pid=$(pgrep -f "realsense2_camera_node" | head -n 1)
|
|
44
|
+
echo "$existing_pid" >"$CAMERA_PID_FILE"
|
|
45
|
+
echo " Detected an existing realsense2_camera_node (pid $existing_pid) — adopted into $CAMERA_PID_FILE"
|
|
40
46
|
else
|
|
41
47
|
nohup ros2 launch realsense2_camera rs_launch.py >"$CAMERA_LOG" 2>&1 &
|
|
42
|
-
|
|
43
|
-
|
|
48
|
+
# $! is the `ros2 launch` parent; the actual camera node is a child that
|
|
49
|
+
# comes up a moment later. Wait briefly so we can record the node's PID
|
|
50
|
+
# (what holds the USB / projector) instead of the parent's.
|
|
51
|
+
launch_pid=$!
|
|
52
|
+
node_pid=""
|
|
53
|
+
for _ in 1 2 3 4 5 6 7 8 9 10; do
|
|
54
|
+
node_pid=$(pgrep -f "realsense2_camera_node" | head -n 1 || true)
|
|
55
|
+
[[ -n "$node_pid" ]] && break
|
|
56
|
+
sleep 0.5
|
|
57
|
+
done
|
|
58
|
+
if [[ -n "$node_pid" ]]; then
|
|
59
|
+
echo "$node_pid" >"$CAMERA_PID_FILE"
|
|
60
|
+
echo " Started (node pid $node_pid, launch pid $launch_pid)"
|
|
61
|
+
else
|
|
62
|
+
# Fallback: launch parent. `agenticros down` also pkills by name, so
|
|
63
|
+
# this still gets cleaned up even if we miss the node PID.
|
|
64
|
+
echo "$launch_pid" >"$CAMERA_PID_FILE"
|
|
65
|
+
echo " Started (launch pid $launch_pid — node not yet visible; pkill fallback will clean up)"
|
|
66
|
+
fi
|
|
44
67
|
fi
|
|
45
68
|
|
|
46
69
|
echo "==> Building TypeScript workspace (@agenticros/core, ros-camera, claude-code, ...)"
|