I've run into this problem several times in various flavors.
Option 1 - eval()
When I want to just hack something out quickly, I use eval() or one of it's cousins in the stdlib. Transfer the source to your master, then compile and eval:
src = getSourceFromMaster()
obj = compile(src, "master.py", "exec")
exec(obj)
As long as your transport to get source from client to server is trustworthy and the actions the source needs to take are relatively straightforward, this works. A few times I've needed tighter integration between the master and slave machines, with lots of back and forth processing or complex data structures. In those cases, I use Pyro.
Option 2 - Pyro
Pyro is a full on, cross-platform remote method execution library for Python. I've used it in production environment to send processing from a linux machine to a windows machine and back, and it's been super stable.
Example from their docs:
Master:
# save this as greeting.py
class GreetingMaker(object):
def get_fortune(self, name):
return "Hello, {0}. Here is your fortune message:\n" \
"Behold the warranty -- the bold print giveth and the fine print taketh away.".format(name)
Slave:
# save this as client.py
import greeting
name=raw_input("What is your name? ")
greeting_maker=greeting.GreetingMaker()
print greeting_maker.get_fortune(name)
output:
$ python client.py
What is your name? Irmen
Hello, Irmen. Here is your fortune message:
Behold the warranty -- the bold print giveth and the fine print taketh away.
The super-awesome thing about Pyro is the "import greeting" line in client.py -- that code comes from the server.
If you're starting from a bare OS install, you can push down a python script to host the client code for either with SSH immediately after you spin up the new instance. Then you'll have a nice infrastructure to work within.
I cannot speak in anymore detail to the application of either of these to AWS, nor how they compare to the utilities provided by the AWS infrastructure. Welcome ideas or discussion on it.
fooand then use the compile and exec builtin functions to turn that string into bytecode and execute it on the remote machine. Of course, I still think the best solution is dropping the requirement that you can't install the code on the slave machines.