mirror of
https://github.com/grocy/grocy.git
synced 2025-04-29 17:45:39 +00:00
Add a "consume all ingredients of this recipe" button (this now closes #32)
This commit is contained in:
parent
9a8c61497b
commit
324487d395
@ -19,4 +19,17 @@ class RecipesApiController extends BaseApiController
|
|||||||
$this->RecipesService->AddNotFulfilledProductsToShoppingList($args['recipeId']);
|
$this->RecipesService->AddNotFulfilledProductsToShoppingList($args['recipeId']);
|
||||||
return $this->VoidApiActionResponse($response);
|
return $this->VoidApiActionResponse($response);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function ConsumeRecipe(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
$this->RecipesService->ConsumeRecipe($args['recipeId']);
|
||||||
|
return $this->VoidApiActionResponse($response);
|
||||||
|
}
|
||||||
|
catch (\Exception $ex)
|
||||||
|
{
|
||||||
|
return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage());
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -1010,6 +1010,37 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
"/recipes/consume-recipe/{recipeId}": {
|
||||||
|
"get": {
|
||||||
|
"description": "Consumes all products of the given recipe",
|
||||||
|
"tags": [
|
||||||
|
"Recipes"
|
||||||
|
],
|
||||||
|
"parameters": [
|
||||||
|
{
|
||||||
|
"in": "path",
|
||||||
|
"name": "recipeId",
|
||||||
|
"required": true,
|
||||||
|
"description": "A valid recipe id",
|
||||||
|
"schema": {
|
||||||
|
"type": "string"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"responses": {
|
||||||
|
"200": {
|
||||||
|
"description": "A VoidApiActionResponse object",
|
||||||
|
"content": {
|
||||||
|
"application/json": {
|
||||||
|
"schema": {
|
||||||
|
"$ref": "#/components/schemas/VoidApiActionResponse"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
"/habits/track-habit-execution/{habitId}": {
|
"/habits/track-habit-execution/{habitId}": {
|
||||||
"get": {
|
"get": {
|
||||||
"description": "Tracks an execution of the given habit",
|
"description": "Tracks an execution of the given habit",
|
||||||
|
@ -209,7 +209,10 @@ return array(
|
|||||||
'This cannot be lower than #1' => 'Dies darf nicht kleiner als #1 sein',
|
'This cannot be lower than #1' => 'Dies darf nicht kleiner als #1 sein',
|
||||||
'-1 means that this product never expires' => '-1 bedeuet, dass dieses Produkt niemals abläuft',
|
'-1 means that this product never expires' => '-1 bedeuet, dass dieses Produkt niemals abläuft',
|
||||||
'Quantity unit' => 'Mengeneinheit',
|
'Quantity unit' => 'Mengeneinheit',
|
||||||
'Only check if a single unit is in stock (a different quantity can then be used above)' => 'Nur prüfen, ob eine einzelne Einheit vorrätig ist (eine abweichende Mengeneinheit kann dann oben verwendet werden)',
|
'Only check if a single unit is in stock (a different quantity can then be used above)' => 'Nur prüfen, ob eine einzelne Einheit vorrätig ist (eine abweichende Mengeneinheit kann dann oben verwendet werden)',
|
||||||
|
'Are you sure to consume all ingredients needed by recipe "#1" (ingredients marked with "check only if a single unit is in stock" will be ignored)?' => 'Sicher, dass alle Zutaten die vom Rezept "#1" benötigt werden aus dem Bestand entfernt werden sollen (Zutaten markiert mit "nur prüfen, ob eine einzelne Einheit vorrätig ist" werden ignoriert)?',
|
||||||
|
'Removed all ingredients of recipe "#1" from stock' => 'Alle Zutaten, die vom Rezept "#1" benötigt werden, wurdem aus dem Bestand entfernt',
|
||||||
|
'Consume all ingredients needed by this recipe' => 'Alle Zutaten, die von diesem Rezept benötigt werden, aus dem Bestand enternen',
|
||||||
|
|
||||||
//Constants
|
//Constants
|
||||||
'manually' => 'Manuell',
|
'manually' => 'Manuell',
|
||||||
|
@ -104,6 +104,42 @@ $(document).on('click', '.recipe-order-missing-button', function(e)
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
$("#selectedRecipeConsumeButton").on('click', function(e)
|
||||||
|
{
|
||||||
|
var objectName = $(e.currentTarget).attr('data-recipe-name');
|
||||||
|
var objectId = $(e.currentTarget).attr('data-recipe-id');
|
||||||
|
|
||||||
|
bootbox.confirm({
|
||||||
|
message: L('Are you sure to consume all ingredients needed by recipe "#1" (ingredients marked with "check only if a single unit is in stock" will be ignored)?', objectName),
|
||||||
|
buttons: {
|
||||||
|
confirm: {
|
||||||
|
label: L('Yes'),
|
||||||
|
className: 'btn-success'
|
||||||
|
},
|
||||||
|
cancel: {
|
||||||
|
label: L('No'),
|
||||||
|
className: 'btn-danger'
|
||||||
|
}
|
||||||
|
},
|
||||||
|
callback: function(result)
|
||||||
|
{
|
||||||
|
if (result === true)
|
||||||
|
{
|
||||||
|
Grocy.Api.Get('recipes/consume-recipe/' + objectId,
|
||||||
|
function(result)
|
||||||
|
{
|
||||||
|
toastr.success(L('Removed all ingredients of recipe "#1" from stock', objectName));
|
||||||
|
},
|
||||||
|
function(xhr)
|
||||||
|
{
|
||||||
|
console.error(xhr);
|
||||||
|
}
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
recipesTables.on('select', function(e, dt, type, indexes)
|
recipesTables.on('select', function(e, dt, type, indexes)
|
||||||
{
|
{
|
||||||
if (type === 'row')
|
if (type === 'row')
|
||||||
|
@ -91,6 +91,7 @@ $app->group('/api', function()
|
|||||||
|
|
||||||
// Recipes
|
// Recipes
|
||||||
$this->get('/recipes/add-not-fulfilled-products-to-shopping-list/{recipeId}', '\Grocy\Controllers\RecipesApiController:AddNotFulfilledProductsToShoppingList');
|
$this->get('/recipes/add-not-fulfilled-products-to-shopping-list/{recipeId}', '\Grocy\Controllers\RecipesApiController:AddNotFulfilledProductsToShoppingList');
|
||||||
|
$this->get('/recipes/consume-recipe/{recipeId}', '\Grocy\Controllers\RecipesApiController:ConsumeRecipe');
|
||||||
|
|
||||||
// Habits
|
// Habits
|
||||||
$this->get('/habits/track-habit-execution/{habitId}', '\Grocy\Controllers\HabitsApiController:TrackHabitExecution');
|
$this->get('/habits/track-habit-execution/{habitId}', '\Grocy\Controllers\HabitsApiController:TrackHabitExecution');
|
||||||
|
@ -2,8 +2,18 @@
|
|||||||
|
|
||||||
namespace Grocy\Services;
|
namespace Grocy\Services;
|
||||||
|
|
||||||
|
use \Grocy\Services\StockService;
|
||||||
|
|
||||||
class RecipesService extends BaseService
|
class RecipesService extends BaseService
|
||||||
{
|
{
|
||||||
|
public function __construct()
|
||||||
|
{
|
||||||
|
parent::__construct();
|
||||||
|
$this->StockService = new StockService();
|
||||||
|
}
|
||||||
|
|
||||||
|
protected $StockService;
|
||||||
|
|
||||||
public function GetRecipesFulfillment()
|
public function GetRecipesFulfillment()
|
||||||
{
|
{
|
||||||
$sql = 'SELECT * from recipes_fulfillment';
|
$sql = 'SELECT * from recipes_fulfillment';
|
||||||
@ -38,4 +48,27 @@ class RecipesService extends BaseService
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function ConsumeRecipe($recipeId)
|
||||||
|
{
|
||||||
|
if (!$this->RecipeExists($recipeId))
|
||||||
|
{
|
||||||
|
throw new \Exception('Recipe does not exist');
|
||||||
|
}
|
||||||
|
|
||||||
|
$recipePositions = $this->Database->recipes_pos()->where('recipe_id', $recipeId)->fetchAll();
|
||||||
|
foreach ($recipePositions as $recipePosition)
|
||||||
|
{
|
||||||
|
if ($recipePosition->only_check_single_unit_in_stock == 0)
|
||||||
|
{
|
||||||
|
$this->StockService->ConsumeProduct($recipePosition->product_id, $recipePosition->amount, false, StockService::TRANSACTION_TYPE_CONSUME);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private function RecipeExists($recipeId)
|
||||||
|
{
|
||||||
|
$recipeRow = $this->Database->recipes()->where('id = :1', $recipeId)->fetch();
|
||||||
|
return $recipeRow !== null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -39,9 +39,6 @@
|
|||||||
<a class="btn btn-sm btn-danger recipe-delete-button" href="#" data-recipe-id="{{ $recipe->id }}" data-recipe-name="{{ $recipe->name }}">
|
<a class="btn btn-sm btn-danger recipe-delete-button" href="#" data-recipe-id="{{ $recipe->id }}" data-recipe-name="{{ $recipe->name }}">
|
||||||
<i class="fas fa-trash"></i>
|
<i class="fas fa-trash"></i>
|
||||||
</a>
|
</a>
|
||||||
<a class="btn btn-sm btn-primary recipe-order-missing-button @if(FindObjectInArrayByPropertyValue($recipesSumFulfillment, 'recipe_id', $recipe->id)->need_fulfilled_with_shopping_list == 1){{ disabled }}@endif" href="#" title="{{ $L('Put missing products on shopping list') }}" data-recipe-id="{{ $recipe->id }}" data-recipe-name="{{ $recipe->name }}">
|
|
||||||
<i class="fas fa-cart-plus"></i>
|
|
||||||
</a>
|
|
||||||
</td>
|
</td>
|
||||||
<td>
|
<td>
|
||||||
{{ $recipe->name }}
|
{{ $recipe->name }}
|
||||||
@ -60,7 +57,13 @@
|
|||||||
<div class="col-xs-12 col-md-6">
|
<div class="col-xs-12 col-md-6">
|
||||||
<div id="selectedRecipeCard" class="card">
|
<div id="selectedRecipeCard" class="card">
|
||||||
<div class="card-header">
|
<div class="card-header">
|
||||||
<i class="fas fa-cocktail"></i> {{ $selectedRecipe->name }}
|
<i class="fas fa-cocktail"></i> {{ $selectedRecipe->name }}
|
||||||
|
<a id="selectedRecipeConsumeButton" class="btn btn-sm btn-outline-success py-0" href="#" title="{{ $L('Consume all ingredients needed by this recipe') }}" data-recipe-id="{{ $selectedRecipe->id }}" data-recipe-name="{{ $selectedRecipe->name }}">
|
||||||
|
<i class="fas fa-utensils"></i>
|
||||||
|
</a>
|
||||||
|
<a class="btn btn-sm btn-outline-primary py-0 recipe-order-missing-button @if(FindObjectInArrayByPropertyValue($recipesSumFulfillment, 'recipe_id', $selectedRecipe->id)->need_fulfilled_with_shopping_list == 1){{ disabled }}@endif" href="#" title="{{ $L('Put missing products on shopping list') }}" data-recipe-id="{{ $selectedRecipe->id }}" data-recipe-name="{{ $selectedRecipe->name }}">
|
||||||
|
<i class="fas fa-cart-plus"></i>
|
||||||
|
</a>
|
||||||
<a id="selectedRecipeToggleFullscreenButton" class="btn btn-sm btn-outline-secondary py-0 float-right" href="#" title="{{ $L('Expand to fullscreen') }}">
|
<a id="selectedRecipeToggleFullscreenButton" class="btn btn-sm btn-outline-secondary py-0 float-right" href="#" title="{{ $L('Expand to fullscreen') }}">
|
||||||
<i class="fas fa-expand-arrows-alt"></i>
|
<i class="fas fa-expand-arrows-alt"></i>
|
||||||
</a>
|
</a>
|
||||||
|
Loading…
x
Reference in New Issue
Block a user