from flask_sqlalchemy import SQLAlchemy import uuid as uuid_lib from datetime import datetime from app import db # Association table for tags plant_tags = db.Table( 'plant_tags', db.metadata, db.Column('plant_id', db.Integer, db.ForeignKey('plant.id'), primary_key=True), db.Column('tag_id', db.Integer, db.ForeignKey('tag.id'), primary_key=True), extend_existing=True ) class Tag(db.Model): __tablename__ = 'tag' __table_args__ = {'extend_existing': True} id = db.Column(db.Integer, primary_key=True) name = db.Column(db.String(255), unique=True, nullable=False) class PlantCommonName(db.Model): __tablename__ = 'plant_common_name' __table_args__ = {'extend_existing': True} id = db.Column(db.Integer, primary_key=True) name = db.Column(db.String(255), unique=True, nullable=False) class PlantScientificName(db.Model): __tablename__ = 'plant_scientific_name' __table_args__ = {'extend_existing': True} id = db.Column(db.Integer, primary_key=True) name = db.Column(db.String(255), unique=True, nullable=False) common_id = db.Column(db.Integer, db.ForeignKey('plant_common_name.id'), nullable=False) class PlantLineage(db.Model): __tablename__ = 'plant_lineage' __table_args__ = {'extend_existing': True} id = db.Column(db.Integer, primary_key=True) child_plant_id = db.Column(db.Integer, db.ForeignKey('plant.id'), nullable=False) parent_plant_id = db.Column(db.Integer, db.ForeignKey('plant.id'), nullable=False) type = db.Column(db.String(50), nullable=False) # cutting, seed, division class PlantOwnershipLog(db.Model): __tablename__ = 'plant_ownership_log' __table_args__ = {'extend_existing': True} id = db.Column(db.Integer, primary_key=True) plant_id = db.Column(db.Integer, db.ForeignKey('plant.id'), nullable=False) user_id = db.Column(db.Integer, db.ForeignKey('users.id'), nullable=False) start_time = db.Column(db.DateTime, nullable=False) end_time = db.Column(db.DateTime, nullable=True) transfer_note = db.Column(db.Text, nullable=True) class Plant(db.Model): __tablename__ = 'plant' __table_args__ = {'extend_existing': True} id = db.Column(db.Integer, primary_key=True) uuid = db.Column(db.String(36), default=lambda: str(uuid_lib.uuid4()), unique=True, nullable=False) custom_slug = db.Column(db.String(255), unique=True, nullable=True) owner_id = db.Column(db.Integer, db.ForeignKey('users.id'), nullable=False) common_id = db.Column(db.Integer, db.ForeignKey('plant_common_name.id'), nullable=False) scientific_id = db.Column(db.Integer, db.ForeignKey('plant_scientific_name.id'), nullable=False) plant_type = db.Column(db.String(50), nullable=False) status = db.Column(db.String(50), nullable=False, default='active') notes = db.Column(db.Text, nullable=True) created_at = db.Column(db.DateTime, default=datetime.utcnow) transferred = db.Column(db.Boolean, default=False) graph_node_id = db.Column(db.String(255), nullable=True) # Relationships updates = db.relationship('PlantUpdate', backref='growlog', lazy=True) lineage = db.relationship('PlantLineage', backref='child', lazy=True, foreign_keys='PlantLineage.child_plant_id') tags = db.relationship('Tag', secondary=plant_tags, backref='plants') common_name = db.relationship( 'PlantCommonName', backref=db.backref('plants', lazy='dynamic'), lazy=True ) scientific_name = db.relationship( 'PlantScientificName', backref=db.backref('plants', lazy='dynamic'), lazy=True ) PlantCommon = PlantCommonName PlantScientific = PlantScientificName