Hi Storm Users,
i played the last days a bit with storm.zope.
Unfortunatly there is no Container for zope.storm,
I´ve looked at the nice z3c.zalchemy [2],
espacially the container implementation.
I have taken the container.py from z3c.zalchemy as
a base for the stormcontainer.py attached to this post.
As i´m using grok[1]. I subclass the container from
grok.Container. But i think this should work in a pure Z3
Environment too. Maybe subclass from zope.container?
I´m waiting for your comments.
Christian
[1] http://grok.zope.org
[2] http://svn.zope.org/z3c.zalchemy/trunk/src/z3c/zalchemy/
import grok
from string import split
from persistent import Persistent
from zope import interface
from zope.component import getUtility
from zope.configuration.name import resolve
from zope.interface import directlyProvides, directlyProvidedBy
from zope.location.interfaces import ILocation
from zope.exceptions.interfaces import UserError
from zope.security.proxy import removeSecurityProxy
from zope.proxy import ProxyBase, sameProxiedObjects
from zope.app.container.contained import Contained
from zope.app.container.contained import NameChooser
from zope.app.container.interfaces import IContained
from zope.app.container.contained import ContainedProxy
from storm.zope.interfaces import IZStorm
from interfaces import IStormContainer
def contained(obj, parent=None, name=None):
"""An implementation of zope.app.container.contained.contained
that doesn't generate events, for internal use.
Borrowed from SQLOS.
"""
if (parent is None):
raise TypeError, 'Must provide a parent'
if not IContained.providedBy(obj):
if ILocation.providedBy(obj):
directlyProvides(obj, IContained, directlyProvidedBy(obj))
else:
obj = ContainedProxy(obj)
oldparent = obj.__parent__
oldname = obj.__name__
if (oldparent is None) or not (oldparent is parent
or sameProxiedObjects(oldparent, parent)):
obj.__parent__ = parent
if oldname != name and name is not None:
obj.__name__ = name
return obj
#class StormNameChooser(NameChooser):
#
# def checkName(self, name, content):
# if isinstance(name, str):
# name = unicode(name)
# elif not isinstance(name, unicode):
# raise TypeError("Invalid name type", type(name))
#
# unproxied = removeSecurityProxy(self.context)
# if not name.startswith(unproxied._class.__name__+'-'):
# raise UserError("Invalid name for Storm object")
# return True
#
# def chooseName(self, name, obj):
# # flush the object to make sure it contains an id
# session = z3c.zalchemy.getSession()
# session.save(obj)
# session.flush()
# return self.context._toStringIdentifier(obj)
class StormContainer(grok.Container):
""" Make a Storm Container for Grok"""
interface.implements(IStormContainer)
def __init__(self):
super(StormContainer,self).__init__()
_className = ''
_class = None
def setClassName(self, name):
self._className = name
self._class=resolve(name)
def getClassName(self):
return self._className
className = property(getClassName, setClassName)
def keys(self):
for name, obj in self.items():
yield name
def values(self):
for name, obj in self.items():
yield obj
def __iter__(self):
return iter(self.keys())
def items(self):
store = getUtility(IZStorm).get('person')
for obj in store.find(self._class):
name = self._toStringIdentifier(obj)
yield (name, contained(obj, self, name) )
def __getitem__(self, name):
if not isinstance(name, basestring):
raise KeyError, "%s is not a string" % name
obj = self._fromStringIdentifier(name)
if obj is None:
raise KeyError(name)
return contained(obj, self, name)
def get(self, name, default=None):
try:
return self[name]
except KeyError:
return default
def __contains__(self, name):
return self.get(name) is not None
def __len__(self):
try:
store = getUtility(IZStorm).get('person')
query = store.find(self._class)
return query.count()
except:
# we don't want an exception in case of database problems
return 0
def __delitem__(self, name):
obj = self[name]
#TODO: better delete objects using a delete adapter
# for dependency handling.
store = getUtility(IZStorm).get('person')
store.delete(obj)
store.flush()
store.commit()
def __setitem__(self, name, item):
store = getUtility(IZStorm).get('person')
store.add(item)
store.flush()
store.commit()
def _toStringIdentifier(self, obj):
store = getUtility(IZStorm).get('person')
ident = self._getInstanceKey(obj)
prefix = "%s-" %self._class.__name__
return "%s%s" %(prefix, ident)
def _fromStringIdentifier(self, name):
prefix = "%s-" %self._class.__name__
if not str(name).startswith(prefix):
return None
store = getUtility(IZStorm).get('person')
name, id = name.split('-')
for obj in store.find(self._class):
if self._getInstanceKey(obj) == str(id):
return obj
return
def _getInstanceKey(self, obj):
""" Get an unique id form obj """
ident=""
for id in obj.__storm_object_info__.get('primary_vars'):
ident += str(id._value)
return ident
--
storm mailing list
[email protected]
Modify settings or unsubscribe at:
https://lists.ubuntu.com/mailman/listinfo/storm