[Python-Dev] object capability; func_closure; __subclasses__

tav tav at espians.com
Thu Jun 28 03:04:42 CEST 2007


rehi all,

I have been looking at the object capability + Python discussions for
a while now, and was wondering what the use cases for
``object.__subclasses__`` and ``FunctionType.func_closure`` were?

I don't see __subclasses__ used anywhere in the standard library. And
whilst I can see exposing func_closure as being useful in terms of
"cloning/modifying" an existing function, isn't it possible to do that
without making it introspectable?

Years ago, Ka-Ping Yee pointed out:

  http://mail.python.org/pipermail/python-dev/2003-March/034284.html

Derived from this we get:

# capability.py functions

def Namespace(*args, **kwargs):

    for arg in args:
        kwargs[arg.__name__] = arg

    def get(key):
        return kwargs.get(key)

    return get

class Getter(object):

    def __init__(self, getter):
        self.getter = getter

    def __repr__(self):
        return self.getter('__repr__') or object.__repr__(self)

    def __getattr__(self, attr):
        return self.getter(attr)

# io.py module

def FileReader(name):

    file = open(name, 'r')

    def __repr__():
        return '<FileReader: %r>' % name

    def read(bufsize=-1):
        return file.read(bufsize)

    def close():
        return file.close()

    return Getter(Namespace(__repr__, read, close))

----

Now, a process A -- which has full access to all objects -- can do:

  >>> motd = FileReader('/etc/motd')

And pass it to "process B" operating in a limited scope, which can then call:

  >>> motd.read()
  >>> motd.close()

But not:

  >>> motd = type(motd)(motd.name, 'w')

which would have been possible *had* motd been created as a ``file``
type by calling: ``open('/etc/motd', 'r')``.

Now, there are probably a million holes in this approach, but as long
as process B's __import__ is sanitised and it operates in a "limited"
scope with regards to references to other functionality, this seems to
be relatively secure.

However, this is where __subclasses__ and func_closure get in the way.

With object.__subclasses__ (as Brett points out), all defined
classes/types are available -- including the ``file`` type we were
trying to deny process B access to! Is it necessary to expose this
attribute publically?

And, likewise with func_closure, one can do
motd.read.func_closure[0].cell_contents and get hold of the original
``file`` object. Is it absolutely necessary to expose func_closure in
this way?

Now, whilst probably wrong, I can see myself being able to create a
minimal object capability system in pure python if those 2 "features"
disappeared. Am I missing something obvious that prevents me from
doing that?

Can we get rid of them for Python 2.6? Or even 2.5.2? Is anyone
besides PJE actually using them? ;p

Thanks in advance for your thoughts.

-- 
love, tav
founder and ceo, esp metanational llp

plex:espians/tav | tav at espians.com | +44 (0) 7809 569 369


More information about the Python-Dev mailing list