dora-rs 0.3.12rc0__cp37-abi3-win_amd64.whl → 0.3.13__cp37-abi3-win_amd64.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 dora-rs might be problematic. Click here for more details.

dora/__init__.pyi CHANGED
@@ -1,100 +1,160 @@
1
- import typing
2
-
3
- import pyarrow
4
-
5
1
  import dora
2
+ import pyarrow
3
+ import typing
6
4
 
7
5
  @typing.final
8
6
  class Enum:
9
- """Generic enumeration.
7
+ """Create a collection of name/value pairs.
8
+
9
+ Example enumeration:
10
+
11
+ >>> class Color(Enum):
12
+ ... RED = 1
13
+ ... BLUE = 2
14
+ ... GREEN = 3
15
+
16
+ Access them by:
17
+
18
+ - attribute access:
19
+
20
+ >>> Color.RED
21
+ <Color.RED: 1>
22
+
23
+ - value lookup:
24
+
25
+ >>> Color(1)
26
+ <Color.RED: 1>
10
27
 
11
- Derive from this class to define new enumerations.
12
- """
28
+ - name lookup:
13
29
 
30
+ >>> Color['RED']
31
+ <Color.RED: 1>
32
+
33
+ Enumerations can be iterated over, and know how many members they have:
34
+
35
+ >>> len(Color)
36
+ 3
37
+
38
+ >>> list(Color)
39
+ [<Color.RED: 1>, <Color.BLUE: 2>, <Color.GREEN: 3>]
40
+
41
+ Methods can be added to enumerations, and members can have their own
42
+ attributes -- see the documentation for details."""
43
+
44
+ @staticmethod
45
+ def __contains__(value: typing.Any) -> bool:
46
+ """Return True if `value` is in `cls`.
47
+
48
+ `value` is in `cls` if:
49
+ 1) `value` is a member of `cls`, or
50
+ 2) `value` is the value of one of the `cls`'s members."""
51
+
52
+ @staticmethod
53
+ def __getitem__(name: typing.Any) -> typing.Any:
54
+ """Return the member matching `name`."""
55
+
56
+ @staticmethod
57
+ def __iter__() -> typing.Any:
58
+ """Return members in definition order."""
59
+
60
+ @staticmethod
61
+ def __len__() -> int:
62
+ """Return the number of members (no aliases)"""
14
63
  __members__: mappingproxy = ...
64
+ __name__: str = ...
65
+ __qualname__: str = ...
15
66
 
16
67
  @typing.final
17
68
  class Node:
18
69
  """The custom node API lets you integrate `dora` into your application.
19
-
20
- It allows you to retrieve input and send output in any fashion you want.
70
+ It allows you to retrieve input and send output in any fashion you want.
21
71
 
22
- Use with:
72
+ Use with:
23
73
 
24
- ```python
25
- from dora import Node
74
+ ```python
75
+ from dora import Node
26
76
 
27
- node = Node()
28
- ```
29
- """
77
+ node = Node()
78
+ ```"""
30
79
 
31
80
  def __init__(self, node_id: str=None) -> None:
32
- """Use the custom node API to embed `dora` into your application.
81
+ """The custom node API lets you integrate `dora` into your application.
82
+ It allows you to retrieve input and send output in any fashion you want.
33
83
 
34
- It allows you to retrieve input and send output in any fashion you want.
84
+ Use with:
35
85
 
36
- Use with:
86
+ ```python
87
+ from dora import Node
37
88
 
38
- ```python
39
- from dora import Node
40
-
41
- node = Node()
42
- ```
43
- """
89
+ node = Node()
90
+ ```"""
44
91
 
45
92
  def dataflow_descriptor(self) -> dict:
46
- """Return the full dataflow descriptor that this node is part of.
93
+ """Returns the full dataflow descriptor that this node is part of.
47
94
 
48
- This method returns the parsed dataflow YAML file.
49
- """
95
+ This method returns the parsed dataflow YAML file."""
50
96
 
51
97
  def dataflow_id(self) -> str:
52
- """Return the dataflow id."""
98
+ """Returns the dataflow id."""
53
99
 
54
100
  def merge_external_events(self, subscription: dora.Ros2Subscription) -> None:
55
101
  """Merge an external event stream with dora main loop.
56
-
57
- This currently only work with ROS2.
58
- """
102
+ This currently only work with ROS2."""
59
103
 
60
104
  def next(self, timeout: float=None) -> dict:
61
105
  """`.next()` gives you the next input that the node has received.
106
+ It blocks until the next event becomes available.
107
+ You can use timeout in seconds to return if no input is available.
108
+ It will return `None` when all senders has been dropped.
109
+
110
+ ```python
111
+ event = node.next()
112
+ ```
62
113
 
63
- It blocks until the next event becomes available.
64
- You can use timeout in seconds to return if no input is available.
65
- It will return `None` when all senders has been dropped.
114
+ You can also iterate over the event stream with a loop
66
115
 
67
- ```python
68
- event = node.next()
69
- ```
116
+ ```python
117
+ for event in node:
118
+ match event["type"]:
119
+ case "INPUT":
120
+ match event["id"]:
121
+ case "image":
122
+ ```"""
70
123
 
71
- You can also iterate over the event stream with a loop
124
+ def node_config(self) -> dict:
125
+ """Returns the node configuration."""
72
126
 
73
- ```python
74
- for event in node:
75
- match event["type"]:
76
- case "INPUT":
77
- match event["id"]:
78
- case "image":
79
- ```
80
- """
127
+ def recv_async(self, timeout: float=None) -> dict:
128
+ """`.recv_async()` gives you the next input that the node has received asynchronously.
129
+ It does not blocks until the next event becomes available.
130
+ You can use timeout in seconds to return if no input is available.
131
+ It will return an Error if the timeout is reached.
132
+ It will return `None` when all senders has been dropped.
133
+
134
+ warning::
135
+ This feature is experimental as pyo3 async (rust-python FFI) is still in development.
136
+
137
+ ```python
138
+ event = await node.recv_async()
139
+ ```
140
+
141
+ You can also iterate over the event stream with a loop"""
81
142
 
82
143
  def send_output(self, output_id: str, data: pyarrow.Array, metadata: dict=None) -> None:
83
144
  """`send_output` send data from the node.
84
145
 
85
- ```python
86
- Args:
87
- output_id: str,
88
- data: pyarrow.Array,
89
- metadata: Option[Dict],
90
- ```
146
+ ```python
147
+ Args:
148
+ output_id: str,
149
+ data: pyarrow.Array,
150
+ metadata: Option[Dict],
151
+ ```
91
152
 
92
- ex:
153
+ ex:
93
154
 
94
- ```python
95
- node.send_output("string", b"string", {"open_telemetry_context": "7632e76"})
96
- ```
97
- """
155
+ ```python
156
+ node.send_output("string", b"string", {"open_telemetry_context": "7632e76"})
157
+ ```"""
98
158
 
99
159
  def __iter__(self) -> typing.Any:
100
160
  """Implement iter(self)."""
@@ -102,70 +162,79 @@ class Node:
102
162
  def __next__(self) -> typing.Any:
103
163
  """Implement next(self)."""
104
164
 
165
+ def __repr__(self) -> str:
166
+ """Return repr(self)."""
167
+
168
+ def __str__(self) -> str:
169
+ """Return str(self)."""
170
+
105
171
  @typing.final
106
172
  class Ros2Context:
107
173
  """ROS2 Context holding all messages definition for receiving and sending messages to ROS2.
108
174
 
109
- By default, Ros2Context will use env `AMENT_PREFIX_PATH` to search for message definition.
175
+ By default, Ros2Context will use env `AMENT_PREFIX_PATH` to search for message definition.
110
176
 
111
- AMENT_PREFIX_PATH folder structure should be the following:
177
+ AMENT_PREFIX_PATH folder structure should be the following:
112
178
 
113
- - For messages: <namespace>/msg/<name>.msg
114
- - For services: <namespace>/srv/<name>.srv
179
+ - For messages: <namespace>/msg/<name>.msg
180
+ - For services: <namespace>/srv/<name>.srv
115
181
 
116
- You can also use `ros_paths` if you don't want to use env variable.
182
+ You can also use `ros_paths` if you don't want to use env variable.
117
183
 
118
- warning::
119
- dora Ros2 bridge functionality is considered **unstable**. It may be changed
120
- at any point without it being considered a breaking change.
184
+ warning::
185
+ dora Ros2 bridge functionality is considered **unstable**. It may be changed
186
+ at any point without it being considered a breaking change.
121
187
 
122
- ```python
123
- context = Ros2Context()
124
- ```
125
- """
188
+ ```python
189
+ context = Ros2Context()
190
+ ```"""
126
191
 
127
- def __init__(self, ros_paths: list[str]=None) -> None:
192
+ def __init__(self, ros_paths: typing.List[str]=None) -> None:
128
193
  """ROS2 Context holding all messages definition for receiving and sending messages to ROS2.
129
194
 
130
- By default, Ros2Context will use env `AMENT_PREFIX_PATH` to search for message definition.
195
+ By default, Ros2Context will use env `AMENT_PREFIX_PATH` to search for message definition.
131
196
 
132
- AMENT_PREFIX_PATH folder structure should be the following:
197
+ AMENT_PREFIX_PATH folder structure should be the following:
133
198
 
134
- - For messages: <namespace>/msg/<name>.msg
135
- - For services: <namespace>/srv/<name>.srv
199
+ - For messages: <namespace>/msg/<name>.msg
200
+ - For services: <namespace>/srv/<name>.srv
136
201
 
137
- You can also use `ros_paths` if you don't want to use env variable.
202
+ You can also use `ros_paths` if you don't want to use env variable.
138
203
 
139
- warning::
140
- dora Ros2 bridge functionality is considered **unstable**. It may be changed
141
- at any point without it being considered a breaking change.
204
+ warning::
205
+ dora Ros2 bridge functionality is considered **unstable**. It may be changed
206
+ at any point without it being considered a breaking change.
142
207
 
143
- ```python
144
- context = Ros2Context()
145
- ```
146
- """
208
+ ```python
209
+ context = Ros2Context()
210
+ ```"""
147
211
 
148
212
  def new_node(self, name: str, namespace: str, options: dora.Ros2NodeOptions) -> dora.Ros2Node:
149
- """Create a new ROS2 node.
213
+ """Create a new ROS2 node
214
+
215
+ ```python
216
+ ros2_node = ros2_context.new_node(
217
+ "turtle_teleop",
218
+ "/ros2_demo",
219
+ Ros2NodeOptions(rosout=True),
220
+ )
221
+ ```
222
+
223
+ warning::
224
+ dora Ros2 bridge functionality is considered **unstable**. It may be changed
225
+ at any point without it being considered a breaking change."""
150
226
 
151
- ```python
152
- ros2_node = ros2_context.new_node(
153
- "turtle_teleop",
154
- "/ros2_demo",
155
- Ros2NodeOptions(rosout=True),
156
- )
157
- ```
227
+ def __repr__(self) -> str:
228
+ """Return repr(self)."""
158
229
 
159
- warning::
160
- dora Ros2 bridge functionality is considered **unstable**. It may be changed
161
- at any point without it being considered a breaking change.
162
- """
230
+ def __str__(self) -> str:
231
+ """Return str(self)."""
163
232
 
164
233
  @typing.final
165
234
  class Ros2Durability:
166
- """DDS 2.2.3.4 DURABILITY."""
235
+ """DDS 2.2.3.4 DURABILITY"""
167
236
 
168
- def __eq__(self, value: object) -> bool:
237
+ def __eq__(self, value: typing.Any) -> bool:
169
238
  """Return self==value."""
170
239
 
171
240
  def __ge__(self, value: typing.Any) -> bool:
@@ -175,7 +244,7 @@ class Ros2Durability:
175
244
  """Return self>value."""
176
245
 
177
246
  def __int__(self) -> None:
178
- """int(self)."""
247
+ """int(self)"""
179
248
 
180
249
  def __le__(self, value: typing.Any) -> bool:
181
250
  """Return self<=value."""
@@ -183,9 +252,14 @@ class Ros2Durability:
183
252
  def __lt__(self, value: typing.Any) -> bool:
184
253
  """Return self<value."""
185
254
 
186
- def __ne__(self, value: object) -> bool:
255
+ def __ne__(self, value: typing.Any) -> bool:
187
256
  """Return self!=value."""
188
257
 
258
+ def __repr__(self) -> str:
259
+ """Return repr(self)."""
260
+
261
+ def __str__(self) -> str:
262
+ """Return str(self)."""
189
263
  Persistent: Ros2Durability = ...
190
264
  Transient: Ros2Durability = ...
191
265
  TransientLocal: Ros2Durability = ...
@@ -193,9 +267,9 @@ class Ros2Durability:
193
267
 
194
268
  @typing.final
195
269
  class Ros2Liveliness:
196
- """DDS 2.2.3.11 LIVELINESS."""
270
+ """DDS 2.2.3.11 LIVELINESS"""
197
271
 
198
- def __eq__(self, value: object) -> bool:
272
+ def __eq__(self, value: typing.Any) -> bool:
199
273
  """Return self==value."""
200
274
 
201
275
  def __ge__(self, value: typing.Any) -> bool:
@@ -205,7 +279,7 @@ class Ros2Liveliness:
205
279
  """Return self>value."""
206
280
 
207
281
  def __int__(self) -> None:
208
- """int(self)."""
282
+ """int(self)"""
209
283
 
210
284
  def __le__(self, value: typing.Any) -> bool:
211
285
  """Return self<=value."""
@@ -213,123 +287,159 @@ class Ros2Liveliness:
213
287
  def __lt__(self, value: typing.Any) -> bool:
214
288
  """Return self<value."""
215
289
 
216
- def __ne__(self, value: object) -> bool:
290
+ def __ne__(self, value: typing.Any) -> bool:
217
291
  """Return self!=value."""
218
292
 
293
+ def __repr__(self) -> str:
294
+ """Return repr(self)."""
295
+
296
+ def __str__(self) -> str:
297
+ """Return str(self)."""
219
298
  Automatic: Ros2Liveliness = ...
220
299
  ManualByParticipant: Ros2Liveliness = ...
221
300
  ManualByTopic: Ros2Liveliness = ...
222
301
 
223
302
  @typing.final
224
303
  class Ros2Node:
225
- """ROS2 Node.
304
+ """ROS2 Node
226
305
 
227
- warnings::
228
- - dora Ros2 bridge functionality is considered **unstable**. It may be changed
229
- at any point without it being considered a breaking change.
230
- - There's a known issue about ROS2 nodes not being discoverable by ROS2
231
- See: https://github.com/jhelovuo/ros2-client/issues/4
232
- """
306
+ warnings::
307
+ - dora Ros2 bridge functionality is considered **unstable**. It may be changed
308
+ at any point without it being considered a breaking change.
309
+ - There's a known issue about ROS2 nodes not being discoverable by ROS2
310
+ See: https://github.com/jhelovuo/ros2-client/issues/4"""
233
311
 
234
312
  def create_publisher(self, topic: dora.Ros2Topic, qos: dora.Ros2QosPolicies=None) -> dora.Ros2Publisher:
235
- """Create a ROS2 publisher.
313
+ """Create a ROS2 publisher
236
314
 
237
- ```python
238
- pose_publisher = ros2_node.create_publisher(turtle_pose_topic)
239
- ```
240
- warnings:
241
- - dora Ros2 bridge functionality is considered **unstable**. It may be changed
242
- at any point without it being considered a breaking change.
243
- """
315
+ ```python
316
+ pose_publisher = ros2_node.create_publisher(turtle_pose_topic)
317
+ ```
318
+ warnings:
319
+ - dora Ros2 bridge functionality is considered **unstable**. It may be changed
320
+ at any point without it being considered a breaking change."""
244
321
 
245
322
  def create_subscription(self, topic: dora.Ros2Topic, qos: dora.Ros2QosPolicies=None) -> dora.Ros2Subscription:
246
- """Create a ROS2 subscription.
247
-
248
- ```python
249
- pose_reader = ros2_node.create_subscription(turtle_pose_topic)
250
- ```
323
+ """Create a ROS2 subscription
251
324
 
252
- Warnings:
253
- - dora Ros2 bridge functionality is considered **unstable**. It may be changed
254
- at any point without it being considered a breaking change.
325
+ ```python
326
+ pose_reader = ros2_node.create_subscription(turtle_pose_topic)
327
+ ```
255
328
 
256
- """
329
+ warnings:
330
+ - dora Ros2 bridge functionality is considered **unstable**. It may be changed
331
+ at any point without it being considered a breaking change."""
257
332
 
258
333
  def create_topic(self, name: str, message_type: str, qos: dora.Ros2QosPolicies) -> dora.Ros2Topic:
259
334
  """Create a ROS2 topic to connect to.
260
335
 
261
- ```python
262
- turtle_twist_topic = ros2_node.create_topic(
263
- "/turtle1/cmd_vel", "geometry_msgs/Twist", topic_qos
264
- )
265
- ```
266
- """
336
+ ```python
337
+ turtle_twist_topic = ros2_node.create_topic(
338
+ "/turtle1/cmd_vel", "geometry_msgs/Twist", topic_qos
339
+ )
340
+ ```"""
341
+
342
+ def __repr__(self) -> str:
343
+ """Return repr(self)."""
344
+
345
+ def __str__(self) -> str:
346
+ """Return str(self)."""
267
347
 
268
348
  @typing.final
269
349
  class Ros2NodeOptions:
270
- """ROS2 Node Options."""
350
+ """ROS2 Node Options"""
271
351
 
272
352
  def __init__(self, rosout: bool=None) -> None:
273
- """ROS2 Node Options."""
353
+ """ROS2 Node Options"""
354
+
355
+ def __repr__(self) -> str:
356
+ """Return repr(self)."""
357
+
358
+ def __str__(self) -> str:
359
+ """Return str(self)."""
274
360
 
275
361
  @typing.final
276
362
  class Ros2Publisher:
277
- """ROS2 Publisher.
278
-
279
- Warnings:
280
- - dora Ros2 bridge functionality is considered **unstable**. It may be changed
281
- at any point without it being considered a breaking change.
363
+ """ROS2 Publisher
282
364
 
283
- """
365
+ warnings:
366
+ - dora Ros2 bridge functionality is considered **unstable**. It may be changed
367
+ at any point without it being considered a breaking change."""
284
368
 
285
369
  def publish(self, data: pyarrow.Array) -> None:
286
370
  """Publish a message into ROS2 topic.
287
371
 
288
- Remember that the data format should respect the structure of the ROS2 message using an arrow Structure.
289
-
290
- ex:
291
- ```python
292
- gripper_command.publish(
293
- pa.array(
294
- [
295
- {
296
- "name": "gripper",
297
- "cmd": np.float32(5),
298
- }
299
- ]
300
- ),
301
- )
302
- ```
303
- """
372
+ Remember that the data format should respect the structure of the ROS2 message using an arrow Structure.
373
+
374
+ ex:
375
+ ```python
376
+ gripper_command.publish(
377
+ pa.array(
378
+ [
379
+ {
380
+ "name": "gripper",
381
+ "cmd": np.float32(5),
382
+ }
383
+ ]
384
+ ),
385
+ )
386
+ ```"""
387
+
388
+ def __repr__(self) -> str:
389
+ """Return repr(self)."""
390
+
391
+ def __str__(self) -> str:
392
+ """Return str(self)."""
304
393
 
305
394
  @typing.final
306
395
  class Ros2QosPolicies:
307
- """ROS2 QoS Policy."""
396
+ """ROS2 QoS Policy"""
308
397
 
309
398
  def __init__(self, durability: dora.Ros2Durability=None, liveliness: dora.Ros2Liveliness=None, reliable: bool=None, keep_all: bool=None, lease_duration: float=None, max_blocking_time: float=None, keep_last: int=None) -> dora.Ros2QoSPolicies:
310
- """ROS2 QoS Policy."""
399
+ """ROS2 QoS Policy"""
400
+
401
+ def __repr__(self) -> str:
402
+ """Return repr(self)."""
403
+
404
+ def __str__(self) -> str:
405
+ """Return str(self)."""
311
406
 
312
407
  @typing.final
313
408
  class Ros2Subscription:
314
- """ROS2 Subscription.
409
+ """ROS2 Subscription
315
410
 
316
- Warnings:
317
- - dora Ros2 bridge functionality is considered **unstable**. It may be changed
318
- at any point without it being considered a breaking change.
319
411
 
320
- """
412
+ warnings:
413
+ - dora Ros2 bridge functionality is considered **unstable**. It may be changed
414
+ at any point without it being considered a breaking change."""
321
415
 
322
416
  def next(self):...
323
417
 
418
+ def __repr__(self) -> str:
419
+ """Return repr(self)."""
420
+
421
+ def __str__(self) -> str:
422
+ """Return str(self)."""
423
+
324
424
  @typing.final
325
425
  class Ros2Topic:
326
- """ROS2 Topic.
426
+ """ROS2 Topic
427
+
428
+ warnings:
429
+ - dora Ros2 bridge functionality is considered **unstable**. It may be changed
430
+ at any point without it being considered a breaking change."""
431
+
432
+ def __repr__(self) -> str:
433
+ """Return repr(self)."""
434
+
435
+ def __str__(self) -> str:
436
+ """Return str(self)."""
327
437
 
328
- Warnings:
329
- - dora Ros2 bridge functionality is considered **unstable**. It may be changed
330
- at any point without it being considered a breaking change.
438
+ def build(dataflow_path: str, uv: bool=None, coordinator_addr: str=None, coordinator_port: int=None, force_local: bool=False) -> None:
439
+ """Build a Dataflow, exactly the same way as `dora build` command line tool."""
331
440
 
332
- """
441
+ def run(dataflow_path: str, uv: bool=None) -> None:
442
+ """Run a Dataflow, exactly the same way as `dora run` command line tool."""
333
443
 
334
444
  def start_runtime() -> None:
335
- """Start a runtime for Operators."""
445
+ """Start a runtime for Operators"""
dora/builder.py ADDED
@@ -0,0 +1,166 @@
1
+ from __future__ import annotations
2
+
3
+ import yaml
4
+
5
+
6
+ class DataflowBuilder:
7
+ """A dora dataflow."""
8
+
9
+ def __init__(self, name: str = "dora-dataflow"):
10
+ self.name = name
11
+ self.nodes = []
12
+
13
+ def add_node(self, id: str, **kwargs) -> Node:
14
+ """Adds a new node to the dataflow."""
15
+ node = Node(id, **kwargs)
16
+ self.nodes.append(node)
17
+ return node
18
+
19
+ def to_yaml(self, path: str = None) -> str | None:
20
+ """Generates the YAML representation of the dataflow."""
21
+ dataflow_spec = {"nodes": [node.to_dict() for node in self.nodes]}
22
+ if path:
23
+ with open(path, "w") as f:
24
+ yaml.dump(dataflow_spec, f)
25
+ return None
26
+ else:
27
+ return yaml.dump(dataflow_spec)
28
+
29
+ def __enter__(self):
30
+ return self
31
+
32
+ def __exit__(self, exc_type, exc_val, exc_tb):
33
+ pass
34
+
35
+
36
+ class Output:
37
+ """Represents an output from a node."""
38
+
39
+ def __init__(self, node: Node, output_id: str):
40
+ self.node = node
41
+ self.output_id = output_id
42
+
43
+ def __str__(self) -> str:
44
+ return f"{self.node.id}/{self.output_id}"
45
+
46
+
47
+ class Node:
48
+ """A node in a dora dataflow."""
49
+
50
+ def __init__(self, id: str, **kwargs):
51
+ self.id = id
52
+ self.config = kwargs
53
+ self.config["id"] = id
54
+ self.operators = []
55
+
56
+ def path(self, path: str) -> Node:
57
+ """Sets the path to the executable or script."""
58
+ self.config["path"] = path
59
+ return self
60
+
61
+ def args(self, args: str) -> Node:
62
+ """Sets the command-line arguments for the node."""
63
+ self.config["args"] = args
64
+ return self
65
+
66
+ def env(self, env: dict) -> Node:
67
+ """Sets the environment variables for the node."""
68
+ self.config["env"] = env
69
+ return self
70
+
71
+ def build(self, build_command: str) -> Node:
72
+ """Sets the build command for the node."""
73
+ self.config["build"] = build_command
74
+ return self
75
+
76
+ def git(
77
+ self, url: str, branch: str = None, tag: str = None, rev: str = None
78
+ ) -> Node:
79
+ """Sets the Git repository for the node."""
80
+ self.config["git"] = url
81
+ if branch:
82
+ self.config["branch"] = branch
83
+ if tag:
84
+ self.config["tag"] = tag
85
+ if rev:
86
+ self.config["rev"] = rev
87
+ return self
88
+
89
+ def add_operator(self, operator: Operator) -> Node:
90
+ """Adds an operator to this node."""
91
+ self.operators.append(operator)
92
+ return self
93
+
94
+ def add_output(self, output_id: str) -> Output:
95
+ """Adds an output to the node and returns an Output object."""
96
+ if "outputs" not in self.config:
97
+ self.config["outputs"] = []
98
+ if output_id not in self.config["outputs"]:
99
+ self.config["outputs"].append(output_id)
100
+ return Output(self, output_id)
101
+
102
+ def add_input(
103
+ self, input_id: str, source: str | Output, queue_size: int = None
104
+ ) -> Node:
105
+ """Adds a user-defined input to the node. Source can be a string or an Output object."""
106
+ if "inputs" not in self.config:
107
+ self.config["inputs"] = {}
108
+
109
+ if isinstance(source, Output):
110
+ source_str = str(source)
111
+ if queue_size is not None:
112
+ self.config["inputs"][input_id] = {
113
+ "source": source_str,
114
+ "queue_size": queue_size,
115
+ }
116
+ else:
117
+ self.config["inputs"][input_id] = source_str
118
+ else:
119
+ if queue_size is not None:
120
+ self.config["inputs"][input_id] = {
121
+ "source": source,
122
+ "queue_size": queue_size,
123
+ }
124
+ else:
125
+ self.config["inputs"][input_id] = source
126
+ return self
127
+
128
+ def to_dict(self) -> dict:
129
+ """Returns the dictionary representation of the node."""
130
+ config = self.config.copy()
131
+ if self.operators:
132
+ config["operators"] = [op.to_dict() for op in self.operators]
133
+ return config
134
+
135
+
136
+ class Operator:
137
+ """An operator in a dora dataflow."""
138
+
139
+ def __init__(
140
+ self,
141
+ id: str,
142
+ name: str = None,
143
+ description: str = None,
144
+ build: str = None,
145
+ python: str = None,
146
+ shared_library: str = None,
147
+ send_stdout_as: str = None,
148
+ ):
149
+ self.id = id
150
+ self.config = {"id": id}
151
+ if name:
152
+ self.config["name"] = name
153
+ if description:
154
+ self.config["description"] = description
155
+ if build:
156
+ self.config["build"] = build
157
+ if python:
158
+ self.config["python"] = python
159
+ if shared_library:
160
+ self.config["shared-library"] = shared_library
161
+ if send_stdout_as:
162
+ self.config["send_stdout_as"] = send_stdout_as
163
+
164
+ def to_dict(self) -> dict:
165
+ """Returns the dictionary representation of the operator."""
166
+ return self.config
dora/dora.pyd CHANGED
Binary file
dora/py.typed ADDED
File without changes
@@ -1,12 +1,11 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: dora-rs
3
- Version: 0.3.12rc0
3
+ Version: 0.3.13
4
4
  Requires-Dist: pyarrow
5
- Summary: `dora` goal is to be a low latency, composable, and distributed data flow.
5
+ Requires-Dist: pyyaml>=6.0
6
6
  License: MIT
7
7
  Requires-Python: >=3.7
8
8
  Description-Content-Type: text/markdown; charset=UTF-8; variant=GFM
9
- Project-URL: Source Code, https://github.com/dora-rs/dora/
10
9
 
11
10
  This crate corresponds to the Node API for Dora.
12
11
 
@@ -0,0 +1,9 @@
1
+ dora/__init__.py,sha256=K87kJCx3z_LKKKSikuEIkkAx4h8qZtS6dB-HzFpz4zc,751
2
+ dora/__init__.pyi,sha256=rwlXqc6RpE9cBq42qN08sFqHpHMb71KD9TxZLkLP3I8,12077
3
+ dora/builder.py,sha256=odH6sUN7ROdVPdU4esIPpmyuJXbo4nuaMOQ5s85mIf0,5122
4
+ dora/cuda.py,sha256=WunE7nb13aIFq5cqkSh52dfZ0KfFm18NU4TofPFopx8,2830
5
+ dora/dora.pyd,sha256=q0ZUZCu-A-C7icbfCHfYWcAT_zZEShDTchYPJt5zCmY,38364160
6
+ dora/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
7
+ dora_rs-0.3.13.dist-info/METADATA,sha256=qP4aJTGoKfiJq4yHMWMH4OqCfsFxiaeS8HkoOXeLet0,528
8
+ dora_rs-0.3.13.dist-info/WHEEL,sha256=0soGNxS0mdPBs8FuoKJYbONpQVGaEwLO8FiDqoHxqMI,94
9
+ dora_rs-0.3.13.dist-info/RECORD,,
@@ -1,4 +1,4 @@
1
1
  Wheel-Version: 1.0
2
- Generator: maturin (1.9.0)
2
+ Generator: maturin (1.9.4)
3
3
  Root-Is-Purelib: false
4
4
  Tag: cp37-abi3-win_amd64
@@ -1,7 +0,0 @@
1
- dora/__init__.py,sha256=K87kJCx3z_LKKKSikuEIkkAx4h8qZtS6dB-HzFpz4zc,751
2
- dora/__init__.pyi,sha256=L-MCRPD_K8RGpzWsfrV28lNh0ast3uNq2-UJZzuJwP8,9483
3
- dora/cuda.py,sha256=WunE7nb13aIFq5cqkSh52dfZ0KfFm18NU4TofPFopx8,2830
4
- dora/dora.pyd,sha256=S5wTsm05Y_iy4MR4f662pIscXiP-oZ5I9bhkE8lW47I,37784576
5
- dora_rs-0.3.12rc0.dist-info/METADATA,sha256=6dteO66PVvK9D__vPfvVbREbUp5isIagZLQHlKf-Xs8,647
6
- dora_rs-0.3.12rc0.dist-info/WHEEL,sha256=G5LfiGOqaNK7XFePKQAOL9sBbuwwBdXf4vgmptkMvPU,94
7
- dora_rs-0.3.12rc0.dist-info/RECORD,,