Skip to content

feat: add enum management group#55

Closed
sgfeniex wants to merge 3 commits intointercreate:mainfrom
sgfeniex:feature/enum-management
Closed

feat: add enum management group#55
sgfeniex wants to merge 3 commits intointercreate:mainfrom
sgfeniex:feature/enum-management

Conversation

@sgfeniex
Copy link
Contributor

@sgfeniex sgfeniex commented Aug 8, 2025

Requires intercreate/smpclient#71

adds

# CONFIG_MCUMGR_ENUM=n
❯ smpmgr --port /dev/ttyACM0 enum get-supported-groups
⠙ Connecting to /dev/ttyACM0... OK
⠋ Waiting for supported groups... OK
EnumManagementErrorV1(
    header=Header(op=<OP.READ_RSP: 1>, version=<Version.V2: 1>, flags=<Flag.UNUSED: 0>, length=6, group_id=10, sequence=1, command_id=1),
    version=<Version.V2: 1>,
    sequence=1,
    smp_data=b'\t\x00\x00\x06\x00\n\x01\x01\xbfbrc\x08\xff',
    rc=<MGMT_ERR.ENOTSUP: 8>,
    rsn=None
)

# CONFIG_MCUMGR_ENUM*=y
❯ smpmgr --port /dev/ttyACM0 enum get-supported-groups
⠙ Connecting to /dev/ttyACM0... OK
⠋ Waiting for supported groups... OK
(<GroupId.ENUM_MANAGEMENT: 10>, 100, <GroupId.FILE_MANAGEMENT: 8>, <GroupId.IMAGE_MANAGEMENT: 1>, <GroupId.OS_MANAGEMENT: 0>, <GroupId.STATISTICS_MANAGEMENT: 2>)
❯ smpmgr --port /dev/ttyACM0 enum get-group-details 8 100 44 80 10 66
⠋ Connecting to /dev/ttyACM0... OK
⠋ Waiting for group details... OK
(
    GroupDetails(group=<GroupId.ENUM_MANAGEMENT: 10>, name='enum mgmt', handlers=4),
    GroupDetails(group=100, name='', handlers=40),
    GroupDetails(group=<GroupId.FILE_MANAGEMENT: 8>, name='fs mgmt', handlers=5)
)

❯ smpmgr --port /dev/ttyACM0 enum get-group-details 
Usage: smpmgr enum get-group-details [OPTIONS] GROUPS...
Try 'smpmgr enum get-group-details --help' for help.
╭─ Error ──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╮
│ Missing argument 'GROUPS...'.                                                                                                                                                                        │
╰──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯

@sgfeniex sgfeniex force-pushed the feature/enum-management branch 6 times, most recently from a6e4425 to 143e44e Compare August 8, 2025 14:19
@sgfeniex sgfeniex force-pushed the feature/enum-management branch from 143e44e to bfdf168 Compare August 8, 2025 14:23
@JPHutchins
Copy link
Collaborator

JPHutchins commented Aug 11, 2025

Thanks for taking this on, it's going to be very useful!

I have one suggestion. Since smpmgr is a tool for developers, most of the commands (rich)print the response itself. The idea is that a developer may be using smpmgr to test their own user facing application. So, for consistency, the enum handlers should simply (rich)print the response itself.

Then, in the next PR we can add a top level "list" command that, like "upgrade", abstracts a series of commands for the user's convenience. "List" would provide a list of the enabled command groups, and commands, if possible. In the interactive session, it could even remove the commands that are not enabled.

LMK your thoughts!

@sgfeniex
Copy link
Contributor Author

thoughts: agree

So I'm clear, are you suggesting removing the if error() ... elif success() conditionals as opposed to rich.print?

I tried to follow an example from one of the other group handlers.

@JPHutchins
Copy link
Collaborator

thoughts: agree

So I'm clear, are you suggesting removing the if error() ... elif success() conditionals as opposed to rich.print?

I tried to follow an example from one of the other group handlers.

Wow, this makes me realize that we've implemented blessed-few of the commands. We've sorta done the hard ones that require abstraction. These are a good example of what I think it most useful to a dev because it's unambiguous:

@app.command()
def echo(ctx: typer.Context, message: str) -> None:
"""Request that the SMP Server echo the given message."""
options = cast(Options, ctx.obj)
smpclient = get_smpclient(options)
async def f() -> None:
await connect_with_spinner(smpclient, options.timeout)
r = await smp_request(smpclient, options, EchoWrite(d=message)) # type: ignore
print(r)
asyncio.run(f())
@app.command()
def reset(ctx: typer.Context) -> None:
"""Request that the SMP Server reset the device."""
options = cast(Options, ctx.obj)
smpclient = get_smpclient(options)
async def f() -> None:
await connect_with_spinner(smpclient, options.timeout)
r = await smp_request(smpclient, options, ResetWrite()) # type: ignore
print(r)
asyncio.run(f())

So yeah, it can even remove the response type checking. E.g., an "error" response is not an smpmgr CLI error, it's a "successful error" response 🤣.

@sgfeniex
Copy link
Contributor Author

Wow, this makes me realize that we've implemented blessed-few of the commands

the next PR we can add a top level "list" command

This will increase utility a bunch. I view smpmgr as a utility tool, both high and low level.

AI was trying to get me to write (docs) looking like ... --group 66 --cmd 3 --raw '{"some": "json"}'. It is easy enough for me to use the plugin system.

This PR has been updated addressing comments.

In the interactive session

Haven't tried that yet. I'm open to implementing the next PR with higher-level functionality.

@JPHutchins
Copy link
Collaborator

Wow, this makes me realize that we've implemented blessed-few of the commands

the next PR we can add a top level "list" command

This will increase utility a bunch. I view smpmgr as a utility tool, both high and low level.

AI was trying to get me to write (docs) looking like ... --group 66 --cmd 3 --raw '{"some": "json"}'. It is easy enough for me to use the plugin system.

This PR has been updated addressing comments.

In the interactive session

Haven't tried that yet. I'm open to implementing the next PR with higher-level functionality.

This is looking great! Let's bump smpclient in the pyproject.toml to require ^5.1.0, which includes the enum support that you added.

@JPHutchins
Copy link
Collaborator

Moved to #67

@JPHutchins JPHutchins closed this Oct 12, 2025
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants