variants/linux: meshcorectl, a dependency-free client for the console - #11
Open
mmmorks wants to merge 1 commit into
Open
variants/linux: meshcorectl, a dependency-free client for the console#11mmmorks wants to merge 1 commit into
meshcorectl, a dependency-free client for the console#11mmmorks wants to merge 1 commit into
Conversation
meshcore-cli's repeater mode covers interactive use of the console well. What it does not cover is scripting: its one-shot form exits 0 whatever the daemon answered, waits a fixed 0.3 s and reads once, and has no way to take commands from stdin -- so a deploy script cannot tell "set freq" from "ERR: bad value" or from a daemon that never read the line. It is also a pipx install that pulls in the BLE stack, on a host that may be a Pi Zero with nothing but python3. meshcorectl is one file on the Python standard library: a readline REPL with history and Tab completion of the real command set (the tables are checked against the dispatch literals in CommonCLI.cpp and MyMesh.cpp), a one-shot form, and a piped form, exiting 0 only if every command was actually run by the daemon. The echo is the proof: the daemon echoes a command byte by byte as it consumes it and only then replies, so text that starts with the echo is a reply and anything else is the reason nothing ran. That makes `reboot` count as run, and a later command in the same script, finding the console hung up, fail with a message that says why. It resolves the console the same way the daemon publishes it (/run/meshcored/console, then $XDG_RUNTIME_DIR/meshcore/console, then /tmp/meshcore-<uid>/console); -s PATH or MESHCORED_CONSOLE overrides. Exercised against a stand-in console (a Python PTY driven like the firmware loop) on macOS and Linux: one-shot, piped, --help, a missing path, a non-console path, a command with no reply text, and a piped script that continues past reboot. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01EXSCjgNEbJfHwLjD2WSHW4
mmmorks
force-pushed
the
pr/05-pty-console
branch
from
September 8, 2026 04:11
bb016db to
b6620be
Compare
mmmorks
force-pushed
the
pr/05b-meshcorectl
branch
from
September 8, 2026 04:11
253377b to
afb34ec
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
A client for the PTY console, for the cases
meshcore-cli -rdoes not cover. Its repeater mode is fine interactively, but in one-shot form it exits0whatever the daemon answered, waits a fixed 0.3 s and reads once, and cannot take commands from stdin, so a deploy script cannot tellset freq 868fromERR: bad valueor from a daemon that never read the line. It is also apipxinstall that pulls in the BLE stack, on a host that may be a Pi Zero with nothing butpython3.meshcorectlis one file on the standard library:~/.meshcorectl_history, and Tab completion of the real command set (tables checked against the dispatch literals inCommonCLI.cppandMyMesh.cpp;getandsethave separate key pools).meshcorectl set name foo) and piped (printf 'ver\nneighbors\n' | meshcorectl) forms.0only if every command was actually run by the daemon. The echo is the proof: the daemon echoes a command byte by byte as it consumes it and only then replies, sorebootcounts as run, and a later command in the same script that finds the console hung up fails with a message saying why./run/meshcored/console, then$XDG_RUNTIME_DIR/meshcore/console, then/tmp/meshcore-<uid>/console);-s PATHorMESHCORED_CONSOLEoverrides.Its docstring records the firmware behaviours it cannot fix (
clock syncneeds a sender timestamp the console passes as 0;region loadis multi-line).What changed
variants/linux/meshcorectl: the client.meshcoredin §1; §5 shows it next tomeshcore-cli;## The control CLIgains the three ways to drive it and the exit-code contract.How it was tested
Exercised against a stand-in console (a Python PTY driven like the firmware loop) on macOS and in the arm64 container: one-shot, piped,
--help, a missing path, a non-console path, a command with no reply text, and a piped script that continues pastreboot(exit 1 with the reason). Not yet run against a real node.Dependencies
Stacked on the PTY console hardening PR (
pr/05-pty-console). Review the last commit only. Optional: the console works withmeshcore-cliwithout this.Shared code touched
None.