mixins.py 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112
  1. from datetime import datetime
  2. import logging
  3. from flask import g
  4. from sqlalchemy import Column, DateTime, ForeignKey, Integer
  5. from sqlalchemy.ext.declarative import declared_attr
  6. from sqlalchemy.orm import relationship
  7. import sqlalchemy.types as types
  8. log = logging.getLogger(__name__)
  9. class FileColumn(types.TypeDecorator):
  10. """
  11. Extends SQLAlchemy to support and mostly identify a File Column
  12. """
  13. impl = types.Text
  14. class ImageColumn(types.TypeDecorator):
  15. """
  16. Extends SQLAlchemy to support and mostly identify an Image Column
  17. """
  18. impl = types.Text
  19. def __init__(self, thumbnail_size=(20, 20, True), size=(100, 100, True), **kw):
  20. types.TypeDecorator.__init__(self, **kw)
  21. self.thumbnail_size = thumbnail_size
  22. self.size = size
  23. class AuditMixin(object):
  24. """
  25. AuditMixin
  26. Mixin for models, adds 4 columns to stamp,
  27. time and user on creation and modification
  28. will create the following columns:
  29. :created on:
  30. :changed on:
  31. :created by:
  32. :changed by:
  33. """
  34. created_on = Column(DateTime, default=lambda: datetime.now(), nullable=False)
  35. changed_on = Column(
  36. DateTime,
  37. default=lambda: datetime.now(),
  38. onupdate=lambda: datetime.now(),
  39. nullable=False,
  40. )
  41. @declared_attr
  42. def created_by_fk(cls):
  43. return Column(
  44. Integer, ForeignKey("ab_user.id"), default=cls.get_user_id, nullable=False
  45. )
  46. @declared_attr
  47. def created_by(cls):
  48. return relationship(
  49. "User",
  50. primaryjoin="%s.created_by_fk == User.id" % cls.__name__,
  51. enable_typechecks=False,
  52. )
  53. @declared_attr
  54. def changed_by_fk(cls):
  55. return Column(
  56. Integer,
  57. ForeignKey("ab_user.id"),
  58. default=cls.get_user_id,
  59. onupdate=cls.get_user_id,
  60. nullable=False,
  61. )
  62. @declared_attr
  63. def changed_by(cls):
  64. return relationship(
  65. "User",
  66. primaryjoin="%s.changed_by_fk == User.id" % cls.__name__,
  67. enable_typechecks=False,
  68. )
  69. @classmethod
  70. def get_user_id(cls):
  71. try:
  72. return g.user.id
  73. except Exception:
  74. return None
  75. class UserExtensionMixin(object):
  76. __tablename__ = "ab_user_extended"
  77. __mapper_args__ = {"polymorphic_identity": "ab_user_extended"}
  78. @declared_attr
  79. def id(cls):
  80. return Column(None, ForeignKey("ab_user.id"), primary_key=True)
  81. """
  82. This is for retro compatibility
  83. """
  84. class BaseMixin(object):
  85. pass