Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #!/usr/bin/env python
- from __future__ import annotations
- import logging
- import os
- import re
- import uuid
- from typing import Any, Dict, Optional, Type
- from uuid import uuid4
- from sqlalchemy import (BigInteger, Boolean, Column, Date, DateTime, ForeignKey,
- ForeignKeyConstraint, Integer, SmallInteger, String,
- create_engine)
- from sqlalchemy.dialects.postgresql import UUID
- from sqlalchemy.ext.declarative import declarative_base
- from sqlalchemy.orm import relationship, scoped_session, sessionmaker
- logger = logging.getLogger(__name__)
- user = os.environ.get('DB_USER', 'postgres')
- password = os.environ.get('DB_PASSWORD', 'password')
- host = os.environ.get('DB_HOST', 'db2')
- port = os.environ.get('DB_PORT', '5432')
- DeclarativeBase = declarative_base()
- class BaseModel(DeclarativeBase):
- __abstract__ = True
- def __repr__(self) -> str:
- """Represent the model with all its fields, like a dataclass would."""
- name = self.__class__.__name__
- attrs_dict = {}
- for column in self.__table__.c:
- key = column.name
- value = getattr(self, key)
- if isinstance(value, str) or isinstance(value, uuid.UUID):
- value = f"'{value}'"
- attrs_dict[key] = value
- attrs_repr = ', '.join(f'{k}={v}' for k, v in attrs_dict.items())
- return f'{name}({attrs_repr})'
- class Order(BaseModel):
- __tablename__ = 'orders'
- id = Column(UUID(as_uuid=True), primary_key=True, default=uuid4)
- actions = relationship('OrderAction', back_populates='order')
- rerun_links = relationship('RerunLink',
- back_populates='rerun_of_order',
- foreign_keys='RerunLink.rerun_of')
- rerun_of_link = relationship('RerunLink',
- back_populates='order',
- foreign_keys='RerunLink.order_id',
- uselist=False)
- reruns = relationship('Order',
- secondary='rerun_links',
- primaryjoin=('rerun_links.c.rerun_of == Order.id'),
- secondaryjoin=('rerun_links.c.order_id == Order.id'),
- back_populates='rerun_of')
- rerun_of = relationship('Order',
- secondary='rerun_links',
- primaryjoin=('rerun_links.c.order_id == Order.id'),
- secondaryjoin=('rerun_links.c.rerun_of == Order.id'),
- back_populates='reruns',
- uselist=False)
- class OrderAction(BaseModel):
- """All order actions (Cancellations, reruns, etc.)"""
- __tablename__ = 'order_actions'
- id = Column(Integer, primary_key=True)
- order_id = Column(UUID(as_uuid=True), ForeignKey('orders.id'), nullable=False)
- rerun = relationship('RerunLink', back_populates='action', uselist=False)
- order = relationship('Order', back_populates='actions')
- class RerunLink(BaseModel):
- """All new orders created based on old orders."""
- __tablename__ = 'rerun_links'
- order_id = Column(UUID(as_uuid=True), ForeignKey('orders.id'), primary_key=True)
- rerun_of = Column(UUID(as_uuid=True), ForeignKey('orders.id'))
- action_id = Column(Integer, ForeignKey('order_actions.id'), unique=True, nullable=False)
- order = relationship('Order', back_populates='rerun_of_link', foreign_keys=[order_id])
- rerun_of_order = relationship('Order', back_populates='rerun_links', foreign_keys=[rerun_of])
- action = relationship('OrderAction', back_populates='rerun')
- class DB:
- class __DB:
- engine: Engine
- session: scoped_session
- def __init__(self) -> None:
- self.engine = create_engine(f'postgresql://{user}:{password}@{host}:{port}', convert_unicode=True)
- self.session = scoped_session(sessionmaker(autocommit=False,
- autoflush=False,
- bind=self.engine))
- def query(self, model_class: Type[BaseModel]) -> Any:
- return self.session.query(model_class) # type: ignore
- def commit(self) -> Any:
- return self.session.commit() # type: ignore
- def drop_all(self) -> Any:
- DeclarativeBase.metadata.drop_all(bind=self.engine)
- def create_all(self) -> Any:
- DeclarativeBase.metadata.create_all(bind=self.engine)
- instance = None
- def __init__(self) -> None:
- if not DB.instance:
- DB.instance = DB.__DB()
- def __getattr__(self, name: str) -> Any:
- return getattr(self.instance, name)
- def recreate_db() -> None:
- DB().drop_all()
- DB().create_all()
- def test():
- # columns: id
- # relationships: actions, rerun_links, rerun_of_link, reruns, rerun_of
- old_order = Order()
- DB().session.add(old_order)
- DB().session.commit()
- # columns: id, order_id
- # relationships: order
- action = OrderAction(order_id=old_order.id)
- DB().session.add(action)
- DB().session.commit()
- # columns: id
- # relationships: actions, rerun_links, rerun_of_link, reruns, rerun_of
- new_order = Order(rerun_of=old_order)
- DB().session.add(new_order)
- DB().session.commit()
- # columns: order_id, rerun_of, action_id
- # relationships: order, rerun_of_order, action
- rerun_link = RerunLink(rerun_of=old_order.id,
- action_id=action.id)
- DB().session.add(rerun_link)
- DB().session.commit()
- if __name__ == '__main__':
- recreate_db()
- test()
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement