Fran Boon
04/01/2024, 4:13 PMresources={"A2":1})
Currently it seems that this could be pretty easily achieved by (ab)using Hamilton's Tags feature:
@tag(**{"ray.resources": json.dumps({"A2": 1}))
def my_hamilton_node_fn_which_needs_an_A2(...) -> ...:
...
RayGraphAdapter.execute_node() would be modified to:
ray_options = {tag[4:]: json.loads(value) for tag, value in tags.items() if tag.startswith("ray.")}
return ray.remote(raify(node.callable), **ray_options).remote(**kwargs)
Any concerns with taking this approach?
Any better options?Thierry Jean
04/01/2024, 4:23 PMLifecycle hooks constructs that allow you to modify how Hamilton executes nodes via .execute(). These hooks have access to the node tags out of all things. So there should be a straightforward way to delegate to Ray!
Here's some technical documentation to get you thinking. Tagging @Elijah Ben Izzy for additional thoughtsElijah Ben Izzy
04/01/2024, 4:29 PMraify, right?
I like the approach you have actually (tags are reasonable for this), although you could easily add a separate ray_remote decorator that has a specific tag-format that the RayGraphAdapter will understand.
Note, we now have more flexible execution as well — a whole system with a queue/scheduler optionally specifiable.Elijah Ben Izzy
04/01/2024, 4:30 PMNodeExecutionMethod is actually doing the same thing as the graph adapter — it’s the same superclass. So that’s an easy way to go about it. If you want to group/execute groups of nodes on Ray, we have tooling there (though its a little more powerful/harder to use)Fran Boon
04/01/2024, 4:32 PMFran Boon
04/01/2024, 4:49 PMElijah Ben Izzy
04/01/2024, 5:12 PMray_remote decorator it’ll just call out to tags. I think its pretty fair to add into the default, given it will be backwards compatible.Stefan Krawczyk
04/01/2024, 5:41 PMStefan Krawczyk
04/01/2024, 5:50 PMStefan Krawczyk
04/01/2024, 5:54 PMFran Boon
04/01/2024, 6:12 PMray_remote. as the namespace matches the proposed ray_remote decorator, which I am very happy to work on implementing...I guess this should also live in the same file?Stefan Krawczyk
04/01/2024, 6:20 PMh_ray.py or metadata.py ?
If you put it in h_ray.py that will couple the hamilton code module to ray, i.e. you’ll need ray on the path to import the hamilton code. Is that acceptable? (gut says that’s okay).
If you put it in metadata.py the hamilton code will still be “standalone”, but we now have a specific Ray decorator in the main libraray. Hmm. I don’t want to overengineer but specifying resources could be more general than just Ray. But we can always add a more generic one later.Stefan Krawczyk
04/01/2024, 6:21 PMh_ray.py would be cleaner but metadata.py would also work.Fran Boon
04/01/2024, 6:21 PMStefan Krawczyk
04/01/2024, 6:21 PMStefan Krawczyk
04/01/2024, 6:22 PMStefan Krawczyk
04/01/2024, 6:22 PMyou’d just need ray in the python environment for the module import to workso if you can make that assumption —
h_ray.py is fine.Fran Boon
04/01/2024, 6:25 PMStefan Krawczyk
04/01/2024, 6:32 PMFran Boon
04/01/2024, 8:53 PMFran Boon
04/01/2024, 8:57 PMStefan Krawczyk
04/01/2024, 9:02 PMElijah Ben Izzy
04/02/2024, 3:51 AMh_ray code, it keeps it decoupled. Then we can add a more general one? I’m also happy to keep the ray_remote namespace. If the problem is reserved_forbidden being passed through we can bypass that at the tag constructor level, and make _key_allowed not static (there’s no reason it should be).
This should be easy, anything ending with an _ is a reserved kwarg, so you can change the tag kwarg to add bypass_reserved_namespaces_=False , then have ray_remote delegate to the True value of the constructor argument.Fran Boon
04/02/2024, 4:09 PM