viam-sdk 0.41.1__py3-none-linux_armv6l.whl → 0.66.0__py3-none-linux_armv6l.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of viam-sdk might be problematic. Click here for more details.
- viam/app/app_client.py +225 -51
- viam/app/billing_client.py +47 -5
- viam/app/data_client.py +771 -234
- viam/app/ml_training_client.py +3 -5
- viam/app/provisioning_client.py +3 -5
- viam/app/viam_client.py +58 -11
- viam/components/arm/arm.py +1 -1
- viam/components/arm/service.py +1 -1
- viam/components/audio_in/__init__.py +24 -0
- viam/components/audio_in/audio_in.py +74 -0
- viam/components/audio_in/client.py +76 -0
- viam/components/audio_in/service.py +83 -0
- viam/components/audio_out/__init__.py +21 -0
- viam/components/audio_out/audio_out.py +72 -0
- viam/components/audio_out/client.py +67 -0
- viam/components/audio_out/service.py +63 -0
- viam/components/base/base.py +1 -1
- viam/components/board/board.py +8 -2
- viam/components/board/client.py +2 -1
- viam/components/board/service.py +1 -0
- viam/components/button/__init__.py +10 -0
- viam/components/button/button.py +41 -0
- viam/components/button/client.py +52 -0
- viam/components/button/service.py +46 -0
- viam/components/camera/camera.py +15 -30
- viam/components/camera/client.py +10 -21
- viam/components/camera/service.py +15 -28
- viam/components/component_base.py +2 -2
- viam/components/gantry/client.py +17 -2
- viam/components/gantry/gantry.py +32 -1
- viam/components/gantry/service.py +21 -5
- viam/components/gripper/__init__.py +2 -0
- viam/components/gripper/client.py +25 -2
- viam/components/gripper/gripper.py +76 -1
- viam/components/gripper/service.py +32 -3
- viam/components/input/input.py +1 -1
- viam/components/motor/motor.py +1 -1
- viam/components/power_sensor/power_sensor.py +1 -1
- viam/components/switch/__init__.py +10 -0
- viam/components/switch/client.py +83 -0
- viam/components/switch/service.py +72 -0
- viam/components/switch/switch.py +98 -0
- viam/gen/app/agent/v1/agent_pb2.py +1 -1
- viam/gen/app/cloudslam/v1/cloud_slam_pb2.py +1 -1
- viam/gen/app/data/v1/data_grpc.py +74 -2
- viam/gen/app/data/v1/data_pb2.py +198 -104
- viam/gen/app/data/v1/data_pb2.pyi +563 -31
- viam/gen/app/datapipelines/__init__.py +0 -0
- viam/gen/app/datapipelines/v1/__init__.py +0 -0
- viam/gen/app/datapipelines/v1/data_pipelines_grpc.py +84 -0
- viam/gen/app/datapipelines/v1/data_pipelines_pb2.py +57 -0
- viam/gen/app/datapipelines/v1/data_pipelines_pb2.pyi +387 -0
- viam/gen/app/dataset/v1/dataset_grpc.py +10 -2
- viam/gen/app/dataset/v1/dataset_pb2.py +8 -4
- viam/gen/app/dataset/v1/dataset_pb2.pyi +36 -1
- viam/gen/app/datasync/v1/data_sync_pb2.py +39 -35
- viam/gen/app/datasync/v1/data_sync_pb2.pyi +21 -8
- viam/gen/app/mlinference/v1/ml_inference_pb2.py +7 -7
- viam/gen/app/mlinference/v1/ml_inference_pb2.pyi +4 -2
- viam/gen/app/mltraining/v1/ml_training_grpc.py +10 -2
- viam/gen/app/mltraining/v1/ml_training_pb2.py +63 -43
- viam/gen/app/mltraining/v1/ml_training_pb2.pyi +112 -7
- viam/gen/app/packages/v1/packages_pb2.py +1 -1
- viam/gen/app/v1/app_grpc.py +74 -3
- viam/gen/app/v1/app_pb2.py +600 -545
- viam/gen/app/v1/app_pb2.pyi +1108 -258
- viam/gen/app/v1/billing_grpc.py +26 -2
- viam/gen/app/v1/billing_pb2.py +52 -36
- viam/gen/app/v1/billing_pb2.pyi +158 -4
- viam/gen/app/v1/end_user_pb2.py +1 -1
- viam/gen/app/v1/robot_pb2.py +95 -89
- viam/gen/app/v1/robot_pb2.pyi +121 -9
- viam/gen/common/v1/common_pb2.py +76 -58
- viam/gen/common/v1/common_pb2.pyi +186 -17
- viam/gen/component/arm/v1/arm_grpc.py +10 -2
- viam/gen/component/arm/v1/arm_pb2.py +5 -3
- viam/gen/component/audioin/__init__.py +0 -0
- viam/gen/component/audioin/v1/__init__.py +0 -0
- viam/gen/component/audioin/v1/audioin_grpc.py +54 -0
- viam/gen/component/audioin/v1/audioin_pb2.py +34 -0
- viam/gen/component/audioin/v1/audioin_pb2.pyi +94 -0
- viam/gen/component/audioinput/v1/audioinput_pb2.py +1 -1
- viam/gen/component/audioout/__init__.py +0 -0
- viam/gen/component/audioout/v1/__init__.py +0 -0
- viam/gen/component/audioout/v1/audioout_grpc.py +54 -0
- viam/gen/component/audioout/v1/audioout_pb2.py +32 -0
- viam/gen/component/audioout/v1/audioout_pb2.pyi +47 -0
- viam/gen/component/base/v1/base_pb2.py +1 -1
- viam/gen/component/board/v1/board_pb2.py +1 -1
- viam/gen/component/button/v1/button_pb2.py +1 -1
- viam/gen/component/camera/v1/camera_grpc.py +1 -0
- viam/gen/component/camera/v1/camera_pb2.py +37 -36
- viam/gen/component/camera/v1/camera_pb2.pyi +31 -4
- viam/gen/component/encoder/v1/encoder_pb2.py +1 -1
- viam/gen/component/gantry/v1/gantry_grpc.py +9 -1
- viam/gen/component/gantry/v1/gantry_pb2.py +5 -3
- viam/gen/component/generic/v1/generic_pb2.py +1 -1
- viam/gen/component/gripper/v1/gripper_grpc.py +18 -2
- viam/gen/component/gripper/v1/gripper_pb2.py +12 -4
- viam/gen/component/gripper/v1/gripper_pb2.pyi +43 -1
- viam/gen/component/inputcontroller/v1/input_controller_pb2.py +1 -1
- viam/gen/component/motor/v1/motor_pb2.py +1 -1
- viam/gen/component/movementsensor/v1/movementsensor_pb2.py +1 -1
- viam/gen/component/posetracker/v1/pose_tracker_pb2.py +1 -1
- viam/gen/component/powersensor/v1/powersensor_pb2.py +1 -1
- viam/gen/component/sensor/v1/sensor_pb2.py +1 -1
- viam/gen/component/servo/v1/servo_pb2.py +1 -1
- viam/gen/component/switch/v1/switch_pb2.py +5 -5
- viam/gen/component/switch/v1/switch_pb2.pyi +9 -2
- viam/gen/component/testecho/v1/testecho_pb2.py +1 -1
- viam/gen/module/v1/module_pb2.py +5 -5
- viam/gen/module/v1/module_pb2.pyi +7 -2
- viam/gen/opentelemetry/__init__.py +0 -0
- viam/gen/opentelemetry/proto/__init__.py +0 -0
- viam/gen/opentelemetry/proto/common/__init__.py +0 -0
- viam/gen/opentelemetry/proto/common/v1/__init__.py +0 -0
- viam/gen/opentelemetry/proto/common/v1/common_grpc.py +0 -0
- viam/gen/opentelemetry/proto/common/v1/common_pb2.py +27 -0
- viam/gen/opentelemetry/proto/common/v1/common_pb2.pyi +208 -0
- viam/gen/opentelemetry/proto/resource/__init__.py +0 -0
- viam/gen/opentelemetry/proto/resource/v1/__init__.py +0 -0
- viam/gen/opentelemetry/proto/resource/v1/resource_grpc.py +0 -0
- viam/gen/opentelemetry/proto/resource/v1/resource_pb2.py +18 -0
- viam/gen/opentelemetry/proto/resource/v1/resource_pb2.pyi +59 -0
- viam/gen/opentelemetry/proto/trace/__init__.py +0 -0
- viam/gen/opentelemetry/proto/trace/v1/__init__.py +0 -0
- viam/gen/opentelemetry/proto/trace/v1/trace_grpc.py +0 -0
- viam/gen/opentelemetry/proto/trace/v1/trace_pb2.py +37 -0
- viam/gen/opentelemetry/proto/trace/v1/trace_pb2.pyi +402 -0
- viam/gen/proto/rpc/examples/echo/v1/echo_pb2.py +1 -1
- viam/gen/proto/rpc/examples/echoresource/v1/echoresource_pb2.py +1 -1
- viam/gen/proto/rpc/v1/auth_pb2.py +1 -1
- viam/gen/proto/rpc/webrtc/v1/grpc_pb2.py +1 -1
- viam/gen/proto/rpc/webrtc/v1/signaling_pb2.py +1 -1
- viam/gen/provisioning/v1/provisioning_grpc.py +10 -2
- viam/gen/provisioning/v1/provisioning_pb2.py +32 -26
- viam/gen/provisioning/v1/provisioning_pb2.pyi +46 -5
- viam/gen/robot/v1/robot_grpc.py +51 -34
- viam/gen/robot/v1/robot_pb2.py +147 -142
- viam/gen/robot/v1/robot_pb2.pyi +153 -86
- viam/gen/service/datamanager/v1/data_manager_grpc.py +11 -2
- viam/gen/service/datamanager/v1/data_manager_pb2.py +15 -8
- viam/gen/service/datamanager/v1/data_manager_pb2.pyi +47 -1
- viam/gen/service/discovery/v1/discovery_pb2.py +1 -1
- viam/gen/service/generic/v1/generic_pb2.py +1 -1
- viam/gen/service/mlmodel/v1/mlmodel_pb2.py +1 -1
- viam/gen/service/motion/v1/motion_pb2.py +92 -62
- viam/gen/service/motion/v1/motion_pb2.pyi +130 -68
- viam/gen/service/navigation/v1/navigation_pb2.py +1 -1
- viam/gen/service/sensors/v1/sensors_pb2.py +1 -1
- viam/gen/service/shell/v1/shell_pb2.py +1 -1
- viam/gen/service/slam/v1/slam_pb2.py +1 -1
- viam/gen/service/slam/v1/slam_pb2.pyi +1 -1
- viam/gen/service/video/__init__.py +0 -0
- viam/gen/service/video/v1/__init__.py +0 -0
- viam/gen/service/video/v1/video_grpc.py +39 -0
- viam/gen/service/video/v1/video_pb2.py +29 -0
- viam/gen/service/video/v1/video_pb2.pyi +72 -0
- viam/gen/service/vision/v1/vision_pb2.py +27 -27
- viam/gen/service/vision/v1/vision_pb2.pyi +28 -3
- viam/gen/service/worldstatestore/__init__.py +0 -0
- viam/gen/service/worldstatestore/v1/__init__.py +0 -0
- viam/gen/service/worldstatestore/v1/world_state_store_grpc.py +55 -0
- viam/gen/service/worldstatestore/v1/world_state_store_pb2.py +39 -0
- viam/gen/service/worldstatestore/v1/world_state_store_pb2.pyi +171 -0
- viam/gen/stream/v1/stream_pb2.py +1 -1
- viam/gen/tagger/v1/tagger_pb2.py +1 -1
- viam/logging.py +9 -8
- viam/media/audio.py +22 -10
- viam/media/utils/pil/__init__.py +5 -1
- viam/media/video.py +54 -40
- viam/module/module.py +85 -16
- viam/module/resource_data_consumer.py +41 -0
- viam/module/service.py +9 -1
- viam/proto/app/__init__.py +68 -0
- viam/proto/app/billing.py +16 -0
- viam/proto/app/data/__init__.py +48 -0
- viam/proto/app/datapipelines/__init__.py +56 -0
- viam/proto/app/dataset/__init__.py +4 -0
- viam/proto/app/mltraining/__init__.py +6 -0
- viam/proto/app/robot.py +6 -0
- viam/proto/common/__init__.py +14 -0
- viam/proto/component/audioin/__init__.py +16 -0
- viam/proto/component/audioout/__init__.py +15 -0
- viam/proto/component/camera/__init__.py +0 -2
- viam/proto/component/gripper/__init__.py +4 -0
- viam/proto/opentelemetry/__init__.py +0 -0
- viam/proto/opentelemetry/proto/__init__.py +0 -0
- viam/proto/opentelemetry/proto/common/__init__.py +15 -0
- viam/proto/opentelemetry/proto/resource/__init__.py +10 -0
- viam/proto/opentelemetry/proto/trace/__init__.py +15 -0
- viam/proto/provisioning/__init__.py +6 -0
- viam/proto/robot/__init__.py +16 -8
- viam/proto/service/datamanager/__init__.py +8 -1
- viam/proto/service/motion/__init__.py +2 -0
- viam/proto/service/video/__init__.py +15 -0
- viam/proto/service/worldstatestore/__init__.py +32 -0
- viam/resource/easy_resource.py +5 -9
- viam/resource/manager.py +4 -3
- viam/resource/registry.py +2 -2
- viam/resource/types.py +2 -2
- viam/robot/client.py +38 -59
- viam/rpc/dial.py +48 -5
- viam/rpc/libviam_rust_utils.so +0 -0
- viam/rpc/server.py +24 -10
- viam/services/motion/client.py +8 -9
- viam/services/motion/motion.py +48 -46
- viam/services/navigation/navigation.py +2 -2
- viam/services/vision/client.py +1 -1
- viam/services/vision/service.py +5 -8
- viam/services/vision/vision.py +5 -3
- viam/services/worldstatestore/__init__.py +18 -0
- viam/services/worldstatestore/client.py +94 -0
- viam/services/worldstatestore/service.py +55 -0
- viam/services/worldstatestore/worldstatestore.py +90 -0
- viam/sessions_client.py +115 -46
- viam/version_metadata.py +2 -2
- {viam_sdk-0.41.1.dist-info → viam_sdk-0.66.0.dist-info}/METADATA +10 -6
- {viam_sdk-0.41.1.dist-info → viam_sdk-0.66.0.dist-info}/RECORD +221 -152
- {viam_sdk-0.41.1.dist-info → viam_sdk-0.66.0.dist-info}/WHEEL +1 -1
- viam/components/audio_input/__init__.py +0 -18
- viam/components/audio_input/audio_input.py +0 -81
- viam/components/audio_input/client.py +0 -70
- viam/components/audio_input/service.py +0 -114
- {viam_sdk-0.41.1.dist-info → viam_sdk-0.66.0.dist-info}/licenses/LICENSE +0 -0
viam/resource/easy_resource.py
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import inspect
|
|
2
2
|
import re
|
|
3
3
|
from abc import ABCMeta
|
|
4
|
-
from typing import Callable, ClassVar, Mapping, Sequence, Union
|
|
4
|
+
from typing import Callable, ClassVar, Mapping, Sequence, Tuple, Union
|
|
5
5
|
|
|
6
6
|
from viam.proto.app.robot import ComponentConfig
|
|
7
7
|
from viam.proto.common import ResourceName
|
|
@@ -113,16 +113,15 @@ class EasyResource:
|
|
|
113
113
|
@classmethod
|
|
114
114
|
def new(cls, config: ComponentConfig, dependencies: Mapping[ResourceName, ResourceBase]):
|
|
115
115
|
"""
|
|
116
|
-
This is passed to register_resource_creator
|
|
116
|
+
This is passed to register_resource_creator. The default implementation only sets the resource name
|
|
117
117
|
when an instance of your model is instantiated. You can override this in your subclass.
|
|
118
118
|
"""
|
|
119
119
|
self = cls(config.name)
|
|
120
120
|
logger.debug("created %s %s %s", cls.API, cls.MODEL, config.name)
|
|
121
|
-
self.reconfigure(config, dependencies)
|
|
122
121
|
return self
|
|
123
122
|
|
|
124
123
|
@classmethod
|
|
125
|
-
def validate_config(cls, config: ComponentConfig) -> Sequence[str]:
|
|
124
|
+
def validate_config(cls, config: ComponentConfig) -> Tuple[Sequence[str], Sequence[str]]:
|
|
126
125
|
"""This method allows you to validate the configuration object received from the machine,
|
|
127
126
|
as well as to return any implicit dependencies based on that `config`.
|
|
128
127
|
|
|
@@ -130,9 +129,9 @@ class EasyResource:
|
|
|
130
129
|
config (ComponentConfig): The configuration for this resource
|
|
131
130
|
|
|
132
131
|
Returns:
|
|
133
|
-
Sequence[str]:
|
|
132
|
+
Tuple[Sequence[str], Sequence[str]]: One list of required implicit dependencies and one of optional deps.
|
|
134
133
|
"""
|
|
135
|
-
return []
|
|
134
|
+
return [], []
|
|
136
135
|
|
|
137
136
|
@classmethod
|
|
138
137
|
def register(cls):
|
|
@@ -148,6 +147,3 @@ class EasyResource:
|
|
|
148
147
|
cls.MODEL,
|
|
149
148
|
ResourceCreatorRegistration(cls.new, cls.validate_config), # pyright: ignore [reportArgumentType]
|
|
150
149
|
)
|
|
151
|
-
|
|
152
|
-
def reconfigure(self, config: ComponentConfig, dependencies: Mapping[ResourceName, ResourceBase]):
|
|
153
|
-
logger.debug("reconfigure %s %s", self.API, self.MODEL)
|
viam/resource/manager.py
CHANGED
|
@@ -103,10 +103,11 @@ class ResourceManager:
|
|
|
103
103
|
try:
|
|
104
104
|
resource = self.resources[name]
|
|
105
105
|
await resource.close()
|
|
106
|
-
except Exception as e:
|
|
107
|
-
raise e
|
|
108
106
|
finally:
|
|
109
|
-
|
|
107
|
+
try:
|
|
108
|
+
del self.resources[name]
|
|
109
|
+
except KeyError:
|
|
110
|
+
pass
|
|
110
111
|
|
|
111
112
|
async def close(self):
|
|
112
113
|
"""Close the resourcce manager by removing all resources.
|
viam/resource/registry.py
CHANGED
|
@@ -27,7 +27,7 @@ class ResourceCreatorRegistration:
|
|
|
27
27
|
"""A function that can create a resource given a mapping of dependencies (``ResourceName`` to ``ResourceBase``
|
|
28
28
|
"""
|
|
29
29
|
|
|
30
|
-
validator: "Validator" = lambda x: []
|
|
30
|
+
validator: "Validator" = lambda x: ([], [])
|
|
31
31
|
"""A function that can validate a resource and return implicit dependencies.
|
|
32
32
|
|
|
33
33
|
If called without a validator function, default to a function returning an empty Sequence
|
|
@@ -170,7 +170,7 @@ class Registry:
|
|
|
170
170
|
try:
|
|
171
171
|
return cls._RESOURCES[f"{api}/{model}"].validator
|
|
172
172
|
except AttributeError:
|
|
173
|
-
return lambda x: []
|
|
173
|
+
return lambda x: ([], [])
|
|
174
174
|
except KeyError:
|
|
175
175
|
raise ResourceNotFoundError(api.resource_type, api.resource_subtype)
|
|
176
176
|
|
viam/resource/types.py
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import re
|
|
2
2
|
import sys
|
|
3
|
-
from typing import TYPE_CHECKING, Callable, ClassVar, Mapping, Optional, Protocol, Sequence, runtime_checkable
|
|
3
|
+
from typing import TYPE_CHECKING, Callable, ClassVar, Mapping, Optional, Protocol, Sequence, Tuple, runtime_checkable
|
|
4
4
|
|
|
5
5
|
if sys.version_info >= (3, 10):
|
|
6
6
|
from typing import TypeAlias
|
|
@@ -203,7 +203,7 @@ def resource_name_from_string(string: str) -> ResourceName:
|
|
|
203
203
|
|
|
204
204
|
|
|
205
205
|
ResourceCreator: TypeAlias = Callable[[ComponentConfig, Mapping[ResourceName, "ResourceBase"]], "ResourceBase"]
|
|
206
|
-
Validator: TypeAlias = Callable[[ComponentConfig], Sequence[str]]
|
|
206
|
+
Validator: TypeAlias = Callable[[ComponentConfig], Tuple[Sequence[str], Sequence[str]]]
|
|
207
207
|
|
|
208
208
|
|
|
209
209
|
@runtime_checkable
|
viam/robot/client.py
CHANGED
|
@@ -1,6 +1,5 @@
|
|
|
1
1
|
import asyncio
|
|
2
2
|
import sys
|
|
3
|
-
import warnings
|
|
4
3
|
from dataclasses import dataclass
|
|
5
4
|
from datetime import datetime
|
|
6
5
|
from threading import RLock
|
|
@@ -18,10 +17,6 @@ from viam.proto.common import LogEntry, PoseInFrame, ResourceName, Transform
|
|
|
18
17
|
from viam.proto.robot import (
|
|
19
18
|
BlockForOperationRequest,
|
|
20
19
|
CancelOperationRequest,
|
|
21
|
-
DiscoverComponentsRequest,
|
|
22
|
-
DiscoverComponentsResponse,
|
|
23
|
-
Discovery,
|
|
24
|
-
DiscoveryQuery,
|
|
25
20
|
FrameSystemConfig,
|
|
26
21
|
FrameSystemConfigRequest,
|
|
27
22
|
FrameSystemConfigResponse,
|
|
@@ -40,6 +35,7 @@ from viam.proto.robot import (
|
|
|
40
35
|
Operation,
|
|
41
36
|
ResourceNamesRequest,
|
|
42
37
|
ResourceNamesResponse,
|
|
38
|
+
RestartModuleRequest,
|
|
43
39
|
RobotServiceStub,
|
|
44
40
|
ShutdownRequest,
|
|
45
41
|
StopAllRequest,
|
|
@@ -52,7 +48,7 @@ from viam.resource.manager import ResourceManager
|
|
|
52
48
|
from viam.resource.registry import Registry
|
|
53
49
|
from viam.resource.rpc_client_base import ReconfigurableResourceRPCClientBase, ResourceRPCClientBase
|
|
54
50
|
from viam.resource.types import API, RESOURCE_TYPE_COMPONENT, RESOURCE_TYPE_SERVICE
|
|
55
|
-
from viam.rpc.dial import DialOptions, ViamChannel, dial
|
|
51
|
+
from viam.rpc.dial import DialOptions, ViamChannel, _dial_inner, dial
|
|
56
52
|
from viam.services.service_base import ServiceBase
|
|
57
53
|
from viam.sessions_client import SessionsClient
|
|
58
54
|
from viam.utils import datetime_to_timestamp, dict_to_struct
|
|
@@ -189,7 +185,7 @@ class RobotClient:
|
|
|
189
185
|
# Replace "<API-KEY-ID>" (including brackets) with your machine's API key ID
|
|
190
186
|
api_key_id='<API-KEY-ID>'
|
|
191
187
|
)
|
|
192
|
-
return await RobotClient.at_address('ADDRESS
|
|
188
|
+
return await RobotClient.at_address('MACHINE ADDRESS', opts)
|
|
193
189
|
|
|
194
190
|
|
|
195
191
|
async def main():
|
|
@@ -207,7 +203,7 @@ class RobotClient:
|
|
|
207
203
|
"""
|
|
208
204
|
logging.setLevel(options.log_level)
|
|
209
205
|
channel = await dial(address, options.dial_options)
|
|
210
|
-
machine = await cls._with_channel(channel, options, True)
|
|
206
|
+
machine = await cls._with_channel(channel, options, True, robot_addr=address)
|
|
211
207
|
machine._address = address
|
|
212
208
|
return machine
|
|
213
209
|
|
|
@@ -242,7 +238,9 @@ class RobotClient:
|
|
|
242
238
|
return await cls._with_channel(channel, options, False)
|
|
243
239
|
|
|
244
240
|
@classmethod
|
|
245
|
-
async def _with_channel(
|
|
241
|
+
async def _with_channel(
|
|
242
|
+
cls, channel: Union[Channel, ViamChannel], options: Options, close_channel: bool, robot_addr: Optional[str] = None
|
|
243
|
+
):
|
|
246
244
|
"""INTERNAL USE ONLY"""
|
|
247
245
|
|
|
248
246
|
self = cls()
|
|
@@ -263,7 +261,7 @@ class RobotClient:
|
|
|
263
261
|
self._options = options
|
|
264
262
|
self._address = self._channel._path if self._channel._path else f"{self._channel._host}:{self._channel._port}"
|
|
265
263
|
self._sessions_client = SessionsClient(
|
|
266
|
-
self._channel, self._address, self._options.dial_options, disabled=self._options.disable_sessions
|
|
264
|
+
self._channel, self._address, self._options.dial_options, disabled=self._options.disable_sessions, robot_addr=robot_addr
|
|
267
265
|
)
|
|
268
266
|
|
|
269
267
|
try:
|
|
@@ -403,7 +401,7 @@ class RobotClient:
|
|
|
403
401
|
try:
|
|
404
402
|
self._sessions_client.reset()
|
|
405
403
|
|
|
406
|
-
channel = await
|
|
404
|
+
channel = await _dial_inner(self._address, self._options.dial_options)
|
|
407
405
|
|
|
408
406
|
client: RobotServiceStub
|
|
409
407
|
if isinstance(channel, Channel):
|
|
@@ -425,6 +423,7 @@ class RobotClient:
|
|
|
425
423
|
direct_dial_address=direct_dial_address,
|
|
426
424
|
dial_options=self._options.dial_options,
|
|
427
425
|
disabled=self._options.disable_sessions,
|
|
426
|
+
robot_addr=self._address,
|
|
428
427
|
)
|
|
429
428
|
|
|
430
429
|
await self.refresh()
|
|
@@ -727,53 +726,6 @@ class RobotClient:
|
|
|
727
726
|
async def transform_point_cloud(self):
|
|
728
727
|
raise NotImplementedError()
|
|
729
728
|
|
|
730
|
-
#######################
|
|
731
|
-
# COMPONENT DISCOVERY #
|
|
732
|
-
#######################
|
|
733
|
-
|
|
734
|
-
async def discover_components(
|
|
735
|
-
self,
|
|
736
|
-
queries: List[DiscoveryQuery],
|
|
737
|
-
) -> List[Discovery]:
|
|
738
|
-
"""
|
|
739
|
-
Deprecated: v0.38.0, use the Discovery Service APIs instead.
|
|
740
|
-
Get a list of discovered potential component configurations, for example listing different supported resolutions. Currently only works for some cameras.
|
|
741
|
-
Returns module names for modules.
|
|
742
|
-
|
|
743
|
-
::
|
|
744
|
-
|
|
745
|
-
from viam.proto.robot import DiscoveryQuery
|
|
746
|
-
|
|
747
|
-
# Define a new discovery query.
|
|
748
|
-
q = DiscoveryQuery(subtype="camera", model="webcam")
|
|
749
|
-
|
|
750
|
-
# Define a list of discovery queries.
|
|
751
|
-
qs = [q]
|
|
752
|
-
|
|
753
|
-
# Get component configurations with these queries.
|
|
754
|
-
component_configs = await machine.discover_components(qs)
|
|
755
|
-
|
|
756
|
-
Args:
|
|
757
|
-
|
|
758
|
-
queries (List[viam.proto.robot.DiscoveryQuery]): The list of component models to lookup potential configurations for.
|
|
759
|
-
|
|
760
|
-
Returns:
|
|
761
|
-
List[Discovery]: A list of discovered potential component configurations.
|
|
762
|
-
|
|
763
|
-
For more information, see `Machine Management API <https://docs.viam.com/appendix/apis/robot/>`_.
|
|
764
|
-
"""
|
|
765
|
-
request = DiscoverComponentsRequest(queries=queries)
|
|
766
|
-
response: DiscoverComponentsResponse = await self._client.DiscoverComponents(request)
|
|
767
|
-
warnings.warn(
|
|
768
|
-
"RobotClient.discover_components is deprecated. It will be removed on March 10 2025. Use the DiscoveryService APIs instead.",
|
|
769
|
-
DeprecationWarning,
|
|
770
|
-
stacklevel=2,
|
|
771
|
-
)
|
|
772
|
-
LOGGER.warning(
|
|
773
|
-
"RobotClient.discover_components is deprecated. It will be removed on March 10 2025. Use the DiscoveryService APIs instead."
|
|
774
|
-
)
|
|
775
|
-
return list(response.discovery)
|
|
776
|
-
|
|
777
729
|
#################
|
|
778
730
|
# MODULE MODELS #
|
|
779
731
|
#################
|
|
@@ -949,10 +901,37 @@ class RobotClient:
|
|
|
949
901
|
config_status = machine_status.config
|
|
950
902
|
|
|
951
903
|
Returns:
|
|
952
|
-
viam.proto.robot.GetMachineStatusResponse: current status of the machine (initializing or running), resources (List[ResourceStatus]) and config of the machine.
|
|
904
|
+
viam.proto.robot.GetMachineStatusResponse: current status of the machine (initializing or running), current status of the resources (List[ResourceStatus]) and the revision of the config of the machine.
|
|
953
905
|
|
|
954
906
|
For more information, see `Machine Management API <https://docs.viam.com/appendix/apis/robot/>`_.
|
|
955
907
|
"""
|
|
956
908
|
|
|
957
909
|
request = GetMachineStatusRequest()
|
|
958
910
|
return await self._client.GetMachineStatus(request)
|
|
911
|
+
|
|
912
|
+
##################
|
|
913
|
+
# Restart Module #
|
|
914
|
+
##################
|
|
915
|
+
|
|
916
|
+
async def restart_module(self, id: Optional[str] = None, name: Optional[str] = None):
|
|
917
|
+
"""
|
|
918
|
+
Restarts a module running on the machine with the given id or name.
|
|
919
|
+
|
|
920
|
+
::
|
|
921
|
+
|
|
922
|
+
await machine.restart_module(id="namespace:module:model", name="my_model")
|
|
923
|
+
|
|
924
|
+
Args:
|
|
925
|
+
id (str): The id matching the module_id field of the registry module in your part configuration.
|
|
926
|
+
name (str): The name matching the name field of the local/registry module in your part configuration.
|
|
927
|
+
|
|
928
|
+
Raises:
|
|
929
|
+
GRPCError: If a module can't be found matching the provided ID or name.
|
|
930
|
+
|
|
931
|
+
For more information, see `Machine Management API <https://docs.viam.com/appendix/apis/robot/>`_.
|
|
932
|
+
"""
|
|
933
|
+
|
|
934
|
+
id = id if id else ""
|
|
935
|
+
name = name if name else ""
|
|
936
|
+
request = RestartModuleRequest(module_id=id, module_name=name)
|
|
937
|
+
await self._client.RestartModule(request)
|
viam/rpc/dial.py
CHANGED
|
@@ -29,9 +29,9 @@ LOGGER = logging.getLogger(__name__)
|
|
|
29
29
|
|
|
30
30
|
@dataclass
|
|
31
31
|
class Credentials:
|
|
32
|
-
"""Credentials to connect to the
|
|
32
|
+
"""Credentials to connect to the machine and app.viam.com."""
|
|
33
33
|
|
|
34
|
-
type: Union[Literal["robot-
|
|
34
|
+
type: Union[Literal["robot-secret"], Literal["api-key"]]
|
|
35
35
|
"""The type of credential
|
|
36
36
|
"""
|
|
37
37
|
|
|
@@ -70,6 +70,14 @@ class DialOptions:
|
|
|
70
70
|
max_reconnect_attempts: int = 3
|
|
71
71
|
"""Max number of times the client attempts to reconnect when connection is lost"""
|
|
72
72
|
|
|
73
|
+
initial_connection_attempts: int = 3
|
|
74
|
+
"""Max number of times the client will attempt to establish an initial connection
|
|
75
|
+
If set to a non-positive integer, then there will be no limit to initial connection attempts"""
|
|
76
|
+
|
|
77
|
+
initial_connection_attempt_timeout: float
|
|
78
|
+
"""Number of seconds before dial connection times out on initial connection attempts
|
|
79
|
+
Defaults to whatever value is set in the `timeout` field"""
|
|
80
|
+
|
|
73
81
|
timeout: float = 20
|
|
74
82
|
"""Number of seconds before the dial connection times out
|
|
75
83
|
Set to 20sec to match _defaultOfferDeadline in goutils/rpc/wrtc_call_queue.go"""
|
|
@@ -85,6 +93,8 @@ class DialOptions:
|
|
|
85
93
|
allow_insecure_with_creds_downgrade: bool = False,
|
|
86
94
|
max_reconnect_attempts: int = 3,
|
|
87
95
|
timeout: float = 20,
|
|
96
|
+
initial_connection_attempts: int = 3,
|
|
97
|
+
initial_connection_attempt_timeout: Optional[float] = None,
|
|
88
98
|
) -> None:
|
|
89
99
|
self.disable_webrtc = disable_webrtc
|
|
90
100
|
self.auth_entity = auth_entity
|
|
@@ -94,6 +104,8 @@ class DialOptions:
|
|
|
94
104
|
self.allow_insecure_with_creds_downgrade = allow_insecure_with_creds_downgrade
|
|
95
105
|
self.max_reconnect_attempts = max_reconnect_attempts
|
|
96
106
|
self.timeout = timeout
|
|
107
|
+
self.initial_connection_attempts = initial_connection_attempts
|
|
108
|
+
self.initial_connection_attempt_timeout = initial_connection_attempt_timeout if initial_connection_attempt_timeout else timeout
|
|
97
109
|
|
|
98
110
|
@classmethod
|
|
99
111
|
def with_api_key(cls, api_key: str, api_key_id: str) -> Self:
|
|
@@ -220,8 +232,9 @@ class _Runtime:
|
|
|
220
232
|
_ptr: ctypes.c_void_p
|
|
221
233
|
|
|
222
234
|
def __init__(self) -> None:
|
|
235
|
+
suffix = "dylib" if sys.platform == "darwin" else "so" if "linux" in sys.platform else "dll"
|
|
223
236
|
LOGGER.debug("Creating new viam-rust-utils runtime")
|
|
224
|
-
libname = pathlib.Path(__file__).parent.absolute() / f"libviam_rust_utils.{
|
|
237
|
+
libname = pathlib.Path(__file__).parent.absolute() / f"libviam_rust_utils.{suffix}"
|
|
225
238
|
self._lib = ctypes.CDLL(libname.__str__())
|
|
226
239
|
self._lib.init_rust_runtime.argtypes = ()
|
|
227
240
|
self._lib.init_rust_runtime.restype = ctypes.c_void_p
|
|
@@ -279,8 +292,38 @@ class _Runtime:
|
|
|
279
292
|
|
|
280
293
|
|
|
281
294
|
async def dial(address: str, options: Optional[DialOptions] = None) -> ViamChannel:
|
|
295
|
+
options = options if options else DialOptions()
|
|
296
|
+
timeout = options.timeout
|
|
297
|
+
options.timeout = options.initial_connection_attempt_timeout
|
|
298
|
+
if options.initial_connection_attempts == 0:
|
|
299
|
+
options.initial_connection_attempts = -1
|
|
300
|
+
attempt_countdown = options.initial_connection_attempts
|
|
301
|
+
exception: Exception
|
|
302
|
+
while attempt_countdown != 0:
|
|
303
|
+
try:
|
|
304
|
+
chan = await _dial_inner(address, options)
|
|
305
|
+
options.timeout = timeout
|
|
306
|
+
return chan
|
|
307
|
+
except Exception as e:
|
|
308
|
+
exception = e
|
|
309
|
+
attempt_countdown -= 1
|
|
310
|
+
# the only way we could get here is if we failed at least once which means we've set the
|
|
311
|
+
# exception, so typechecker concerns about a possibly unbounded variable are unfounded
|
|
312
|
+
raise exception # type: ignore
|
|
313
|
+
|
|
314
|
+
|
|
315
|
+
def _create_chan(path: str) -> Channel:
|
|
316
|
+
if sys.platform == "win32" or sys.platform == "cygwin":
|
|
317
|
+
# we have to use a TCP connection, so we want a host and port for our channel.
|
|
318
|
+
host, port = _host_port_from_url(path)
|
|
319
|
+
return Channel(host=host, port=port, ssl=None)
|
|
320
|
+
# we're not on windows and so can use a UDS
|
|
321
|
+
return Channel(path=path, ssl=None)
|
|
322
|
+
|
|
323
|
+
|
|
324
|
+
async def _dial_inner(address: str, options: Optional[DialOptions] = None) -> ViamChannel:
|
|
282
325
|
async def send_request(event: SendRequest):
|
|
283
|
-
event.metadata["
|
|
326
|
+
event.metadata["viam_client"] = f"python;v{SDK_VERSION};v{API_VERSION}"
|
|
284
327
|
|
|
285
328
|
opts = options if options else DialOptions()
|
|
286
329
|
if opts.disable_webrtc:
|
|
@@ -291,7 +334,7 @@ async def dial(address: str, options: Optional[DialOptions] = None) -> ViamChann
|
|
|
291
334
|
path, path_ptr = await runtime.dial(address, opts)
|
|
292
335
|
if path:
|
|
293
336
|
LOGGER.info(f"Connecting to socket: {path}")
|
|
294
|
-
chan =
|
|
337
|
+
chan = _create_chan(path)
|
|
295
338
|
listen(chan, SendRequest, send_request)
|
|
296
339
|
|
|
297
340
|
def release():
|
viam/rpc/libviam_rust_utils.so
CHANGED
|
Binary file
|
viam/rpc/server.py
CHANGED
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import sys
|
|
1
2
|
from typing import TYPE_CHECKING, Callable, List, Optional
|
|
2
3
|
|
|
3
4
|
from grpclib import GRPCError, Status
|
|
@@ -82,6 +83,24 @@ class Server(ResourceManager):
|
|
|
82
83
|
|
|
83
84
|
event.method_func = log_resource_name
|
|
84
85
|
|
|
86
|
+
async def _serve(
|
|
87
|
+
self,
|
|
88
|
+
host: Optional[str] = "localhost",
|
|
89
|
+
port: Optional[int] = 9090,
|
|
90
|
+
log_level: Optional[int] = logging.INFO,
|
|
91
|
+
*,
|
|
92
|
+
path: Optional[str] = None,
|
|
93
|
+
):
|
|
94
|
+
if path:
|
|
95
|
+
await self._server.start(path=path)
|
|
96
|
+
LOGGER.info(f"Serving on {path}")
|
|
97
|
+
else:
|
|
98
|
+
await self._server.start(host, port)
|
|
99
|
+
LOGGER.info(f"Serving on {host}:{port}")
|
|
100
|
+
await self._server.wait_closed()
|
|
101
|
+
await self.close()
|
|
102
|
+
LOGGER.debug("gRPC server closed")
|
|
103
|
+
|
|
85
104
|
async def serve(
|
|
86
105
|
self,
|
|
87
106
|
host: Optional[str] = "localhost",
|
|
@@ -105,16 +124,11 @@ class Server(ResourceManager):
|
|
|
105
124
|
logging.setLevel(log_level)
|
|
106
125
|
listen(self._server, RecvRequest, self._grpc_recvrequest_handler)
|
|
107
126
|
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
await self.
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
await self._server.start(host, port)
|
|
114
|
-
LOGGER.info(f"Serving on {host}:{port}")
|
|
115
|
-
await self._server.wait_closed()
|
|
116
|
-
await self.close()
|
|
117
|
-
LOGGER.debug("gRPC server closed")
|
|
127
|
+
if sys.platform != "win32":
|
|
128
|
+
with graceful_exit([self._server]):
|
|
129
|
+
await self._serve(host=host, port=port, log_level=log_level, path=path)
|
|
130
|
+
else:
|
|
131
|
+
await self._serve(host=host, port=port, log_level=log_level, path=path)
|
|
118
132
|
|
|
119
133
|
@classmethod
|
|
120
134
|
async def create_and_serve(
|
viam/services/motion/client.py
CHANGED
|
@@ -10,7 +10,6 @@ from viam.proto.common import (
|
|
|
10
10
|
GeoPoint,
|
|
11
11
|
Pose,
|
|
12
12
|
PoseInFrame,
|
|
13
|
-
ResourceName,
|
|
14
13
|
Transform,
|
|
15
14
|
WorldState,
|
|
16
15
|
)
|
|
@@ -54,7 +53,7 @@ class MotionClient(Motion, ReconfigurableResourceRPCClientBase):
|
|
|
54
53
|
|
|
55
54
|
async def move(
|
|
56
55
|
self,
|
|
57
|
-
component_name:
|
|
56
|
+
component_name: str,
|
|
58
57
|
destination: PoseInFrame,
|
|
59
58
|
world_state: Optional[WorldState] = None,
|
|
60
59
|
constraints: Optional[Constraints] = None,
|
|
@@ -77,9 +76,9 @@ class MotionClient(Motion, ReconfigurableResourceRPCClientBase):
|
|
|
77
76
|
|
|
78
77
|
async def move_on_globe(
|
|
79
78
|
self,
|
|
80
|
-
component_name:
|
|
79
|
+
component_name: str,
|
|
81
80
|
destination: GeoPoint,
|
|
82
|
-
movement_sensor_name:
|
|
81
|
+
movement_sensor_name: str,
|
|
83
82
|
obstacles: Optional[Sequence[GeoGeometry]] = None,
|
|
84
83
|
heading: Optional[float] = None,
|
|
85
84
|
configuration: Optional[MotionConfiguration] = None,
|
|
@@ -106,9 +105,9 @@ class MotionClient(Motion, ReconfigurableResourceRPCClientBase):
|
|
|
106
105
|
|
|
107
106
|
async def move_on_map(
|
|
108
107
|
self,
|
|
109
|
-
component_name:
|
|
108
|
+
component_name: str,
|
|
110
109
|
destination: Pose,
|
|
111
|
-
slam_service_name:
|
|
110
|
+
slam_service_name: str,
|
|
112
111
|
configuration: Optional[MotionConfiguration] = None,
|
|
113
112
|
obstacles: Optional[Sequence[Geometry]] = None,
|
|
114
113
|
*,
|
|
@@ -131,7 +130,7 @@ class MotionClient(Motion, ReconfigurableResourceRPCClientBase):
|
|
|
131
130
|
|
|
132
131
|
async def stop_plan(
|
|
133
132
|
self,
|
|
134
|
-
component_name:
|
|
133
|
+
component_name: str,
|
|
135
134
|
*,
|
|
136
135
|
extra: Optional[Mapping[str, ValueTypes]] = None,
|
|
137
136
|
timeout: Optional[float] = None,
|
|
@@ -149,7 +148,7 @@ class MotionClient(Motion, ReconfigurableResourceRPCClientBase):
|
|
|
149
148
|
|
|
150
149
|
async def get_plan(
|
|
151
150
|
self,
|
|
152
|
-
component_name:
|
|
151
|
+
component_name: str,
|
|
153
152
|
last_plan_only: bool = False,
|
|
154
153
|
execution_id: Optional[str] = None,
|
|
155
154
|
*,
|
|
@@ -189,7 +188,7 @@ class MotionClient(Motion, ReconfigurableResourceRPCClientBase):
|
|
|
189
188
|
|
|
190
189
|
async def get_pose(
|
|
191
190
|
self,
|
|
192
|
-
component_name:
|
|
191
|
+
component_name: str,
|
|
193
192
|
destination_frame: str,
|
|
194
193
|
supplemental_transforms: Optional[Sequence[Transform]] = None,
|
|
195
194
|
*,
|