Rope part 3ΒΆ

Tags: rdf, plone

Miserable bug day. Rdflib integration ==================

Ok, now I'm ready to start the rdflib integration into this boilerplate product:

 # Import of the needed rdflib functionality
 from rdflib.InMemoryTripleStore import InMemoryTripleStore
 from rdflib.Literal import Literal
 from rdflib.Namespace import Namespace

And RopeProduct inherits from InMemoryTripleStore. That should probably be changed to some b-tree based zodb storage, but for the moment it is ok:

 class RopeProduct(Implicit, Persistent, RoleManager, PropertyManager,
                   Item, InMemoryTripleStore):

Ouch, that turned into a two hour obscure bug hunt. I finally figured out that rdflib uses the super() function extensively, which doesn't work for some reason. I started zope within the python console (zopectl debug in zope 2.7 at least) and tried to get at my test rope object. It presented itself as a Acquisition.ImplicitAcquirerWrapper object. Calling super() on that thingy won't work. Now what...

I did put from Acquisition import Implicit, prompted by the ZDG. I'm seeing some talk about "automatically wrapping the object in its context". Apparently the super() method bugs the wrapper object instead of the RopeProduct object... Ok, I'll switch to explicit acquisition to see whether that works:

 from Acquisition import Explicit

That seems to work. Now for some testing: Most of it didn't seem to work. And once something was wrong I got an unclear exceptions.TypeError error message: "TypeError: function takes exactly 2 arguments (1 given)". After another hour I figured out that the error display function was having fits. Probable cause is of course some of the rdflib stuff that I subclassed from. But another two hours didn't help, so I decided to attach a rdflib store to a local variable.

This hack worked. I can now add a triple and view it. A lot isn't right yet, but:

 # Standard zope inclusions: acquisition, persistence in the zope
 # database, access control. Rope isn't a folder containing other
 # things at the moment, so we'll make it into a simple item.
 from Acquisition import Explicit
 from Globals import Persistent
 from AccessControl.Role import RoleManager
 from OFS.SimpleItem import Item

 # Extra: property tab in the management interface and security
 # declarations plus instantiation.
 from OFS.PropertyManager import PropertyManager
 from AccessControl import ClassSecurityInfo
 from Globals import InitializeClass

 # Import of the needed rdflib functionality
 from rdflib.InMemoryTripleStore import InMemoryTripleStore
 from rdflib.Literal import Literal
 from rdflib.Namespace import Namespace

 class RopeProduct(Explicit, Persistent, RoleManager, PropertyManager,
                   Item):
     """
     Rope product class. Makes rdflib available to zope.
     """
     meta_type = 'Rope' # Required by Item baseclass
     security = ClassSecurityInfo()
     manage_options = RoleManager.manage_options + (
         {'label': 'View', 'action': 'index_html'},
         )
     ns_rdf = Namespace("http://www.w3.org/1999/02/22-rdf-syntax-ns#")
     store = InMemoryTripleStore()

     def __init__(self, id):
         self.id = id # id needed by Item baseclass

     security.declarePublic('index_html')
     def index_html(self):
         """
         Dummy index page.
         """
         header = """
         Role product instance
         <p>My id is %s</p>
         """ % self.id
         footer = """
         """
         main = ''
         for s,p,o in self.store.triples((None,None,None)):
             main += '%s %s %s<br>' % (s,p,o)
         return header + main + footer

     security.declarePublic('add')
     def add(self, s, p, o):
         """Adds a triple to the store"""
         self.store.add((self.ns_rdf[s], self.ns_rdf[p], self.ns_rdf[o]))

 def addForm(unknown): # I couldn't really find what 'unknown' does...
     """
     Returns an html form used to instantiate a RopeProduct
     instance.
     """
     return """
     Add Rope

     id: <br>

     """

 def addRope(dispatcher, id):
     """
     Create a new Rope and add it to myself.
     """
     rope = RopeProduct(id)
     dispatcher.Destination()._setObject(id,rope)

 InitializeClass(RopeProduct)

Well, I'm going to relax for a week.

 
vanrees.org logo

About me

My name is Reinout van Rees and I work a lot with Python (programming language) and Django (website framework). I live in The Netherlands and I'm happily married to Annie van Rees-Kooiman.

Weblog feeds

Most of my website content is in my weblog. You can keep up to date by subscribing to the automatic feeds (for instance with Google reader):