2010-06-13

Convenient improvised classes in Python

When writing a test suite for a little project I'm working on (multi-part blog post forthcoming), I wanted to return an array of objects from a function. Since they were only going to hold some values that would be passed to another function and then forgotten, I didn't feel like writing a proper class for them. The standard way would be to return a tuple or a dictionary, but I prefer the attribute access notation (foo.bar) to indexing (foo["bar"]), especially when sending the object to some other function that doesn't really care to keep track of what's a normal object and what just happens to be a dictionary because I was lazy.

So, what can be done? Turns you you can both have your cake and eat it too.


class improvise(object):
def __init__(self, **kws):
for (name, value) in kws.items():
setattr(self, name, value)

This little class takes keyword arguments to its constructor, and assigns each key/value pair as attributes on the instance. Use it like this: improvise(from_user=from_user, subject=subject, query=query), and the caller then gets an object that can be used like this: message.subject. Since the class doesn't care about which keyword arguments are used, it can be re-used by every function that wants to return objects without having to declare classes for them.

Chalk up one more for the flexibility of Python. Which, by the way, zooms.

2010-06-06

AIDL callbacks in Android

There are several blog posts on the internet about doing this stuff so you probably can find better descriptions elsewhere. Probably by people that actually knows Android coding better than I do but anyway, this is my first attempt at hacking Android. You can find the source here: http://code.google.com/p/tretris/
So for our first Android app we (that is me and my pals) wanted to make a multiplayer Tetris-clone (I'll probably incur the wrath of the Tetris Company by even writing this blog). After a while we finally figured out that we wanted the game logic implemented in a Service that could run in the background on one device and push updates to game clients on the network and of course display something nice on the device hosting the service.
So, the use of XMPP and and the Smack library for network communication is food for another blog post but to put it simply, smack zooms.

Anyway, implementing a Service in Android isn't all that hard. You extend the android.app.Service class and do interesting stuff in onCreate like constructing a Timer.
You start the service from your activity by calling (you guessed it) startService.

Now we have a running service and there are a few ways to talk to a running service, using intents and messages, using the producer/consumer but I wanted to try my hand on method invocation. The nice thing about a service is that it is running in it's own Linux process but this makes it impossible to simply call methods on it. There is an RPC-mechanism in Android invented to handle this and it isn't as hard as writing WSDL/SOAP-stuff but there are some hoops to jump through.

First off: The interface description. You have to create a description of your RPC methods in Android Interface Description Language (AIDL). A poorly documented and strange language that looks a lot like java interfaces. To be fair, the documentation is brief but as far as I can tell correct and it gets you started.

Since I was using the android plug-in for eclipse it happily let me place the aidl-file amongst the java source and generated the stub classes automatically. So if you create a MyService.aidl with all the right package and import and wierd 'in' modifiers here and there you end up with a MyService java interface generated.

Second: we have a description and the tools works. Now, how do you get a GUI-activity to find the service? Well, you bind to it using intents (like so much else in Android). This is where the lack of closures in java (eerr, dalvik... whatever) becomes painful. Binding to a service is an asynchronous thing, so android makes a callback when the service is bound and running. This is a good thing but makes for messy code.
This is basically what we do:
bindService(serviceIntent, serviceConnection, BIND_AUTO_CREATE);
The serviceIntent is the usual kind of Intent object (in our case naming the implementation class directly). The serviceConnection is an instance of a class implementing the ServiceConnection interface (see it is involved just saying it). The BIND_AUTO_CREATE constant tells Android to create and run the service if it isn't already running.
So we end up with something like:
ServiceConnection serviceConnection = new ServiceConnection() {
public void onServiceDisconnected(ComponentName name) {
...
}

public void onServiceConnected(ComponentName name, IBinder service) {
MyService serviceInstance = MyService.Stub.asInterface(service);
...
}
};
Intent serviceIntent = new Intent(this, XXXService.class);
bindService(serviceIntent, serviceConnection, BIND_AUTO_CREATE);

Wait a minute, what is that Stub doing there? Well, this is just one of those conventions the Android developers put there, it reminds me of the javax.rmi.PortableRemoteObject.narrow and you can think of it in those terms, as a strange kind of cast from generated stub code to what you are really after.
This is pretty sweet, some client cruft and we finally get the methods we expose on the service. Or at least a stub object that can call methods on the service.

Third: How to expose methods on the service. The service must implement the public IBinder onBind(Intent intent) and return an IBinder instance but not only that, an IBinder that can be "narrowed" to the generated interface. The place to find such a class is again the Stub-class on the generated MyService interface. What you do is that you create a sub-class of the Stub-class and return an instance of the sub-class (get the 't' right here). Like this in your service:

private MyService.Stub idlStub = new MyService.Stub() {
public boolean myMethod() throws RemoteException {
...
}
}
So the service has an anonymous subclass of the Stub as a member instance. This anonymous class implements all the methods in your RPC-interface. The anonymous instance also happens to be an IBinder. So what you return from onBind is simpy the idlStub instance.

To recap. The client binds to the service and gets an IBinder back, which it can "narrow" to the interface described in the aidl-file. The service implements a subclass to the generated Stub-class in the interface and returns that subclas for onBind. Easy as 1,2,3, well, actually my head is spinning already :-)

Callbacks: So now we have a GUI-client that can call methods on the service. So let us make the service call back into the GUI-client.
To do that we first define a call back interface, so create a MyCallback.aidl and define the methods that the service should be able to call on the clients. Then add a method on the service for registering clients, the nice thing the Android team did was to make the RPC symmetric, which means that you can use aidl-created interfaces as types for method parameters.
Great, now we have an interface called MyCallbak and a service method called something like registerClient(MyCallback client).
The service side is really easy to implement, there is no Stub voodoo at all, you get an invocation for register client, the method argument is already marshalled and ready to use.
The client side, the one that is to receive the callbacks has some more work to do. It must do the same thing with the Stub-class we did on the service side:

private MyCallback.Stub callback = new MyCallback.Stub() {
...
}

That callback member can then be used as argument to the registerClient(callback);

Conclusion: So does the RPC mechanism in android zoom. Well, it works and is reasonably easy to use but until I see some annotations on interfaces and more automagic I wouldn't say it zooms.