我有这样的代码正常工作:
def get_timestamp(ts):
return datetime.utcfromtimestamp(ts)
def set_timestamp(dt):
return time.mktime(dt.timetuple())
class Group(Base):
__tablename__ = 'group'
_created = Column('created', Integer, nullable=False)
@property
def created(self):
return get_timestamp(self._created)
@created.setter
def created(self, value):
self._created = set_timestamp(value)
我想要一些这样的代码,但它不起作用:
created = synonym('_created',
descriptor=property(get_timestamp,
set_created))
因为它总是以self
作为第一个参数传递。
我希望在我的事业项目中使用get_timestamp
和set_timestamp
。所以我不打算让他们成为班级的方法,而是独立的功能。
我怎样才能做到这一点?
编辑:我会接受Option2,仍然可以接受其他答案。
答案 0 :(得分:1)
选项-1 :以下代码应该有效(您无需为了定义self
而拥有一个类):
def pget_timestamp(self):
return datetime.utcfromtimestamp(self._created)
def pset_timestamp(self, dt):
self._created = time.mktime(dt.timetuple())
class Group(Base):
__tablename__ = 'group'
id = Column(Integer, primary_key=True)
_created = Column('created', Integer, nullable=False)
created = synonym(_created,
descriptor=property(pget_timestamp, pset_timestamp),
)
选项-2 :如果您在许多课程中确实需要相同的内容,请使用Mixins
from sqlalchemy.ext.declarative import declared_attr
class _CreatedMixin(object):
_created = Column('created', Integer, nullable=False)
def pget_timestamp(self):
return datetime.utcfromtimestamp(self._created)
def pset_timestamp(self, dt):
self._created = time.mktime(dt.timetuple())
@declared_attr
def created(cls):
return synonym('_created',
descriptor=property(cls.pget_timestamp, cls.pset_timestamp),
)
class Group(_CreatedMixin, Base):
# @note: adding *_CreatedMixin* to bases defines both the column and the synonym
__tablename__ = 'group'
id = Column(Integer, primary_key=True)
或者,如果这是针对您的课程的所有,那么您可以为所有模型制作_CreatedMixin
基类:
Base = declarative_base(engine, cls=_CreatedMixin)
class Group(Base):
__tablename__ = 'group'
id = Column(Integer, primary_key=True)
选项-3 :您可以使用Hybrid Attributes
注意:使您的set / get函数同步:两者都使用或不使用启用UTC的功能。目前(除非你是UTC-0)将一个值设置为created
将不会返回相同的值。
答案 1 :(得分:0)
我现在正在使用不同的实现。它与原始标题无关,但如果您需要它。
使用sqlalchemy.types.TypeDecorator
。 Defining a table with sqlalchemy with a mysql unix timestamp
class UTCTimestampType(TypeDecorator):
impl = Integer
def process_bind_param(self, value, dialect):
if value is None:
return None # support nullability
elif isinstance(value, datetime):
return int(time.mktime(value.timetuple()))
raise ValueError("Can operate only on datetime values. Offending value type: {0}".format(type(value).__name__))
def process_result_value(self, value, dialect):
if value is not None: # support nullability
return datetime.fromtimestamp(float(value))
class ModelA(Base):
__tablename__ = 'model_a'
id = Column(Integer, primary_key=True)
created = Column(UTCTimestampType, nullable=False)
关于alembic的问题。 Alembic: How to migrate custom type in a model?
# manually change the line
sa.Column('created', sa.UTCTImestampType(), nullable=False),
# to
sa.Column('created', sa.Integer(), nullable=False),