class Answer(Base): __tablename__ = 'answers' id = db.Column(db.Integer, primary_key=True) question_id = db.Column(db.Integer, db.ForeignKey('questions.id')) text_en = db.Column(db.Unicode(50)) text_ru = db.Column(db.Unicode(50)) is_correct = db.Column(db.Boolean) # relations question = db.relationship('Question', foreign_keys=[question_id])
class Question(Base): __tablename__ = 'questions' id = db.Column(db.Integer, primary_key=True) theme_id = db.Column(db.Integer, db.ForeignKey('themes.id')) image_name = db.Column(db.String(50), nullable=True) text_en = db.Column(db.Unicode(50)) text_ru = db.Column(db.Unicode(50)) approved = db.Column(db.Boolean, default=True) # relations theme = db.relationship('Theme', foreign_keys=[theme_id]) answers = db.relationship('Answer', cascade='all, delete-orphan')
class VideoTag(db.Model): """ Video tag / category """ __tablename__ = 'mylust_video_tag' id = db.Column(db.BigInteger, primary_key=True) name = db.Column(db.Unicode(256), index=True, unique=True) @property def slug(self): return slugify(self.name) def __repr__(self): return "<VideoTag '{0}'>".format(self.name.title())
class Video(db.Model): """ Main video model """ __tablename__ = 'mylust_video' __table_args__ = ( db.UniqueConstraint('masturbator', 'remote_id', name='masturbator_remote_id_uc'), ) id = db.Column(db.BigInteger, primary_key=True) title = db.Column(db.Unicode(256), index=True) duration = db.Column(db.Integer, default=0) masturbator = db.Column(db.String(32), index=True) remote_id = db.Column(db.BigInteger) remote_url = db.Column(db.String(256), index=True) remote_date = db.Column(db.DateTime(), nullable=True) import_date = db.Column(db.DateTime(), default=datetime.datetime.now, index=True) views = db.Column(db.BigInteger, default=0) tags = db.relationship('VideoTag', secondary=video_tags, backref=db.backref('videos', lazy='dynamic'), lazy='dynamic') thumbs = db.relationship('VideoThumb', backref=db.backref('video', cascade='all,delete'), lazy='dynamic') stars = db.relationship('VideoStar', secondary=video_stars, backref=db.backref('videos', lazy='dynamic'), lazy='dynamic') @property def slug(self): return slugify(self.title) @property def duration_formated(self): return time.strftime('%H:%M:%S', time.gmtime(self.duration)) def __repr__(self): return "<Video '{0}'>".format(self.remote_url)
class Item(db.Model): ''' An item that can be bought or borrowed Some methods require the request-context. TODO: Proper context validation with exceptions et al.''' id = db.Column(db.String(), primary_key=True) name = db.Column(db.Unicode(), unique=True) description = db.Column(db.UnicodeText) count = db.Column(db.Integer, default=1) # The corresponding image is saved saved under uploads/<entity.id>.jpg tax_base_int = db.Column(db.Float, default=0) tax_base_edu = db.Column(db.Float, default=0) tax_base_ext = db.Column(db.Float, default=0) tax_int = db.Column(db.Float) tax_edu = db.Column(db.Float) tax_ext = db.Column(db.Float) tax_period = db.Column(db.Enum('week', 'day'), default='week') price_buy = db.Column(db.Float) category = db.Column(db.Enum(*CATEGORIES)) related = db.relationship( 'Item', secondary=related, primaryjoin=id == related.c.item_id, secondaryjoin=id == related.c.related_item_id, ) def __repr__(self): return u"<Item %s>" % (self.id) def in_stock(self, start, end=None): ''' Returns the amount of this item in stock during the selected time- span. ''' if not end: end = start affected_tas = Transaction.query.filter( db.and_( Transaction.date_end >= start, Transaction.date_start <= end, )).all() out = 0 for ta in affected_tas: if not self.id in ta.lend: continue out += ta.lend[self.id].amount return self.count - out @property def buying(self): ta = g.ta if not self.id in ta.buy: return 0 return ta.buy[self.id].amount @property def lending(self): ta = g.ta if not self.id in ta.lend: return 0 return ta.lend[self.id].amount @property def available(self): return self.count - self.lending @property def lendable(self): return self.tax() is not None @property def buyable(self): return self.price_buy is not None def tax_base(self, transaction=None): ta = transaction or g.ta return getattr(self, 'tax_base_' + ta.group) def tax(self, transaction=None): ta = transaction or g.ta return getattr(self, 'tax_' + ta.group) def tax_ta(self, transaction=None): ta = transaction or g.ta from math import ceil if self.tax_period == 'week': periods = int(ceil(ta.days / 7.0)) else: periods = ta.days if self.tax_base(ta) is None or self.tax(ta) is None: return -1.0 return self.tax_base(ta) + periods * self.tax(ta)
class Transaction(db.Model): ''' Whenever an item is lent or bought, a transaction entity is created ''' id = db.Column(db.Integer, primary_key=True) name = db.Column(db.Unicode()) email = db.Column(db.Unicode()) tel = db.Column(db.Unicode()) group = db.Column(db.Enum(*GROUPS)) payment = db.Column(db.Unicode()) delivery = db.Column(db.Unicode()) # Address remarks = db.Column(db.UnicodeText()) progress = db.Column(db.Enum(*PROGRESS), default='new') buy = db.relationship( 'Buy', backref='transaction', collection_class=attribute_mapped_collection('item_id'), cascade="save-update, merge, delete, delete-orphan") lend = db.relationship( 'Lend', backref='transaction', collection_class=attribute_mapped_collection('item_id'), cascade="save-update, merge, delete, delete-orphan") date_start = db.Column(db.Date) date_end = db.Column(db.Date) date = db.Column(db.DateTime) @property def days(self): if not self.date_end or not self.date_start: return 0 return (self.date_end - self.date_start).days @property def weeks(self): from math import ceil return int(ceil(self.days / 7.0)) @property def n_in_cart(self): lend = [item.amount for item in self.lend.values()] buy = [item.amount for item in self.buy.values()] return sum(lend) + sum(buy) @property def cost(self): lends = [il.cost(self) for il in self.lend.values()] buys = [il.cost() for il in self.buy.values()] return sum(lends) + sum(buys) def __init__(self): self.group = 'int' self.date = datetime.datetime.utcnow() def __repr__(self): if self.id is not None: return u"<Transaction %u>" % (self.id) return u"<Transaction (no ID)>"
class User(Base): __tablename__ = 'users' id = db.Column(db.Integer, primary_key=True) username = db.Column(db.Unicode(50), unique=True, nullable=False) password_hash = db.Column(db.String(128)) premium = db.Column(db.Boolean, default=False) email = db.Column(db.String(50), unique=False, nullable=True) mmr = db.Column(db.Integer, nullable=False, default=4000) kda = db.Column(db.Float, nullable=True, default=1.0) gpm = db.Column(db.Integer, nullable=True, default=300) wallpapers_image_name = db.Column(db.String(50), nullable=False, default='wallpaper_default.jpg') avatar_image_name = db.Column(db.String(50), nullable=False, default='avatar_default.png') total_correct_answers = db.Column(db.Integer, nullable=True, default=0) total_incorrect_answers = db.Column(db.Integer, nullable=True, default=0) total_matches_won = db.Column(db.Integer, default=0) total_matches_lost = db.Column(db.Integer, default=0) total_time_for_answers = db.Column(db.Integer, default=0) role = db.Column(db.SmallInteger, default=ROLE_USER) # relations # TODO: divide matches onto: current_matches & recent_matches matches = db.relationship('Match', secondary='users_matches') def __init__(self, username=None, password=None, avatar_image_name=None, wallpapers_image_name=None, mmr=None): if username is not None: self.username = username if password is not None: self.hash_password(password) if avatar_image_name is not None: self.avatar_image_name = avatar_image_name if wallpapers_image_name is not None: self.wallpapers_image_name = wallpapers_image_name if mmr is not None: self.mmr = mmr def hash_password(self, password): self.password_hash = pwd_context.encrypt(password) def verify_password(self, password): return pwd_context.verify(password, self.password_hash) def generate_auth_token(self): s = Serializer(app.config['SECRET_KEY']) return s.dumps({'id': self.id}) @staticmethod def verify_auth_token(token): s = Serializer(app.config['SECRET_KEY']) try: data = s.loads(token) except SignatureExpired: return None # valid token, but expired except BadSignature: return None # invalid token user = User.query.get(data['id']) return user def sendRequest(self, aUser): if aUser.isPending(self): self.acceptRequest(aUser) db.session.add(self) db.session.add(aUser) else: f = Friends(confirmed=False, from_id=self.id, to_id=aUser.id) db.session.add(f) def isPending(self, aUser): return self.out_requests.filter(Friends.to_id == aUser.id, Friends.confirmed == False).count() > 0 def isFriend(self, aUser): b1 = self.out_requests.filter(Friends.to_id == aUser.id, Friends.confirmed == True).count() > 0 b2 = self.in_requests.filter(Friends.from_id == aUser.id, Friends.confirmed == True).count() > 0 return b1 or b2 def acceptRequest(self, aUser): if aUser.isPending(self): f = self.in_requests.filter(Friends.from_id == aUser.id).one() f.confirmed = True def removeFriend(self, aUser): if self.isFriend(aUser) == True: if self.out_requests.filter(Friends.to_id == aUser.id, Friends.confirmed == True).count() > 0: f = self.out_requests.filter(Friends.to_id == aUser.id, Friends.confirmed == True).one() Friends.query.filter(Friends.to_id == f.to_id, Friends.from_id == f.from_id).delete( synchronize_session=False) elif self.in_requests.filter(Friends.from_id == aUser.id, Friends.confirmed == True).count() > 0: f = self.in_requests.filter(Friends.from_id == aUser.id, Friends.confirmed == True).one() Friends.query.filter(Friends.to_id == f.to_id, Friends.from_id == f.from_id).delete( synchronize_session=False) else: print self.username + ' has no friend with username = '******'utf-8'), self.mmr) def __iter__(self): return self def __eq__(self, other): return self.id == other.id def is_authenticated(self): return True def is_active(self): return True def is_anonimous(self): return False def get_id(self): str = unicode(self.id) return str