fix: 修复Task 3数据库模型问题

- 修复导入路径:从绝对导入改为相对导入
- 添加外键约束:Project.created_by添加ForeignKey,使用ON DELETE RESTRICT
- 添加索引:为常用查询字段添加index=True(username, email, department, role, project_no, engineering_type等)
- 优化Enum使用:创建UserRoleEnum和AdjustmentEnum类替代字符串枚举
- 添加关系映射:User.created_projects和Project.creator建立双向关系
- 添加User.created_by字段:保持与Project表一致性
This commit is contained in:
xsl
2026-01-26 09:47:50 +08:00
parent 5bfe260aa0
commit e17b29ca41
2 changed files with 38 additions and 19 deletions
+21 -13
View File
@@ -1,7 +1,13 @@
# backend/src/models/project.py
from sqlalchemy import Column, Integer, String, Text, Date, Numeric, DateTime, Enum
from sqlalchemy import Column, Integer, String, Text, Date, Numeric, DateTime, Enum, ForeignKey
from sqlalchemy.sql import func
from config.database import Base
from sqlalchemy.orm import relationship
from ..config.database import Base
class AdjustmentEnum(str, Enum):
yes = ""
no = ""
class Project(Base):
@@ -10,7 +16,7 @@ class Project(Base):
id = Column(Integer, primary_key=True, autoincrement=True, comment="项目ID")
# 基础信息
project_no = Column(String(50), unique=True, nullable=False, comment="合同编号")
project_no = Column(String(50), unique=True, nullable=False, index=True, comment="合同编号")
power_contract_no = Column(String(100), comment="供电局项目合同编号")
name = Column(String(200), nullable=False, comment="项目名称")
subitem_count = Column(Integer, default=0, comment="子项个数")
@@ -21,28 +27,28 @@ class Project(Base):
settlement_amount = Column(Numeric(15, 2), comment="结算金额(万元)")
total_cost_estimated = Column(Numeric(15, 2), comment="总成本测算")
voltage_level = Column(String(50), comment="工程电压等级")
engineering_type = Column(String(50), comment="工程类别")
owner_unit = Column(String(200), comment="业主单位")
engineering_type = Column(String(50), index=True, comment="工程类别")
owner_unit = Column(String(200), index=True, comment="业主单位")
owner_contact = Column(String(200), comment="业主联系人及电话")
bidding_type = Column(String(50), comment="中标形式")
signing_date = Column(Date, comment="签订日期")
start_date = Column(Date, comment="开工日期")
planned_end_date = Column(Date, comment="计划竣工日期")
actual_end_date = Column(Date, comment="实际竣工日期")
signing_date = Column(Date, index=True, comment="签订日期")
start_date = Column(Date, index=True, comment="开工日期")
planned_end_date = Column(Date, index=True, comment="计划竣工日期")
actual_end_date = Column(Date, index=True, comment="实际竣工日期")
# 质保信息
warranty_amount = Column(Numeric(15, 2), default=0, comment="质保金(万元)")
warranty_expiry_date = Column(Date, comment="质保期截止日")
warranty_expiry_date = Column(Date, index=True, comment="质保期截止日")
actual_warranty_refund_date = Column(Date, comment="实际退质保金日期")
# 项目信息
project_department = Column(String(100), comment="所属项目部")
project_department = Column(String(100), index=True, comment="所属项目部")
project_leader = Column(String(200), comment="项目负责人及电话")
payment_method = Column(Text, comment="工程款拨付方式")
# 成本控制
total_cost_control = Column(Numeric(15, 2), comment="总体成本(控制)")
is_adjusted = Column(Enum("", ""), default="", comment="是否调整")
is_adjusted = Column(Enum(AdjustmentEnum), default=AdjustmentEnum.no, index=True, comment="是否调整")
labor_cost_control = Column(Numeric(15, 2), comment="人工成本(控制)")
labor_cost_planned = Column(Numeric(15, 2), comment="农民工工资(计划)")
labor_cost_paid = Column(Numeric(15, 2), comment="农民工工资(实付)")
@@ -88,7 +94,7 @@ class Project(Base):
remarks = Column(Text, comment="备注")
# 系统字段
created_by = Column(Integer, nullable=False, comment="创建人ID")
created_by = Column(Integer, ForeignKey("users.id", ondelete="RESTRICT"), nullable=False, index=True, comment="创建人ID")
created_at = Column(
DateTime,
server_default=func.now(),
@@ -100,3 +106,5 @@ class Project(Base):
onupdate=func.now(),
comment="更新时间",
)
creator = relationship("User", back_populates="created_projects")
+17 -6
View File
@@ -1,21 +1,29 @@
# backend/src/models/user.py
from sqlalchemy import Column, Integer, String, Boolean, DateTime, Enum
from sqlalchemy.sql import func
from config.database import Base
from sqlalchemy.orm import relationship
from ..config.database import Base
class UserRoleEnum(str, Enum):
admin = "admin"
market = "market"
other = "other"
class User(Base):
__tablename__ = "users"
id = Column(Integer, primary_key=True, autoincrement=True, comment="用户ID")
username = Column(String(50), unique=True, nullable=False, comment="用户名")
username = Column(String(50), unique=True, nullable=False, index=True, comment="用户名")
password_hash = Column(String(255), nullable=False, comment="密码哈希")
real_name = Column(String(100), nullable=False, comment="真实姓名")
department = Column(String(50), nullable=False, comment="部门")
role = Column(Enum("admin", "market", "other"), nullable=False, comment="角色")
email = Column(String(100), unique=True, comment="邮箱")
department = Column(String(50), nullable=False, index=True, comment="部门")
role = Column(Enum(UserRoleEnum), nullable=False, index=True, comment="角色")
email = Column(String(100), unique=True, index=True, comment="邮箱")
phone = Column(String(20), comment="电话")
is_active = Column(Boolean, default=True, comment="是否激活")
is_active = Column(Boolean, default=True, index=True, comment="是否激活")
created_by = Column(Integer, comment="创建人ID")
created_at = Column(
DateTime,
server_default=func.now(),
@@ -27,3 +35,6 @@ class User(Base):
onupdate=func.now(),
comment="更新时间",
)
creator = relationship("User", remote_side="User.id", backref="created_users")
created_projects = relationship("Project", back_populates="creator", cascade="all, delete-orphan")