Imagenes en productos.
This commit is contained in:
@@ -68,13 +68,39 @@ class ProductosController extends Controller
|
|||||||
'min_stock_alert' => 'required|integer|min:0',
|
'min_stock_alert' => 'required|integer|min:0',
|
||||||
'type' => 'required|in:bike,accessory,clothing,spare,service,children,skate,rollers,other',
|
'type' => 'required|in:bike,accessory,clothing,spare,service,children,skate,rollers,other',
|
||||||
'serial_number' => 'nullable|string|max:100',
|
'serial_number' => 'nullable|string|max:100',
|
||||||
'image' => 'nullable|image|mimes:jpeg,png,jpg,webp|max:2048',
|
'image' => 'nullable|image|mimes:jpeg,png,jpg,webp|max:20480',
|
||||||
'suppliers_id' => 'required|exists:suppliers,id',
|
'suppliers_id' => 'required|exists:suppliers,id',
|
||||||
'description' => 'nullable|string'
|
'description' => 'nullable|string'
|
||||||
|
], [
|
||||||
|
'image.uploaded' => 'La imagen supera el límite de subida permitido por el servidor.',
|
||||||
|
'image.max' => 'La imagen no debe pesar más de 20 MB.',
|
||||||
|
'image.image' => 'El archivo debe ser una imagen válida.',
|
||||||
|
'image.mimes' => 'La imagen debe tener formato jpeg, png, jpg o webp.',
|
||||||
]);
|
]);
|
||||||
|
|
||||||
if ($request->hasFile('image')) {
|
if ($request->hasFile('image')) {
|
||||||
$path = $request->file('image')->store('products', 'public');
|
$file = $request->file('image');
|
||||||
|
|
||||||
|
// Elevar temporalmente el límite de memoria para procesar la imagen
|
||||||
|
ini_set('memory_limit', '512M');
|
||||||
|
|
||||||
|
// Usar Intervention Image v4 con driver GD para procesar la imagen
|
||||||
|
$manager = new \Intervention\Image\ImageManager(new \Intervention\Image\Drivers\Gd\Driver());
|
||||||
|
$image = $manager->decode($file->getRealPath());
|
||||||
|
|
||||||
|
// Redimensionar proporcionalmente si excede 1200px
|
||||||
|
if ($image->width() > 1200 || $image->height() > 1200) {
|
||||||
|
$image->scale(width: 1200, height: 1200);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Comprimir a JPEG con 80% de calidad
|
||||||
|
$encoded = $image->encode(new \Intervention\Image\Encoders\JpegEncoder(80));
|
||||||
|
|
||||||
|
// Nombre de archivo único
|
||||||
|
$path = 'products/' . uniqid() . '.jpg';
|
||||||
|
|
||||||
|
// Guardar en disco public
|
||||||
|
Storage::disk('public')->put($path, $encoded->toString());
|
||||||
$validated['image_path'] = $path;
|
$validated['image_path'] = $path;
|
||||||
}
|
}
|
||||||
unset($validated['image']);
|
unset($validated['image']);
|
||||||
@@ -106,9 +132,14 @@ class ProductosController extends Controller
|
|||||||
'stock_quantity' => 'required|integer|min:0',
|
'stock_quantity' => 'required|integer|min:0',
|
||||||
'min_stock_alert' => 'required|integer|min:0',
|
'min_stock_alert' => 'required|integer|min:0',
|
||||||
'serial_number' => 'nullable|string|max:100',
|
'serial_number' => 'nullable|string|max:100',
|
||||||
'image' => 'nullable|image|mimes:jpeg,png,jpg,webp|max:2048',
|
'image' => 'nullable|image|mimes:jpeg,png,jpg,webp|max:20480',
|
||||||
'suppliers_id' => 'required|exists:suppliers,id',
|
'suppliers_id' => 'required|exists:suppliers,id',
|
||||||
'description' => 'nullable|string'
|
'description' => 'nullable|string'
|
||||||
|
], [
|
||||||
|
'image.uploaded' => 'La imagen supera el límite de subida permitido por el servidor.',
|
||||||
|
'image.max' => 'La imagen no debe pesar más de 20 MB.',
|
||||||
|
'image.image' => 'El archivo debe ser una imagen válida.',
|
||||||
|
'image.mimes' => 'La imagen debe tener formato jpeg, png, jpg o webp.',
|
||||||
]);
|
]);
|
||||||
|
|
||||||
if ($request->hasFile('image')) {
|
if ($request->hasFile('image')) {
|
||||||
@@ -116,7 +147,28 @@ class ProductosController extends Controller
|
|||||||
Storage::disk('public')->delete($product->image_path);
|
Storage::disk('public')->delete($product->image_path);
|
||||||
}
|
}
|
||||||
|
|
||||||
$path = $request->file('image')->store('products', 'public');
|
$file = $request->file('image');
|
||||||
|
|
||||||
|
// Elevar temporalmente el límite de memoria para procesar la imagen
|
||||||
|
ini_set('memory_limit', '512M');
|
||||||
|
|
||||||
|
// Usar Intervention Image v4 con driver GD para procesar la imagen
|
||||||
|
$manager = new \Intervention\Image\ImageManager(new \Intervention\Image\Drivers\Gd\Driver());
|
||||||
|
$image = $manager->decode($file->getRealPath());
|
||||||
|
|
||||||
|
// Redimensionar proporcionalmente si excede 1200px
|
||||||
|
if ($image->width() > 1200 || $image->height() > 1200) {
|
||||||
|
$image->scale(width: 1200, height: 1200);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Comprimir a JPEG con 80% de calidad
|
||||||
|
$encoded = $image->encode(new \Intervention\Image\Encoders\JpegEncoder(80));
|
||||||
|
|
||||||
|
// Nombre de archivo único
|
||||||
|
$path = 'products/' . uniqid() . '.jpg';
|
||||||
|
|
||||||
|
// Guardar en disco public
|
||||||
|
Storage::disk('public')->put($path, $encoded->toString());
|
||||||
$validated['image_path'] = $path;
|
$validated['image_path'] = $path;
|
||||||
}
|
}
|
||||||
unset($validated['image']);
|
unset($validated['image']);
|
||||||
|
|||||||
@@ -7,6 +7,7 @@
|
|||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"require": {
|
"require": {
|
||||||
"php": "^8.2",
|
"php": "^8.2",
|
||||||
|
"intervention/image": "^4.1",
|
||||||
"laravel-lang/common": "^6.7",
|
"laravel-lang/common": "^6.7",
|
||||||
"laravel/framework": "^12.0",
|
"laravel/framework": "^12.0",
|
||||||
"laravel/tinker": "^2.10.1"
|
"laravel/tinker": "^2.10.1"
|
||||||
|
|||||||
Generated
+145
-1
@@ -4,7 +4,7 @@
|
|||||||
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
|
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
|
||||||
"This file is @generated automatically"
|
"This file is @generated automatically"
|
||||||
],
|
],
|
||||||
"content-hash": "c5327d228d42dad14f6185dd57e05dde",
|
"content-hash": "54a99d812eb7e5412ada7f4366c3065c",
|
||||||
"packages": [
|
"packages": [
|
||||||
{
|
{
|
||||||
"name": "archtechx/enums",
|
"name": "archtechx/enums",
|
||||||
@@ -1568,6 +1568,150 @@
|
|||||||
],
|
],
|
||||||
"time": "2025-02-03T10:55:03+00:00"
|
"time": "2025-02-03T10:55:03+00:00"
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
"name": "intervention/gif",
|
||||||
|
"version": "5.0.1",
|
||||||
|
"source": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/Intervention/gif.git",
|
||||||
|
"reference": "bb395af960deffe64d70c976b4df9283f68e762d"
|
||||||
|
},
|
||||||
|
"dist": {
|
||||||
|
"type": "zip",
|
||||||
|
"url": "https://api.github.com/repos/Intervention/gif/zipball/bb395af960deffe64d70c976b4df9283f68e762d",
|
||||||
|
"reference": "bb395af960deffe64d70c976b4df9283f68e762d",
|
||||||
|
"shasum": ""
|
||||||
|
},
|
||||||
|
"require": {
|
||||||
|
"php": "^8.3"
|
||||||
|
},
|
||||||
|
"require-dev": {
|
||||||
|
"phpstan/phpstan": "^2.1",
|
||||||
|
"phpunit/phpunit": "^12.0",
|
||||||
|
"slevomat/coding-standard": "~8.0",
|
||||||
|
"squizlabs/php_codesniffer": "^4"
|
||||||
|
},
|
||||||
|
"type": "library",
|
||||||
|
"autoload": {
|
||||||
|
"psr-4": {
|
||||||
|
"Intervention\\Gif\\": "src"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"notification-url": "https://packagist.org/downloads/",
|
||||||
|
"license": [
|
||||||
|
"MIT"
|
||||||
|
],
|
||||||
|
"authors": [
|
||||||
|
{
|
||||||
|
"name": "Oliver Vogel",
|
||||||
|
"email": "oliver@intervention.io",
|
||||||
|
"homepage": "https://intervention.io/"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "PHP GIF Encoder/Decoder",
|
||||||
|
"homepage": "https://github.com/intervention/gif",
|
||||||
|
"keywords": [
|
||||||
|
"animation",
|
||||||
|
"gd",
|
||||||
|
"gif",
|
||||||
|
"image"
|
||||||
|
],
|
||||||
|
"support": {
|
||||||
|
"issues": "https://github.com/Intervention/gif/issues",
|
||||||
|
"source": "https://github.com/Intervention/gif/tree/5.0.1"
|
||||||
|
},
|
||||||
|
"funding": [
|
||||||
|
{
|
||||||
|
"url": "https://paypal.me/interventionio",
|
||||||
|
"type": "custom"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://github.com/Intervention",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://ko-fi.com/interventionphp",
|
||||||
|
"type": "ko_fi"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"time": "2026-05-03T06:04:47+00:00"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"name": "intervention/image",
|
||||||
|
"version": "4.1.2",
|
||||||
|
"source": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "https://github.com/Intervention/image.git",
|
||||||
|
"reference": "ba4a7cc8042882d479a78b0835f3f0e991e40a71"
|
||||||
|
},
|
||||||
|
"dist": {
|
||||||
|
"type": "zip",
|
||||||
|
"url": "https://api.github.com/repos/Intervention/image/zipball/ba4a7cc8042882d479a78b0835f3f0e991e40a71",
|
||||||
|
"reference": "ba4a7cc8042882d479a78b0835f3f0e991e40a71",
|
||||||
|
"shasum": ""
|
||||||
|
},
|
||||||
|
"require": {
|
||||||
|
"ext-mbstring": "*",
|
||||||
|
"intervention/gif": "^5",
|
||||||
|
"php": "^8.3"
|
||||||
|
},
|
||||||
|
"require-dev": {
|
||||||
|
"mockery/mockery": "^1.6",
|
||||||
|
"phpstan/phpstan": "^2.1",
|
||||||
|
"phpunit/phpunit": "^12.0",
|
||||||
|
"slevomat/coding-standard": "~8.0",
|
||||||
|
"squizlabs/php_codesniffer": "^4"
|
||||||
|
},
|
||||||
|
"suggest": {
|
||||||
|
"ext-exif": "Recommended to be able to read EXIF data properly."
|
||||||
|
},
|
||||||
|
"type": "library",
|
||||||
|
"autoload": {
|
||||||
|
"psr-4": {
|
||||||
|
"Intervention\\Image\\": "src"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"notification-url": "https://packagist.org/downloads/",
|
||||||
|
"license": [
|
||||||
|
"MIT"
|
||||||
|
],
|
||||||
|
"authors": [
|
||||||
|
{
|
||||||
|
"name": "Oliver Vogel",
|
||||||
|
"email": "oliver@intervention.io",
|
||||||
|
"homepage": "https://intervention.io"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"description": "PHP Image Processing",
|
||||||
|
"homepage": "https://image.intervention.io",
|
||||||
|
"keywords": [
|
||||||
|
"gd",
|
||||||
|
"image",
|
||||||
|
"imagick",
|
||||||
|
"resize",
|
||||||
|
"thumbnail",
|
||||||
|
"watermark"
|
||||||
|
],
|
||||||
|
"support": {
|
||||||
|
"issues": "https://github.com/Intervention/image/issues",
|
||||||
|
"source": "https://github.com/Intervention/image/tree/4.1.2"
|
||||||
|
},
|
||||||
|
"funding": [
|
||||||
|
{
|
||||||
|
"url": "https://paypal.me/interventionio",
|
||||||
|
"type": "custom"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://github.com/Intervention",
|
||||||
|
"type": "github"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"url": "https://ko-fi.com/interventionphp",
|
||||||
|
"type": "ko_fi"
|
||||||
|
}
|
||||||
|
],
|
||||||
|
"time": "2026-05-23T06:51:28+00:00"
|
||||||
|
},
|
||||||
{
|
{
|
||||||
"name": "laravel-lang/actions",
|
"name": "laravel-lang/actions",
|
||||||
"version": "1.10.2",
|
"version": "1.10.2",
|
||||||
|
|||||||
@@ -23,3 +23,12 @@
|
|||||||
RewriteCond %{REQUEST_FILENAME} !-f
|
RewriteCond %{REQUEST_FILENAME} !-f
|
||||||
RewriteRule ^ index.php [L]
|
RewriteRule ^ index.php [L]
|
||||||
</IfModule>
|
</IfModule>
|
||||||
|
|
||||||
|
<IfModule mod_php.c>
|
||||||
|
php_value upload_max_filesize 20M
|
||||||
|
php_value post_max_size 20M
|
||||||
|
php_value memory_limit 512M
|
||||||
|
</IfModule>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,4 @@
|
|||||||
|
upload_max_filesize = 20M
|
||||||
|
post_max_size = 20M
|
||||||
|
max_execution_time = 300
|
||||||
|
memory_limit = 256M
|
||||||
Reference in New Issue
Block a user