Commit Graph
6 Commits
Author SHA1 Message Date
cristhian a95d804f0b fix jogging stepping by holding one velocity instead of re-arming
validate / validate (pull_request) Successful in 58m41s
validate / test (pull_request) Successful in 58m50s
validate / markdownlint (pull_request) Successful in 58m39s
`set_cartesian_velocity` passed `duration=velocity_command_ttl_s` on every
message, so each one re-armed a timed segment and the controller re-planned
the same motion. On a real Lite6 that is not smooth travel: the arm moves in
steps. Reducing how often the velocity is sent does not help — re-arming four
times a second still steps — so it now uses `duration=0`, the SDK's "always
effective, will not stop automatically", and skips a velocity that has not
changed. One command stands until a different one replaces it.

That removes the controller-side expiry, which `_expire_jog` was relying on:
it flipped `_jogging` and reported `ready` without commanding anything,
because the controller's own timer had already stopped the arm. With the
velocity held indefinitely that would leave an arm travelling while the node
reported idle, so `_expire_jog` now queues the stop itself. It goes through
the job queue rather than the driver, since it runs on the reporter thread
and the control thread owns the driver.

`VELOCITY_COMMAND_TTL_S` is unchanged in value and meaning to a caller, but
it is now enforced here rather than by the controller.

Both halves are one commit on purpose: `duration=0` without the stop in
`_expire_jog` is an arm that never stops when its sender dies.

Adds tests/test_driver.py — the driver had no direct coverage, because
FakeArm replaces it everywhere else, which is why this was invisible to the
suite.
2026-09-16 14:27:46 -03:00
cristhianandClaude Opus 5 8cd4db93f1 docs: update the test count
validate / markdownlint (pull_request) Successful in 58m43s
validate / validate (pull_request) Successful in 58m48s
validate / test (pull_request) Successful in 58m55s
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-09-15 12:32:43 -05:00
cristhianandClaude Opus 5 4427da9c34 fix requests queued while the arm is down never being answered
_run_control never drained the job queue while the arm had not been reached, so
every request that arrived during an outage waited for a connection that might
never come. That breaks the one-response-per-request rule the node states as
absolute, and it was circular: requests are queued before the arm is reached
because recover is what a caller sends then, yet recover is served by the
control thread and so was the one service that could never run while down.

Serve the queue during the wait between connection attempts. Non-motion services
are tried on the arm, which is what lets recover and clear reach a controller
that answers while refusing to serve. A motion is refused rather than held: the
arm is somewhere unknown and nobody is watching, so a held motion would fire
unattended the moment the link came back.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-09-15 12:32:31 -05:00
cristhian 412aeac955 docs: rewrite README and AGENTS for the service node
validate / validate (pull_request) Successful in 58m45s
validate / test (pull_request) Successful in 58m51s
validate / markdownlint (pull_request) Successful in 58m44s
Documents the eleven services, the wait flag, motion_state and
preemption, and the lifecycle guarantees around restart and shutdown.

AGENTS.md records the two rules that are easy to break by accident: the
stopping event must stay set-to-stop, because an event that is set while
running makes every wait() return at once and turns each cadence into a
busy loop; and every request gets exactly one response, since a caller
has no other way to know its request finished.
2026-09-12 11:47:06 -03:00
cristhian aguileraandClaude Sonnet 4.6 a5f05ddc6f fix AGENTS.md line-length lint errors
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-04-09 08:52:13 -04:00
cristhian aguilera 8e3d976a17 add dora_ulite6 standalone node with command lifecycle status
Migrates the ulite6 Python dora node from dora_littlehand into a
self-contained repository following the dora-zed structure. Adds
command lifecycle state ("started"/"done"/"failed") and type
("command"/"error") to the status output so coordinator nodes can
reliably sequence robot actions without polling.
2026-04-01 08:51:19 -03:00