Feeds:
Posts
Comments

So I’ve been reading a little about metaclasses. As I said before, they are the classes of classes, thus their name.

Here are the first things I found out:

  • Not that important. Everybody, everywhere says not to use them unless absolutely necessary, whatever that means. Every time I read something on the internet regarding metaclasses, somewhere in there it said “but they are rarely used, and you should ask yourself if you really need them”.
  • Metaclasses always inherits from type. Stupid, but I would think that there is some kind of analogy between everything inheriting from type and everything inheriting from object.
  • The __init__ and __new__ are executed only once, that’s when the class is created. It is not executed when an instance of the class is created but only when the instance of the metaclass.
  • Obviously, when you instance a metaclass, the instance is the class. This classes can access the metaclass meta-attributes, but the classes’s instances cannot do that. It’s like they are like… two different parallel worlds. On one hand you have the Metaclasses – Classes world and on the other hand you’ve got the Classes – Objects world. You can, by using some kind of non-standard way, move from one world to the other one, like black holes or sth. like that… =D.
    The same thing happens with the meta-methods. The instances of the metaclass can call the metaclasse’s meta-method, but the class’es instances cannot.

In later posts I’ll try to understand more of these crazy beast, as well as find out where the heck they are used. (Django?)

Twisted – Clients

In the tutorial, there are a couple of ways to write clients. This is quite, really easy and non production state, but it’s useful to learn some few stuff…

from twisted.internet.protocol import Protocol

# This first way just sends a message when the connection is made.
def myClient(Protocol): # It seems that every client should subclass the Protocol class.
    def connectionMade(self):
        self.transport.write("Hello server, it's me!!")
        self.transport.loseConnection()

There is a ClientCreator class that creates clients. This ClientCreator is pretty straight forward and it seems that it’s quite usefull when you just need the client to connect to the server, execute some thing and then lose the connection.

from twisted.internet import reactor
from twisted.internet.protocol import Protocol

def MyProtocol(Protocol):
    def hello_dude(self):
        self.transport.write("Yay, it's me!")

c = ClientCreator(reactor, MyProtocol)
c.connectTCP("localhost", 1234).addCallback(lambda p: p.hello_dude())

So it just connects to the server and sends a message.

The other alternative that the tutorial shows is the one that, via the ClientFactory class, which returns instances of the desired protocol, and the usage of the reactor object, you can have the very same as before and even more…


from twisted.internet.protocol import Protocol, ClientFactory
from sys import stdout

class Echo(Protocol):
    def dataReceived(self, data):
        stdout.write(data)

class EchoClientFactory(ClientFactory):
    def startedConnecting(self, connector):
        print 'Started to connect.'

    def buildProtocol(self, addr):
        print 'Connected.'
        return Echo()

    def clientConnectionLost(self, connector, reason):
        print 'Lost connection.  Reason:', reason

    def clientConnectionFailed(self, connector, reason):
        print 'Connection failed. Reason:', reason

from twisted.internet import reactor
reactor.connectTCP(host, port, EchoClientFactory())
reactor.run()

Protocols (twisted.internet.protocols import Protocol)

Here is where you write the entire logic of the server.
It’s kinda divided in events. Each of these events are called whenever they
appear. The server does not wait for each event, but rather it executes them as
they arrive from the network.
Just by reading the method you should have an idea to which event the method
will respond.

For example…connectionMade, connectionLost, dataReceived

Some examples from the book…


from twisted.internet.protocol import Protocol

class Echo(Protocol):

    def connectionMade(self):
        self.factory.numProtocols = self.factory.numProtocols+1
        if self.factory.numProtocols > 100:
            self.transport.write("Too many connections, try later")
            self.transport.loseConnection()

    def connectionLost(self, reason):
        self.factory.numProtocols = self.factory.numProtocols-1

    def dataReceived(self, data):
        self.transport.write(data)

It is quite straighforward. Whenever a new connection is made, connectionMade is called, it validates whether the number of protocols is < 100, otherwise it looses the connection. This event makes the connectionLost method to get called.

I’m reading the twisted documentation and I’ll post here my notes.
The idea is that these notes become a useful resource for me, to which I’ll
consult whenever I have a doubt.

It seems that Twisted is a networking framework to mainly build asynchronic
applications.

To build these asynchronic apps, twisted abstract itself into the deferred
concept.

A deferred is an object to which the user will attach some callbacks to get
executed whenever a result is present. The problem it solves is the delay of
non-computational tasks, such as networking latency.  So the idea is
that you tell the program to handle data whenever is available using a
deferred object, without blocking the entire thing.

The deferred object will have some callbacks that you’ll attach. When the data
is present, the deferred object will execute each of the callbacks. Oh, BTW,
callbacks can be stacked, so that the result of each callback is the input of
the next one.
If an error occured, then an errback gets called, which you also pass
to the deferred object.

Example using callbacks and errbacks

from twisted.web.client import getPage

from twisted.internet import reactor

def errorHandler(error):
    '''
    This is an 'errback' function, added to the Deferred which will call
    it in the event of an error
    '''

    # this isn't a very effective handling of the error, we just print it out:
    print "An error has occurred: <%s>" % str(error)
    # and then we stop the entire process:
    reactor.stop()

def printContents(contents):
    '''
    This a 'callback' function, added to the Deferred and called by it with
    the page content
    '''

    print contents
    reactor.stop()

# We request a page which doesn't exist in order to demonstrate the
# error chain
deferred = getPage('http://twistedmatrix.com/does-not-exist')

# add the callback to the Deferred to handle the page content
deferred.addCallback(printContents)

# add the errback to the Deferred to handle any errors
deferred.addErrback(errorHandler)

reactor.run()

Learning twisted!

So I downloaded the Twisted Documentation. Besides trying to understand a little more about python per se (I know I know.. I still didn’t write anything regardin Metaclasses… but they’ll come, I promise!) I wanted to learn some more specialized libraries written in purely python.

So I hope to post something related to this subject in the next few days/weeks.

stay tuned.

Metaclasses

Metaclasses are something that someone would rarely use.

So why should I learn this stuff?

Well, because someday I might find something that uses it and I would love to understand what the heck it’ s doing.
So… metaclasses are a like the constructors of objects, but for classes.
It determines how classes are created. (Yes… how classes, not objects, are created)

That’s pretty weird indeed. At least for me. I didn’t know that the construction for classes could be, somehow, manipulated.

Actually, it seems that you can construct classes dynamically, that’s even weirder!! But I’ll try to talk about it later.

Anyways.. I plan to write about metaclases in the future, so, stay tuned!

So I’ ve been reading Michele Simionato’ s “Things to know about Super” series and dude… what a mess. (That Simionato guy really knows sth. about python :P )

Anyway… what I really don’t like is that it confuses the hell out of me. It would just have to be sth like super(params) and that’s it. Call my father’s method and that’s it. And if we are using multiple inheritance then solve it consistently with the MRO stuff.

I don’t know why there are more than one way to use super. It should be only get used to call the instance’s parent.

So far, here is a sum up of the first two articles.

  1. super(cls, obj).method(…) gives you the right bound method to execute, exclusively using the method resolution order.
  2. super(cls, sub_cls).method(…) gives you the right unbound method to execute, exclusively using the method resolution order.
  3. If descr is an attribute descriptor for C, then, the method call c.descr(), actually is a call to descr.__get__(c, type(c)). (Descriptors are classes that, at least, define the method __get__(self, obj, type = None). Used with super in python 2.5.x, d.__repr__.__get__(None, D) will get you a bound method. To get the unbound method, you type d.__repr__.im_func.__get__(None, D)
  4. Unless absolutely necessary, never, ever use super(cls), meaning that never use it with a single argument. It’s not worth the pain.

You can inherit from multiple classes this way:


class A(object): 

    pass

class B(A): 

    pass

class C(A): 

    pass

class D(B,C): # Multiple inheritance

    pass

The diamond problem is a known one for those languages that support multiple inheritance.

Python attacks this tiny little problem with what’s called the Method Resolution Order.

First of all, how do you know which method to call? Well, the first one that appears in the class MRO. That simple.

You can read about the MRO in Michele Simionato’s paper, which explains quite succintinly what this means and how python linearizes the inheritance tree.

If you want to see how and what will get called, just read your class __mro__ tuple.


>>> class A(object): pass
...
>>> class B(A): pass
...
>>> class C(A): pass
...
>>> class D(B,C): pass
...
>>> D.__mro__
(<class '__main__.D'>, <class '__main__.B'>, <class '__main__.C'>, <class '__main__.A'>, <type 'object'>)

So, here if there was a method that was defined in lots of places, it would execute the one that first appears in the __mro__ tuple.


>>> class A(object):
...     def hola(self):
...             print "A"
...
>>> class B(A):
...     def hola(self):
...             print "B"
...
>>> class C(A):
...     def hola(self):
...             print "C"
...
>>> class D(B,C):
...     def hola(self):
...             print "D"
...
>>> d = D()
>>> d.hola()
D
>>> class D(B,C):
...     pass
...
>>> d = D()
>>> d.hola()
B
>>>

Simple uh?

Python Inheritance 101

How to subclass in Python? That’s easy…


class A(object):

    def __init__(self, *args, **kwargs):
        pass

    def hello(self):
        print "Hello, I'm A!"

class B(A):
    def __init__(self, *args, **kwargs):
        A.__init__(self, *args, **kwargs)
        pass

    def hello(self):
        print "Hello, I'm B!"    

    def goodBye(self):
        print "B'bye!"

So here class B inherits from A. And it also overrides the method hello().
So, whenever you call method hello() to an object which is an instance of B,
you’ll get the overriden method.

>>> a = A()
>>> a.hello()
Hello, I'm A!
>>> b = B()
>>> b.hello()
Hello, I'm B!
>>> b.goodBye()
B'bye!

What if I wanted to call, from an instance of b, a method defined in class A? And without
any type casting at all? (In python there is no such thing as type casting)
The only way I found is this….

>>> A
<class 'classes.A'>
>>> A.hello
<unbound method A.hello>
>>> A.hello(b)
Hello, I'm A!

Those unbound method come here quite handy :D .
Anyways, I don’t know if it’s nice or not, but if I ever want to call some base class method,
I’ll use this way (if somebody know another one, please let me know).
Actually, I think it sucks. I don’t know why we should do this kind of hack just to do the equivalent
of a simple “casting”.

The worst syntax is the B.__init__(self, *args, **kwargs) part. That’s horrible. I know that explicit should be better than implicit, but dude… come on, It’s not nice, period.

Anyways…in python, you can subclass from multiple classes, cause python follows the multiple inheritance model.

And, as in any multiple inheritance capable programming language, there are some stuff that has to be treated carefully, such as that diamond problem.

But that’s something for another post.

cya

Jeff Atwood and Joel Spolsky started a new project, which basically is a Q&A site. But is absolutely oriented to programming and technology questions. There is a nice post that talks about “Python hidden features”. Have a look at it and, if you know some “hidden” feature, post it!

Python hidden features

Older Posts »