Add default value to nislsc python api - #67
Conversation
--------- Signed-off-by: zoechanzy <zoe.chan@emerson.com>
* Update function_helpers.py and templates files to consume default value field from nislscapi_full.json * Refactor the order of parameters to avoid python TypeError: positional argument follows keyword argument error * Regenerate generated Python module files --------- Signed-off-by: zoechanzy <zoe.chan@emerson.com>
✅ Snyk checks have passed. No issues have been found so far.
💻 Catch issues earlier using the plugins for VS Code, JetBrains IDEs, Visual Studio, and Eclipse. |
af3371e to
6bb49f5
Compare
* Added default value of None for the library parameter * Regenerate generated Python module files --------- Signed-off-by: zoechanzy <zoe.chan@emerson.com>
6bb49f5 to
646ecac
Compare
* Refactor parameter ordering in unit tests --------- Signed-off-by: zoechanzy <zoe.chan@emerson.com>
851de41 to
fdd3ed9
Compare
There was a problem hiding this comment.
Pull request overview
This PR updates the codegen metadata and templates so generated NI-SLSC Python APIs can expose parameter default values (notably library=None, timeouts, and “default resource” sentinels), and regenerates the affected modules and tests accordingly.
Changes:
- Added
defaultfields tonislscapi_full.jsonfor various parameters (timeouts, default resources). - Updated codegen helpers/templates to emit defaults in generated Python signatures (and to reorder required vs defaulted parameters).
- Regenerated
generated/nislsc/session.pyand updated unit tests/examples to match the new call signatures.
Reviewed changes
Copilot reviewed 12 out of 13 changed files in this pull request and generated 2 comments.
Show a summary per file
| File | Description |
|---|---|
| tests/unit/test_session.py | Updates test calls to match reordered/generated Session method signatures and new keyword usage. |
| tests/unit/conftest.py | Updates the session fixture to use new initialize_session_with_devices signature/keywords. |
| src/codegen/utilities/function_helpers.py | Adds “include defaults” support, default formatting helpers, and signature reordering logic. |
| src/codegen/templates/utils.py.mako | Enables default emission for module-level generated functions. |
| src/codegen/templates/session.py.mako | Enables default emission for generated Session methods/classmethods. |
| src/codegen/templates/property.py.mako | Enables default emission for generated PropertyReference APIs. |
| src/codegen/templates/library.py.mako | Enables default emission for generated Library APIs. |
| src/codegen/templates/command.py.mako | Enables default emission for generated CommandReference APIs. |
| src/codegen/metadata/nislscapi_full.json | Adds default values in metadata (timeouts, $Default* resource sentinels). |
| generated/nislsc/session.py | Regenerated Session API with defaults and reordered parameters. |
| examples/show_command_and_property_tree.py | Updates example calls to match new Session method parameter order. |
| examples/reset_device.py | Updates example initialization call to use new keyword/default patterns. |
| examples/check_chassis_battery.py | Updates example property calls to match new parameter ordering/defaults. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| ) | ||
| physical_channel_properties = session.get_physical_channel_property_string_array( | ||
| physical_channel, PhysicalChannelProperty.PROPERTIES | ||
| PhysicalChannelProperty.PROPERTIES, physical_channel |
There was a problem hiding this comment.
@bkeryan With $DefaultPhysChans and $DefaultDevices set, we have to put the physical_channel and device_name to the back. Feels a bit weird (I am still fine with it).
Alternative is having positional arguments default to None or "", then we error out if not set. But that will probably mess the docstring and IntelliSense. Thoughts?
There was a problem hiding this comment.
I agree it seems a little weird.
The approach used by other NI driver APIs for Python is to have a collection of objects (e.g. nidaqmx channels or MI repeated capabilities) that returns proxy objects with the 1st parameter bound (e.g. device).
# session.devices["Mod1"] returns a Device object that is bound to Mod1
session.devices["Mod1"].set_property_string_array(XYZ, ["a","b","c"]) # passes Mod1 for 1st parameter
SLSC is not an IVI driver, but the new Python IVI spec also uses this approach.
The collection can expose a separate property that returns a proxy that is bound to $DeviceDevices:
# session.devices.default returns a Device object that is bound to $DefaultDevices
session.devices.default.set_property_string_array(XYZ, ["a","b","c"]) # passes $DefaultDevices for 1st parameter
That is a bigger API change, though. Working within the current API, I think it would be ok for (get|set)_device_xyz(), (get|set)_phys_chan_xyz(), (get|set)_nvmem_bytes(), etc. to not have a default for the "active context" (1st parameter that specifies which device/physchan/nvmem you are accessing).
There was a problem hiding this comment.
If we remove the default "active context" parameter, users can still write session.set_device_property_string_array("$DefaultDevices", XYZ, ["a","b","c"]).
Also, I think that defining constants for the resource aliases like DEFAULT_DEVICES_ALIAS = "$DefaultDevices" would make them more discoverable.
There was a problem hiding this comment.
(get|set)_device_xyz(), (get|set)_phys_chan_xyz(), (get|set)_nvmem_bytes(), etc. to not have a default for the "active context" (1st parameter that specifies which device/physchan/nvmem you are accessing)
I think there is a few ways to address it:
Method1:
drop devices, physChans or nvmemAreas default value of (get|set)_device_xyz(), (get|set)_phys_chan_xyz(), (get|set)_nvmem_bytes(), etc from nislscapi.json directly
Method2:
Remain devices, physChans or nvmemAreas default value of (get|set)_device_xyz(), (get|set)_phys_chan_xyz(), (get|set)_nvmem_bytes(), etc in nislscapi.json. Add addtional function in function_helpers.py to ignore the corresponding default values in the setter / getter, etc
I think method 1 is easier and straight-forward.
|
Perform the tests on actual hardware and make sure the examples still work. Also try writing a simple python script to test if the default parameter is working as intended, especially the |
* Refactor parameter ordering in examples to match new defaults * Remove library,connection_timeout and reservation_timeout parameters from examples since they have default values. --------- Signed-off-by: zoechanzy <zoe.chan@emerson.com>
…types --------- Signed-off-by: zoechanzy <zoe.chan@emerson.com>
0bf3a56 to
30845a7
Compare
|
|
||
| @classmethod | ||
| def initialize_session_with_physical_channels(cls, library: Library | None, physical_channel_names: str, connection_timeout: float, reservation_access: ReservationAccess, reservation_group: str, reservation_timeout: float) -> Self: | ||
| def initialize_session_with_physical_channels(cls, physical_channel_names: str, reservation_access: ReservationAccess, reservation_group: str, library: Library | None = None, connection_timeout: float = -1.0, reservation_timeout: float = -1.0) -> Self: |
There was a problem hiding this comment.
Thank you so much. I will update reservationAccess and reservationGroup parameters of functions like InitializeSessionWithDevices to have the default value in the nislscapi.json.
| return chassis_name | ||
|
|
||
| def reserve_devices(self, device_names: str, reservation_access: ReservationAccess, reservation_group: str, reservation_timeout: float) -> None: | ||
| def reserve_devices(self, reservation_access: ReservationAccess, reservation_group: str, device_names: str = '$DefaultDevices', reservation_timeout: float = -1.0) -> None: |
| ) | ||
| physical_channel_properties = session.get_physical_channel_property_string_array( | ||
| physical_channel, PhysicalChannelProperty.PROPERTIES | ||
| PhysicalChannelProperty.PROPERTIES, physical_channel |
There was a problem hiding this comment.
I agree it seems a little weird.
The approach used by other NI driver APIs for Python is to have a collection of objects (e.g. nidaqmx channels or MI repeated capabilities) that returns proxy objects with the 1st parameter bound (e.g. device).
# session.devices["Mod1"] returns a Device object that is bound to Mod1
session.devices["Mod1"].set_property_string_array(XYZ, ["a","b","c"]) # passes Mod1 for 1st parameter
SLSC is not an IVI driver, but the new Python IVI spec also uses this approach.
The collection can expose a separate property that returns a proxy that is bound to $DeviceDevices:
# session.devices.default returns a Device object that is bound to $DefaultDevices
session.devices.default.set_property_string_array(XYZ, ["a","b","c"]) # passes $DefaultDevices for 1st parameter
That is a bigger API change, though. Working within the current API, I think it would be ok for (get|set)_device_xyz(), (get|set)_phys_chan_xyz(), (get|set)_nvmem_bytes(), etc. to not have a default for the "active context" (1st parameter that specifies which device/physchan/nvmem you are accessing).
| connection_timeout=-1.0, | ||
| reservation_timeout=-1.0, |
There was a problem hiding this comment.
Omit the timeouts when they are the same as the default.
| ReservationAccess.NONE, | ||
| "", | ||
| library=library, | ||
| connection_timeout=-1.0, |
There was a problem hiding this comment.
Omit the timeouts when they are the same as the default.
| "Area1", | ||
| ReservationAccess.NONE, | ||
| "", | ||
| library=None, |
There was a problem hiding this comment.
Omit library=None when it is the same as the default.
* Add * in get_function_parameter_list to make the Booleans keyword-only * Remove argument from get_function_parameter_list if the argument have default value. * Use named parameters for get_function_parameter_list to avoid ambiguity
* Add CONNECTED_DEVICES_ALIAS constant * Add RESERVED_DEVICES_ALIAS constant * Add DEFAULT_NVMEM_AREAS_ALIAS constant * Add DEFAULT_PHYS_CHANS_ALIAS constant * Add RESERVED_DEVICES_ALIAS constant * Add SESSION_ALIAS constant * Add SYSTEM_ALIAS constant --------- Signed-off-by: zoechanzy <zoe.chan@emerson.com>


What does this Pull Request accomplish?
Why should this Pull Request be merged?
nislscapi.json is updated to have default values. Function helper and template files should be updated so that the default value can be used in code-gen.
What testing has been done?
Passed unit tests
Related work item:
USER STORY 3221873