diff --git a/app/Enums/Products/ProductLabelEnum.php b/app/Enums/Products/ProductLabelEnum.php index a685d81..4bd67a6 100644 --- a/app/Enums/Products/ProductLabelEnum.php +++ b/app/Enums/Products/ProductLabelEnum.php @@ -7,9 +7,12 @@ use Kwaadpepper\Enum\BaseEnum; /** * @method static self bio() * @method static self lr() - * @method static self bea() - * @method static self nutriscore() + * @method static self bea_a() + * @method static self bea_b() + * @method static self nutriscore_a() + * @method static self nutriscore_b() * @method static self planetscore() + * @method static self igp() */ final class ProductLabelEnum extends BaseEnum { @@ -23,9 +26,12 @@ final class ProductLabelEnum extends BaseEnum return [ 'bio' => 0, 'lr' => 1, - 'bea' => 2, - 'nutriscore' => 3, - 'planetscore' => 4 + 'bea_a' => 2, + 'bea_b' => 3, + 'nutriscore_a' => 4, + 'nutriscore_b' => 5, + 'planetscore' => 6, + 'igp' => 7 ]; } @@ -39,9 +45,12 @@ final class ProductLabelEnum extends BaseEnum return [ 'bio' => trans('Bio'), 'lr' => trans('Label Rouge'), - 'bea' => trans('Bea'), - 'nutriscore' => trans('Nutriscore'), + 'bea_a' => trans('Bea A'), + 'bea_b' => trans('Bea B'), + 'nutriscore_a' => trans('Nutriscore A'), + 'nutriscore_b' => trans('Nutriscore B'), 'planetscore' => trans('PlanetScore'), + 'igp' => trans('IGP') ]; } } diff --git a/app/Enums/Ranges/RangeCategoryEnum.php b/app/Enums/Ranges/RangeCategoryEnum.php index 9a0ab95..ca29ffa 100644 --- a/app/Enums/Ranges/RangeCategoryEnum.php +++ b/app/Enums/Ranges/RangeCategoryEnum.php @@ -8,6 +8,7 @@ use Kwaadpepper\Enum\BaseEnum; * @method static self poultry() * @method static self egg() * @method static self partners() + * @method static self fields() */ final class RangeCategoryEnum extends BaseEnum { @@ -21,7 +22,8 @@ final class RangeCategoryEnum extends BaseEnum return [ 'poultry' => 0, 'egg' => 1, - 'partners' => 2 + 'partners' => 2, + 'fields' => 3 ]; } @@ -33,9 +35,10 @@ final class RangeCategoryEnum extends BaseEnum protected static function labels(): array { return [ - 'poultry' => trans('🐔 Vollaille'), + 'poultry' => trans('🐔 Volaille'), 'egg' => trans('🥚 Oeuf'), 'partners' => trans('🤝 Produits partenaires'), + 'fields' => trans('🌳 Plein champs'), ]; } } diff --git a/app/Http/Requests/Bo/Products/StoreProductRequest.php b/app/Http/Requests/Bo/Products/StoreProductRequest.php index ecb85fc..a6d708f 100644 --- a/app/Http/Requests/Bo/Products/StoreProductRequest.php +++ b/app/Http/Requests/Bo/Products/StoreProductRequest.php @@ -70,6 +70,7 @@ class StoreProductRequest extends FormRequest 'status' => 'required|boolean', 'range_id' => 'required|exists:ranges,id', + 'ref_article' => 'required|numeric|min:0', 'ingredients' => 'required|string|min:15', 'preparation_advices' => 'required|string|min:15', 'sales_pitch' => 'required|string|min:15', @@ -97,6 +98,9 @@ class StoreProductRequest extends FormRequest 'saturated_fatty_acids' => 'required|numeric', 'dietary_fiber' => 'required|numeric', 'salt' => 'required|numeric', + + 'link1' => self::getUrlValidationRules(), + 'link2' => self::getUrlValidationRules(), ], $this->pictureRules('picture', 700, 700, 700, 700), $this->pictureRules('picture_thumb', 300, 300, 300, 300) @@ -136,6 +140,35 @@ class StoreProductRequest extends FormRequest 'nutritional.saturated_fatty_acids' => trans('acides gras saturés'), 'nutritional.dietary_fiber' => trans('fibres alimentaires'), 'nutritional.salt' => trans('sel'), + + 'link1' => trans('lien 1'), + 'link2' => trans('lien 2'), ]; } + + /** + * Url validation rules + * Validates an internal url format + * + * @return array + */ + public static function getUrlValidationRules(): array + { + return ['nullable', function ($attribute, $value, $fail) { + $params = collect(\explode('#', \ltrim(\rtrim($value, '#'), '#'))); + if ( + !\in_array( + $params->get(0), + [Breeder::class, Recipe::class] + ) + ) { + $fail(trans('Invalid internal url')); + return; + } + // Check if model id exists. Param 0 is class, 1 is id. + if (!\forward_static_call([$params->get(0), 'find'], $params->get(1))) { + $fail(trans("$attribute n\'est plus un lien valide.")); + } + }]; + } } diff --git a/app/Http/Requests/Bo/Ranges/StoreRangeRequest.php b/app/Http/Requests/Bo/Ranges/StoreRangeRequest.php index 58a4da0..fc8f647 100644 --- a/app/Http/Requests/Bo/Ranges/StoreRangeRequest.php +++ b/app/Http/Requests/Bo/Ranges/StoreRangeRequest.php @@ -57,6 +57,7 @@ class StoreRangeRequest extends FormRequest 'seo_title' => 'required|min:45|max:70', 'seo_description' => 'required|min:50|max:160', 'description' => 'required|string|min:15', + 'argumentation' => 'required|string|min:15', 'picture_alt' => 'required_with:picture|nullable|string|min:6|max:255', 'picture_title' => 'required_with:picture|nullable|string|min:6|max:255', 'picture_thumb_alt' => 'required_with:picture_thumb|nullable|string|min:6|max:255', @@ -85,6 +86,7 @@ class StoreRangeRequest extends FormRequest 'seo_title' => trans('title') . ' seo', 'seo_description' => trans('description') . ' seo', 'description' => trans('description'), + 'argumentation' => trans('argumentation'), 'picture' => trans('illustration'), 'picture_alt' => trans('Texte alternatif de l\'illustration'), 'picture_title' => trans('Titre de l\'illustration'), @@ -107,7 +109,6 @@ class StoreRangeRequest extends FormRequest */ public static function getUrlValidationRules(): array { - // phpcs:ignore Generic.CodeAnalysis.UnusedFunctionParameter.FoundInExtendedClassBeforeLastUsed return ['nullable', function ($attribute, $value, $fail) { $params = collect(\explode('#', \ltrim(\rtrim($value, '#'), '#'))); if ( diff --git a/app/Models/Product.php b/app/Models/Product.php index 74d3031..b88bc17 100644 --- a/app/Models/Product.php +++ b/app/Models/Product.php @@ -31,6 +31,7 @@ class Product extends Model 'picture_thumb_title', 'picture_thumb_alt', 'labels', + 'ref_article', 'ingredients', 'preparation_advices', 'sales_pitch', @@ -45,7 +46,9 @@ class Product extends Model 'show_sales_pitch', 'show_allergen_list', 'show_nutrionnal_values', - 'show_portions' + 'show_portions', + 'link1', + 'link2' ]; /** @@ -94,6 +97,12 @@ class Product extends Model } else { $model->unpublish_at = null; } + if ($model->link1) { + self::validateLinkAttribute('link1', $model->link1); + } + if ($model->link2) { + self::validateLinkAttribute('link2', $model->link2); + } }); static::updating(function (self $model) { static::assertTitleIsUnique($model->title, $model->id); @@ -118,6 +127,12 @@ class Product extends Model if ($model->picture_thumb != $model->getOriginal('picture_thumb')) { $model->picture_thumb = ToolboxHelper::storeImage($model, $model->picture_thumb); } + if ($model->link1) { + self::validateLinkAttribute('link1', $model->link1); + } + if ($model->link2) { + self::validateLinkAttribute('link2', $model->link2); + } }); static::updated(function (self $model) { ToolboxHelper::removeUnusedImagesOnCkEditor($model, 'description'); diff --git a/app/Models/Range.php b/app/Models/Range.php index 42826d2..0bbca38 100644 --- a/app/Models/Range.php +++ b/app/Models/Range.php @@ -27,6 +27,7 @@ class Range extends Model 'seo_title', 'seo_description', 'description', + 'argumentation', 'category', 'picture', 'picture_title', @@ -38,7 +39,7 @@ class Range extends Model 'publish_at', 'unpublish_at', 'link1', - 'link2', + 'link2' ]; /** @@ -73,8 +74,10 @@ class Range extends Model static::creating(function (self $model) { static::assertTitleIsUnique($model->title); ToolboxHelper::assertNoInternalBoUrls('description', $model->description); + ToolboxHelper::assertNoInternalBoUrls('argumentation', $model->argumentation); $model->slug = Str::slug($model->title); $model->description = clean($model->description); + $model->argumentation = clean($model->argumentation); $model->picture = ToolboxHelper::storeImage($model, $model->picture); $model->picture_thumb = ToolboxHelper::storeImage($model, $model->picture_thumb); if (!$model->status) { @@ -92,6 +95,7 @@ class Range extends Model static::updating(function (self $model) { static::assertTitleIsUnique($model->title, $model->id); ToolboxHelper::assertNoInternalBoUrls('description', $model->description); + ToolboxHelper::assertNoInternalBoUrls('argumentation', $model->argumentation); if ($model->picture != $model->getOriginal('picture')) { $model->picture = ToolboxHelper::storeImage($model, $model->picture); } diff --git a/database/factories/ProductFactory.php b/database/factories/ProductFactory.php index a1033cb..9aeafa6 100644 --- a/database/factories/ProductFactory.php +++ b/database/factories/ProductFactory.php @@ -27,7 +27,7 @@ class ProductFactory extends Factory 'title' => $title, 'slug' => \Illuminate\Support\Str::slug($title), 'seo_title' => $this->faker->words(8, true), - 'seo_description' => $this->faker->words(25, true), + 'seo_description' => $this->faker->words(20, true), 'description' => $this->faker->words(25, true), 'picture' => '/assets/images/products/product_fake_700_700.jpg', 'picture_title' => $this->faker->words(8, true), @@ -36,6 +36,7 @@ class ProductFactory extends Factory 'picture_thumb_title' => $this->faker->words(8, true), 'picture_thumb_alt' => $this->faker->words(8, true), 'labels' => collect(ProductLabelEnum::toArray())->random(rand(0, 4))->all(), + 'ref_article' => $this->faker->numberBetween(0, 1000000000), 'ingredients' => $this->faker->words(8, true), 'preparation_advices' => $this->faker->text(\mt_rand(15, 150)), 'sales_pitch' => $this->faker->text(\mt_rand(15, 150)), diff --git a/database/factories/RangeFactory.php b/database/factories/RangeFactory.php index 5337ddd..73f1db1 100644 --- a/database/factories/RangeFactory.php +++ b/database/factories/RangeFactory.php @@ -28,8 +28,9 @@ class RangeFactory extends Factory 'title' => $title, 'slug' => Str::slug($title), 'seo_title' => $this->faker->words(8, true), - 'seo_description' => $this->faker->words(25, true), + 'seo_description' => $this->faker->words(20, true), 'description' => $this->faker->words(25, true), + 'argumentation' => $this->faker->words(25, true), 'category' => collect(RangeCategoryEnum::toArray())->random(1)->get(0), 'picture' => '/assets/images/ranges/range_fake_700_700.jpg', 'picture_title' => $this->faker->words(8, true), diff --git a/database/migrations/2022_07_12_164017_create_ranges_table.php b/database/migrations/2022_07_12_164017_create_ranges_table.php index ad8c5b5..6b9bd7d 100644 --- a/database/migrations/2022_07_12_164017_create_ranges_table.php +++ b/database/migrations/2022_07_12_164017_create_ranges_table.php @@ -25,6 +25,7 @@ class CreateRangesTable extends Migration ->comment('Utilisé pour la balise méta description de la gamme. De 50 à 160 chars recommandés.'); $table->text('description')->comment('Description de la gamme'); + $table->text('argumentation')->comment('Argumentation sur les labels'); $table->unsignedTinyInteger('category')->comment('Enum Ranges\\RangeCategoryEnum'); diff --git a/database/migrations/2022_07_12_164018_create_products_table.php b/database/migrations/2022_07_12_164018_create_products_table.php index 2ab24e3..9e353a2 100644 --- a/database/migrations/2022_07_12_164018_create_products_table.php +++ b/database/migrations/2022_07_12_164018_create_products_table.php @@ -37,6 +37,7 @@ class CreateProductsTable extends Migration $table->json('labels')->comment('List of Products\\ProductLabelEnum'); + $table->text('ref_article')->comment('Ref. Article Inco'); $table->text('ingredients')->comment('Ingredients'); $table->text('preparation_advices')->comment('Preparation advices'); $table->text('sales_pitch')->comment('Arguments de vente'); @@ -57,6 +58,11 @@ class CreateProductsTable extends Migration $table->timestamp('unpublish_at')->nullable() ->comment('The date where the product status state should be set off.'); + $table->string('link1')->nullable() + ->comment('Category Link 1 #App\Models\Model#ID#, Sould be validated on store and update'); + $table->string('link2')->nullable() + ->comment('Category Link 2 #App\Models\Model#ID#, Sould be validated on store and update'); + $table->foreignIdFor(Range::class)->constrained(); $table->timestamps(); diff --git a/package-lock.json b/package-lock.json index 10c1ce9..15ace42 100644 --- a/package-lock.json +++ b/package-lock.json @@ -16988,4 +16988,4 @@ "dev": true } } -} +} \ No newline at end of file diff --git a/resources/ts/components/bo/ModelLinkComponent.vue b/resources/ts/components/bo/ModelLinkComponent.vue index 9e718d2..31d923c 100644 --- a/resources/ts/components/bo/ModelLinkComponent.vue +++ b/resources/ts/components/bo/ModelLinkComponent.vue @@ -12,16 +12,14 @@ :filterable="true" :searchable="true" > -