mirror of https://github.com/kcal-app/kcal.git
Update ingredient handlers on recipe save
This commit is contained in:
parent
72b62e420b
commit
47a8f5675f
|
|
@ -2,9 +2,9 @@
|
||||||
|
|
||||||
namespace App\Http\Controllers;
|
namespace App\Http\Controllers;
|
||||||
|
|
||||||
use App\Models\Food;
|
|
||||||
use App\Models\IngredientAmount;
|
use App\Models\IngredientAmount;
|
||||||
use App\Models\Recipe;
|
use App\Models\Recipe;
|
||||||
|
use App\Models\RecipeSeparator;
|
||||||
use App\Models\RecipeStep;
|
use App\Models\RecipeStep;
|
||||||
use App\Rules\ArrayNotEmpty;
|
use App\Rules\ArrayNotEmpty;
|
||||||
use App\Rules\StringIsDecimalOrFraction;
|
use App\Rules\StringIsDecimalOrFraction;
|
||||||
|
|
@ -186,6 +186,12 @@ class RecipeController extends Controller
|
||||||
'ingredients.key.*' => ['nullable', 'int'],
|
'ingredients.key.*' => ['nullable', 'int'],
|
||||||
'ingredients.weight' => ['required', 'array', new ArrayNotEmpty],
|
'ingredients.weight' => ['required', 'array', new ArrayNotEmpty],
|
||||||
'ingredients.weight.*' => ['required', 'int'],
|
'ingredients.weight.*' => ['required', 'int'],
|
||||||
|
'separators.key' => ['nullable', 'array'],
|
||||||
|
'separators.key.*' => ['nullable', 'int'],
|
||||||
|
'separators.weight' => ['nullable', 'array'],
|
||||||
|
'separators.weight.*' => ['required', 'int'],
|
||||||
|
'separators.text' => ['nullable', 'array'],
|
||||||
|
'separators.text.*' => ['nullable', 'string'],
|
||||||
'steps.step' => ['required', 'array', new ArrayNotEmpty],
|
'steps.step' => ['required', 'array', new ArrayNotEmpty],
|
||||||
'steps.step.*' => ['nullable', 'string'],
|
'steps.step.*' => ['nullable', 'string'],
|
||||||
'steps.key' => ['nullable', 'array'],
|
'steps.key' => ['nullable', 'array'],
|
||||||
|
|
@ -213,52 +219,11 @@ class RecipeController extends Controller
|
||||||
try {
|
try {
|
||||||
DB::transaction(function () use ($recipe, $input) {
|
DB::transaction(function () use ($recipe, $input) {
|
||||||
$recipe->saveOrFail();
|
$recipe->saveOrFail();
|
||||||
|
$this->updateIngredients($recipe, $input);
|
||||||
// Delete any removed ingredients.
|
if (isset($input['separators'])) {
|
||||||
$removed = array_diff($recipe->ingredientAmounts->keys()->all(), $input['ingredients']['key']);
|
$this->updateIngredientSeparators($recipe, $input);
|
||||||
foreach ($removed as $removed_key) {
|
|
||||||
$recipe->ingredientAmounts[$removed_key]->delete();
|
|
||||||
}
|
}
|
||||||
|
$this->updateSteps($recipe, $input);
|
||||||
// Add/update current ingredients.
|
|
||||||
$ingredient_amounts = [];
|
|
||||||
foreach (array_filter($input['ingredients']['id']) as $key => $ingredient_id) {
|
|
||||||
if (!is_null($input['ingredients']['key'][$key])) {
|
|
||||||
$ingredient_amounts[$key] = $recipe->ingredientAmounts[$input['ingredients']['key'][$key]];
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
$ingredient_amounts[$key] = new IngredientAmount();
|
|
||||||
}
|
|
||||||
$ingredient_amounts[$key]->fill([
|
|
||||||
'amount' => Number::floatFromString($input['ingredients']['amount'][$key]),
|
|
||||||
'unit' => $input['ingredients']['unit'][$key],
|
|
||||||
'detail' => $input['ingredients']['detail'][$key],
|
|
||||||
'weight' => (int) $input['ingredients']['weight'][$key],
|
|
||||||
]);
|
|
||||||
$ingredient_amounts[$key]->ingredient()
|
|
||||||
->associate($input['ingredients']['type'][$key]::where('id', $ingredient_id)->first());
|
|
||||||
}
|
|
||||||
$recipe->ingredientAmounts()->saveMany($ingredient_amounts);
|
|
||||||
|
|
||||||
$steps = [];
|
|
||||||
$number = 1;
|
|
||||||
|
|
||||||
// Delete any removed steps.
|
|
||||||
$removed = array_diff($recipe->steps->keys()->all(), $input['steps']['key']);
|
|
||||||
foreach ($removed as $removed_key) {
|
|
||||||
$recipe->steps[$removed_key]->delete();
|
|
||||||
}
|
|
||||||
|
|
||||||
foreach (array_filter($input['steps']['step']) as $key => $step) {
|
|
||||||
if (!is_null($input['steps']['key'][$key])) {
|
|
||||||
$steps[$key] = $recipe->steps[$input['steps']['key'][$key]];
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
$steps[$key] = new RecipeStep();
|
|
||||||
}
|
|
||||||
$steps[$key]->fill(['number' => $number++, 'step' => $step]);
|
|
||||||
}
|
|
||||||
$recipe->steps()->saveMany($steps);
|
|
||||||
});
|
});
|
||||||
} catch (\Exception $e) {
|
} catch (\Exception $e) {
|
||||||
DB::rollBack();
|
DB::rollBack();
|
||||||
|
|
@ -293,6 +258,106 @@ class RecipeController extends Controller
|
||||||
return redirect()->route('recipes.show', $recipe);
|
return redirect()->route('recipes.show', $recipe);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Updates recipe ingredients data based on input.
|
||||||
|
*
|
||||||
|
* @param \App\Models\Recipe $recipe
|
||||||
|
* @param array $input
|
||||||
|
*
|
||||||
|
* @throws \Exception
|
||||||
|
*/
|
||||||
|
private function updateIngredients(Recipe $recipe, array $input): void {
|
||||||
|
// Delete any removed ingredients.
|
||||||
|
$removed = array_diff($recipe->ingredientAmounts->keys()->all(), $input['ingredients']['key']);
|
||||||
|
foreach ($removed as $removed_key) {
|
||||||
|
$recipe->ingredientAmounts[$removed_key]->delete();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Add/update current ingredients.
|
||||||
|
$ingredient_amounts = [];
|
||||||
|
foreach (array_filter($input['ingredients']['id']) as $key => $ingredient_id) {
|
||||||
|
if (!is_null($input['ingredients']['key'][$key])) {
|
||||||
|
$ingredient_amounts[$key] = $recipe->ingredientAmounts[$input['ingredients']['key'][$key]];
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
$ingredient_amounts[$key] = new IngredientAmount();
|
||||||
|
}
|
||||||
|
$ingredient_amounts[$key]->fill([
|
||||||
|
'amount' => Number::floatFromString($input['ingredients']['amount'][$key]),
|
||||||
|
'unit' => $input['ingredients']['unit'][$key],
|
||||||
|
'detail' => $input['ingredients']['detail'][$key],
|
||||||
|
'weight' => (int) $input['ingredients']['weight'][$key],
|
||||||
|
]);
|
||||||
|
$ingredient_amounts[$key]->ingredient()
|
||||||
|
->associate($input['ingredients']['type'][$key]::where('id', $ingredient_id)->first());
|
||||||
|
}
|
||||||
|
$recipe->ingredientAmounts()->saveMany($ingredient_amounts);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Updates recipe steps data based on input.
|
||||||
|
*
|
||||||
|
* @param \App\Models\Recipe $recipe
|
||||||
|
* @param array $input
|
||||||
|
*
|
||||||
|
* @throws \Exception
|
||||||
|
*/
|
||||||
|
private function updateSteps(Recipe $recipe, array $input): void {
|
||||||
|
$steps = [];
|
||||||
|
$number = 1;
|
||||||
|
|
||||||
|
// Delete any removed steps.
|
||||||
|
$removed = array_diff($recipe->steps->keys()->all(), $input['steps']['key']);
|
||||||
|
foreach ($removed as $removed_key) {
|
||||||
|
$recipe->steps[$removed_key]->delete();
|
||||||
|
}
|
||||||
|
|
||||||
|
foreach (array_filter($input['steps']['step']) as $key => $step) {
|
||||||
|
if (!is_null($input['steps']['key'][$key])) {
|
||||||
|
$steps[$key] = $recipe->steps[$input['steps']['key'][$key]];
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
$steps[$key] = new RecipeStep();
|
||||||
|
}
|
||||||
|
$steps[$key]->fill(['number' => $number++, 'step' => $step]);
|
||||||
|
}
|
||||||
|
$recipe->steps()->saveMany($steps);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Updates recipe ingredient separators data based on input.
|
||||||
|
*
|
||||||
|
* @param \App\Models\Recipe $recipe
|
||||||
|
* @param array $input
|
||||||
|
*
|
||||||
|
* @throws \Exception
|
||||||
|
*/
|
||||||
|
private function updateIngredientSeparators(Recipe $recipe, array $input): void {
|
||||||
|
// Delete any removed separators.
|
||||||
|
$removed = array_diff($recipe->ingredientSeparators->keys()->all(), $input['separators']['key']);
|
||||||
|
foreach ($removed as $removed_key) {
|
||||||
|
$recipe->ingredientSeparators[$removed_key]->delete();
|
||||||
|
}
|
||||||
|
|
||||||
|
// Add/update current ingredients.
|
||||||
|
$ingredient_separators = [];
|
||||||
|
foreach ($input['separators']['key'] as $index => $key) {
|
||||||
|
if (!is_null($key)) {
|
||||||
|
$ingredient_separators[$index] = $recipe->ingredientSeparators[$key];
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
$ingredient_separators[$index] = new RecipeSeparator();
|
||||||
|
}
|
||||||
|
$ingredient_separators[$index]->fill([
|
||||||
|
'container' => 'ingredients',
|
||||||
|
'text' => $input['separators']['text'][$index],
|
||||||
|
'weight' => (int) $input['separators']['weight'][$index],
|
||||||
|
]);
|
||||||
|
|
||||||
|
}
|
||||||
|
$recipe->ingredientSeparators()->saveMany($ingredient_separators);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Confirm removal of specified resource.
|
* Confirm removal of specified resource.
|
||||||
*/
|
*/
|
||||||
|
|
|
||||||
|
|
@ -28,7 +28,7 @@ use Illuminate\Database\Eloquent\Relations\BelongsTo;
|
||||||
* @method static \Illuminate\Database\Eloquent\Builder|RecipeSeparator whereWeight($value)
|
* @method static \Illuminate\Database\Eloquent\Builder|RecipeSeparator whereWeight($value)
|
||||||
* @mixin \Eloquent
|
* @mixin \Eloquent
|
||||||
*/
|
*/
|
||||||
class RecipeSeparator extends Model
|
final class RecipeSeparator extends Model
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
* @inheritdoc
|
* @inheritdoc
|
||||||
|
|
|
||||||
|
|
@ -42,6 +42,8 @@ class ArrayFormat
|
||||||
*
|
*
|
||||||
* @return array
|
* @return array
|
||||||
* The flipped array.
|
* The flipped array.
|
||||||
|
*
|
||||||
|
* @todo Return Collection instead of array.
|
||||||
*/
|
*/
|
||||||
public static function flipTwoDimensionalKeys(array $array): array {
|
public static function flipTwoDimensionalKeys(array $array): array {
|
||||||
$flipped = [];
|
$flipped = [];
|
||||||
|
|
|
||||||
|
|
@ -19,7 +19,7 @@ class CreateRecipeSeparatorsTable extends Migration
|
||||||
$table->foreignIdFor(Recipe::class)->index()->constrained()->cascadeOnUpdate()->cascadeOnDelete();
|
$table->foreignIdFor(Recipe::class)->index()->constrained()->cascadeOnUpdate()->cascadeOnDelete();
|
||||||
$table->string('container')->index();
|
$table->string('container')->index();
|
||||||
$table->unsignedInteger('weight')->index();
|
$table->unsignedInteger('weight')->index();
|
||||||
$table->longText('text');
|
$table->longText('text')->nullable();
|
||||||
$table->timestamps();
|
$table->timestamps();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue