python-objectbroker/objectbroker/objectbroker.py

116 lines
2.6 KiB
Python

import weakref
import collections
import pickle
from simplelog import log,LLDEBUGCALL,LLDEBUG,LLINFO,LLERROR
from objectbroker import Persistence,NoPersistence
def dump_state(state):
print("Persistent ID: %s" % (state["pid"],))
print("Type: %s.%s" % (state["module"],state["class"]))
print("Non-Persistent:")
for n in state["fields"].keys():
print("K: %s = %s" % (n,state["fields"][n]))
print("Persistent:")
for n in state["pfields"].keys():
print("K: %s = %s" % (n,state["pfields"][n]))
print("")
def obj_getstate(o):
if not isinstance(o, Persistence):
raise TypeError("obj_getstate() needs Persistence object")
state = {}
state["pid"] = Persistence._persistence_id( o )
state["module"] = o.__class__.__module__
state["class"] = o.__class__.__name__
state["fields"] = {}
state["pfields"] = {}
state["pvalues"] = {}
d = object.__getattribute__(o, "__dict__")
for n in d.keys():
a = getattr( o, n )
if (not isinstance( a, collections.Callable)) or isinstance( a, object ):
if (isinstance( a, NoPersistence)):
state["fields"][n] = None
elif (isinstance( a, Persistence)):
state["pvalues"][n] = a
state["pfields"][n] = Persistence._persistence_id( a )
else:
state["fields"][n] = a
return state
class ObjectBroker:
"""ObjectBroker """
def __init__(self, store={}):
self.__store = store
self.__cache = weakref.WeakValueDictionary()
self.__unsaved = {}
log("ObjectBroker instantiated", LLDEBUGCALL)
def save(self,o,recursed=False):
if (o in self.__unsaved):
return
state = obj_getstate(o)
# dump_state( state )
self.__cache[ state["pid"] ] = o
self.__unsaved[o] = state
for pn in state["pvalues"]:
self.save( state["pvalues"][pn], recursed=True )
# dump_state(state)
if not recursed:
for n in list( self.__unsaved.keys() ):
s = self.__unsaved[n]
s["pvalues"] = None
self.__store[ s["pid"] ] = pickle.dumps(s)
del self.__unsaved[n]
return state["pid"]
def load(self,persistence_id):
if (persistence_id in self.__cache):
o = self.__cache[persistence_id]
if not o is None:
return o
state = pickle.loads(self.__store[ persistence_id ])
# dump_state(state)
m = __import__(state["module"],fromlist=[state["class"]])
cls = getattr(m, state["class"] )
o = cls.__new__(cls)
self.__cache[ persistence_id ] = o
for n in state["fields"]:
setattr( o, n, state["fields"][n] )
for n in state["pfields"]:
print("SS: %s = %s" % (n,state["pfields"][n]))
setattr( o, n, self.load( state["pfields"][n] ))
return o
def remove(self,o=None,persistence_id=None):
pass