Model
Model is the ActiveRecord-style base class every generated model subclasses. It combines SQLModel with a fluent Query builder, accessible both from instances (task.save()) and directly on the class (Task.where(...)) via the _ModelMeta metaclass.
from typing import Optional
from grace.model import Field, Model
class User(Model):
id: Optional[int] = Field(default=None, primary_key=True)
name: str
email: str
age: int
active: bool = True
user = User.create(name="Test", email="test@example.com", age=20)
User.find(1)
User.find_by(name="Alice")
User.where(User.age > 25, active=True).order_by(User.age.desc()).limit(10).all()
User.with_("posts", "comments").where(User.active == True).all()
See Models & Migrations for the full guide.
grace.model.Model
Bases: SQLModel
set_engine
classmethod
set_engine(engine)
Sets the database engine used by the model.
Must be called before performing any queries.
Examples
from sqlmodel import create_engine
engine = create_engine("sqlite:///db.sqlite3")
User.set_engine(engine)
Source code in grace/model.py
377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 | |
get_engine
classmethod
get_engine()
Returns the engine currently associated with this model.
Raises a RuntimeError if no engine has been set.
Examples
engine = User.get_engine()
Source code in grace/model.py
393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 | |
query
classmethod
query()
Returns a new query object for the model.
Enables chaining methods such as where, order_by, limit, etc.
Examples
User.query().where(User.active == True).order_by(User.created_at).all()
Source code in grace/model.py
411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 | |
create
classmethod
create(**kwargs)
Creates and saves a new record with the given attributes.
Examples
User.create(name="Alice", email="alice@example.com")
Source code in grace/model.py
427 428 429 430 431 432 433 434 435 436 437 438 | |
save
save()
Saves the current model instance to the database.
Commits changes immediately and refreshes the instance.
Examples
user = User(name="Alice")
user.save()
Source code in grace/model.py
440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 | |
delete
delete()
Deletes the current record from the database.
Examples
user = User.find(1)
user.delete()
Source code in grace/model.py
458 459 460 461 462 463 464 465 466 467 468 469 470 471 472 | |
update
update(**kwargs)
Updates the current instance with the given attributes and saves the changes to the database.
Examples
user = User.find(1)
user.update(name="Alice Smith", active=False)
Source code in grace/model.py
474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 | |
reload
reload()
Reloads the instance from the database, discarding any unsaved changes.
Similar to ActiveRecord's reload method.
Examples
user = User.find(1)
user.name = "Changed"
user.reload() # Discards the change
Source code in grace/model.py
490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 | |
grace.model.Query
Query(model_class)
Source code in grace/model.py
17 18 19 20 | |
model_class
instance-attribute
model_class = model_class
engine
instance-attribute
engine = model_class.get_engine()
statement
property
writable
statement
find
find(value)
Finds a record by its primary key (id only).
Returns None if the record does not exist.
Examples
user = User.find(1)
Source code in grace/model.py
33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 | |
find_by
find_by(**kwargs)
Finds the first record matching the provided conditions.
Equivalent to calling .query().where(...).first().
Examples
User.find_by(name="Alice")
User.find_by(email="alice@example.com", active=True)
Source code in grace/model.py
55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 | |
where
where(*conditions, **kwargs)
Adds one or more filtering conditions to the query.
Accepts both SQLAlchemy expressions (e.g. User.age > 18)
and simple equality filters through keyword arguments.
Examples
# Using SQLAlchemy expressions
User.where(User.age > 18, User.active == True)
# Using keyword arguments for equality
User.where(name="Alice", active=True)
# Equivalent: combines both styles
User.where(User.age > 18, active=True)
Source code in grace/model.py
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 | |
not_
not_(*conditions, **kwargs)
Applies negation of one or more filtering conditions to the query.
Accepts SQLAlchemy expressions directly, or simple equality conditions expressed as keyword arguments. Keyword arguments are interpreted as equality checks that will then be negated.
Use this when you want to exclude records matching specific conditions.
Examples
# Exclude a specific user by name
User.not_(name="Alice").all()
# Exclude inactive users (negating an expression)
User.not_(User.active == False).all()
# Mixed usage
User.not_(User.age > 30, role="admin").all()
Source code in grace/model.py
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 | |
with_
with_(*relationships)
Eagerly loads specified relationships for optimization.
Use this when querying multiple records to avoid N+1 queries. For relationships configured with lazy="selectin", this combines the relationship loading into the main query instead of a separate one.
Examples
# Loading a single record: with_() doesn't help much
trigger = Trigger.find_by(name="Linus") # Already loads trigger_words efficiently
# Loading multiple records: with_() prevents N+1 queries
# Without with_: 1 query for triggers + 1 query for all trigger_words = 2 queries
triggers = Trigger.all()
# With with_: 1 combined query = 1 query (more efficient)
triggers = Trigger.with_("trigger_words").all()
# Load multiple relationships at once
User.with_("posts", "comments").where(User.active == True).all()
Source code in grace/model.py
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 | |
order_by
order_by(*args, **kwargs)
Orders query results by one or more columns.
Supports passing SQLAlchemy expressions directly,
or using keyword arguments like name="asc" or age="desc".
Examples
User.order_by(User.name)
User.order_by(User.created_at.desc())
User.order_by(name="asc", age="desc")
Source code in grace/model.py
169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 | |
limit
limit(count)
Limits the number of results returned by the query.
Examples
User.limit(10).all()
Source code in grace/model.py
207 208 209 210 211 212 213 214 215 216 217 | |
offset
offset(count)
Skips a given number of records before returning results.
Useful for pagination.
Examples
User.offset(20).limit(10).all()
Source code in grace/model.py
219 220 221 222 223 224 225 226 227 228 229 230 231 | |
distinct
distinct()
Returns only distinct/unique records.
Removes duplicate rows from the result set.
Examples
# Get unique users
User.distinct().all()
# Get distinct active users
User.where(User.active == True).distinct().all()
# Combined with other query methods
User.distinct().order_by(User.name).limit(10).all()
Source code in grace/model.py
233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 | |
all
all()
Executes the query and returns all matching records as a list.
Examples
users = User.where(User.active == True).all()
Source code in grace/model.py
254 255 256 257 258 259 260 261 262 263 264 | |
first
first()
Executes the query and returns the first matching record.
Returns None if no result is found.
Examples
user = User.where(User.name == "Alice").first()
Source code in grace/model.py
266 267 268 269 270 271 272 273 274 275 276 277 278 | |
one
one()
Executes the query and returns exactly one result.
Raises an exception if no result or multiple results are found.
Examples
user = User.where(User.email == "alice@example.com").one()
Source code in grace/model.py
280 281 282 283 284 285 286 287 288 289 290 291 292 | |
count
count()
Returns the number of records matching the current query.
Examples
total = User.where(User.active == True).count()
Source code in grace/model.py
294 295 296 297 298 299 300 301 302 303 304 305 306 307 | |