mxaccesscli: route write through Advise vs AdviseSupervisory by user

WriteCommand now picks the LMXProxyServer advise variant based on
whether credentials were supplied:

  --username given  -> Advise            (operator action; the write
                                          is attributed to the
                                          authenticated Galaxy user
                                          in the alarm/event audit
                                          trail)
  no --username     -> AdviseSupervisory (supervisory action; the
                                          write is attributed to the
                                          hosting client itself, no
                                          Galaxy user claimed)

MxItem grows AdviseSupervisory() alongside Advise() and shares the
same UnAdvise / RemoveItem teardown.

Verified live with the trigger / ack-as-dohertj2 / clear sequence on
TestMachine_001.TestAlarm002. The Set (anonymous, supervisory) and
Clear (anonymous, supervisory) rows pair with the Acknowledged row
(authenticated, Advise) under one Alarm_ID. On this development
galaxy every action still maps to User_Name=DefaultUser regardless
of advise variant — that's a galaxy-security configuration trait,
not a CLI bug. The routing is in place and will differentiate
correctly on a strict galaxy with real user records.

docs/usage.md gains an "Advise variant" section explaining the rule
and the expected User_Name population on strict vs permissive
galaxies.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
Joseph Doherty
2026-05-03 22:10:25 -04:00
parent 0d25ec445f
commit 9de8660688
3 changed files with 39 additions and 1 deletions
@@ -122,11 +122,21 @@ namespace MxAccess.Cli.Commands
// within the expected range" because the proxy doesn't yet
// know the destination type.
//
// Pick the advise variant based on whether a user was supplied:
// - --username given → Advise (operator action, attribute
// the write to the authenticated Galaxy user in the audit
// trail).
// - anonymous → AdviseSupervisory (the write is on
// behalf of the hosting client itself; the audit trail
// records it as a supervisory action without trying to
// attribute it to a specific user).
//
// Caveat: a bare-array reference (no brackets) will return
// MxCategoryCommunicationError, Detail=1003 here — same as on
// a `read` of that form. Tag the user-facing error so the
// failure mode is recognizable.
item.Advise();
if (verifyUser != null) item.Advise();
else item.AdviseSupervisory();
var resolveTimeout = TimeSpan.FromSeconds(TimeoutSeconds);
if (!session.WaitForUpdate(
u => u.Kind == MxUpdateKind.DataChange && u.ItemHandle == item.Handle,
+12
View File
@@ -32,6 +32,18 @@ namespace MxAccess.Cli.Mx
_advised = true;
}
/// Subscribe in supervisory mode. Use this for actions that should
/// be attributed to the hosting client (rather than to a Galaxy user)
/// in the alarm/event audit trail — e.g. anonymous bulk operators,
/// integration scripts, or automation acting on its own authority.
/// Pairs with the same UnAdvise / RemoveItem teardown as Advise().
public void AdviseSupervisory()
{
if (_advised) return;
_proxy.AdviseSupervisory(_hServer, Handle);
_advised = true;
}
public void UnAdvise()
{
if (!_advised) return;