Commit f419f974 authored by Julien Muchembled's avatar Julien Muchembled

storage: define interface for backends and check they implement it

parent c6b80f7b
#
# Copyright (C) 2015 Nexedi SA
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 2
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
import inspect
from functools import wraps
def implements(obj, ignore=()):
tobj = type(obj)
ignore = set(ignore)
not_implemented = []
for name in dir(obj):
method = getattr(obj if issubclass(tobj, type) or name in obj.__dict__
else tobj, name)
if inspect.ismethod(method):
try:
method.__abstract__
ignore.remove(name)
except KeyError:
not_implemented.append(name)
except AttributeError:
not_implemented.extend(func.__name__
for func in getattr(method, "__requires__", ())
if not hasattr(obj, func.__name__))
assert not ignore, ignore
assert not not_implemented, not_implemented
return obj
def _set_code(func):
args, varargs, varkw, _ = inspect.getargspec(func)
if varargs:
args.append("*" + varargs)
if varkw:
args.append("**" + varkw)
exec "def %s(%s): raise NotImplementedError\nf = %s" % (
func.__name__, ",".join(args), func.__name__)
func.func_code = f.func_code
def abstract(func):
_set_code(func)
func.__abstract__ = 1
return func
def requires(*args):
for func in args:
_set_code(func)
def decorator(func):
func.__requires__ = args
return func
return decorator
......@@ -17,7 +17,6 @@
LOG_QUERIES = False
from neo.lib.exception import DatabaseFailure
from .manager import DatabaseManager
DATABASE_MANAGER_DICT = {
'Importer': 'importer.ImporterDatabaseManager',
......
......@@ -23,10 +23,13 @@ from ConfigParser import SafeConfigParser
from ZODB.config import storageFromString
from ZODB.POSException import POSKeyError
from . import buildDatabaseManager, DatabaseManager
from . import buildDatabaseManager
from .manager import DatabaseManager
from neo.lib import logging, patch, util
from neo.lib.exception import DatabaseFailure
from neo.lib.protocol import CellStates, ZERO_OID, ZERO_TID, ZERO_HASH, MAX_TID
from neo.lib.interfaces import implements
from neo.lib.protocol import BackendNotImplemented, CellStates, \
MAX_TID, ZERO_HASH, ZERO_OID, ZERO_TID
patch.speedupFileStorageTxnLookup()
......@@ -280,6 +283,9 @@ class ImporterDatabaseManager(DatabaseManager):
def __init__(self, *args, **kw):
super(ImporterDatabaseManager, self).__init__(*args, **kw)
self.db._connect()
implements(self, """_getNextTID checkSerialRange checkTIDRange
deleteObject deleteTransaction dropPartitions getLastTID
getReplicationObjectList getTIDList nonempty""".split())
_uncommitted_data = property(
lambda self: self.db._uncommitted_data,
......@@ -549,3 +555,8 @@ class ImporterDatabaseManager(DatabaseManager):
length, partition)
return r
def getObjectHistory(self, *args, **kw):
raise BackendNotImplemented(self.getObjectHistory)
def pack(self, *args, **kw):
raise BackendNotImplemented(self.pack)
This diff is collapsed.
......@@ -28,10 +28,11 @@ import string
import struct
import time
from . import DatabaseManager, LOG_QUERIES
from .manager import CreationUndone, splitOIDField
from . import LOG_QUERIES
from .manager import CreationUndone, DatabaseManager, splitOIDField
from neo.lib import logging, util
from neo.lib.exception import DatabaseFailure
from neo.lib.interfaces import implements
from neo.lib.protocol import CellStates, ZERO_OID, ZERO_TID, ZERO_HASH
......@@ -40,6 +41,7 @@ def getPrintableQuery(query, max=70):
else '\\x%02x' % ord(c) for c in query)
@implements
class MySQLDatabaseManager(DatabaseManager):
"""This class manages a database on MySQL."""
......
......@@ -20,10 +20,11 @@ from hashlib import sha1
import string
import traceback
from . import DatabaseManager, LOG_QUERIES
from .manager import CreationUndone, splitOIDField
from . import LOG_QUERIES
from .manager import CreationUndone, DatabaseManager, splitOIDField
from neo.lib import logging, util
from neo.lib.exception import DatabaseFailure
from neo.lib.interfaces import implements
from neo.lib.protocol import CellStates, ZERO_OID, ZERO_TID, ZERO_HASH
def unique_constraint_message(table, *columns):
......@@ -57,6 +58,7 @@ def retry_if_locked(f, *args):
raise
@implements
class SQLiteDatabaseManager(DatabaseManager):
"""This class manages a database on SQLite.
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment