Repositories
Table of contents
- Introduction
- Adding a query
- Saving several records in one transaction
- Changing how a record is stored
- Reference
- See also
Introduction
A repository holds every database query for one model. Your services call it instead of db.session, so each model’s queries live in one place, easy to find and to test.
from splent_framework.repositories.BaseRepository import BaseRepository
from splent_io.splent_feature_notes.models import Note
class NotesRepository(BaseRepository[Note]):
def __init__(self):
super().__init__(Note)
That gives you the methods in the reference. The [Note] tells your editor what they return.
Adding a query
from sqlalchemy import select
class NotesRepository(BaseRepository[Note]):
def __init__(self):
super().__init__(Note)
def get_by_slug(self, slug):
return self.session.scalars(select(Note).where(Note.slug == slug)).first()
Write each query as a method. self.model is the model and self.session the shared db.session.
Saving several records in one transaction
from splent_framework.db import db
note = notes_repository.create(commit=False, title="First")
tags_repository.create(commit=False, note_id=note.id, name="draft")
db.session.commit()
create commits by default. With commit=False it only flushes, so note.id is ready and nothing is saved until you commit.
Changing how a record is stored
class NotesRepository(BaseRepository[Note]):
def create(self, commit=True, **kwargs):
content = kwargs.pop("content")
note = self.model(**kwargs)
note.set_content(content)
self.session.add(note)
if commit:
self.session.commit()
else:
self.session.flush()
return note
Override a method when the change is about how the model is stored. A business rule belongs in the service.
Reference
| Method | Returns | What it does |
|---|---|---|
create(commit=True, **kwargs) |
The record | Adds it, then commits or flushes |
get_by_id(id) |
The record or None |
Finds by primary key |
get_or_404(id) |
The record | Finds by primary key, or a 404 |
get_by_column(column, value) |
A list | Every row whose column equals value |
update(id, **kwargs) |
The record or None |
Sets the fields and commits |
delete(id) |
bool |
Deletes by primary key and commits |
delete_by_column(column, value) |
bool |
Deletes every matching row and commits. False when none matched |
count() |
int |
How many rows there are |
get_by_column and delete_by_column take a mapped column, a relationship or a hybrid property. Any other name, such as a method or a typo, raises ValueError and touches no row.