diff --git a/cookbook/serializer.py b/cookbook/serializer.py index 18253126..da6c8266 100644 --- a/cookbook/serializer.py +++ b/cookbook/serializer.py @@ -364,16 +364,23 @@ class SupermarketSerializer(UniqueFieldsMixin, SpacedModelSerializer): fields = ('id', 'name', 'description', 'category_to_supermarket') -class RecipeSimpleSerializer(serializers.ModelSerializer): +class RecipeSimpleSerializer(WritableNestedModelSerializer): url = serializers.SerializerMethodField('get_url') def get_url(self, obj): return reverse('view_recipe', args=[obj.id]) + def create(self, validated_data): + # don't allow writing to Recipe via this API + return Recipe.objects.get(**validated_data) + + def update(self, instance, validated_data): + # don't allow writing to Recipe via this API + return Recipe.objects.get(**validated_data) + class Meta: model = Recipe fields = ('id', 'name', 'url') - read_only_fields = ['id', 'name', 'url'] class FoodSimpleSerializer(serializers.ModelSerializer): @@ -427,6 +434,8 @@ class FoodSerializer(UniqueFieldsMixin, WritableNestedModelSerializer, ExtendedR name=sc_name, space=space, defaults=sm_category) onhand = validated_data.pop('food_onhand', None) + if recipe := validated_data.get('recipe', None): + validated_data['recipe'] = Recipe.objects.get(**recipe) # assuming if on hand for user also onhand for shopping_share users if not onhand is None: diff --git a/vue/src/apps/RecipeEditView/RecipeEditView.vue b/vue/src/apps/RecipeEditView/RecipeEditView.vue index cba02f75..4aab4ef6 100644 --- a/vue/src/apps/RecipeEditView/RecipeEditView.vue +++ b/vue/src/apps/RecipeEditView/RecipeEditView.vue @@ -79,7 +79,7 @@ :loading="keywords_loading" @search-change="searchKeywords" > - + @@ -140,6 +140,24 @@ + + {{ $t("additional_options") }} + + + + + {{ $t("Create Food") }} + + + + {{ $t("Name") }} + + + + {{ $t("create_food_desc") }} + + + @@ -260,7 +278,7 @@ style="flex-grow: 1; flex-shrink: 1; flex-basis: 0" @search-change="searchFiles" > - + - + @@ -362,7 +380,7 @@ :loading="units_loading" @search-change="searchUnits" > - +
@@ -392,7 +410,7 @@ :loading="foods_loading" @search-change="searchFoods" > - +
@@ -617,6 +635,8 @@ export default { paste_step: undefined, show_file_create: false, step_for_file_create: undefined, + additional_visible: false, + create_food: undefined, } }, computed: { @@ -648,6 +668,12 @@ export default { this.recipe_changed = this.recipe_changed !== undefined }, }, + "recipe.name": function () { + this.recipe.food_name = this.recipe.name.toLowerCase() + }, + "recipe.create_food": function () { + this.create_food = this.recipe.create_food + }, }, methods: { keyboardListener: function (e) { @@ -734,6 +760,9 @@ export default { .then((response) => { StandardToasts.makeStandardToast(StandardToasts.SUCCESS_UPDATE) this.recipe_changed = false + if (this.create_food) { + apiFactory.createFood({ name: this.recipe.food_name, recipe: { id: this.recipe.id, name: this.recipe.name } }) + } if (view_after) { location.href = resolveDjangoUrl("view_recipe", this.recipe_id) } diff --git a/vue/src/locales/en.json b/vue/src/locales/en.json index f2dfeb44..c6d79cf9 100644 --- a/vue/src/locales/en.json +++ b/vue/src/locales/en.json @@ -376,5 +376,8 @@ "Keyword": "Keyword", "Advanced": "Advanced", "Page": "Page", - "Reset": "Reset" + "Reset": "Reset", + "Create Food": "Create Food", + "create_food_desc": "Create a food and link it to this recipe.", + "additional_options": "Additional Options" }