added user to shopping list

This commit is contained in:
Michael Genson 2024-02-23 16:49:37 +00:00
parent 3d4405cd42
commit 74d6f58363
3 changed files with 90 additions and 1 deletions

View File

@ -0,0 +1,85 @@
"""added user to shopping list
Revision ID: 2298bb460ffd
Revises: ba1e4a6cfe99
Create Date: 2024-02-23 16:15:07.115641
"""
from uuid import UUID
import sqlalchemy as sa
from sqlalchemy import orm
import mealie.db.migration_types
from alembic import op
# revision identifiers, used by Alembic.
revision = "2298bb460ffd"
down_revision = "ba1e4a6cfe99"
branch_labels = None
depends_on = None
def is_postgres():
return op.get_context().dialect.name == "postgresql"
def find_user_id_for_group(group_id: UUID):
bind = op.get_bind()
session = orm.Session(bind=bind)
if is_postgres():
stmt = "SELECT id FROM users WHERE group_id=:group_id AND admin = TRUE LIMIT 1"
else:
stmt = "SELECT id FROM users WHERE group_id=:group_id AND admin = 1 LIMIT 1"
with session:
try:
# try to find an admin user
user_id = session.execute(sa.text(stmt).bindparams(group_id=group_id)).scalar_one()
except orm.exc.NoResultFound:
# fallback to any user
user_id = session.execute(
sa.text("SELECT id FROM users LIMIT 1").bindparams(group_id=group_id)
).scalar_one()
return user_id
def populate_shopping_list_users():
bind = op.get_bind()
session = orm.Session(bind=bind)
with session:
list_ids_and_group_ids = session.execute(sa.text("SELECT id, group_id FROM shopping_lists")).all()
for list_id, group_id in list_ids_and_group_ids:
user_id = find_user_id_for_group(group_id)
session.execute(
sa.text(f"UPDATE shopping_lists SET user_id=:user_id WHERE id=:id").bindparams(
user_id=user_id, id=list_id
)
)
def upgrade():
# ### commands auto generated by Alembic - please adjust! ###
with op.batch_alter_table("shopping_lists") as batch_op:
# allow nulls during migration
batch_op.add_column(sa.Column("user_id", mealie.db.migration_types.GUID(), nullable=True))
batch_op.create_index(op.f("ix_shopping_lists_user_id"), ["user_id"], unique=False)
batch_op.create_foreign_key("fk_user_shopping_lists", "users", ["user_id"], ["id"])
# ### end Alembic commands ###
populate_shopping_list_users()
# forbid nulls after migration
with op.batch_alter_table("shopping_lists") as batch_op:
batch_op.alter_column("user_id", nullable=False)
def downgrade():
# ### commands auto generated by Alembic - please adjust! ###
op.drop_constraint(None, "shopping_lists", type_="foreignkey")
op.drop_index(op.f("ix_shopping_lists_user_id"), table_name="shopping_lists")
op.drop_column("shopping_lists", "user_id")
# ### end Alembic commands ###

View File

@ -14,6 +14,7 @@ from ..recipe.ingredient import IngredientFoodModel, IngredientUnitModel
if TYPE_CHECKING:
from group import Group
from users import User
from ..recipe import RecipeModel
@ -122,6 +123,8 @@ class ShoppingList(SqlAlchemyBase, BaseMixins):
group_id: Mapped[GUID] = mapped_column(GUID, ForeignKey("groups.id"), nullable=False, index=True)
group: Mapped["Group"] = orm.relationship("Group", back_populates="shopping_lists")
user_id: Mapped[GUID] = mapped_column(GUID, ForeignKey("users.id"), nullable=False, index=True)
user: Mapped["User"] = orm.relationship("User", back_populates="shopping_lists")
name: Mapped[str | None] = mapped_column(String)
list_items: Mapped[ShoppingListItem] = orm.relationship(

View File

@ -17,6 +17,7 @@ from .user_to_favorite import users_to_favorites
if TYPE_CHECKING:
from ..group import Group
from ..group.mealplan import GroupMealPlan
from ..group.shopping_list import ShoppingList
from ..recipe import RecipeComment, RecipeModel, RecipeTimelineEvent
from .password_reset import PasswordResetModel
@ -81,7 +82,7 @@ class User(SqlAlchemyBase, BaseMixins):
mealplans: Mapped[Optional["GroupMealPlan"]] = orm.relationship(
"GroupMealPlan", order_by="GroupMealPlan.date", **sp_args
)
shopping_lists: Mapped[Optional["ShoppingList"]] = orm.relationship("ShoppingList", **sp_args)
favorite_recipes: Mapped[list["RecipeModel"]] = orm.relationship(
"RecipeModel", secondary=users_to_favorites, back_populates="favorited_by"
)