from sqlalchemy import Column, BigInteger, String, DateTime, event from sqlalchemy.ext.declarative import declared_attr from config.auth import context_sub from config.database import Base from datetime import datetime from utils.common import camel_to_snake from id_generator import options, generator # https://github.com/yitter/IdGenerator/tree/master/Python options = options.IdGeneratorOptions(worker_id=23) idgen = generator.DefaultIdGenerator() idgen.set_id_generator(options) # 第二层基类:包含ID class IdBase(Base): __abstract__ = True id = Column(BigInteger, primary_key=True, index=True) @declared_attr def __tablename__(cls): # 自动把数据库实体类名驼峰转为数据库表名下划线 return camel_to_snake(cls.__name__) # 自动填充id @event.listens_for(IdBase, 'before_insert', propagate=True) def before_insert_listener(mapper, connection, target): if target.id is None: target.id = idgen.next_id() # 第二层基类:包含ID和审计字段 class AuditBase(IdBase): __abstract__ = True create_time = Column(DateTime, nullable=True, default=datetime.now) create_by = Column(String(255), nullable=True) update_time = Column(DateTime, nullable=True, default=datetime.now, onupdate=datetime.now) update_by = Column(String(255), nullable=True) @event.listens_for(AuditBase, 'before_insert', propagate=True) def before_insert(mapper, connection, target): value = context_sub.get(None) if value is not None: target.create_by = value @event.listens_for(AuditBase, 'before_update', propagate=True) def before_update(mapper, connection, target): value = context_sub.get(None) if value is not None: target.update_by = value