1""" 2Py2/3 compatibility layer 3 4Mostly copied straight from six: 5 http://pypi.python.org/pypi/six/ 6 7""" 8from __future__ import absolute_import 9import psycopg2 10from psycopg2 import extensions 11import json 12 13# If psycopg2 < 2.5, register json type 14psycopg2_version = tuple(psycopg2.__version__.split(' ')[0].split('.')) 15if psycopg2_version < ('2', '5'): 16 JSON_OID = 114 17 newtype = extensions.new_type( 18 (JSON_OID,), "JSON", lambda data, cursor: json.loads(data)) 19 extensions.register_type(newtype) 20 21def with_metaclass(meta, *bases): 22 """Create a base class with a metaclass.""" 23 # This requires a bit of explanation: the basic idea is to make a dummy 24 # metaclass for one level of class instantiation that replaces itself with 25 # the actual metaclass. 26 class metaclass(meta): 27 """The actual metaclass.""" 28 def __new__(cls, name, _, d): 29 return meta(name, bases, d) 30 return type.__new__(metaclass, 'temporary_class', (), {}) 31 32class classproperty(object): 33 """ 34 A descriptor similar to property, but using the class. 35 """ 36 37 def __init__(self, getter): 38 self.getter = getter 39 40 def __get__(self, instance, owner): 41 return self.getter(owner) 42 43 44class hybridmethod(object): 45 """ 46 Decorator allowing to define method which behaves differently 47 if called at the instance or at the class level. 48 """ 49 50 def __init__(self, class_method=None, instance_method=None): 51 self._class_method = class_method 52 self._instance_method = instance_method or class_method 53 54 def instance_method(self, instance_method): 55 """Setter for the instance method.""" 56 self._instance_method = instance_method 57 return self 58 59 def class_method(self, class_method): 60 """Setter for class method.""" 61 self._class_method = class_method 62 return self 63 64 def __get__(self, instance, owner): 65 if instance is None: 66 return self._class_method.__get__(owner, owner.__class__) 67 else: 68 return self._instance_method.__get__(instance, owner) 69