diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index d1e5e38e..2f7ea86d 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -21,8 +21,8 @@ See [GitHub's official documentation](https://help.github.com/articles/using-pul # Getting Started -This is the command to generate the files in /src/ni/pythonpanel/v1/: -`poetry run python -m grpc_tools.protoc --proto_path=protos --python_out=src/ --grpc_python_out=src/ --mypy_out=src/ --mypy_grpc_out=src/ ni/pythonpanel/v1/python_panel_service.proto` +This is the command to generate the files in /src/ni/panels/v1/: +`poetry run python -m grpc_tools.protoc --proto_path=protos --python_out=src/ --grpc_python_out=src/ --mypy_out=src/ --mypy_grpc_out=src/ ni/panels/v1/panel_service.proto ni/panels/v1/panel_types.proto ni/panels/v1/streamlit_panel_configuration.proto` # Testing diff --git a/examples/all_types/all_types.py b/examples/all_types/all_types.py index 8162b6e6..3a73c743 100644 --- a/examples/all_types/all_types.py +++ b/examples/all_types/all_types.py @@ -7,7 +7,7 @@ import nipanel panel_script_path = Path(__file__).with_name("all_types_panel.py") -panel = nipanel.create_panel(panel_script_path) +panel = nipanel.create_streamlit_panel(panel_script_path) print("Setting values") for name, value in all_types_with_values.items(): diff --git a/examples/all_types/all_types_panel.py b/examples/all_types/all_types_panel.py index b2e046b3..529d39b2 100644 --- a/examples/all_types/all_types_panel.py +++ b/examples/all_types/all_types_panel.py @@ -12,7 +12,7 @@ st.set_page_config(page_title="All Types Example", page_icon="📊", layout="wide") st.title("All Types Example") -panel = nipanel.get_panel_accessor() +panel = nipanel.get_streamlit_panel_accessor() for name in all_types_with_values.keys(): st.markdown("---") diff --git a/examples/hello/hello.py b/examples/hello/hello.py index ad2d97a6..9c2bcea2 100644 --- a/examples/hello/hello.py +++ b/examples/hello/hello.py @@ -5,7 +5,7 @@ import nipanel panel_script_path = Path(__file__).with_name("hello_panel.py") -panel = nipanel.create_panel(panel_script_path) +panel = nipanel.create_streamlit_panel(panel_script_path) panel.set_value("hello_string", "Hello, World!") diff --git a/examples/hello/hello_panel.py b/examples/hello/hello_panel.py index 4242e2ad..9f96538a 100644 --- a/examples/hello/hello_panel.py +++ b/examples/hello/hello_panel.py @@ -8,5 +8,5 @@ st.set_page_config(page_title="Hello World Example", page_icon="📊", layout="wide") st.title("Hello World Example") -panel = nipanel.get_panel_accessor() +panel = nipanel.get_streamlit_panel_accessor() st.write(panel.get_value("hello_string", "")) diff --git a/examples/nidaqmx/nidaqmx_continuous_analog_input.py b/examples/nidaqmx/nidaqmx_continuous_analog_input.py index bed43eb7..f8210a8a 100644 --- a/examples/nidaqmx/nidaqmx_continuous_analog_input.py +++ b/examples/nidaqmx/nidaqmx_continuous_analog_input.py @@ -17,7 +17,7 @@ import nipanel panel_script_path = Path(__file__).with_name("nidaqmx_continuous_analog_input_panel.py") -panel = nipanel.create_panel(panel_script_path) +panel = nipanel.create_streamlit_panel(panel_script_path) try: print(f"Panel URL: {panel.panel_url}") diff --git a/examples/nidaqmx/nidaqmx_continuous_analog_input_panel.py b/examples/nidaqmx/nidaqmx_continuous_analog_input_panel.py index 59e108e3..89a22316 100644 --- a/examples/nidaqmx/nidaqmx_continuous_analog_input_panel.py +++ b/examples/nidaqmx/nidaqmx_continuous_analog_input_panel.py @@ -34,7 +34,7 @@ unsafe_allow_html=True, ) -panel = nipanel.get_panel_accessor() +panel = nipanel.get_streamlit_panel_accessor() is_running = panel.get_value("is_running", False) if is_running: diff --git a/examples/niscope/niscope_ex_fetch_forever.py b/examples/niscope/niscope_ex_fetch_forever.py index 68d73161..78b43a45 100644 --- a/examples/niscope/niscope_ex_fetch_forever.py +++ b/examples/niscope/niscope_ex_fetch_forever.py @@ -11,7 +11,7 @@ import nipanel panel_script_path = Path(__file__).with_name("niscope_ex_fetch_forever_panel.py") -panel = nipanel.create_panel(panel_script_path) +panel = nipanel.create_streamlit_panel(panel_script_path) print(f"Panel URL: {panel.panel_url}") diff --git a/examples/niscope/niscope_ex_fetch_forever_panel.py b/examples/niscope/niscope_ex_fetch_forever_panel.py index 3c2d1b0e..a2355fed 100644 --- a/examples/niscope/niscope_ex_fetch_forever_panel.py +++ b/examples/niscope/niscope_ex_fetch_forever_panel.py @@ -8,7 +8,7 @@ st.set_page_config(page_title="NI-SCOPE Example", page_icon="📈", layout="wide") st.title("NIScope EX Fetch Forever") -panel = nipanel.get_panel_accessor() +panel = nipanel.get_streamlit_panel_accessor() waveform = panel.get_value("Waveform", [0]) diff --git a/examples/performance_checker/performance_checker.py b/examples/performance_checker/performance_checker.py index 3bbc8851..26f3067a 100644 --- a/examples/performance_checker/performance_checker.py +++ b/examples/performance_checker/performance_checker.py @@ -11,7 +11,7 @@ panel_script_path = Path(__file__).with_name("performance_checker_panel.py") -panel = nipanel.create_panel(panel_script_path) +panel = nipanel.create_streamlit_panel(panel_script_path) amplitude = 1.0 frequency = 1.0 diff --git a/examples/performance_checker/performance_checker_panel.py b/examples/performance_checker/performance_checker_panel.py index e29f58c4..23e56ea3 100644 --- a/examples/performance_checker/performance_checker_panel.py +++ b/examples/performance_checker/performance_checker_panel.py @@ -13,7 +13,7 @@ def profile_get_value( - panel: "nipanel.StreamlitPanelValueAccessor", + panel: "nipanel.PanelValueAccessor", value_id: str, default_value: Any = None, num_runs: int = 5, @@ -69,7 +69,7 @@ def profile_get_value( max_refresh_time = max(refresh_history) if refresh_history else 0 avg_refresh_time = statistics.mean(refresh_history) if refresh_history else 0 -panel = nipanel.get_panel_accessor() +panel = nipanel.get_streamlit_panel_accessor() num_timing_runs = 5 time_points, time_points_ms = profile_get_value(panel, "time_points", [0.0], num_timing_runs) diff --git a/examples/simple_graph/simple_graph.py b/examples/simple_graph/simple_graph.py index 4b63530f..bebdf32e 100644 --- a/examples/simple_graph/simple_graph.py +++ b/examples/simple_graph/simple_graph.py @@ -10,7 +10,7 @@ panel_script_path = Path(__file__).with_name("simple_graph_panel.py") -panel = nipanel.create_panel(panel_script_path) +panel = nipanel.create_streamlit_panel(panel_script_path) amplitude = 1.0 frequency = 1.0 diff --git a/examples/simple_graph/simple_graph_panel.py b/examples/simple_graph/simple_graph_panel.py index 6550627a..f3200c90 100644 --- a/examples/simple_graph/simple_graph_panel.py +++ b/examples/simple_graph/simple_graph_panel.py @@ -9,7 +9,7 @@ st.set_page_config(page_title="Simple Graph Example", page_icon="📈", layout="wide") st.title("Simple Graph Example") -panel = nipanel.get_panel_accessor() +panel = nipanel.get_streamlit_panel_accessor() time_points = panel.get_value("time_points", [0.0]) sine_values = panel.get_value("sine_values", [0.0]) amplitude = panel.get_value("amplitude", 1.0) diff --git a/protos/ni/pythonpanel/v1/python_panel_service.proto b/protos/ni/panels/v1/panel_service.proto similarity index 77% rename from protos/ni/pythonpanel/v1/python_panel_service.proto rename to protos/ni/panels/v1/panel_service.proto index ab833acc..a96acc0d 100644 --- a/protos/ni/pythonpanel/v1/python_panel_service.proto +++ b/protos/ni/panels/v1/panel_service.proto @@ -1,29 +1,28 @@ syntax = "proto3"; -package ni.pythonpanel.v1; +package ni.panels.v1; import "google/protobuf/any.proto"; option cc_enable_arenas = true; -option csharp_namespace = "NationalInstruments.PythonPanel.V1"; -option go_package = "pythonpanelv1"; +option csharp_namespace = "NationalInstruments.Panels.V1"; +option go_package = "panelsv1"; option java_multiple_files = true; -option java_outer_classname = "PythonPanelServiceProto"; -option java_package = "com.ni.pythonpanel.v1"; -option objc_class_prefix = "NIPP"; -option php_namespace = "NI\\PythonPanel\\V1"; -option ruby_package = "NI::PythonPanel::V1"; - -// Service interface for interacting with python panels -service PythonPanelService { - // Start a panel (or connect to if it has already been started) +option java_outer_classname = "PanelsProto"; +option java_package = "com.ni.panels.v1"; +option objc_class_prefix = "NIPS"; +option php_namespace = "NI\\Panels\\V1"; +option ruby_package = "NI::Panels::V1"; + +// Service interface for interacting with NI panels +service PanelService { + // Start a panel using the provided configuration (or connect to if it has already been started) // Status Codes for errors: // - INVALID_ARGUMENT: - // - The panel script filename doesn't end in .py. // - The panel identifier contains invalid characters. Only alphanumeric characters and underscores are allowed. + // - The panel configuration has an invalid argument. // - NOT_FOUND: - // - The panel script file was not found. - // - The python executable file was not found. + // - The panel configuration includes a file that was not found. rpc StartPanel(StartPanelRequest) returns (StartPanelResponse); // Stop a panel @@ -64,16 +63,13 @@ message StartPanelRequest { // Unique ID of the panel string panel_id = 1; - // Absolute path of the panel script's file on disk, or network path to the file - string panel_script_path = 2; - - // Path to the python interpreter to use for the panel script. - string python_path = 3; + // Configuration for the panel, packed as Any + google.protobuf.Any panel_configuration = 2; } message StartPanelResponse { - // Location of the panel's webpage - string panel_url = 1; + // Location of the panel + string panel_uri = 1; } message StopPanelRequest { @@ -94,8 +90,8 @@ message PanelInformation { // Unique ID of the panel string panel_id = 1; - // Location of the panel's webpage - string panel_url = 2; + // Location of the panel + string panel_uri = 2; // IDs of all of the values associated with the panel repeated string value_ids = 3; @@ -128,7 +124,7 @@ message TryGetValueRequest { } message TryGetValueResponse { - // The value, if it was found + // The value, if it was found optional google.protobuf.Any value = 1; } diff --git a/protos/ni/pythonpanel/v1/python_panel_types.proto b/protos/ni/panels/v1/panel_types.proto similarity index 51% rename from protos/ni/pythonpanel/v1/python_panel_types.proto rename to protos/ni/panels/v1/panel_types.proto index 8306bbfc..09995fe5 100644 --- a/protos/ni/pythonpanel/v1/python_panel_types.proto +++ b/protos/ni/panels/v1/panel_types.proto @@ -1,16 +1,16 @@ syntax = "proto3"; -package ni.pythonpanel.v1; +package ni.panels.v1; option cc_enable_arenas = true; -option csharp_namespace = "NationalInstruments.PythonPanel.V1"; -option go_package = "pythonpanelv1"; +option csharp_namespace = "NationalInstruments.Panels.V1"; +option go_package = "panelsv1"; option java_multiple_files = true; -option java_outer_classname = "PythonPanelServiceProto"; -option java_package = "com.ni.pythonpanel.v1"; -option objc_class_prefix = "NIPP"; -option php_namespace = "NI\\PythonPanel\\V1"; -option ruby_package = "NI::PythonPanel::V1"; +option java_outer_classname = "PanelsProto"; +option java_package = "com.ni.panels.v1"; +option objc_class_prefix = "NIPS"; +option php_namespace = "NI\\Panels\\V1"; +option ruby_package = "NI::Panels::V1"; message BoolCollection { repeated bool values = 1; diff --git a/protos/ni/panels/v1/streamlit_panel_configuration.proto b/protos/ni/panels/v1/streamlit_panel_configuration.proto new file mode 100644 index 00000000..82e3abfb --- /dev/null +++ b/protos/ni/panels/v1/streamlit_panel_configuration.proto @@ -0,0 +1,23 @@ +syntax = "proto3"; + +package ni.panels.v1; + +option cc_enable_arenas = true; +option csharp_namespace = "NationalInstruments.Panels.V1"; +option go_package = "panelsv1"; +option java_multiple_files = true; +option java_outer_classname = "StreamlitPanelConfigurationProto"; +option java_package = "com.ni.panels.v1"; +option objc_class_prefix = "NIPS"; +option php_namespace = "NI\\Panels\\V1"; +option ruby_package = "NI::Panels::V1"; + +// Pack this into PanelService.StartPanelRequest.panel_configuration to start a Streamlit panel. +message StreamlitPanelConfiguration +{ + // Absolute path of the streamlit script file on disk, or network path to the file. This must end in ".py". + string panel_script_path = 1; + + // Path to the python interpreter to use for running the streamlit script. + string python_path = 2; +} \ No newline at end of file diff --git a/pyproject.toml b/pyproject.toml index 751929e8..199b079b 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -72,10 +72,10 @@ requires = ["poetry-core>=1.8.0"] build-backend = "poetry.core.masonry.api" [tool.ni-python-styleguide] -extend_exclude = ".tox,docs,src/ni/pythonpanel/v1,src/ni/protobuf/types/" +extend_exclude = ".tox,docs,src/ni/panels/v1,src/ni/protobuf/types/" [tool.black] -extend-exclude = '\.tox/|docs/|src/ni/pythonpanel/v1/|src/ni/protobuf/types/' +extend-exclude = '\.tox/|docs/|src/ni/panels/v1/|src/ni/protobuf/types/' line-length = 100 [tool.mypy] @@ -105,4 +105,4 @@ testpaths = ["src/nipanel", "tests"] [tool.pyright] include = ["examples/", "src/", "tests/"] -exclude = ["src/ni/protobuf/types/", "src/ni/pythonpanel/v1/","examples/nidaqmx/nidaqmx_continuous_analog_input.py","examples/niscope/niscope_ex_fetch_forever.py"] \ No newline at end of file +exclude = ["src/ni/protobuf/types/", "src/ni/panels/v1/","examples/nidaqmx/nidaqmx_continuous_analog_input.py","examples/niscope/niscope_ex_fetch_forever.py"] \ No newline at end of file diff --git a/src/ni/panels/__init__.py b/src/ni/panels/__init__.py new file mode 100644 index 00000000..c744f82e --- /dev/null +++ b/src/ni/panels/__init__.py @@ -0,0 +1 @@ +"""gRPC stubs for NI Panels.""" diff --git a/src/ni/panels/v1/__init__.py b/src/ni/panels/v1/__init__.py new file mode 100644 index 00000000..6519cfc2 --- /dev/null +++ b/src/ni/panels/v1/__init__.py @@ -0,0 +1 @@ +"""gRPC client for NI Panels.""" diff --git a/src/ni/panels/v1/panel_service_pb2.py b/src/ni/panels/v1/panel_service_pb2.py new file mode 100644 index 00000000..fe0a80c8 --- /dev/null +++ b/src/ni/panels/v1/panel_service_pb2.py @@ -0,0 +1,53 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: ni/panels/v1/panel_service.proto +"""Generated protocol buffer code.""" +from google.protobuf.internal import builder as _builder +from google.protobuf import descriptor as _descriptor +from google.protobuf import descriptor_pool as _descriptor_pool +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + + +from google.protobuf import any_pb2 as google_dot_protobuf_dot_any__pb2 + + +DESCRIPTOR = _descriptor_pool.Default().AddSerializedFile(b'\n ni/panels/v1/panel_service.proto\x12\x0cni.panels.v1\x1a\x19google/protobuf/any.proto\"X\n\x11StartPanelRequest\x12\x10\n\x08panel_id\x18\x01 \x01(\t\x12\x31\n\x13panel_configuration\x18\x02 \x01(\x0b\x32\x14.google.protobuf.Any\"\'\n\x12StartPanelResponse\x12\x11\n\tpanel_uri\x18\x01 \x01(\t\"3\n\x10StopPanelRequest\x12\x10\n\x08panel_id\x18\x01 \x01(\t\x12\r\n\x05reset\x18\x02 \x01(\x08\"\x13\n\x11StopPanelResponse\"\x18\n\x16\x45numeratePanelsRequest\"J\n\x10PanelInformation\x12\x10\n\x08panel_id\x18\x01 \x01(\t\x12\x11\n\tpanel_uri\x18\x02 \x01(\t\x12\x11\n\tvalue_ids\x18\x03 \x03(\t\"I\n\x17\x45numeratePanelsResponse\x12.\n\x06panels\x18\x01 \x03(\x0b\x32\x1e.ni.panels.v1.PanelInformation\"5\n\x0fGetValueRequest\x12\x10\n\x08panel_id\x18\x01 \x01(\t\x12\x10\n\x08value_id\x18\x02 \x01(\t\"7\n\x10GetValueResponse\x12#\n\x05value\x18\x01 \x01(\x0b\x32\x14.google.protobuf.Any\"8\n\x12TryGetValueRequest\x12\x10\n\x08panel_id\x18\x01 \x01(\t\x12\x10\n\x08value_id\x18\x02 \x01(\t\"I\n\x13TryGetValueResponse\x12(\n\x05value\x18\x01 \x01(\x0b\x32\x14.google.protobuf.AnyH\x00\x88\x01\x01\x42\x08\n\x06_value\"j\n\x0fSetValueRequest\x12\x10\n\x08panel_id\x18\x01 \x01(\t\x12\x10\n\x08value_id\x18\x02 \x01(\t\x12#\n\x05value\x18\x03 \x01(\x0b\x32\x14.google.protobuf.Any\x12\x0e\n\x06notify\x18\x04 \x01(\x08\"\x12\n\x10SetValueResponse2\xf7\x03\n\x0cPanelService\x12O\n\nStartPanel\x12\x1f.ni.panels.v1.StartPanelRequest\x1a .ni.panels.v1.StartPanelResponse\x12L\n\tStopPanel\x12\x1e.ni.panels.v1.StopPanelRequest\x1a\x1f.ni.panels.v1.StopPanelResponse\x12^\n\x0f\x45numeratePanels\x12$.ni.panels.v1.EnumeratePanelsRequest\x1a%.ni.panels.v1.EnumeratePanelsResponse\x12I\n\x08GetValue\x12\x1d.ni.panels.v1.GetValueRequest\x1a\x1e.ni.panels.v1.GetValueResponse\x12R\n\x0bTryGetValue\x12 .ni.panels.v1.TryGetValueRequest\x1a!.ni.panels.v1.TryGetValueResponse\x12I\n\x08SetValue\x12\x1d.ni.panels.v1.SetValueRequest\x1a\x1e.ni.panels.v1.SetValueResponseBu\n\x10\x63om.ni.panels.v1B\x0bPanelsProtoP\x01Z\x08panelsv1\xf8\x01\x01\xa2\x02\x04NIPS\xaa\x02\x1dNationalInstruments.Panels.V1\xca\x02\x0cNI\\Panels\\V1\xea\x02\x0eNI::Panels::V1b\x06proto3') + +_builder.BuildMessageAndEnumDescriptors(DESCRIPTOR, globals()) +_builder.BuildTopDescriptorsAndMessages(DESCRIPTOR, 'ni.panels.v1.panel_service_pb2', globals()) +if _descriptor._USE_C_DESCRIPTORS == False: + + DESCRIPTOR._options = None + DESCRIPTOR._serialized_options = b'\n\020com.ni.panels.v1B\013PanelsProtoP\001Z\010panelsv1\370\001\001\242\002\004NIPS\252\002\035NationalInstruments.Panels.V1\312\002\014NI\\Panels\\V1\352\002\016NI::Panels::V1' + _STARTPANELREQUEST._serialized_start=77 + _STARTPANELREQUEST._serialized_end=165 + _STARTPANELRESPONSE._serialized_start=167 + _STARTPANELRESPONSE._serialized_end=206 + _STOPPANELREQUEST._serialized_start=208 + _STOPPANELREQUEST._serialized_end=259 + _STOPPANELRESPONSE._serialized_start=261 + _STOPPANELRESPONSE._serialized_end=280 + _ENUMERATEPANELSREQUEST._serialized_start=282 + _ENUMERATEPANELSREQUEST._serialized_end=306 + _PANELINFORMATION._serialized_start=308 + _PANELINFORMATION._serialized_end=382 + _ENUMERATEPANELSRESPONSE._serialized_start=384 + _ENUMERATEPANELSRESPONSE._serialized_end=457 + _GETVALUEREQUEST._serialized_start=459 + _GETVALUEREQUEST._serialized_end=512 + _GETVALUERESPONSE._serialized_start=514 + _GETVALUERESPONSE._serialized_end=569 + _TRYGETVALUEREQUEST._serialized_start=571 + _TRYGETVALUEREQUEST._serialized_end=627 + _TRYGETVALUERESPONSE._serialized_start=629 + _TRYGETVALUERESPONSE._serialized_end=702 + _SETVALUEREQUEST._serialized_start=704 + _SETVALUEREQUEST._serialized_end=810 + _SETVALUERESPONSE._serialized_start=812 + _SETVALUERESPONSE._serialized_end=830 + _PANELSERVICE._serialized_start=833 + _PANELSERVICE._serialized_end=1336 +# @@protoc_insertion_point(module_scope) diff --git a/src/ni/pythonpanel/v1/python_panel_service_pb2.pyi b/src/ni/panels/v1/panel_service_pb2.pyi similarity index 87% rename from src/ni/pythonpanel/v1/python_panel_service_pb2.pyi rename to src/ni/panels/v1/panel_service_pb2.pyi index f55eb02f..538636b4 100644 --- a/src/ni/pythonpanel/v1/python_panel_service_pb2.pyi +++ b/src/ni/panels/v1/panel_service_pb2.pyi @@ -18,22 +18,21 @@ class StartPanelRequest(google.protobuf.message.Message): DESCRIPTOR: google.protobuf.descriptor.Descriptor PANEL_ID_FIELD_NUMBER: builtins.int - PANEL_SCRIPT_PATH_FIELD_NUMBER: builtins.int - PYTHON_PATH_FIELD_NUMBER: builtins.int + PANEL_CONFIGURATION_FIELD_NUMBER: builtins.int panel_id: builtins.str """Unique ID of the panel""" - panel_script_path: builtins.str - """Absolute path of the panel script's file on disk, or network path to the file""" - python_path: builtins.str - """Path to the python interpreter to use for the panel script.""" + @property + def panel_configuration(self) -> google.protobuf.any_pb2.Any: + """Configuration for the panel, packed as Any""" + def __init__( self, *, panel_id: builtins.str = ..., - panel_script_path: builtins.str = ..., - python_path: builtins.str = ..., + panel_configuration: google.protobuf.any_pb2.Any | None = ..., ) -> None: ... - def ClearField(self, field_name: typing.Literal["panel_id", b"panel_id", "panel_script_path", b"panel_script_path", "python_path", b"python_path"]) -> None: ... + def HasField(self, field_name: typing.Literal["panel_configuration", b"panel_configuration"]) -> builtins.bool: ... + def ClearField(self, field_name: typing.Literal["panel_configuration", b"panel_configuration", "panel_id", b"panel_id"]) -> None: ... global___StartPanelRequest = StartPanelRequest @@ -41,15 +40,15 @@ global___StartPanelRequest = StartPanelRequest class StartPanelResponse(google.protobuf.message.Message): DESCRIPTOR: google.protobuf.descriptor.Descriptor - PANEL_URL_FIELD_NUMBER: builtins.int - panel_url: builtins.str - """Location of the panel's webpage""" + PANEL_URI_FIELD_NUMBER: builtins.int + panel_uri: builtins.str + """Location of the panel""" def __init__( self, *, - panel_url: builtins.str = ..., + panel_uri: builtins.str = ..., ) -> None: ... - def ClearField(self, field_name: typing.Literal["panel_url", b"panel_url"]) -> None: ... + def ClearField(self, field_name: typing.Literal["panel_uri", b"panel_uri"]) -> None: ... global___StartPanelResponse = StartPanelResponse @@ -98,12 +97,12 @@ class PanelInformation(google.protobuf.message.Message): DESCRIPTOR: google.protobuf.descriptor.Descriptor PANEL_ID_FIELD_NUMBER: builtins.int - PANEL_URL_FIELD_NUMBER: builtins.int + PANEL_URI_FIELD_NUMBER: builtins.int VALUE_IDS_FIELD_NUMBER: builtins.int panel_id: builtins.str """Unique ID of the panel""" - panel_url: builtins.str - """Location of the panel's webpage""" + panel_uri: builtins.str + """Location of the panel""" @property def value_ids(self) -> google.protobuf.internal.containers.RepeatedScalarFieldContainer[builtins.str]: """IDs of all of the values associated with the panel""" @@ -112,10 +111,10 @@ class PanelInformation(google.protobuf.message.Message): self, *, panel_id: builtins.str = ..., - panel_url: builtins.str = ..., + panel_uri: builtins.str = ..., value_ids: collections.abc.Iterable[builtins.str] | None = ..., ) -> None: ... - def ClearField(self, field_name: typing.Literal["panel_id", b"panel_id", "panel_url", b"panel_url", "value_ids", b"value_ids"]) -> None: ... + def ClearField(self, field_name: typing.Literal["panel_id", b"panel_id", "panel_uri", b"panel_uri", "value_ids", b"value_ids"]) -> None: ... global___PanelInformation = PanelInformation @@ -203,7 +202,7 @@ class TryGetValueResponse(google.protobuf.message.Message): VALUE_FIELD_NUMBER: builtins.int @property def value(self) -> google.protobuf.any_pb2.Any: - """The value, if it was found""" + """The value, if it was found""" def __init__( self, diff --git a/src/ni/pythonpanel/v1/python_panel_service_pb2_grpc.py b/src/ni/panels/v1/panel_service_pb2_grpc.py similarity index 56% rename from src/ni/pythonpanel/v1/python_panel_service_pb2_grpc.py rename to src/ni/panels/v1/panel_service_pb2_grpc.py index f2a3f727..ef44db2a 100644 --- a/src/ni/pythonpanel/v1/python_panel_service_pb2_grpc.py +++ b/src/ni/panels/v1/panel_service_pb2_grpc.py @@ -2,11 +2,11 @@ """Client and server classes corresponding to protobuf-defined services.""" import grpc -from ni.pythonpanel.v1 import python_panel_service_pb2 as ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2 +from ni.panels.v1 import panel_service_pb2 as ni_dot_panels_dot_v1_dot_panel__service__pb2 -class PythonPanelServiceStub(object): - """Service interface for interacting with python panels +class PanelServiceStub(object): + """Service interface for interacting with NI panels """ def __init__(self, channel): @@ -16,50 +16,49 @@ def __init__(self, channel): channel: A grpc.Channel. """ self.StartPanel = channel.unary_unary( - '/ni.pythonpanel.v1.PythonPanelService/StartPanel', - request_serializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.StartPanelRequest.SerializeToString, - response_deserializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.StartPanelResponse.FromString, + '/ni.panels.v1.PanelService/StartPanel', + request_serializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.StartPanelRequest.SerializeToString, + response_deserializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.StartPanelResponse.FromString, ) self.StopPanel = channel.unary_unary( - '/ni.pythonpanel.v1.PythonPanelService/StopPanel', - request_serializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.StopPanelRequest.SerializeToString, - response_deserializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.StopPanelResponse.FromString, + '/ni.panels.v1.PanelService/StopPanel', + request_serializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.StopPanelRequest.SerializeToString, + response_deserializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.StopPanelResponse.FromString, ) self.EnumeratePanels = channel.unary_unary( - '/ni.pythonpanel.v1.PythonPanelService/EnumeratePanels', - request_serializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.EnumeratePanelsRequest.SerializeToString, - response_deserializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.EnumeratePanelsResponse.FromString, + '/ni.panels.v1.PanelService/EnumeratePanels', + request_serializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.EnumeratePanelsRequest.SerializeToString, + response_deserializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.EnumeratePanelsResponse.FromString, ) self.GetValue = channel.unary_unary( - '/ni.pythonpanel.v1.PythonPanelService/GetValue', - request_serializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.GetValueRequest.SerializeToString, - response_deserializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.GetValueResponse.FromString, + '/ni.panels.v1.PanelService/GetValue', + request_serializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.GetValueRequest.SerializeToString, + response_deserializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.GetValueResponse.FromString, ) self.TryGetValue = channel.unary_unary( - '/ni.pythonpanel.v1.PythonPanelService/TryGetValue', - request_serializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.TryGetValueRequest.SerializeToString, - response_deserializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.TryGetValueResponse.FromString, + '/ni.panels.v1.PanelService/TryGetValue', + request_serializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.TryGetValueRequest.SerializeToString, + response_deserializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.TryGetValueResponse.FromString, ) self.SetValue = channel.unary_unary( - '/ni.pythonpanel.v1.PythonPanelService/SetValue', - request_serializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.SetValueRequest.SerializeToString, - response_deserializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.SetValueResponse.FromString, + '/ni.panels.v1.PanelService/SetValue', + request_serializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.SetValueRequest.SerializeToString, + response_deserializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.SetValueResponse.FromString, ) -class PythonPanelServiceServicer(object): - """Service interface for interacting with python panels +class PanelServiceServicer(object): + """Service interface for interacting with NI panels """ def StartPanel(self, request, context): - """Start a panel (or connect to if it has already been started) + """Start a panel using the provided configuration (or connect to if it has already been started) Status Codes for errors: - INVALID_ARGUMENT: - - The panel script filename doesn't end in .py. - The panel identifier contains invalid characters. Only alphanumeric characters and underscores are allowed. + - The panel configuration has an invalid argument. - NOT_FOUND: - - The panel script file was not found. - - The python executable file was not found. + - The panel configuration includes a file that was not found. """ context.set_code(grpc.StatusCode.UNIMPLEMENTED) context.set_details('Method not implemented!') @@ -119,47 +118,47 @@ def SetValue(self, request, context): raise NotImplementedError('Method not implemented!') -def add_PythonPanelServiceServicer_to_server(servicer, server): +def add_PanelServiceServicer_to_server(servicer, server): rpc_method_handlers = { 'StartPanel': grpc.unary_unary_rpc_method_handler( servicer.StartPanel, - request_deserializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.StartPanelRequest.FromString, - response_serializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.StartPanelResponse.SerializeToString, + request_deserializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.StartPanelRequest.FromString, + response_serializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.StartPanelResponse.SerializeToString, ), 'StopPanel': grpc.unary_unary_rpc_method_handler( servicer.StopPanel, - request_deserializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.StopPanelRequest.FromString, - response_serializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.StopPanelResponse.SerializeToString, + request_deserializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.StopPanelRequest.FromString, + response_serializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.StopPanelResponse.SerializeToString, ), 'EnumeratePanels': grpc.unary_unary_rpc_method_handler( servicer.EnumeratePanels, - request_deserializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.EnumeratePanelsRequest.FromString, - response_serializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.EnumeratePanelsResponse.SerializeToString, + request_deserializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.EnumeratePanelsRequest.FromString, + response_serializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.EnumeratePanelsResponse.SerializeToString, ), 'GetValue': grpc.unary_unary_rpc_method_handler( servicer.GetValue, - request_deserializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.GetValueRequest.FromString, - response_serializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.GetValueResponse.SerializeToString, + request_deserializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.GetValueRequest.FromString, + response_serializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.GetValueResponse.SerializeToString, ), 'TryGetValue': grpc.unary_unary_rpc_method_handler( servicer.TryGetValue, - request_deserializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.TryGetValueRequest.FromString, - response_serializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.TryGetValueResponse.SerializeToString, + request_deserializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.TryGetValueRequest.FromString, + response_serializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.TryGetValueResponse.SerializeToString, ), 'SetValue': grpc.unary_unary_rpc_method_handler( servicer.SetValue, - request_deserializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.SetValueRequest.FromString, - response_serializer=ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.SetValueResponse.SerializeToString, + request_deserializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.SetValueRequest.FromString, + response_serializer=ni_dot_panels_dot_v1_dot_panel__service__pb2.SetValueResponse.SerializeToString, ), } generic_handler = grpc.method_handlers_generic_handler( - 'ni.pythonpanel.v1.PythonPanelService', rpc_method_handlers) + 'ni.panels.v1.PanelService', rpc_method_handlers) server.add_generic_rpc_handlers((generic_handler,)) # This class is part of an EXPERIMENTAL API. -class PythonPanelService(object): - """Service interface for interacting with python panels +class PanelService(object): + """Service interface for interacting with NI panels """ @staticmethod @@ -173,9 +172,9 @@ def StartPanel(request, wait_for_ready=None, timeout=None, metadata=None): - return grpc.experimental.unary_unary(request, target, '/ni.pythonpanel.v1.PythonPanelService/StartPanel', - ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.StartPanelRequest.SerializeToString, - ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.StartPanelResponse.FromString, + return grpc.experimental.unary_unary(request, target, '/ni.panels.v1.PanelService/StartPanel', + ni_dot_panels_dot_v1_dot_panel__service__pb2.StartPanelRequest.SerializeToString, + ni_dot_panels_dot_v1_dot_panel__service__pb2.StartPanelResponse.FromString, options, channel_credentials, insecure, call_credentials, compression, wait_for_ready, timeout, metadata) @@ -190,9 +189,9 @@ def StopPanel(request, wait_for_ready=None, timeout=None, metadata=None): - return grpc.experimental.unary_unary(request, target, '/ni.pythonpanel.v1.PythonPanelService/StopPanel', - ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.StopPanelRequest.SerializeToString, - ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.StopPanelResponse.FromString, + return grpc.experimental.unary_unary(request, target, '/ni.panels.v1.PanelService/StopPanel', + ni_dot_panels_dot_v1_dot_panel__service__pb2.StopPanelRequest.SerializeToString, + ni_dot_panels_dot_v1_dot_panel__service__pb2.StopPanelResponse.FromString, options, channel_credentials, insecure, call_credentials, compression, wait_for_ready, timeout, metadata) @@ -207,9 +206,9 @@ def EnumeratePanels(request, wait_for_ready=None, timeout=None, metadata=None): - return grpc.experimental.unary_unary(request, target, '/ni.pythonpanel.v1.PythonPanelService/EnumeratePanels', - ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.EnumeratePanelsRequest.SerializeToString, - ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.EnumeratePanelsResponse.FromString, + return grpc.experimental.unary_unary(request, target, '/ni.panels.v1.PanelService/EnumeratePanels', + ni_dot_panels_dot_v1_dot_panel__service__pb2.EnumeratePanelsRequest.SerializeToString, + ni_dot_panels_dot_v1_dot_panel__service__pb2.EnumeratePanelsResponse.FromString, options, channel_credentials, insecure, call_credentials, compression, wait_for_ready, timeout, metadata) @@ -224,9 +223,9 @@ def GetValue(request, wait_for_ready=None, timeout=None, metadata=None): - return grpc.experimental.unary_unary(request, target, '/ni.pythonpanel.v1.PythonPanelService/GetValue', - ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.GetValueRequest.SerializeToString, - ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.GetValueResponse.FromString, + return grpc.experimental.unary_unary(request, target, '/ni.panels.v1.PanelService/GetValue', + ni_dot_panels_dot_v1_dot_panel__service__pb2.GetValueRequest.SerializeToString, + ni_dot_panels_dot_v1_dot_panel__service__pb2.GetValueResponse.FromString, options, channel_credentials, insecure, call_credentials, compression, wait_for_ready, timeout, metadata) @@ -241,9 +240,9 @@ def TryGetValue(request, wait_for_ready=None, timeout=None, metadata=None): - return grpc.experimental.unary_unary(request, target, '/ni.pythonpanel.v1.PythonPanelService/TryGetValue', - ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.TryGetValueRequest.SerializeToString, - ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.TryGetValueResponse.FromString, + return grpc.experimental.unary_unary(request, target, '/ni.panels.v1.PanelService/TryGetValue', + ni_dot_panels_dot_v1_dot_panel__service__pb2.TryGetValueRequest.SerializeToString, + ni_dot_panels_dot_v1_dot_panel__service__pb2.TryGetValueResponse.FromString, options, channel_credentials, insecure, call_credentials, compression, wait_for_ready, timeout, metadata) @@ -258,8 +257,8 @@ def SetValue(request, wait_for_ready=None, timeout=None, metadata=None): - return grpc.experimental.unary_unary(request, target, '/ni.pythonpanel.v1.PythonPanelService/SetValue', - ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.SetValueRequest.SerializeToString, - ni_dot_pythonpanel_dot_v1_dot_python__panel__service__pb2.SetValueResponse.FromString, + return grpc.experimental.unary_unary(request, target, '/ni.panels.v1.PanelService/SetValue', + ni_dot_panels_dot_v1_dot_panel__service__pb2.SetValueRequest.SerializeToString, + ni_dot_panels_dot_v1_dot_panel__service__pb2.SetValueResponse.FromString, options, channel_credentials, insecure, call_credentials, compression, wait_for_ready, timeout, metadata) diff --git a/src/ni/pythonpanel/v1/python_panel_service_pb2_grpc.pyi b/src/ni/panels/v1/panel_service_pb2_grpc.pyi similarity index 60% rename from src/ni/pythonpanel/v1/python_panel_service_pb2_grpc.pyi rename to src/ni/panels/v1/panel_service_pb2_grpc.pyi index a38cae8c..030c5a37 100644 --- a/src/ni/pythonpanel/v1/python_panel_service_pb2_grpc.pyi +++ b/src/ni/panels/v1/panel_service_pb2_grpc.pyi @@ -7,7 +7,7 @@ import abc import collections.abc import grpc import grpc.aio -import ni.pythonpanel.v1.python_panel_service_pb2 +import ni.panels.v1.panel_service_pb2 import typing _T = typing.TypeVar("_T") @@ -17,27 +17,26 @@ class _MaybeAsyncIterator(collections.abc.AsyncIterator[_T], collections.abc.Ite class _ServicerContext(grpc.ServicerContext, grpc.aio.ServicerContext): # type: ignore[misc, type-arg] ... -class PythonPanelServiceStub: - """Service interface for interacting with python panels""" +class PanelServiceStub: + """Service interface for interacting with NI panels""" def __init__(self, channel: typing.Union[grpc.Channel, grpc.aio.Channel]) -> None: ... StartPanel: grpc.UnaryUnaryMultiCallable[ - ni.pythonpanel.v1.python_panel_service_pb2.StartPanelRequest, - ni.pythonpanel.v1.python_panel_service_pb2.StartPanelResponse, + ni.panels.v1.panel_service_pb2.StartPanelRequest, + ni.panels.v1.panel_service_pb2.StartPanelResponse, ] - """Start a panel (or connect to if it has already been started) + """Start a panel using the provided configuration (or connect to if it has already been started) Status Codes for errors: - INVALID_ARGUMENT: - - The panel script filename doesn't end in .py. - The panel identifier contains invalid characters. Only alphanumeric characters and underscores are allowed. + - The panel configuration has an invalid argument. - NOT_FOUND: - - The panel script file was not found. - - The python executable file was not found. + - The panel configuration includes a file that was not found. """ StopPanel: grpc.UnaryUnaryMultiCallable[ - ni.pythonpanel.v1.python_panel_service_pb2.StopPanelRequest, - ni.pythonpanel.v1.python_panel_service_pb2.StopPanelResponse, + ni.panels.v1.panel_service_pb2.StopPanelRequest, + ni.panels.v1.panel_service_pb2.StopPanelResponse, ] """Stop a panel Status Codes for errors: @@ -46,16 +45,16 @@ class PythonPanelServiceStub: """ EnumeratePanels: grpc.UnaryUnaryMultiCallable[ - ni.pythonpanel.v1.python_panel_service_pb2.EnumeratePanelsRequest, - ni.pythonpanel.v1.python_panel_service_pb2.EnumeratePanelsResponse, + ni.panels.v1.panel_service_pb2.EnumeratePanelsRequest, + ni.panels.v1.panel_service_pb2.EnumeratePanelsResponse, ] """Enumerate the panels available in the system, including information about the state of the panels and what values they have. Status Codes for errors: """ GetValue: grpc.UnaryUnaryMultiCallable[ - ni.pythonpanel.v1.python_panel_service_pb2.GetValueRequest, - ni.pythonpanel.v1.python_panel_service_pb2.GetValueResponse, + ni.panels.v1.panel_service_pb2.GetValueRequest, + ni.panels.v1.panel_service_pb2.GetValueResponse, ] """Get a value for a control on the panel Status Codes for errors: @@ -67,8 +66,8 @@ class PythonPanelServiceStub: """ TryGetValue: grpc.UnaryUnaryMultiCallable[ - ni.pythonpanel.v1.python_panel_service_pb2.TryGetValueRequest, - ni.pythonpanel.v1.python_panel_service_pb2.TryGetValueResponse, + ni.panels.v1.panel_service_pb2.TryGetValueRequest, + ni.panels.v1.panel_service_pb2.TryGetValueResponse, ] """Try to get a value for a control on the panel Status Codes for errors: @@ -78,8 +77,8 @@ class PythonPanelServiceStub: """ SetValue: grpc.UnaryUnaryMultiCallable[ - ni.pythonpanel.v1.python_panel_service_pb2.SetValueRequest, - ni.pythonpanel.v1.python_panel_service_pb2.SetValueResponse, + ni.panels.v1.panel_service_pb2.SetValueRequest, + ni.panels.v1.panel_service_pb2.SetValueResponse, ] """Set a value for a control on the panel Status Codes for errors: @@ -88,26 +87,25 @@ class PythonPanelServiceStub: - The value identifier contains invalid characters. Only alphanumeric characters and underscores are allowed. """ -class PythonPanelServiceAsyncStub: - """Service interface for interacting with python panels""" +class PanelServiceAsyncStub: + """Service interface for interacting with NI panels""" StartPanel: grpc.aio.UnaryUnaryMultiCallable[ - ni.pythonpanel.v1.python_panel_service_pb2.StartPanelRequest, - ni.pythonpanel.v1.python_panel_service_pb2.StartPanelResponse, + ni.panels.v1.panel_service_pb2.StartPanelRequest, + ni.panels.v1.panel_service_pb2.StartPanelResponse, ] - """Start a panel (or connect to if it has already been started) + """Start a panel using the provided configuration (or connect to if it has already been started) Status Codes for errors: - INVALID_ARGUMENT: - - The panel script filename doesn't end in .py. - The panel identifier contains invalid characters. Only alphanumeric characters and underscores are allowed. + - The panel configuration has an invalid argument. - NOT_FOUND: - - The panel script file was not found. - - The python executable file was not found. + - The panel configuration includes a file that was not found. """ StopPanel: grpc.aio.UnaryUnaryMultiCallable[ - ni.pythonpanel.v1.python_panel_service_pb2.StopPanelRequest, - ni.pythonpanel.v1.python_panel_service_pb2.StopPanelResponse, + ni.panels.v1.panel_service_pb2.StopPanelRequest, + ni.panels.v1.panel_service_pb2.StopPanelResponse, ] """Stop a panel Status Codes for errors: @@ -116,16 +114,16 @@ class PythonPanelServiceAsyncStub: """ EnumeratePanels: grpc.aio.UnaryUnaryMultiCallable[ - ni.pythonpanel.v1.python_panel_service_pb2.EnumeratePanelsRequest, - ni.pythonpanel.v1.python_panel_service_pb2.EnumeratePanelsResponse, + ni.panels.v1.panel_service_pb2.EnumeratePanelsRequest, + ni.panels.v1.panel_service_pb2.EnumeratePanelsResponse, ] """Enumerate the panels available in the system, including information about the state of the panels and what values they have. Status Codes for errors: """ GetValue: grpc.aio.UnaryUnaryMultiCallable[ - ni.pythonpanel.v1.python_panel_service_pb2.GetValueRequest, - ni.pythonpanel.v1.python_panel_service_pb2.GetValueResponse, + ni.panels.v1.panel_service_pb2.GetValueRequest, + ni.panels.v1.panel_service_pb2.GetValueResponse, ] """Get a value for a control on the panel Status Codes for errors: @@ -137,8 +135,8 @@ class PythonPanelServiceAsyncStub: """ TryGetValue: grpc.aio.UnaryUnaryMultiCallable[ - ni.pythonpanel.v1.python_panel_service_pb2.TryGetValueRequest, - ni.pythonpanel.v1.python_panel_service_pb2.TryGetValueResponse, + ni.panels.v1.panel_service_pb2.TryGetValueRequest, + ni.panels.v1.panel_service_pb2.TryGetValueResponse, ] """Try to get a value for a control on the panel Status Codes for errors: @@ -148,8 +146,8 @@ class PythonPanelServiceAsyncStub: """ SetValue: grpc.aio.UnaryUnaryMultiCallable[ - ni.pythonpanel.v1.python_panel_service_pb2.SetValueRequest, - ni.pythonpanel.v1.python_panel_service_pb2.SetValueResponse, + ni.panels.v1.panel_service_pb2.SetValueRequest, + ni.panels.v1.panel_service_pb2.SetValueResponse, ] """Set a value for a control on the panel Status Codes for errors: @@ -158,31 +156,30 @@ class PythonPanelServiceAsyncStub: - The value identifier contains invalid characters. Only alphanumeric characters and underscores are allowed. """ -class PythonPanelServiceServicer(metaclass=abc.ABCMeta): - """Service interface for interacting with python panels""" +class PanelServiceServicer(metaclass=abc.ABCMeta): + """Service interface for interacting with NI panels""" @abc.abstractmethod def StartPanel( self, - request: ni.pythonpanel.v1.python_panel_service_pb2.StartPanelRequest, + request: ni.panels.v1.panel_service_pb2.StartPanelRequest, context: _ServicerContext, - ) -> typing.Union[ni.pythonpanel.v1.python_panel_service_pb2.StartPanelResponse, collections.abc.Awaitable[ni.pythonpanel.v1.python_panel_service_pb2.StartPanelResponse]]: - """Start a panel (or connect to if it has already been started) + ) -> typing.Union[ni.panels.v1.panel_service_pb2.StartPanelResponse, collections.abc.Awaitable[ni.panels.v1.panel_service_pb2.StartPanelResponse]]: + """Start a panel using the provided configuration (or connect to if it has already been started) Status Codes for errors: - INVALID_ARGUMENT: - - The panel script filename doesn't end in .py. - The panel identifier contains invalid characters. Only alphanumeric characters and underscores are allowed. + - The panel configuration has an invalid argument. - NOT_FOUND: - - The panel script file was not found. - - The python executable file was not found. + - The panel configuration includes a file that was not found. """ @abc.abstractmethod def StopPanel( self, - request: ni.pythonpanel.v1.python_panel_service_pb2.StopPanelRequest, + request: ni.panels.v1.panel_service_pb2.StopPanelRequest, context: _ServicerContext, - ) -> typing.Union[ni.pythonpanel.v1.python_panel_service_pb2.StopPanelResponse, collections.abc.Awaitable[ni.pythonpanel.v1.python_panel_service_pb2.StopPanelResponse]]: + ) -> typing.Union[ni.panels.v1.panel_service_pb2.StopPanelResponse, collections.abc.Awaitable[ni.panels.v1.panel_service_pb2.StopPanelResponse]]: """Stop a panel Status Codes for errors: - INVALID_ARGUMENT: @@ -192,9 +189,9 @@ class PythonPanelServiceServicer(metaclass=abc.ABCMeta): @abc.abstractmethod def EnumeratePanels( self, - request: ni.pythonpanel.v1.python_panel_service_pb2.EnumeratePanelsRequest, + request: ni.panels.v1.panel_service_pb2.EnumeratePanelsRequest, context: _ServicerContext, - ) -> typing.Union[ni.pythonpanel.v1.python_panel_service_pb2.EnumeratePanelsResponse, collections.abc.Awaitable[ni.pythonpanel.v1.python_panel_service_pb2.EnumeratePanelsResponse]]: + ) -> typing.Union[ni.panels.v1.panel_service_pb2.EnumeratePanelsResponse, collections.abc.Awaitable[ni.panels.v1.panel_service_pb2.EnumeratePanelsResponse]]: """Enumerate the panels available in the system, including information about the state of the panels and what values they have. Status Codes for errors: """ @@ -202,9 +199,9 @@ class PythonPanelServiceServicer(metaclass=abc.ABCMeta): @abc.abstractmethod def GetValue( self, - request: ni.pythonpanel.v1.python_panel_service_pb2.GetValueRequest, + request: ni.panels.v1.panel_service_pb2.GetValueRequest, context: _ServicerContext, - ) -> typing.Union[ni.pythonpanel.v1.python_panel_service_pb2.GetValueResponse, collections.abc.Awaitable[ni.pythonpanel.v1.python_panel_service_pb2.GetValueResponse]]: + ) -> typing.Union[ni.panels.v1.panel_service_pb2.GetValueResponse, collections.abc.Awaitable[ni.panels.v1.panel_service_pb2.GetValueResponse]]: """Get a value for a control on the panel Status Codes for errors: - INVALID_ARGUMENT: @@ -217,9 +214,9 @@ class PythonPanelServiceServicer(metaclass=abc.ABCMeta): @abc.abstractmethod def TryGetValue( self, - request: ni.pythonpanel.v1.python_panel_service_pb2.TryGetValueRequest, + request: ni.panels.v1.panel_service_pb2.TryGetValueRequest, context: _ServicerContext, - ) -> typing.Union[ni.pythonpanel.v1.python_panel_service_pb2.TryGetValueResponse, collections.abc.Awaitable[ni.pythonpanel.v1.python_panel_service_pb2.TryGetValueResponse]]: + ) -> typing.Union[ni.panels.v1.panel_service_pb2.TryGetValueResponse, collections.abc.Awaitable[ni.panels.v1.panel_service_pb2.TryGetValueResponse]]: """Try to get a value for a control on the panel Status Codes for errors: - INVALID_ARGUMENT: @@ -230,9 +227,9 @@ class PythonPanelServiceServicer(metaclass=abc.ABCMeta): @abc.abstractmethod def SetValue( self, - request: ni.pythonpanel.v1.python_panel_service_pb2.SetValueRequest, + request: ni.panels.v1.panel_service_pb2.SetValueRequest, context: _ServicerContext, - ) -> typing.Union[ni.pythonpanel.v1.python_panel_service_pb2.SetValueResponse, collections.abc.Awaitable[ni.pythonpanel.v1.python_panel_service_pb2.SetValueResponse]]: + ) -> typing.Union[ni.panels.v1.panel_service_pb2.SetValueResponse, collections.abc.Awaitable[ni.panels.v1.panel_service_pb2.SetValueResponse]]: """Set a value for a control on the panel Status Codes for errors: - INVALID_ARGUMENT: @@ -240,4 +237,4 @@ class PythonPanelServiceServicer(metaclass=abc.ABCMeta): - The value identifier contains invalid characters. Only alphanumeric characters and underscores are allowed. """ -def add_PythonPanelServiceServicer_to_server(servicer: PythonPanelServiceServicer, server: typing.Union[grpc.Server, grpc.aio.Server]) -> None: ... +def add_PanelServiceServicer_to_server(servicer: PanelServiceServicer, server: typing.Union[grpc.Server, grpc.aio.Server]) -> None: ... diff --git a/src/ni/panels/v1/panel_types_pb2.py b/src/ni/panels/v1/panel_types_pb2.py new file mode 100644 index 00000000..d637414f --- /dev/null +++ b/src/ni/panels/v1/panel_types_pb2.py @@ -0,0 +1,34 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: ni/panels/v1/panel_types.proto +"""Generated protocol buffer code.""" +from google.protobuf.internal import builder as _builder +from google.protobuf import descriptor as _descriptor +from google.protobuf import descriptor_pool as _descriptor_pool +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + + + + +DESCRIPTOR = _descriptor_pool.Default().AddSerializedFile(b'\n\x1eni/panels/v1/panel_types.proto\x12\x0cni.panels.v1\" \n\x0e\x42oolCollection\x12\x0e\n\x06values\x18\x01 \x03(\x08\"&\n\x14\x42yteStringCollection\x12\x0e\n\x06values\x18\x01 \x03(\x0c\"!\n\x0f\x46loatCollection\x12\x0e\n\x06values\x18\x01 \x03(\x01\"\x1f\n\rIntCollection\x12\x0e\n\x06values\x18\x01 \x03(\x12\"\"\n\x10StringCollection\x12\x0e\n\x06values\x18\x01 \x03(\tBu\n\x10\x63om.ni.panels.v1B\x0bPanelsProtoP\x01Z\x08panelsv1\xf8\x01\x01\xa2\x02\x04NIPS\xaa\x02\x1dNationalInstruments.Panels.V1\xca\x02\x0cNI\\Panels\\V1\xea\x02\x0eNI::Panels::V1b\x06proto3') + +_builder.BuildMessageAndEnumDescriptors(DESCRIPTOR, globals()) +_builder.BuildTopDescriptorsAndMessages(DESCRIPTOR, 'ni.panels.v1.panel_types_pb2', globals()) +if _descriptor._USE_C_DESCRIPTORS == False: + + DESCRIPTOR._options = None + DESCRIPTOR._serialized_options = b'\n\020com.ni.panels.v1B\013PanelsProtoP\001Z\010panelsv1\370\001\001\242\002\004NIPS\252\002\035NationalInstruments.Panels.V1\312\002\014NI\\Panels\\V1\352\002\016NI::Panels::V1' + _BOOLCOLLECTION._serialized_start=48 + _BOOLCOLLECTION._serialized_end=80 + _BYTESTRINGCOLLECTION._serialized_start=82 + _BYTESTRINGCOLLECTION._serialized_end=120 + _FLOATCOLLECTION._serialized_start=122 + _FLOATCOLLECTION._serialized_end=155 + _INTCOLLECTION._serialized_start=157 + _INTCOLLECTION._serialized_end=188 + _STRINGCOLLECTION._serialized_start=190 + _STRINGCOLLECTION._serialized_end=224 +# @@protoc_insertion_point(module_scope) diff --git a/src/ni/pythonpanel/v1/python_panel_types_pb2.pyi b/src/ni/panels/v1/panel_types_pb2.pyi similarity index 100% rename from src/ni/pythonpanel/v1/python_panel_types_pb2.pyi rename to src/ni/panels/v1/panel_types_pb2.pyi diff --git a/src/ni/pythonpanel/v1/python_panel_types_pb2_grpc.py b/src/ni/panels/v1/panel_types_pb2_grpc.py similarity index 100% rename from src/ni/pythonpanel/v1/python_panel_types_pb2_grpc.py rename to src/ni/panels/v1/panel_types_pb2_grpc.py diff --git a/src/ni/pythonpanel/v1/python_panel_types_pb2_grpc.pyi b/src/ni/panels/v1/panel_types_pb2_grpc.pyi similarity index 100% rename from src/ni/pythonpanel/v1/python_panel_types_pb2_grpc.pyi rename to src/ni/panels/v1/panel_types_pb2_grpc.pyi diff --git a/src/ni/pythonpanel/v1/py.typed b/src/ni/panels/v1/py.typed similarity index 100% rename from src/ni/pythonpanel/v1/py.typed rename to src/ni/panels/v1/py.typed diff --git a/src/ni/panels/v1/streamlit_panel_configuration_pb2.py b/src/ni/panels/v1/streamlit_panel_configuration_pb2.py new file mode 100644 index 00000000..6e4f6eb1 --- /dev/null +++ b/src/ni/panels/v1/streamlit_panel_configuration_pb2.py @@ -0,0 +1,26 @@ +# -*- coding: utf-8 -*- +# Generated by the protocol buffer compiler. DO NOT EDIT! +# source: ni/panels/v1/streamlit_panel_configuration.proto +"""Generated protocol buffer code.""" +from google.protobuf.internal import builder as _builder +from google.protobuf import descriptor as _descriptor +from google.protobuf import descriptor_pool as _descriptor_pool +from google.protobuf import symbol_database as _symbol_database +# @@protoc_insertion_point(imports) + +_sym_db = _symbol_database.Default() + + + + +DESCRIPTOR = _descriptor_pool.Default().AddSerializedFile(b'\n0ni/panels/v1/streamlit_panel_configuration.proto\x12\x0cni.panels.v1\"M\n\x1bStreamlitPanelConfiguration\x12\x19\n\x11panel_script_path\x18\x01 \x01(\t\x12\x13\n\x0bpython_path\x18\x02 \x01(\tB\x8a\x01\n\x10\x63om.ni.panels.v1B StreamlitPanelConfigurationProtoP\x01Z\x08panelsv1\xf8\x01\x01\xa2\x02\x04NIPS\xaa\x02\x1dNationalInstruments.Panels.V1\xca\x02\x0cNI\\Panels\\V1\xea\x02\x0eNI::Panels::V1b\x06proto3') + +_builder.BuildMessageAndEnumDescriptors(DESCRIPTOR, globals()) +_builder.BuildTopDescriptorsAndMessages(DESCRIPTOR, 'ni.panels.v1.streamlit_panel_configuration_pb2', globals()) +if _descriptor._USE_C_DESCRIPTORS == False: + + DESCRIPTOR._options = None + DESCRIPTOR._serialized_options = b'\n\020com.ni.panels.v1B StreamlitPanelConfigurationProtoP\001Z\010panelsv1\370\001\001\242\002\004NIPS\252\002\035NationalInstruments.Panels.V1\312\002\014NI\\Panels\\V1\352\002\016NI::Panels::V1' + _STREAMLITPANELCONFIGURATION._serialized_start=66 + _STREAMLITPANELCONFIGURATION._serialized_end=143 +# @@protoc_insertion_point(module_scope) diff --git a/src/ni/panels/v1/streamlit_panel_configuration_pb2.pyi b/src/ni/panels/v1/streamlit_panel_configuration_pb2.pyi new file mode 100644 index 00000000..d62d0af0 --- /dev/null +++ b/src/ni/panels/v1/streamlit_panel_configuration_pb2.pyi @@ -0,0 +1,33 @@ +""" +@generated by mypy-protobuf. Do not edit manually! +isort:skip_file +""" + +import builtins +import google.protobuf.descriptor +import google.protobuf.message +import typing + +DESCRIPTOR: google.protobuf.descriptor.FileDescriptor + +@typing.final +class StreamlitPanelConfiguration(google.protobuf.message.Message): + """Pack this into PanelService.StartPanelRequest.panel_configuration to start a Streamlit panel.""" + + DESCRIPTOR: google.protobuf.descriptor.Descriptor + + PANEL_SCRIPT_PATH_FIELD_NUMBER: builtins.int + PYTHON_PATH_FIELD_NUMBER: builtins.int + panel_script_path: builtins.str + """Absolute path of the streamlit script file on disk, or network path to the file. This must end in ".py".""" + python_path: builtins.str + """Path to the python interpreter to use for running the streamlit script.""" + def __init__( + self, + *, + panel_script_path: builtins.str = ..., + python_path: builtins.str = ..., + ) -> None: ... + def ClearField(self, field_name: typing.Literal["panel_script_path", b"panel_script_path", "python_path", b"python_path"]) -> None: ... + +global___StreamlitPanelConfiguration = StreamlitPanelConfiguration diff --git a/src/ni/panels/v1/streamlit_panel_configuration_pb2_grpc.py b/src/ni/panels/v1/streamlit_panel_configuration_pb2_grpc.py new file mode 100644 index 00000000..2daafffe --- /dev/null +++ b/src/ni/panels/v1/streamlit_panel_configuration_pb2_grpc.py @@ -0,0 +1,4 @@ +# Generated by the gRPC Python protocol compiler plugin. DO NOT EDIT! +"""Client and server classes corresponding to protobuf-defined services.""" +import grpc + diff --git a/src/ni/panels/v1/streamlit_panel_configuration_pb2_grpc.pyi b/src/ni/panels/v1/streamlit_panel_configuration_pb2_grpc.pyi new file mode 100644 index 00000000..a6a9cff9 --- /dev/null +++ b/src/ni/panels/v1/streamlit_panel_configuration_pb2_grpc.pyi @@ -0,0 +1,17 @@ +""" +@generated by mypy-protobuf. Do not edit manually! +isort:skip_file +""" + +import abc +import collections.abc +import grpc +import grpc.aio +import typing + +_T = typing.TypeVar("_T") + +class _MaybeAsyncIterator(collections.abc.AsyncIterator[_T], collections.abc.Iterator[_T], metaclass=abc.ABCMeta): ... + +class _ServicerContext(grpc.ServicerContext, grpc.aio.ServicerContext): # type: ignore[misc, type-arg] + ... diff --git a/src/ni/pythonpanel/__init__.py b/src/ni/pythonpanel/__init__.py deleted file mode 100644 index 9dc74c4b..00000000 --- a/src/ni/pythonpanel/__init__.py +++ /dev/null @@ -1 +0,0 @@ -"""gRPC stubs for NI PythonPanel.""" diff --git a/src/ni/pythonpanel/v1/__init__.py b/src/ni/pythonpanel/v1/__init__.py deleted file mode 100644 index 7a90cada..00000000 --- a/src/ni/pythonpanel/v1/__init__.py +++ /dev/null @@ -1 +0,0 @@ -"""gRPC client for PythonPanel.""" diff --git a/src/ni/pythonpanel/v1/python_panel_service_pb2.py b/src/ni/pythonpanel/v1/python_panel_service_pb2.py deleted file mode 100644 index b8b36dd3..00000000 --- a/src/ni/pythonpanel/v1/python_panel_service_pb2.py +++ /dev/null @@ -1,53 +0,0 @@ -# -*- coding: utf-8 -*- -# Generated by the protocol buffer compiler. DO NOT EDIT! -# source: ni/pythonpanel/v1/python_panel_service.proto -"""Generated protocol buffer code.""" -from google.protobuf.internal import builder as _builder -from google.protobuf import descriptor as _descriptor -from google.protobuf import descriptor_pool as _descriptor_pool -from google.protobuf import symbol_database as _symbol_database -# @@protoc_insertion_point(imports) - -_sym_db = _symbol_database.Default() - - -from google.protobuf import any_pb2 as google_dot_protobuf_dot_any__pb2 - - -DESCRIPTOR = _descriptor_pool.Default().AddSerializedFile(b'\n,ni/pythonpanel/v1/python_panel_service.proto\x12\x11ni.pythonpanel.v1\x1a\x19google/protobuf/any.proto\"U\n\x11StartPanelRequest\x12\x10\n\x08panel_id\x18\x01 \x01(\t\x12\x19\n\x11panel_script_path\x18\x02 \x01(\t\x12\x13\n\x0bpython_path\x18\x03 \x01(\t\"\'\n\x12StartPanelResponse\x12\x11\n\tpanel_url\x18\x01 \x01(\t\"3\n\x10StopPanelRequest\x12\x10\n\x08panel_id\x18\x01 \x01(\t\x12\r\n\x05reset\x18\x02 \x01(\x08\"\x13\n\x11StopPanelResponse\"\x18\n\x16\x45numeratePanelsRequest\"J\n\x10PanelInformation\x12\x10\n\x08panel_id\x18\x01 \x01(\t\x12\x11\n\tpanel_url\x18\x02 \x01(\t\x12\x11\n\tvalue_ids\x18\x03 \x03(\t\"N\n\x17\x45numeratePanelsResponse\x12\x33\n\x06panels\x18\x01 \x03(\x0b\x32#.ni.pythonpanel.v1.PanelInformation\"5\n\x0fGetValueRequest\x12\x10\n\x08panel_id\x18\x01 \x01(\t\x12\x10\n\x08value_id\x18\x02 \x01(\t\"7\n\x10GetValueResponse\x12#\n\x05value\x18\x01 \x01(\x0b\x32\x14.google.protobuf.Any\"8\n\x12TryGetValueRequest\x12\x10\n\x08panel_id\x18\x01 \x01(\t\x12\x10\n\x08value_id\x18\x02 \x01(\t\"I\n\x13TryGetValueResponse\x12(\n\x05value\x18\x01 \x01(\x0b\x32\x14.google.protobuf.AnyH\x00\x88\x01\x01\x42\x08\n\x06_value\"j\n\x0fSetValueRequest\x12\x10\n\x08panel_id\x18\x01 \x01(\t\x12\x10\n\x08value_id\x18\x02 \x01(\t\x12#\n\x05value\x18\x03 \x01(\x0b\x32\x14.google.protobuf.Any\x12\x0e\n\x06notify\x18\x04 \x01(\x08\"\x12\n\x10SetValueResponse2\xb9\x04\n\x12PythonPanelService\x12Y\n\nStartPanel\x12$.ni.pythonpanel.v1.StartPanelRequest\x1a%.ni.pythonpanel.v1.StartPanelResponse\x12V\n\tStopPanel\x12#.ni.pythonpanel.v1.StopPanelRequest\x1a$.ni.pythonpanel.v1.StopPanelResponse\x12h\n\x0f\x45numeratePanels\x12).ni.pythonpanel.v1.EnumeratePanelsRequest\x1a*.ni.pythonpanel.v1.EnumeratePanelsResponse\x12S\n\x08GetValue\x12\".ni.pythonpanel.v1.GetValueRequest\x1a#.ni.pythonpanel.v1.GetValueResponse\x12\\\n\x0bTryGetValue\x12%.ni.pythonpanel.v1.TryGetValueRequest\x1a&.ni.pythonpanel.v1.TryGetValueResponse\x12S\n\x08SetValue\x12\".ni.pythonpanel.v1.SetValueRequest\x1a#.ni.pythonpanel.v1.SetValueResponseB\x9a\x01\n\x15\x63om.ni.pythonpanel.v1B\x17PythonPanelServiceProtoP\x01Z\rpythonpanelv1\xf8\x01\x01\xa2\x02\x04NIPP\xaa\x02\"NationalInstruments.PythonPanel.V1\xca\x02\x11NI\\PythonPanel\\V1\xea\x02\x13NI::PythonPanel::V1b\x06proto3') - -_builder.BuildMessageAndEnumDescriptors(DESCRIPTOR, globals()) -_builder.BuildTopDescriptorsAndMessages(DESCRIPTOR, 'ni.pythonpanel.v1.python_panel_service_pb2', globals()) -if _descriptor._USE_C_DESCRIPTORS == False: - - DESCRIPTOR._options = None - DESCRIPTOR._serialized_options = b'\n\025com.ni.pythonpanel.v1B\027PythonPanelServiceProtoP\001Z\rpythonpanelv1\370\001\001\242\002\004NIPP\252\002\"NationalInstruments.PythonPanel.V1\312\002\021NI\\PythonPanel\\V1\352\002\023NI::PythonPanel::V1' - _STARTPANELREQUEST._serialized_start=94 - _STARTPANELREQUEST._serialized_end=179 - _STARTPANELRESPONSE._serialized_start=181 - _STARTPANELRESPONSE._serialized_end=220 - _STOPPANELREQUEST._serialized_start=222 - _STOPPANELREQUEST._serialized_end=273 - _STOPPANELRESPONSE._serialized_start=275 - _STOPPANELRESPONSE._serialized_end=294 - _ENUMERATEPANELSREQUEST._serialized_start=296 - _ENUMERATEPANELSREQUEST._serialized_end=320 - _PANELINFORMATION._serialized_start=322 - _PANELINFORMATION._serialized_end=396 - _ENUMERATEPANELSRESPONSE._serialized_start=398 - _ENUMERATEPANELSRESPONSE._serialized_end=476 - _GETVALUEREQUEST._serialized_start=478 - _GETVALUEREQUEST._serialized_end=531 - _GETVALUERESPONSE._serialized_start=533 - _GETVALUERESPONSE._serialized_end=588 - _TRYGETVALUEREQUEST._serialized_start=590 - _TRYGETVALUEREQUEST._serialized_end=646 - _TRYGETVALUERESPONSE._serialized_start=648 - _TRYGETVALUERESPONSE._serialized_end=721 - _SETVALUEREQUEST._serialized_start=723 - _SETVALUEREQUEST._serialized_end=829 - _SETVALUERESPONSE._serialized_start=831 - _SETVALUERESPONSE._serialized_end=849 - _PYTHONPANELSERVICE._serialized_start=852 - _PYTHONPANELSERVICE._serialized_end=1421 -# @@protoc_insertion_point(module_scope) diff --git a/src/ni/pythonpanel/v1/python_panel_types_pb2.py b/src/ni/pythonpanel/v1/python_panel_types_pb2.py deleted file mode 100644 index 684da292..00000000 --- a/src/ni/pythonpanel/v1/python_panel_types_pb2.py +++ /dev/null @@ -1,34 +0,0 @@ -# -*- coding: utf-8 -*- -# Generated by the protocol buffer compiler. DO NOT EDIT! -# source: ni/pythonpanel/v1/python_panel_types.proto -"""Generated protocol buffer code.""" -from google.protobuf.internal import builder as _builder -from google.protobuf import descriptor as _descriptor -from google.protobuf import descriptor_pool as _descriptor_pool -from google.protobuf import symbol_database as _symbol_database -# @@protoc_insertion_point(imports) - -_sym_db = _symbol_database.Default() - - - - -DESCRIPTOR = _descriptor_pool.Default().AddSerializedFile(b'\n*ni/pythonpanel/v1/python_panel_types.proto\x12\x11ni.pythonpanel.v1\" \n\x0e\x42oolCollection\x12\x0e\n\x06values\x18\x01 \x03(\x08\"&\n\x14\x42yteStringCollection\x12\x0e\n\x06values\x18\x01 \x03(\x0c\"!\n\x0f\x46loatCollection\x12\x0e\n\x06values\x18\x01 \x03(\x01\"\x1f\n\rIntCollection\x12\x0e\n\x06values\x18\x01 \x03(\x12\"\"\n\x10StringCollection\x12\x0e\n\x06values\x18\x01 \x03(\tB\x9a\x01\n\x15\x63om.ni.pythonpanel.v1B\x17PythonPanelServiceProtoP\x01Z\rpythonpanelv1\xf8\x01\x01\xa2\x02\x04NIPP\xaa\x02\"NationalInstruments.PythonPanel.V1\xca\x02\x11NI\\PythonPanel\\V1\xea\x02\x13NI::PythonPanel::V1b\x06proto3') - -_builder.BuildMessageAndEnumDescriptors(DESCRIPTOR, globals()) -_builder.BuildTopDescriptorsAndMessages(DESCRIPTOR, 'ni.pythonpanel.v1.python_panel_types_pb2', globals()) -if _descriptor._USE_C_DESCRIPTORS == False: - - DESCRIPTOR._options = None - DESCRIPTOR._serialized_options = b'\n\025com.ni.pythonpanel.v1B\027PythonPanelServiceProtoP\001Z\rpythonpanelv1\370\001\001\242\002\004NIPP\252\002\"NationalInstruments.PythonPanel.V1\312\002\021NI\\PythonPanel\\V1\352\002\023NI::PythonPanel::V1' - _BOOLCOLLECTION._serialized_start=65 - _BOOLCOLLECTION._serialized_end=97 - _BYTESTRINGCOLLECTION._serialized_start=99 - _BYTESTRINGCOLLECTION._serialized_end=137 - _FLOATCOLLECTION._serialized_start=139 - _FLOATCOLLECTION._serialized_end=172 - _INTCOLLECTION._serialized_start=174 - _INTCOLLECTION._serialized_end=205 - _STRINGCOLLECTION._serialized_start=207 - _STRINGCOLLECTION._serialized_end=241 -# @@protoc_insertion_point(module_scope) diff --git a/src/nipanel/__init__.py b/src/nipanel/__init__.py index 05d5a737..65262b5c 100644 --- a/src/nipanel/__init__.py +++ b/src/nipanel/__init__.py @@ -2,21 +2,22 @@ from importlib.metadata import version -from nipanel._panel import Panel +from nipanel._panel_value_accessor import PanelValueAccessor from nipanel._streamlit_panel import StreamlitPanel -from nipanel._streamlit_panel_initializer import create_panel, get_panel_accessor -from nipanel._streamlit_panel_value_accessor import StreamlitPanelValueAccessor +from nipanel._streamlit_panel_initializer import ( + create_streamlit_panel, + get_streamlit_panel_accessor, +) __all__ = [ - "create_panel", - "get_panel_accessor", - "Panel", + "create_streamlit_panel", + "get_streamlit_panel_accessor", + "PanelValueAccessor", "StreamlitPanel", - "StreamlitPanelValueAccessor", ] # Hide that it was defined in a helper file -Panel.__module__ = __name__ +PanelValueAccessor.__module__ = __name__ StreamlitPanel.__module__ = __name__ __version__ = version(__name__) diff --git a/src/nipanel/_panel.py b/src/nipanel/_panel.py deleted file mode 100644 index 25f5bed6..00000000 --- a/src/nipanel/_panel.py +++ /dev/null @@ -1,86 +0,0 @@ -from __future__ import annotations - -import sys -from abc import ABC -from pathlib import Path - -import grpc -from ni_measurement_plugin_sdk_service.discovery import DiscoveryClient -from ni_measurement_plugin_sdk_service.grpc.channelpool import GrpcChannelPool - -from nipanel._panel_value_accessor import PanelValueAccessor - - -class Panel(PanelValueAccessor, ABC): - """This class allows you to open a panel and specify values for its controls.""" - - __slots__ = ["_panel_script_path", "_panel_url"] - - def __init__( - self, - *, - panel_id: str, - panel_script_path: str, - provided_interface: str, - service_class: str, - discovery_client: DiscoveryClient | None = None, - grpc_channel_pool: GrpcChannelPool | None = None, - grpc_channel: grpc.Channel | None = None, - ) -> None: - """Initialize the panel.""" - super().__init__( - panel_id=panel_id, - provided_interface=provided_interface, - service_class=service_class, - discovery_client=discovery_client, - grpc_channel_pool=grpc_channel_pool, - grpc_channel=grpc_channel, - ) - self._panel_script_path = panel_script_path - python_path = self._get_python_path() - self._panel_url = self._panel_client.start_panel(panel_id, panel_script_path, python_path) - - @property - def panel_script_path(self) -> str: - """Read-only accessor for the panel script path.""" - return self._panel_script_path - - @property - def panel_url(self) -> str: - """Read-only accessor for the panel URL.""" - return self._panel_url - - def _get_python_path(self) -> str: - """Get the Python interpreter path for the panel that ensures the same environment.""" - if sys.executable is None or sys.executable == "": - raise RuntimeError("Python environment not found") - if getattr(sys, "frozen", False): - raise RuntimeError("Panel cannot be used in a frozen application (e.g., PyInstaller).") - - if sys.prefix != sys.base_prefix: - # If we're in a virtual environment, build the path to the Python executable - # On Linux: .venv/bin/python, On Windows: .venv\Scripts\python.exe - if sys.platform.startswith("win"): - python_executable = "python.exe" - bin_dir = "Scripts" - else: - python_executable = "python" - bin_dir = "bin" - - # Construct path to the Python in the virtual environment based on sys.prefix - python_path = str(Path(sys.prefix) / bin_dir / python_executable) - - # Fall back to sys.executable if the constructed path doesn't exist - if not Path(python_path).exists(): - python_path = str(Path(sys.executable).resolve()) - else: - # If not in a .venv environment, use sys.executable - python_path = str(Path(sys.executable).resolve()) - - if sys.prefix not in python_path: - # Ensure the Python path is within the current environment - raise RuntimeError( - f"Python path '{python_path}' does not match the current environment prefix '{sys.prefix}'." - ) - - return python_path diff --git a/src/nipanel/_panel_client.py b/src/nipanel/_panel_client.py index 9de42d3a..8c284b06 100644 --- a/src/nipanel/_panel_client.py +++ b/src/nipanel/_panel_client.py @@ -5,7 +5,8 @@ from typing import Callable, TypeVar import grpc -from ni.pythonpanel.v1.python_panel_service_pb2 import ( +from google.protobuf.any_pb2 import Any +from ni.panels.v1.panel_service_pb2 import ( StartPanelRequest, StopPanelRequest, EnumeratePanelsRequest, @@ -13,7 +14,8 @@ TryGetValueRequest, SetValueRequest, ) -from ni.pythonpanel.v1.python_panel_service_pb2_grpc import PythonPanelServiceStub +from ni.panels.v1.panel_service_pb2_grpc import PanelServiceStub +from ni.panels.v1.streamlit_panel_configuration_pb2 import StreamlitPanelConfiguration from ni_measurement_plugin_sdk_service.discovery import DiscoveryClient from ni_measurement_plugin_sdk_service.grpc.channelpool import GrpcChannelPool from typing_extensions import ParamSpec @@ -28,31 +30,34 @@ _logger = logging.getLogger(__name__) +PANEL_SERVICE = "ni.panels.v1.PanelService" + class _PanelClient: def __init__( self, *, - provided_interface: str, - service_class: str, discovery_client: DiscoveryClient | None = None, grpc_channel_pool: GrpcChannelPool | None = None, grpc_channel: grpc.Channel | None = None, ) -> None: self._initialization_lock = threading.Lock() - self._provided_interface = provided_interface - self._service_class = service_class self._discovery_client = discovery_client self._grpc_channel_pool = grpc_channel_pool self._grpc_channel = grpc_channel - self._stub: PythonPanelServiceStub | None = None + self._stub: PanelServiceStub | None = None - def start_panel(self, panel_id: str, panel_script_path: str, python_path: str) -> str: + def start_streamlit_panel(self, panel_id: str, panel_script_path: str, python_path: str) -> str: + streamlit_panel_configuration = StreamlitPanelConfiguration( + panel_script_path=panel_script_path, python_path=python_path + ) + panel_configuration_any = Any() + panel_configuration_any.Pack(streamlit_panel_configuration) start_panel_request = StartPanelRequest( - panel_id=panel_id, panel_script_path=panel_script_path, python_path=python_path + panel_id=panel_id, panel_configuration=panel_configuration_any ) response = self._invoke_with_retry(self._get_stub().StartPanel, start_panel_request) - return response.panel_url + return response.panel_uri def stop_panel(self, panel_id: str, reset: bool) -> None: stop_panel_request = StopPanelRequest(panel_id=panel_id, reset=reset) @@ -64,7 +69,7 @@ def enumerate_panels(self) -> dict[str, tuple[str, list[str]]]: self._get_stub().EnumeratePanels, enumerate_panels_request ) return { - panel.panel_id: (panel.panel_url, list(panel.value_ids)) for panel in response.panels + panel.panel_id: (panel.panel_uri, list(panel.value_ids)) for panel in response.panels } def set_value(self, panel_id: str, value_id: str, value: object, notify: bool) -> None: @@ -87,10 +92,10 @@ def try_get_value(self, panel_id: str, value_id: str) -> object | None: else: return None - def _get_stub(self) -> PythonPanelServiceStub: + def _get_stub(self) -> PanelServiceStub: if self._stub is None: if self._grpc_channel is not None: - self._stub = PythonPanelServiceStub(self._grpc_channel) + self._stub = PanelServiceStub(self._grpc_channel) else: with self._initialization_lock: if self._grpc_channel_pool is None: @@ -103,11 +108,10 @@ def _get_stub(self) -> PythonPanelServiceStub: ) service_location = self._discovery_client.resolve_service( - provided_interface=self._provided_interface, - service_class=self._service_class, + provided_interface=PANEL_SERVICE ) channel = self._grpc_channel_pool.get_channel(service_location.insecure_address) - self._stub = PythonPanelServiceStub(channel) + self._stub = PanelServiceStub(channel) return self._stub def _invoke_with_retry( diff --git a/src/nipanel/_panel_value_accessor.py b/src/nipanel/_panel_value_accessor.py index c123bd0f..4f0f0803 100644 --- a/src/nipanel/_panel_value_accessor.py +++ b/src/nipanel/_panel_value_accessor.py @@ -29,8 +29,6 @@ def __init__( self, *, panel_id: str, - provided_interface: str, - service_class: str, notify_on_set_value: bool = True, discovery_client: DiscoveryClient | None = None, grpc_channel_pool: GrpcChannelPool | None = None, @@ -38,8 +36,6 @@ def __init__( ) -> None: """Initialize the accessor.""" self._panel_client = _PanelClient( - provided_interface=provided_interface, - service_class=service_class, discovery_client=discovery_client, grpc_channel_pool=grpc_channel_pool, grpc_channel=grpc_channel, @@ -70,6 +66,9 @@ def get_value(self, value_id: str, default_value: _T | None = None) -> _T | obje Returns: The value, or the default value if not set + + Raises: + KeyError: If the value is not set and no default value is provided """ value = self._panel_client.try_get_value(self._panel_id, value_id) if value is None: diff --git a/src/nipanel/_streamlit_constants.py b/src/nipanel/_streamlit_constants.py deleted file mode 100644 index 2cd9601e..00000000 --- a/src/nipanel/_streamlit_constants.py +++ /dev/null @@ -1 +0,0 @@ -STREAMLIT_PYTHON_PANEL_SERVICE = "ni.pythonpanel.v1.PythonPanelService" diff --git a/src/nipanel/_streamlit_panel.py b/src/nipanel/_streamlit_panel.py index 16607cb6..2d258fa7 100644 --- a/src/nipanel/_streamlit_panel.py +++ b/src/nipanel/_streamlit_panel.py @@ -1,23 +1,26 @@ from __future__ import annotations +import sys +from pathlib import Path from typing import final import grpc from ni_measurement_plugin_sdk_service.discovery import DiscoveryClient from ni_measurement_plugin_sdk_service.grpc.channelpool import GrpcChannelPool -from nipanel._panel import Panel -from nipanel._streamlit_constants import STREAMLIT_PYTHON_PANEL_SERVICE +from nipanel._panel_value_accessor import PanelValueAccessor @final -class StreamlitPanel(Panel): +class StreamlitPanel(PanelValueAccessor): """This class allows you to open a Streamlit panel and specify values for its controls.""" + __slots__ = ["_panel_script_path", "_panel_url"] + def __init__( self, panel_id: str, - streamlit_script_path: str, + panel_script_path: str, *, discovery_client: DiscoveryClient | None = None, grpc_channel_pool: GrpcChannelPool | None = None, @@ -27,7 +30,9 @@ def __init__( Args: panel_id: A unique identifier for the panel. - streamlit_script_path: The file path of the Streamlit script. + panel_script_path: The file path of the Streamlit script. + discovery_client: An optional DiscoveryClient for service discovery. + grpc_channel_pool: An optional GrpcChannelPool for managing gRPC channels. grpc_channel: An optional gRPC channel to use for communication with the panel service. Returns: @@ -35,10 +40,57 @@ def __init__( """ super().__init__( panel_id=panel_id, - panel_script_path=streamlit_script_path, - provided_interface=STREAMLIT_PYTHON_PANEL_SERVICE, - service_class=STREAMLIT_PYTHON_PANEL_SERVICE, discovery_client=discovery_client, grpc_channel_pool=grpc_channel_pool, grpc_channel=grpc_channel, ) + self._panel_script_path = panel_script_path + python_path = self._get_python_path() + self._panel_url = self._panel_client.start_streamlit_panel( + panel_id, panel_script_path, python_path + ) + + @property + def panel_script_path(self) -> str: + """Read-only accessor for the streamlit script file path.""" + return self._panel_script_path + + @property + def panel_url(self) -> str: + """Read-only accessor for the panel's streamlit webpage URL.""" + return self._panel_url + + def _get_python_path(self) -> str: + """Get the Python interpreter path for the panel that ensures the same environment.""" + if sys.executable is None or sys.executable == "": + raise RuntimeError("Python environment not found") + if getattr(sys, "frozen", False): + raise RuntimeError("Panel cannot be used in a frozen application (e.g., PyInstaller).") + + if sys.prefix != sys.base_prefix: + # If we're in a virtual environment, build the path to the Python executable + # On Linux: .venv/bin/python, On Windows: .venv\Scripts\python.exe + if sys.platform.startswith("win"): + python_executable = "python.exe" + bin_dir = "Scripts" + else: + python_executable = "python" + bin_dir = "bin" + + # Construct path to the Python in the virtual environment based on sys.prefix + python_path = str(Path(sys.prefix) / bin_dir / python_executable) + + # Fall back to sys.executable if the constructed path doesn't exist + if not Path(python_path).exists(): + python_path = str(Path(sys.executable).resolve()) + else: + # If not in a .venv environment, use sys.executable + python_path = str(Path(sys.executable).resolve()) + + if sys.prefix not in python_path: + # Ensure the Python path is within the current environment + raise RuntimeError( + f"Python path '{python_path}' does not match the current environment prefix '{sys.prefix}'." + ) + + return python_path diff --git a/src/nipanel/_streamlit_panel_initializer.py b/src/nipanel/_streamlit_panel_initializer.py index a05822d0..40eb35d5 100644 --- a/src/nipanel/_streamlit_panel_initializer.py +++ b/src/nipanel/_streamlit_panel_initializer.py @@ -4,26 +4,28 @@ import streamlit as st from nipanel._convert import is_supported_type +from nipanel._panel_value_accessor import PanelValueAccessor from nipanel._streamlit_panel import StreamlitPanel -from nipanel._streamlit_panel_value_accessor import StreamlitPanelValueAccessor from nipanel.streamlit_refresh import initialize_refresh_component PANEL_ACCESSOR_KEY = "StreamlitPanelValueAccessor" -def create_panel(streamlit_script_path: Path) -> StreamlitPanel: +def create_streamlit_panel(streamlit_script_path: Path, panel_id: str = "") -> StreamlitPanel: """Create a Streamlit panel with the specified script path. - This function initializes a Streamlit panel using the provided script path. It derives the panel - ID from the script's path, which it expects to be a valid Streamlit script. For example, if the - value for streamlit_script_path is "c:/example/some_example.py", then the panel's ID becomes - "some_example". + This function initializes a Streamlit panel using the provided script path. By default, it + derives the panel ID from the script's path, which it expects to be a valid Streamlit script. + For example, if the value for streamlit_script_path is "c:/example/some_example.py", then the + panel's ID becomes "some_example". Alternatively, you can specify a custom panel_id. Use this function when you want to create a new panel instance to use in a Streamlit application. Do not call this function from within a Streamlit script. Args: streamlit_script_path: The file path of the Streamlit script to be used for the panel. + panel_id: Optional custom panel ID. If not provided, it will be derived from the script + path. Returns: A StreamlitPanel instance initialized with the given panel ID. @@ -38,12 +40,14 @@ def create_panel(streamlit_script_path: Path) -> StreamlitPanel: "The provided script path must be a valid Streamlit script ending with '.py'." ) - panel_id = streamlit_script_path.stem + if not panel_id: + panel_id = streamlit_script_path.stem + path_str = str(streamlit_script_path) return StreamlitPanel(panel_id, path_str) -def get_panel_accessor() -> StreamlitPanelValueAccessor: +def get_streamlit_panel_accessor() -> PanelValueAccessor: """Initialize and return the Streamlit panel value accessor. This function retrieves the Streamlit panel value accessor for the current Streamlit script. @@ -51,7 +55,7 @@ def get_panel_accessor() -> StreamlitPanelValueAccessor: in the Streamlit session state to ensure that it is reused across reruns of the script. Returns: - A StreamlitPanelValueAccessor instance for the current panel. + A PanelValueAccessor instance for the current panel. """ if st.get_option("server.baseUrlPath") == "": raise RuntimeError( @@ -61,25 +65,28 @@ def get_panel_accessor() -> StreamlitPanelValueAccessor: if PANEL_ACCESSOR_KEY not in st.session_state: st.session_state[PANEL_ACCESSOR_KEY] = _initialize_panel_from_base_path() - panel = cast(StreamlitPanelValueAccessor, st.session_state[PANEL_ACCESSOR_KEY]) + panel = cast(PanelValueAccessor, st.session_state[PANEL_ACCESSOR_KEY]) _sync_session_state(panel) refresh_component = initialize_refresh_component(panel.panel_id) refresh_component() return panel -def _initialize_panel_from_base_path() -> StreamlitPanelValueAccessor: - """Validate and parse the Streamlit base URL path and return a StreamlitPanelValueAccessor.""" +def _initialize_panel_from_base_path() -> PanelValueAccessor: + """Validate and parse the Streamlit base URL path and return a PanelValueAccessor.""" base_url_path = st.get_option("server.baseUrlPath") if not base_url_path.startswith("/"): raise ValueError("Invalid or missing Streamlit server.baseUrlPath option.") panel_id = base_url_path.split("/")[-1] if not panel_id: raise ValueError(f"Panel ID is empty in baseUrlPath: '{base_url_path}'") - return StreamlitPanelValueAccessor(panel_id) + return PanelValueAccessor( + panel_id=panel_id, + notify_on_set_value=False, + ) -def _sync_session_state(panel: StreamlitPanelValueAccessor) -> None: +def _sync_session_state(panel: PanelValueAccessor) -> None: """Automatically read keyed control values from the session state.""" for key in st.session_state.keys(): value = st.session_state[key] diff --git a/src/nipanel/_streamlit_panel_value_accessor.py b/src/nipanel/_streamlit_panel_value_accessor.py deleted file mode 100644 index dc9e1d29..00000000 --- a/src/nipanel/_streamlit_panel_value_accessor.py +++ /dev/null @@ -1,45 +0,0 @@ -from __future__ import annotations - -from typing import final - -import grpc -from ni_measurement_plugin_sdk_service.discovery import DiscoveryClient -from ni_measurement_plugin_sdk_service.grpc.channelpool import GrpcChannelPool - -from nipanel._panel_value_accessor import PanelValueAccessor -from nipanel._streamlit_constants import STREAMLIT_PYTHON_PANEL_SERVICE - - -@final -class StreamlitPanelValueAccessor(PanelValueAccessor): - """This class provides access to values for a Streamlit panel's controls. - - This class should only be used within a Streamlit script. - """ - - def __init__( - self, - panel_id: str, - *, - discovery_client: DiscoveryClient | None = None, - grpc_channel_pool: GrpcChannelPool | None = None, - grpc_channel: grpc.Channel | None = None, - ) -> None: - """Create an accessor for a Streamlit panel. - - Args: - panel_id: A unique identifier for the panel. - grpc_channel: An optional gRPC channel to use for communication with the panel service. - - Returns: - A new StreamlitPanelAccessor instance. - """ - super().__init__( - panel_id=panel_id, - provided_interface=STREAMLIT_PYTHON_PANEL_SERVICE, - service_class=STREAMLIT_PYTHON_PANEL_SERVICE, - notify_on_set_value=False, - discovery_client=discovery_client, - grpc_channel_pool=grpc_channel_pool, - grpc_channel=grpc_channel, - ) diff --git a/src/nipanel/controls/_enum_selectbox.py b/src/nipanel/controls/_enum_selectbox.py index a75277c3..6b90b363 100644 --- a/src/nipanel/controls/_enum_selectbox.py +++ b/src/nipanel/controls/_enum_selectbox.py @@ -5,13 +5,13 @@ import streamlit as st -from nipanel._streamlit_panel_value_accessor import StreamlitPanelValueAccessor +from nipanel._panel_value_accessor import PanelValueAccessor TEnumType = TypeVar("TEnumType", bound=Enum) def enum_selectbox( - panel: StreamlitPanelValueAccessor, + panel: PanelValueAccessor, label: str, value: TEnumType, key: str, diff --git a/src/nipanel/controls/_flag_checkboxes.py b/src/nipanel/controls/_flag_checkboxes.py index 7887a534..2d12cfa3 100644 --- a/src/nipanel/controls/_flag_checkboxes.py +++ b/src/nipanel/controls/_flag_checkboxes.py @@ -5,13 +5,13 @@ import streamlit as st -from nipanel._streamlit_panel_value_accessor import StreamlitPanelValueAccessor +from nipanel._panel_value_accessor import PanelValueAccessor TFlagType = TypeVar("TFlagType", bound=Flag) def flag_checkboxes( - panel: StreamlitPanelValueAccessor, + panel: PanelValueAccessor, label: str, value: TFlagType, key: str, diff --git a/src/nipanel/converters/builtin.py b/src/nipanel/converters/builtin.py index bcd1e449..c004315c 100644 --- a/src/nipanel/converters/builtin.py +++ b/src/nipanel/converters/builtin.py @@ -4,7 +4,7 @@ from typing import Type from google.protobuf import wrappers_pb2 -from ni.pythonpanel.v1 import python_panel_types_pb2 +from ni.panels.v1 import panel_types_pb2 from nipanel.converters import Converter @@ -119,7 +119,7 @@ def to_python_value(self, protobuf_message: wrappers_pb2.StringValue) -> str: return protobuf_message.value -class BoolCollectionConverter(Converter[Collection[bool], python_panel_types_pb2.BoolCollection]): +class BoolCollectionConverter(Converter[Collection[bool], panel_types_pb2.BoolCollection]): """A converter for a Collection of bools.""" @property @@ -128,26 +128,20 @@ def python_typename(self) -> str: return f"{Collection.__name__}.{bool.__name__}" @property - def protobuf_message(self) -> Type[python_panel_types_pb2.BoolCollection]: + def protobuf_message(self) -> Type[panel_types_pb2.BoolCollection]: """The type-specific protobuf message for the Python type.""" - return python_panel_types_pb2.BoolCollection + return panel_types_pb2.BoolCollection - def to_protobuf_message( - self, python_value: Collection[bool] - ) -> python_panel_types_pb2.BoolCollection: - """Convert the collection of bools to python_panel_types_pb2.BoolCollection.""" + def to_protobuf_message(self, python_value: Collection[bool]) -> panel_types_pb2.BoolCollection: + """Convert the collection of bools to panel_types_pb2.BoolCollection.""" return self.protobuf_message(values=python_value) - def to_python_value( - self, protobuf_message: python_panel_types_pb2.BoolCollection - ) -> Collection[bool]: + def to_python_value(self, protobuf_message: panel_types_pb2.BoolCollection) -> Collection[bool]: """Convert the protobuf message to a Python collection of bools.""" return list(protobuf_message.values) -class BytesCollectionConverter( - Converter[Collection[bytes], python_panel_types_pb2.ByteStringCollection] -): +class BytesCollectionConverter(Converter[Collection[bytes], panel_types_pb2.ByteStringCollection]): """A converter for a Collection of byte strings.""" @property @@ -156,26 +150,24 @@ def python_typename(self) -> str: return f"{Collection.__name__}.{bytes.__name__}" @property - def protobuf_message(self) -> Type[python_panel_types_pb2.ByteStringCollection]: + def protobuf_message(self) -> Type[panel_types_pb2.ByteStringCollection]: """The type-specific protobuf message for the Python type.""" - return python_panel_types_pb2.ByteStringCollection + return panel_types_pb2.ByteStringCollection def to_protobuf_message( self, python_value: Collection[bytes] - ) -> python_panel_types_pb2.ByteStringCollection: - """Convert the collection of byte strings to python_panel_types_pb2.ByteStringCollection.""" + ) -> panel_types_pb2.ByteStringCollection: + """Convert the collection of byte strings to panel_types_pb2.ByteStringCollection.""" return self.protobuf_message(values=python_value) def to_python_value( - self, protobuf_message: python_panel_types_pb2.ByteStringCollection + self, protobuf_message: panel_types_pb2.ByteStringCollection ) -> Collection[bytes]: """Convert the protobuf message to a Python collection of byte strings.""" return list(protobuf_message.values) -class FloatCollectionConverter( - Converter[Collection[float], python_panel_types_pb2.FloatCollection] -): +class FloatCollectionConverter(Converter[Collection[float], panel_types_pb2.FloatCollection]): """A converter for a Collection of floats.""" @property @@ -184,24 +176,24 @@ def python_typename(self) -> str: return f"{Collection.__name__}.{float.__name__}" @property - def protobuf_message(self) -> Type[python_panel_types_pb2.FloatCollection]: + def protobuf_message(self) -> Type[panel_types_pb2.FloatCollection]: """The type-specific protobuf message for the Python type.""" - return python_panel_types_pb2.FloatCollection + return panel_types_pb2.FloatCollection def to_protobuf_message( self, python_value: Collection[float] - ) -> python_panel_types_pb2.FloatCollection: - """Convert the collection of floats to python_panel_types_pb2.FloatCollection.""" + ) -> panel_types_pb2.FloatCollection: + """Convert the collection of floats to panel_types_pb2.FloatCollection.""" return self.protobuf_message(values=python_value) def to_python_value( - self, protobuf_message: python_panel_types_pb2.FloatCollection + self, protobuf_message: panel_types_pb2.FloatCollection ) -> Collection[float]: """Convert the protobuf message to a Python collection of floats.""" return list(protobuf_message.values) -class IntCollectionConverter(Converter[Collection[int], python_panel_types_pb2.IntCollection]): +class IntCollectionConverter(Converter[Collection[int], panel_types_pb2.IntCollection]): """A converter for a Collection of integers.""" @property @@ -210,24 +202,20 @@ def python_typename(self) -> str: return f"{Collection.__name__}.{int.__name__}" @property - def protobuf_message(self) -> Type[python_panel_types_pb2.IntCollection]: + def protobuf_message(self) -> Type[panel_types_pb2.IntCollection]: """The type-specific protobuf message for the Python type.""" - return python_panel_types_pb2.IntCollection + return panel_types_pb2.IntCollection - def to_protobuf_message( - self, python_value: Collection[int] - ) -> python_panel_types_pb2.IntCollection: - """Convert the collection of integers to python_panel_types_pb2.IntCollection.""" + def to_protobuf_message(self, python_value: Collection[int]) -> panel_types_pb2.IntCollection: + """Convert the collection of integers to panel_types_pb2.IntCollection.""" return self.protobuf_message(values=python_value) - def to_python_value( - self, protobuf_message: python_panel_types_pb2.IntCollection - ) -> Collection[int]: + def to_python_value(self, protobuf_message: panel_types_pb2.IntCollection) -> Collection[int]: """Convert the protobuf message to a Python collection of integers.""" return list(protobuf_message.values) -class StrCollectionConverter(Converter[Collection[str], python_panel_types_pb2.StringCollection]): +class StrCollectionConverter(Converter[Collection[str], panel_types_pb2.StringCollection]): """A converter for a Collection of strings.""" @property @@ -236,18 +224,18 @@ def python_typename(self) -> str: return f"{Collection.__name__}.{str.__name__}" @property - def protobuf_message(self) -> Type[python_panel_types_pb2.StringCollection]: + def protobuf_message(self) -> Type[panel_types_pb2.StringCollection]: """The type-specific protobuf message for the Python type.""" - return python_panel_types_pb2.StringCollection + return panel_types_pb2.StringCollection def to_protobuf_message( self, python_value: Collection[str] - ) -> python_panel_types_pb2.StringCollection: - """Convert the collection of strings to python_panel_types_pb2.StringCollection.""" + ) -> panel_types_pb2.StringCollection: + """Convert the collection of strings to panel_types_pb2.StringCollection.""" return self.protobuf_message(values=python_value) def to_python_value( - self, protobuf_message: python_panel_types_pb2.StringCollection + self, protobuf_message: panel_types_pb2.StringCollection ) -> Collection[str]: """Convert the protobuf message to a Python collection of strings.""" return list(protobuf_message.values) diff --git a/tests/conftest.py b/tests/conftest.py index 963fc3a9..ff9c2a01 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -7,7 +7,7 @@ import grpc import pytest from grpc.framework.foundation import logging_pool -from ni.pythonpanel.v1.python_panel_service_pb2_grpc import PythonPanelServiceStub +from ni.panels.v1.panel_service_pb2_grpc import PanelServiceStub from tests.utils._fake_python_panel_service import FakePythonPanelService @@ -38,6 +38,6 @@ def fake_panel_channel( @pytest.fixture def python_panel_service_stub( fake_panel_channel: grpc.Channel, -) -> Generator[PythonPanelServiceStub]: - """Fixture to get a PythonPanelServiceStub, attached to a FakePythonPanelService.""" - yield PythonPanelServiceStub(fake_panel_channel) +) -> Generator[PanelServiceStub]: + """Fixture to get a PanelServiceStub, attached to a FakePythonPanelService.""" + yield PanelServiceStub(fake_panel_channel) diff --git a/tests/unit/test_convert.py b/tests/unit/test_convert.py index 7580fef8..a68131c0 100644 --- a/tests/unit/test_convert.py +++ b/tests/unit/test_convert.py @@ -4,8 +4,8 @@ import pytest from google.protobuf import any_pb2, wrappers_pb2 from google.protobuf.message import Message +from ni.panels.v1 import panel_types_pb2 from ni.protobuf.types.scalar_pb2 import ScalarData -from ni.pythonpanel.v1 import python_panel_types_pb2 from ni_measurement_plugin_sdk_service._internal.stubs.ni.protobuf.types.array_pb2 import ( Double2DArray, ) @@ -29,11 +29,11 @@ ] _AnyPanelPbTypes: TypeAlias = Union[ - python_panel_types_pb2.BoolCollection, - python_panel_types_pb2.ByteStringCollection, - python_panel_types_pb2.FloatCollection, - python_panel_types_pb2.IntCollection, - python_panel_types_pb2.StringCollection, + panel_types_pb2.BoolCollection, + panel_types_pb2.ByteStringCollection, + panel_types_pb2.FloatCollection, + panel_types_pb2.IntCollection, + panel_types_pb2.StringCollection, ] @@ -126,11 +126,11 @@ def test___python_builtin_scalar___to_any___valid_wrapperpb2_value( @pytest.mark.parametrize( "proto_type, default_value, expected_value", [ - (python_panel_types_pb2.BoolCollection, [False, False, False], [True, True, True]), - (python_panel_types_pb2.ByteStringCollection, [b"", b"", b""], [b"a", b"b", b"c"]), - (python_panel_types_pb2.FloatCollection, [0.0, 0.0, 0.0], [1.0, 2.0, 3.0]), - (python_panel_types_pb2.IntCollection, [0, 0, 0], [1, 2, 3]), - (python_panel_types_pb2.StringCollection, ["", "", ""], ["a", "b", "c"]), + (panel_types_pb2.BoolCollection, [False, False, False], [True, True, True]), + (panel_types_pb2.ByteStringCollection, [b"", b"", b""], [b"a", b"b", b"c"]), + (panel_types_pb2.FloatCollection, [0.0, 0.0, 0.0], [1.0, 2.0, 3.0]), + (panel_types_pb2.IntCollection, [0, 0, 0], [1, 2, 3]), + (panel_types_pb2.StringCollection, ["", "", ""], ["a", "b", "c"]), ], ) def test___python_panel_collection___to_any___valid_paneltype_value( @@ -178,11 +178,11 @@ def test___wrapperpb2_value___from_any___valid_python_value( @pytest.mark.parametrize( "proto_type, expected_value", [ - (python_panel_types_pb2.BoolCollection, [True, True, True]), - (python_panel_types_pb2.ByteStringCollection, [b"a", b"b", b"c"]), - (python_panel_types_pb2.FloatCollection, [1.0, 2.0, 3.0]), - (python_panel_types_pb2.IntCollection, [1, 2, 3]), - (python_panel_types_pb2.StringCollection, ["a", "b", "c"]), + (panel_types_pb2.BoolCollection, [True, True, True]), + (panel_types_pb2.ByteStringCollection, [b"a", b"b", b"c"]), + (panel_types_pb2.FloatCollection, [1.0, 2.0, 3.0]), + (panel_types_pb2.IntCollection, [1, 2, 3]), + (panel_types_pb2.StringCollection, ["a", "b", "c"]), ], ) def test___paneltype_value___from_any___valid_python_value( diff --git a/tests/unit/test_panel_client.py b/tests/unit/test_panel_client.py index 6f422dac..be71f2ef 100644 --- a/tests/unit/test_panel_client.py +++ b/tests/unit/test_panel_client.py @@ -5,16 +5,16 @@ def test___enumerate_is_empty(fake_panel_channel: grpc.Channel) -> None: - client = create_panel_client(fake_panel_channel) + client = _PanelClient(grpc_channel=fake_panel_channel) assert client.enumerate_panels() == {} def test___start_panels___enumerate_has_panels(fake_panel_channel: grpc.Channel) -> None: - client = create_panel_client(fake_panel_channel) + client = _PanelClient(grpc_channel=fake_panel_channel) - client.start_panel("panel1", "uri1", "python.exe") - client.start_panel("panel2", "uri2", "python.exe") + client.start_streamlit_panel("panel1", "uri1", "python.exe") + client.start_streamlit_panel("panel2", "uri2", "python.exe") assert client.enumerate_panels() == { "panel1": ("http://localhost:50051/panel1", []), @@ -25,9 +25,9 @@ def test___start_panels___enumerate_has_panels(fake_panel_channel: grpc.Channel) def test___start_panels___stop_panel_1_with_reset___enumerate_has_panel_2( fake_panel_channel: grpc.Channel, ) -> None: - client = create_panel_client(fake_panel_channel) - client.start_panel("panel1", "uri1", "python.exe") - client.start_panel("panel2", "uri2", "python.exe") + client = _PanelClient(grpc_channel=fake_panel_channel) + client.start_streamlit_panel("panel1", "uri1", "python.exe") + client.start_streamlit_panel("panel2", "uri2", "python.exe") client.stop_panel("panel1", reset=True) @@ -39,9 +39,9 @@ def test___start_panels___stop_panel_1_with_reset___enumerate_has_panel_2( def test___start_panels___stop_panel_1_without_reset___enumerate_has_both_panels( fake_panel_channel: grpc.Channel, ) -> None: - client = create_panel_client(fake_panel_channel) - client.start_panel("panel1", "uri1", "python.exe") - client.start_panel("panel2", "uri2", "python.exe") + client = _PanelClient(grpc_channel=fake_panel_channel) + client.start_streamlit_panel("panel1", "uri1", "python.exe") + client.start_streamlit_panel("panel2", "uri2", "python.exe") client.stop_panel("panel1", reset=False) @@ -52,7 +52,7 @@ def test___start_panels___stop_panel_1_without_reset___enumerate_has_both_panels def test___get_unset_value___raises_exception(fake_panel_channel: grpc.Channel) -> None: - client = create_panel_client(fake_panel_channel) + client = _PanelClient(grpc_channel=fake_panel_channel) with pytest.raises(grpc.RpcError) as exc_info: client.get_value("panel1", "unset_id") @@ -61,7 +61,7 @@ def test___get_unset_value___raises_exception(fake_panel_channel: grpc.Channel) def test___try_get_unset_value___returns_none(fake_panel_channel: grpc.Channel) -> None: - client = create_panel_client(fake_panel_channel) + client = _PanelClient(grpc_channel=fake_panel_channel) response = client.try_get_value("panel1", "unset_id") @@ -71,7 +71,7 @@ def test___try_get_unset_value___returns_none(fake_panel_channel: grpc.Channel) def test___set_value___enumerate_panels_shows_value( fake_panel_channel: grpc.Channel, ) -> None: - client = create_panel_client(fake_panel_channel) + client = _PanelClient(grpc_channel=fake_panel_channel) client.set_value("panel1", "val1", "value1", notify=False) @@ -79,16 +79,8 @@ def test___set_value___enumerate_panels_shows_value( def test___set_value___gets_value(fake_panel_channel: grpc.Channel) -> None: - client = create_panel_client(fake_panel_channel) + client = _PanelClient(grpc_channel=fake_panel_channel) client.set_value("panel1", "val1", "value1", notify=False) assert client.try_get_value("panel1", "val1") == "value1" - - -def create_panel_client(fake_panel_channel: grpc.Channel) -> _PanelClient: - return _PanelClient( - provided_interface="iface", - service_class="svc", - grpc_channel=fake_panel_channel, - ) diff --git a/tests/unit/test_streamlit_panel_value_accessor.py b/tests/unit/test_panel_value_accessor.py similarity index 87% rename from tests/unit/test_streamlit_panel_value_accessor.py rename to tests/unit/test_panel_value_accessor.py index 4a845b6b..e75c13f3 100644 --- a/tests/unit/test_streamlit_panel_value_accessor.py +++ b/tests/unit/test_panel_value_accessor.py @@ -1,6 +1,6 @@ import grpc -from nipanel import StreamlitPanelValueAccessor +from nipanel import PanelValueAccessor from tests.types import MyIntEnum from tests.utils._fake_python_panel_service import FakePythonPanelService @@ -8,7 +8,7 @@ def test___no_previous_value___set_value_if_changed___sets_value( fake_panel_channel: grpc.Channel, ) -> None: - accessor = StreamlitPanelValueAccessor("panel_id", grpc_channel=fake_panel_channel) + accessor = PanelValueAccessor(panel_id="panel_id", grpc_channel=fake_panel_channel) accessor.set_value_if_changed("test_id", "test_value") @@ -19,7 +19,7 @@ def test___set_value_if_changed___set_same_value___does_not_set_value_again( fake_panel_channel: grpc.Channel, fake_python_panel_service: FakePythonPanelService, ) -> None: - accessor = StreamlitPanelValueAccessor("panel_id", grpc_channel=fake_panel_channel) + accessor = PanelValueAccessor(panel_id="panel_id", grpc_channel=fake_panel_channel) accessor.set_value_if_changed("test_id", "test_value") initial_set_count = fake_python_panel_service.servicer.set_count @@ -32,7 +32,7 @@ def test___set_value_if_changed___set_same_value___does_not_set_value_again( def test___set_value_if_changed___set_different_value___sets_new_value( fake_panel_channel: grpc.Channel, ) -> None: - accessor = StreamlitPanelValueAccessor("panel_id", grpc_channel=fake_panel_channel) + accessor = PanelValueAccessor(panel_id="panel_id", grpc_channel=fake_panel_channel) accessor.set_value_if_changed("test_id", "test_value") accessor.set_value_if_changed("test_id", "new_value") @@ -43,7 +43,7 @@ def test___set_value_if_changed___set_different_value___sets_new_value( def test___set_value_if_changed___different_value_ids___tracks_separately( fake_panel_channel: grpc.Channel, ) -> None: - accessor = StreamlitPanelValueAccessor("panel_id", grpc_channel=fake_panel_channel) + accessor = PanelValueAccessor(panel_id="panel_id", grpc_channel=fake_panel_channel) accessor.set_value_if_changed("id1", "value1") accessor.set_value_if_changed("id2", "value2") @@ -58,7 +58,7 @@ def test___set_value_if_changed_with_list_value___set_same_value___does_not_set_ fake_panel_channel: grpc.Channel, fake_python_panel_service: FakePythonPanelService, ) -> None: - accessor = StreamlitPanelValueAccessor("panel_id", grpc_channel=fake_panel_channel) + accessor = PanelValueAccessor(panel_id="panel_id", grpc_channel=fake_panel_channel) accessor.set_value_if_changed("test_id", [1, 2, 3]) initial_set_count = fake_python_panel_service.servicer.set_count @@ -72,7 +72,7 @@ def test___set_value_if_changed_with_list_value___set_different_value___sets_new fake_panel_channel: grpc.Channel, fake_python_panel_service: FakePythonPanelService, ) -> None: - accessor = StreamlitPanelValueAccessor("panel_id", grpc_channel=fake_panel_channel) + accessor = PanelValueAccessor(panel_id="panel_id", grpc_channel=fake_panel_channel) accessor.set_value_if_changed("test_id", [1, 2, 3]) initial_set_count = fake_python_panel_service.servicer.set_count @@ -86,7 +86,7 @@ def test___set_value_if_changed_with_enum_value___set_same_value___does_not_set_ fake_panel_channel: grpc.Channel, fake_python_panel_service: FakePythonPanelService, ) -> None: - accessor = StreamlitPanelValueAccessor("panel_id", grpc_channel=fake_panel_channel) + accessor = PanelValueAccessor(panel_id="panel_id", grpc_channel=fake_panel_channel) accessor.set_value_if_changed("test_id", MyIntEnum.VALUE20) initial_set_count = fake_python_panel_service.servicer.set_count @@ -100,7 +100,7 @@ def test___set_value_if_changed_with_enum_value___set_different_value___sets_new fake_panel_channel: grpc.Channel, fake_python_panel_service: FakePythonPanelService, ) -> None: - accessor = StreamlitPanelValueAccessor("panel_id", grpc_channel=fake_panel_channel) + accessor = PanelValueAccessor(panel_id="panel_id", grpc_channel=fake_panel_channel) accessor.set_value_if_changed("test_id", MyIntEnum.VALUE20) initial_set_count = fake_python_panel_service.servicer.set_count diff --git a/tests/unit/test_python_panel_service_stub.py b/tests/unit/test_python_panel_service_stub.py index a26f671c..e2521e26 100644 --- a/tests/unit/test_python_panel_service_stub.py +++ b/tests/unit/test_python_panel_service_stub.py @@ -1,7 +1,7 @@ import pytest from google.protobuf.any_pb2 import Any from google.protobuf.wrappers_pb2 import StringValue -from ni.pythonpanel.v1.python_panel_service_pb2 import ( +from ni.panels.v1.panel_service_pb2 import ( StartPanelRequest, StopPanelRequest, EnumeratePanelsRequest, @@ -9,30 +9,37 @@ TryGetValueRequest, SetValueRequest, ) -from ni.pythonpanel.v1.python_panel_service_pb2_grpc import PythonPanelServiceStub +from ni.panels.v1.panel_service_pb2_grpc import PanelServiceStub +from ni.panels.v1.streamlit_panel_configuration_pb2 import StreamlitPanelConfiguration -def test___start_panel___gets_response(python_panel_service_stub: PythonPanelServiceStub) -> None: - request = StartPanelRequest(panel_id="test_panel", panel_script_path="path/to/panel") +def test___start_panel___gets_response(python_panel_service_stub: PanelServiceStub) -> None: + configuration = StreamlitPanelConfiguration(panel_script_path="path/to/panel.py") + configuration_any = Any() + configuration_any.Pack(configuration) + request = StartPanelRequest(panel_id="test_panel", panel_configuration=configuration_any) response = python_panel_service_stub.StartPanel(request) - assert response.panel_url == "http://localhost:50051/test_panel" + assert response.panel_uri == "http://localhost:50051/test_panel" def test___start_panel___stop_panel___gets_response( - python_panel_service_stub: PythonPanelServiceStub, + python_panel_service_stub: PanelServiceStub, ) -> None: - open_request = StartPanelRequest(panel_id="test_panel", panel_script_path="path/to/panel") - python_panel_service_stub.StartPanel(open_request) + configuration = StreamlitPanelConfiguration(panel_script_path="path/to/panel.py") + configuration_any = Any() + configuration_any.Pack(configuration) + start_request = StartPanelRequest(panel_id="test_panel", panel_configuration=configuration_any) + python_panel_service_stub.StartPanel(start_request) - request = StopPanelRequest(panel_id="test_panel", reset=False) - response = python_panel_service_stub.StopPanel(request) + stop_request = StopPanelRequest(panel_id="test_panel", reset=False) + response = python_panel_service_stub.StopPanel(stop_request) assert response is not None # Ensure response is returned def test___enumerate_panels___gets_response( - python_panel_service_stub: PythonPanelServiceStub, + python_panel_service_stub: PanelServiceStub, ) -> None: request = EnumeratePanelsRequest() response = python_panel_service_stub.EnumeratePanels(request) @@ -41,7 +48,7 @@ def test___enumerate_panels___gets_response( def test___set_value___gets_response( - python_panel_service_stub: PythonPanelServiceStub, + python_panel_service_stub: PanelServiceStub, ) -> None: test_value = Any() test_value.Pack(StringValue(value="test_value")) @@ -52,7 +59,7 @@ def test___set_value___gets_response( def test___set_value___get_value___gets_response( - python_panel_service_stub: PythonPanelServiceStub, + python_panel_service_stub: PanelServiceStub, ) -> None: test_value = Any() test_value.Pack(StringValue(value="test_value")) @@ -67,7 +74,7 @@ def test___set_value___get_value___gets_response( def test___no_value___get_value___raises_exception( - python_panel_service_stub: PythonPanelServiceStub, + python_panel_service_stub: PanelServiceStub, ) -> None: request = GetValueRequest(panel_id="test_panel", value_id="test_value") with pytest.raises(Exception): @@ -75,7 +82,7 @@ def test___no_value___get_value___raises_exception( def test___set_value___try_get_value___gets_response( - python_panel_service_stub: PythonPanelServiceStub, + python_panel_service_stub: PanelServiceStub, ) -> None: test_value = Any() test_value.Pack(StringValue(value="test_value")) @@ -90,7 +97,7 @@ def test___set_value___try_get_value___gets_response( def test___no_value___try_get_value___gets_no_value( - python_panel_service_stub: PythonPanelServiceStub, + python_panel_service_stub: PanelServiceStub, ) -> None: request = TryGetValueRequest(panel_id="test_panel", value_id="test_value") response = python_panel_service_stub.TryGetValue(request) diff --git a/tests/unit/test_streamlit_panel.py b/tests/unit/test_streamlit_panel.py index 9b67bf6d..027a7c40 100644 --- a/tests/unit/test_streamlit_panel.py +++ b/tests/unit/test_streamlit_panel.py @@ -6,7 +6,7 @@ from typing_extensions import assert_type import tests.types as test_types -from nipanel import StreamlitPanel, StreamlitPanelValueAccessor +from nipanel import StreamlitPanel, PanelValueAccessor from tests.utils._fake_python_panel_service import FakePythonPanelService @@ -45,7 +45,7 @@ def test___panel___panel_set_value___accessor_gets_same_value( fake_panel_channel: grpc.Channel, ) -> None: panel = StreamlitPanel("my_panel", "path/to/script", grpc_channel=fake_panel_channel) - accessor = StreamlitPanelValueAccessor("my_panel", grpc_channel=fake_panel_channel) + accessor = PanelValueAccessor(panel_id="my_panel", grpc_channel=fake_panel_channel) value_id = "test_id" string_value = "test_value" @@ -58,7 +58,7 @@ def test___panel___accessor_set_value___panel_gets_same_value( fake_panel_channel: grpc.Channel, ) -> None: panel = StreamlitPanel("my_panel", "path/to/script", grpc_channel=fake_panel_channel) - accessor = StreamlitPanelValueAccessor("my_panel", grpc_channel=fake_panel_channel) + accessor = PanelValueAccessor(panel_id="my_panel", grpc_channel=fake_panel_channel) value_id = "test_id" string_value = "test_value" @@ -85,7 +85,9 @@ def test___accessor___set_value___does_not_notify( fake_panel_channel: grpc.Channel, ) -> None: service = fake_python_panel_service - accessor = StreamlitPanelValueAccessor("my_panel", grpc_channel=fake_panel_channel) + accessor = PanelValueAccessor( + panel_id="my_panel", grpc_channel=fake_panel_channel, notify_on_set_value=False + ) assert service.servicer.notification_count == 0 accessor.set_value("value_id", "string_value") diff --git a/tests/utils/_fake_python_panel_service.py b/tests/utils/_fake_python_panel_service.py index 547f0db6..13eef73a 100644 --- a/tests/utils/_fake_python_panel_service.py +++ b/tests/utils/_fake_python_panel_service.py @@ -1,8 +1,8 @@ from concurrent import futures import grpc -from ni.pythonpanel.v1.python_panel_service_pb2_grpc import ( - add_PythonPanelServiceServicer_to_server, +from ni.panels.v1.panel_service_pb2_grpc import ( + add_PanelServiceServicer_to_server, ) from tests.utils._fake_python_panel_servicer import FakePythonPanelServicer @@ -20,7 +20,7 @@ def __init__(self) -> None: def start(self, thread_pool: futures.ThreadPoolExecutor) -> None: """Start the gRPC server and return the port it is bound to.""" self._server = grpc.server(thread_pool) - add_PythonPanelServiceServicer_to_server(self._servicer, self._server) + add_PanelServiceServicer_to_server(self._servicer, self._server) self._port = self._server.add_insecure_port("[::1]:0") self._server.start() diff --git a/tests/utils/_fake_python_panel_servicer.py b/tests/utils/_fake_python_panel_servicer.py index 77d5824c..d6d4c102 100644 --- a/tests/utils/_fake_python_panel_servicer.py +++ b/tests/utils/_fake_python_panel_servicer.py @@ -1,7 +1,7 @@ from typing import Any import grpc -from ni.pythonpanel.v1.python_panel_service_pb2 import ( +from ni.panels.v1.panel_service_pb2 import ( StartPanelRequest, StartPanelResponse, StopPanelRequest, @@ -16,11 +16,12 @@ SetValueRequest, SetValueResponse, ) -from ni.pythonpanel.v1.python_panel_service_pb2_grpc import PythonPanelServiceServicer +from ni.panels.v1.panel_service_pb2_grpc import PanelServiceServicer +from ni.panels.v1.streamlit_panel_configuration_pb2 import StreamlitPanelConfiguration -class FakePythonPanelServicer(PythonPanelServiceServicer): - """Fake implementation of the PythonPanelServicer for testing.""" +class FakePythonPanelServicer(PanelServiceServicer): + """Fake implementation of the PanelServiceServicer for testing.""" def __init__(self) -> None: """Initialize the fake PythonPanelServicer.""" @@ -36,12 +37,14 @@ def StartPanel( # noqa: N802 self, request: StartPanelRequest, context: Any ) -> StartPanelResponse: """Trivial implementation for testing.""" - self._python_path = request.python_path + streamlit_panel_configuration = StreamlitPanelConfiguration() + request.panel_configuration.Unpack(streamlit_panel_configuration) + self._python_path = streamlit_panel_configuration.python_path if self._fail_next_start_panel: self._fail_next_start_panel = False context.abort(grpc.StatusCode.UNAVAILABLE, "Simulated failure") self._start_panel(request.panel_id) - return StartPanelResponse(panel_url=self._get_panel_url(request.panel_id)) + return StartPanelResponse(panel_uri=self._get_panel_uri(request.panel_id)) def StopPanel(self, request: StopPanelRequest, context: Any) -> StopPanelResponse: # noqa: N802 """Trivial implementation for testing.""" @@ -56,7 +59,7 @@ def EnumeratePanels( # noqa: N802 for panel_id in self._panel_ids: panel = PanelInformation( panel_id=panel_id, - panel_url=self._get_panel_url(panel_id), + panel_uri=self._get_panel_uri(panel_id), value_ids=self._panel_value_ids[panel_id], ) response.panels.append(panel) @@ -128,7 +131,7 @@ def _stop_panel(self, reset: bool, panel_id: str) -> None: else: self._panel_is_running[panel_id] = False - def _get_panel_url(self, panel_id: str) -> str: + def _get_panel_uri(self, panel_id: str) -> str: if not self._panel_is_running.get(panel_id, False): return "" return f"http://localhost:50051/{panel_id}"