Spaces:
Runtime error
Runtime error
File size: 5,275 Bytes
71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 71a3948 ec5cc84 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 |
from typing import List, Optional
from sqlmodel import Field, Relationship, SQLModel
from enum import Enum
# --- Enums for choices ---
class Role(str, Enum):
ADMIN = "admin"
STAFF = "staff"
STUDENT = "student"
class Department(str, Enum):
COMPUTER_SCIENCE = "Computer Science"
ENGINEERING = "Engineering"
BUSINESS_ADMIN = "Business Administration"
LAW = "Law"
MEDICINE = "Medicine"
class ClearanceDepartment(str, Enum):
LIBRARY = "Library"
STUDENT_AFFAIRS = "Student Affairs"
BURSARY = "Bursary"
ACADEMIC_AFFAIRS = "Academic Affairs"
HEALTH_CENTER = "Health Center"
class ClearanceStatusEnum(str, Enum):
PENDING = "pending"
APPROVED = "approved"
REJECTED = "rejected"
# --- Database Table Models ---
class User(SQLModel, table=True):
id: Optional[int] = Field(default=None, primary_key=True)
username: str = Field(index=True, unique=True)
email: str = Field(index=True, unique=True)
full_name: str
hashed_password: str
role: Role
department: Optional[Department] = None # For staff members
rfid_tag: Optional["RFIDTag"] = Relationship(back_populates="user", sa_relationship_kwargs={"cascade": "all, delete-orphan"})
class Student(SQLModel, table=True):
id: Optional[int] = Field(default=None, primary_key=True)
full_name: str
matric_no: str = Field(index=True, unique=True)
email: str = Field(index=True, unique=True)
department: Department
# A student's login is handled by their associated User record, not directly here.
rfid_tag: Optional["RFIDTag"] = Relationship(back_populates="student", sa_relationship_kwargs={"cascade": "all, delete-orphan"})
clearance_statuses: List["ClearanceStatus"] = Relationship(back_populates="student", sa_relationship_kwargs={"cascade": "all, delete-orphan"})
class ClearanceStatus(SQLModel, table=True):
id: Optional[int] = Field(default=None, primary_key=True)
department: ClearanceDepartment
status: ClearanceStatusEnum = Field(default=ClearanceStatusEnum.PENDING)
remarks: Optional[str] = None
student_id: int = Field(foreign_key="student.id")
student: "Student" = Relationship(back_populates="clearance_statuses")
class RFIDTag(SQLModel, table=True):
tag_id: str = Field(primary_key=True, index=True)
student_id: Optional[int] = Field(default=None, foreign_key="student.id", unique=True)
user_id: Optional[int] = Field(default=None, foreign_key="user.id", unique=True)
student: Optional["Student"] = Relationship(back_populates="rfid_tag")
user: Optional["User"] = Relationship(back_populates="rfid_tag")
class Device(SQLModel, table=True):
id: Optional[int] = Field(default=None, primary_key=True)
device_name: str = Field(unique=True, index=True)
api_key: str = Field(unique=True, index=True)
location: str
is_active: bool = Field(default=True)
# --- Pydantic Models for API Operations ---
# Token Model
class Token(SQLModel):
access_token: str
token_type: str
# User Models
class UserCreate(SQLModel):
username: str
password: str
email: str
full_name: str
role: Role
department: Optional[Department] = None
class UserUpdate(SQLModel):
username: Optional[str] = None
email: Optional[str] = None
full_name: Optional[str] = None
role: Optional[Role] = None
department: Optional[Department] = None
password: Optional[str] = None
class UserRead(SQLModel):
id: int
username: str
email: str
full_name: str
role: Role
department: Optional[Department] = None
# Student Models
class StudentCreate(SQLModel):
full_name: str
matric_no: str
email: str
department: Department
password: str # This will be used to create the associated User account for the student
class StudentUpdate(SQLModel):
full_name: Optional[str] = None
department: Optional[Department] = None
email: Optional[str] = None
class StudentRead(SQLModel):
id: int
full_name: str
matric_no: str
department: Department
# Clearance Status Models
class ClearanceStatusRead(SQLModel):
department: ClearanceDepartment
status: ClearanceStatusEnum
remarks: Optional[str] = None
class ClearanceUpdate(SQLModel):
matric_no: str
department: ClearanceDepartment
status: ClearanceStatusEnum
remarks: Optional[str] = None
# Combined Read Model
class StudentReadWithClearance(StudentRead):
clearance_statuses: List[ClearanceStatusRead] = []
rfid_tag: Optional["RFIDTagRead"] = None
# RFID Tag Models
class RFIDTagRead(SQLModel):
tag_id: str
student_id: Optional[int] = None
user_id: Optional[int] = None
class TagLink(SQLModel):
tag_id: str
matric_no: Optional[str] = None
username: Optional[str] = None
# RFID Device-Specific Models
class RFIDScanRequest(SQLModel):
tag_id: str
class RFIDStatusResponse(SQLModel):
status: str
full_name: Optional[str] = None
message: Optional[str] = None
clearance: Optional[str] = None
class TagScan(SQLModel):
tag_id: str
# Device Models
class DeviceCreate(SQLModel):
device_name: str
location: str
class DeviceRead(SQLModel):
id: int
device_name: str
api_key: str
location: str
is_active: bool
|