Bénévole : vœux d'artistes (entité Artist) et vœux de postes
Nouvelle entité `Artist` (nom + jour de passage), CRUD
`/editions/{id}/artists` (lecture ouverte à tout compte de l'édition,
écriture COORDINATION), unicité (édition, nom, date).
La fiche bénévole porte deux listes de vœux, sur le modèle de
`skill_codes` (None = inchangé, [] = vider) :
- `artist_ids` : artistes que le bénévole veut voir (`volunteer_artist`) ;
- `wished_position_ids` : postes qu'il voudrait tenir
(`volunteer_position_wish`), distinct de l'affectation.
Un id étranger à l'édition renvoie 422 (`artist.unknown` /
`position.unknown`). Suppression d'un artiste : cascade sur les vœux.
Migration 0006. Jeu de démonstration et frontend inchangés (le front
suivra).
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017uUsRg7XzopkCPWimwg9ZM
This commit is contained in:
co-authored by
Claude Sonnet 5
parent
609514369a
commit
24caece7df
@@ -49,6 +49,32 @@ class ShiftRequiredSkill(SQLModel, table=True):
|
||||
)
|
||||
|
||||
|
||||
class VolunteerArtist(SQLModel, table=True):
|
||||
"""Vœu d'un bénévole : « je veux voir cet artiste »."""
|
||||
|
||||
__tablename__ = "volunteer_artist"
|
||||
|
||||
volunteer_id: uuid.UUID = Field(
|
||||
foreign_key="volunteer.id", primary_key=True, ondelete="CASCADE"
|
||||
)
|
||||
artist_id: uuid.UUID = Field(
|
||||
foreign_key="artist.id", primary_key=True, ondelete="CASCADE"
|
||||
)
|
||||
|
||||
|
||||
class VolunteerPositionWish(SQLModel, table=True):
|
||||
"""Vœu d'un bénévole : « je voudrais tenir ce poste »."""
|
||||
|
||||
__tablename__ = "volunteer_position_wish"
|
||||
|
||||
volunteer_id: uuid.UUID = Field(
|
||||
foreign_key="volunteer.id", primary_key=True, ondelete="CASCADE"
|
||||
)
|
||||
position_id: uuid.UUID = Field(
|
||||
foreign_key="position.id", primary_key=True, ondelete="CASCADE"
|
||||
)
|
||||
|
||||
|
||||
# --------------------------------------------------------------------------- #
|
||||
# Édition et découpage des journées #
|
||||
# --------------------------------------------------------------------------- #
|
||||
@@ -120,6 +146,35 @@ class Skill(TimestampMixin, table=True):
|
||||
)
|
||||
|
||||
|
||||
class Artist(TimestampMixin, table=True):
|
||||
"""Artiste programmé sur l'édition.
|
||||
|
||||
La coordination constitue la liste (présentée par jour de passage). Les
|
||||
bénévoles y choisissent les artistes qu'ils veulent voir (`VolunteerArtist`).
|
||||
"""
|
||||
|
||||
__table_args__ = (
|
||||
UniqueConstraint(
|
||||
"edition_id", "name", "performance_date",
|
||||
name="uq_artist_edition_name_date",
|
||||
),
|
||||
)
|
||||
|
||||
id: uuid.UUID = Field(default_factory=uuid.uuid4, primary_key=True)
|
||||
edition_id: uuid.UUID = Field(
|
||||
foreign_key="edition.id", index=True, ondelete="CASCADE"
|
||||
)
|
||||
name: str
|
||||
# Jour de passage, dans les dates de l'édition.
|
||||
performance_date: dt.date = Field(index=True)
|
||||
|
||||
fans: list["Volunteer"] = Relationship(
|
||||
back_populates="wished_artists",
|
||||
link_model=VolunteerArtist,
|
||||
sa_relationship_kwargs=_PASSIVE,
|
||||
)
|
||||
|
||||
|
||||
class Volunteer(TimestampMixin, table=True):
|
||||
__table_args__ = (
|
||||
UniqueConstraint(
|
||||
@@ -144,6 +199,16 @@ class Volunteer(TimestampMixin, table=True):
|
||||
link_model=VolunteerSkill,
|
||||
sa_relationship_kwargs=_PASSIVE,
|
||||
)
|
||||
wished_artists: list[Artist] = Relationship(
|
||||
back_populates="fans",
|
||||
link_model=VolunteerArtist,
|
||||
sa_relationship_kwargs=_PASSIVE,
|
||||
)
|
||||
wished_positions: list["Position"] = Relationship(
|
||||
back_populates="wishing_volunteers",
|
||||
link_model=VolunteerPositionWish,
|
||||
sa_relationship_kwargs=_PASSIVE,
|
||||
)
|
||||
availabilities: list["Availability"] = Relationship(
|
||||
back_populates="volunteer", sa_relationship_kwargs=_PASSIVE
|
||||
)
|
||||
@@ -219,6 +284,11 @@ class Position(TimestampMixin, table=True):
|
||||
shifts: list["Shift"] = Relationship(
|
||||
back_populates="position", sa_relationship_kwargs=_PASSIVE
|
||||
)
|
||||
wishing_volunteers: list["Volunteer"] = Relationship(
|
||||
back_populates="wished_positions",
|
||||
link_model=VolunteerPositionWish,
|
||||
sa_relationship_kwargs=_PASSIVE,
|
||||
)
|
||||
|
||||
|
||||
class Shift(TimestampMixin, table=True):
|
||||
|
||||
Reference in New Issue
Block a user