mirror of
https://github.com/openclaw/openclaw.git
synced 2026-05-28 15:37:16 +00:00
90 lines
3.5 KiB
TypeScript
90 lines
3.5 KiB
TypeScript
import type { Command } from "commander";
|
|
import { randomIdempotencyKey } from "../../gateway/call.js";
|
|
import { defaultRuntime } from "../../runtime.js";
|
|
import { normalizeOptionalLowercaseString } from "../../shared/string-coerce.js";
|
|
import { runNodesCommand } from "./cli-utils.js";
|
|
import {
|
|
callGatewayCli,
|
|
nodesCallOpts,
|
|
parseOptionalNodeNonNegativeInteger,
|
|
parseOptionalNodePositiveInteger,
|
|
resolveNodeId,
|
|
} from "./rpc.js";
|
|
import type { NodesRpcOpts } from "./types.js";
|
|
|
|
export function registerNodesLocationCommands(nodes: Command) {
|
|
const location = nodes.command("location").description("Fetch location from a paired node");
|
|
|
|
nodesCallOpts(
|
|
location
|
|
.command("get")
|
|
.description("Fetch the current location from a node")
|
|
.requiredOption("--node <idOrNameOrIp>", "Node id, name, or IP")
|
|
.option("--max-age <ms>", "Use cached location newer than this (ms)")
|
|
.option(
|
|
"--accuracy <coarse|balanced|precise>",
|
|
"Desired accuracy (default: balanced/precise depending on node setting)",
|
|
)
|
|
.option("--location-timeout <ms>", "Location fix timeout (ms)", "10000")
|
|
.option("--invoke-timeout <ms>", "Node invoke timeout in ms (default 20000)", "20000")
|
|
.action(async (opts: NodesRpcOpts) => {
|
|
await runNodesCommand("location get", async () => {
|
|
const nodeId = await resolveNodeId(opts, opts.node ?? "");
|
|
const maxAgeMs = parseOptionalNodeNonNegativeInteger(opts.maxAge, "--max-age");
|
|
const desiredAccuracyRaw = normalizeOptionalLowercaseString(opts.accuracy);
|
|
const desiredAccuracy =
|
|
desiredAccuracyRaw === "coarse" ||
|
|
desiredAccuracyRaw === "balanced" ||
|
|
desiredAccuracyRaw === "precise"
|
|
? desiredAccuracyRaw
|
|
: undefined;
|
|
const timeoutMs = parseOptionalNodePositiveInteger(
|
|
opts.locationTimeout,
|
|
"--location-timeout",
|
|
);
|
|
const invokeTimeoutMs = parseOptionalNodePositiveInteger(
|
|
opts.invokeTimeout,
|
|
"--invoke-timeout",
|
|
);
|
|
|
|
const invokeParams: Record<string, unknown> = {
|
|
nodeId,
|
|
command: "location.get",
|
|
params: {
|
|
maxAgeMs: Number.isFinite(maxAgeMs) ? maxAgeMs : undefined,
|
|
desiredAccuracy,
|
|
timeoutMs: Number.isFinite(timeoutMs) ? timeoutMs : undefined,
|
|
},
|
|
idempotencyKey: randomIdempotencyKey(),
|
|
};
|
|
if (typeof invokeTimeoutMs === "number" && Number.isFinite(invokeTimeoutMs)) {
|
|
invokeParams.timeoutMs = invokeTimeoutMs;
|
|
}
|
|
|
|
const raw = await callGatewayCli("node.invoke", opts, invokeParams);
|
|
const res = typeof raw === "object" && raw !== null ? (raw as { payload?: unknown }) : {};
|
|
const payload =
|
|
res.payload && typeof res.payload === "object"
|
|
? (res.payload as Record<string, unknown>)
|
|
: {};
|
|
|
|
if (opts.json) {
|
|
defaultRuntime.writeJson(payload);
|
|
return;
|
|
}
|
|
|
|
const lat = payload.lat;
|
|
const lon = payload.lon;
|
|
const acc = payload.accuracyMeters;
|
|
if (typeof lat === "number" && typeof lon === "number") {
|
|
const accText = typeof acc === "number" ? ` ±${acc.toFixed(1)}m` : "";
|
|
defaultRuntime.log(`${lat},${lon}${accText}`);
|
|
return;
|
|
}
|
|
defaultRuntime.writeJson(payload, 0);
|
|
});
|
|
}),
|
|
{ timeoutMs: 30_000 },
|
|
);
|
|
}
|