A handler can only be registered once
This commit is contained in:
@@ -349,4 +349,5 @@ See LICENSE file for details.
|
||||
|
||||
## Version History
|
||||
* 0.1.0 - Initial release
|
||||
* 0.2.0 - Added custom reference handlers
|
||||
* 0.2.0 - Added custom reference handlers
|
||||
* 0.2.1 - A handler can only be registered once
|
||||
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
|
||||
|
||||
[project]
|
||||
name = "mydbengine"
|
||||
version = "0.2.0"
|
||||
version = "0.2.1"
|
||||
description = "A lightweight, git-inspired database engine that maintains complete history of all modifications"
|
||||
readme = "README.md"
|
||||
requires-python = ">=3.8"
|
||||
|
||||
@@ -9,11 +9,11 @@ TAG_SPECIAL = "__special__"
|
||||
|
||||
class BaseHandler:
|
||||
"""Base class for all handlers. Subclasses must implement is_eligible_for() and tag()."""
|
||||
|
||||
|
||||
def is_eligible_for(self, obj):
|
||||
"""Check if this handler can process the given object."""
|
||||
raise NotImplementedError
|
||||
|
||||
|
||||
def tag(self):
|
||||
"""Return a unique tag identifying this handler type."""
|
||||
raise NotImplementedError
|
||||
@@ -21,11 +21,11 @@ class BaseHandler:
|
||||
|
||||
class BaseInlineHandler(BaseHandler):
|
||||
"""Handler that serializes data directly into the JSON snapshot."""
|
||||
|
||||
|
||||
def serialize(self, obj) -> dict:
|
||||
"""Serialize object to dict for inline storage in JSON snapshot."""
|
||||
raise NotImplementedError
|
||||
|
||||
|
||||
def deserialize(self, data: dict) -> object:
|
||||
"""Deserialize object from dict stored in JSON snapshot."""
|
||||
raise NotImplementedError
|
||||
@@ -33,15 +33,15 @@ class BaseInlineHandler(BaseHandler):
|
||||
|
||||
class BaseRefHandler(BaseHandler):
|
||||
"""Handler that serializes data to refs/ directory using content-addressable storage."""
|
||||
|
||||
|
||||
def serialize_to_bytes(self, obj) -> bytes:
|
||||
"""Serialize object to bytes for storage in refs/. Must be implemented by subclass."""
|
||||
raise NotImplementedError
|
||||
|
||||
|
||||
def deserialize_from_bytes(self, data: bytes) -> object:
|
||||
"""Deserialize object from bytes loaded from refs/. Must be implemented by subclass."""
|
||||
raise NotImplementedError
|
||||
|
||||
|
||||
def serialize(self, obj, ref_helper) -> dict:
|
||||
"""
|
||||
Default implementation: converts object to bytes, saves to refs/, returns dict with tag and digest.
|
||||
@@ -52,10 +52,10 @@ class BaseRefHandler(BaseHandler):
|
||||
from dbengine.serializer import TAG_DIGEST
|
||||
TAG_SPECIAL = "__special__"
|
||||
return {
|
||||
TAG_SPECIAL: self.tag(),
|
||||
TAG_DIGEST: digest
|
||||
TAG_SPECIAL: self.tag(),
|
||||
TAG_DIGEST: digest
|
||||
}
|
||||
|
||||
|
||||
def deserialize(self, data: dict, ref_helper) -> object:
|
||||
"""
|
||||
Default implementation: loads bytes from refs/ using digest, deserializes from bytes.
|
||||
@@ -89,7 +89,7 @@ class DateHandler(BaseInlineHandler):
|
||||
class Handlers:
|
||||
|
||||
def __init__(self, handlers_):
|
||||
self.handlers = handlers_
|
||||
self.handlers = handlers_ or []
|
||||
|
||||
def get_handler(self, obj):
|
||||
if has_tag(obj, TAG_SPECIAL):
|
||||
@@ -102,7 +102,14 @@ class Handlers:
|
||||
return None
|
||||
|
||||
def register_handler(self, handler):
|
||||
for h in self.handlers:
|
||||
if type(h) == type(handler):
|
||||
return # won't register twice the same handler
|
||||
|
||||
self.handlers.append(handler)
|
||||
|
||||
def unregister_handler(self, handler):
|
||||
self.handlers = [h for h in self.handlers if type(h) != type(handler)]
|
||||
|
||||
|
||||
handlers = Handlers([DateHandler()])
|
||||
|
||||
16
tests/test_handlers.py
Normal file
16
tests/test_handlers.py
Normal file
@@ -0,0 +1,16 @@
|
||||
from dbengine.handlers import BaseHandler, handlers
|
||||
|
||||
|
||||
class DummyHandler(BaseHandler):
|
||||
pass
|
||||
|
||||
|
||||
def test_i_can_register_only_once():
|
||||
handlers.register_handler(DummyHandler())
|
||||
count = len(handlers.handlers)
|
||||
|
||||
handlers.register_handler(DummyHandler()) # second time is skipped as the class is already registered
|
||||
assert count == len(handlers.handlers)
|
||||
|
||||
handlers.unregister_handler(DummyHandler()) # clean the handlers list
|
||||
assert len(handlers.handlers) == count - 1
|
||||
Reference in New Issue
Block a user