I have several instances of a python script in my document and I want to make sure they all match each other. I would normally do this by wrapping the script instance in a cluster, but I can’t seem to get my event handlers to work across cluster boundaries.
The way I’m currently handling this is each script has both a local and a global copy of its text stored as sticky variables. This way when I edit one instance, it can update the global reference and expire the other script instances which then notice that they don’t match the global reference and mark themselves as out-of-date.
It would be better if the modified instance could directly edit the other instances, but the IronPython2Component.Text property is read-only. Is there a way for one python script instance to modify the text of another instance?
A different way I found was to have a “master” script component that exports its own text to sc.sticky. (I had to strip out the ‘\r’ characters to get python to parse it.) The rest of the script instances in the document just read the script text from the sticky key and exec() it.
1 Like
Why don’t you put all the shared code in my_module.py
? That’s all that needs to happen to create a Python module. Then in each component do:
import sys
PATH = r'c:\the\path\of\my_module\parent_directory'
try:
original_sys_path = sys.path.copy()
sys.path.append(PATH)
import my_module
finally:
sys.path = original_sys_path
There’s a lot more tools to manage imports in C Python, especially packages, virtual environments and packing libraries for other users, so in C Python it’s frowned on to mess around with sys.path
.
But just to define a single source of truth for your own RhinoPython or GhPython IronPython script, the latter two (venv and pip) aren’t really available. So it’s best to keep it simple in my opinion.
Just don’t save any other .py files in the same directory with the same name as a library something else you’re running needs.
1 Like
I think I prefer to keep the shared code inside the grasshopper document though for now since I only have one project that uses this code. If I end up needing it for something else, then I might split it out.
Would this still work if the grasshopper file is on a network drive and multiple users are accessing it from different computers on the network?
So you should be using a Version Control System (VCS) already. Or at least a very very good system of back ups.
If they’re not all going to import your script from the same central location as I suggested (just the same as your own personal multiple components do), then for multiple users you need to start thinking about issuing versions. It’s work. But it’s much less work than spending hours supporting a user, only to find they’re on an old version of your code and you fixed their issue 4 months ago.
That then naturally leads to a code repo in a VCS (take the time to learn Git, or at least a GUI for Git, or Github. You’ll thank me later if you don’t already know it) with/and an official source of releases, that your users can install from.
It will probably work. It can definitely be made to work, as it’s not asking too much at all, and that’s the benefit of Python. The question is what will it take?
I wouldn’t presume anything integrates with Onedrive at all, without requiring lots of extra work. Let alone Sharepoint. But it’s just another drive in File Explorer at least.
Otherwise Python can read files, run executables with subprocess, and most likely therefore import from, any normal drive, even remote drives. It just uses the operating system’s file system to find modules. It should be fine. Should.
But you need to test that. I don’t know what else is running on your network, and haven’t used every network architecture in existence out there.
On Linux there might be file permission issues, for example.
This would basically be equivalent to option 2) here right (i.e. overwriting the GHPython component Code
property)? If that’s not possible with the new Rhino 8 script editor, that sounds like another regression from GHPython (ping @eirannejad).
I’m using the IronPython component (IronPython2Component
). It doesn’t have a Code
property, but it does have a Text
property that gives read access to the script text.
- First, enable script input on your component by holding Shift and right-clicking.
This is something I was missing. I didn’t realize holding Shift would reveal hidden menu options.