Agrega Productos y sus recetas

This commit is contained in:
2021-07-12 19:10:43 -04:00
parent df5238850e
commit d3713e2f93
10 changed files with 408 additions and 1 deletions

View File

@@ -0,0 +1,21 @@
<?php
namespace App\Exceptions;
use Exception;
class AlreadyExistsException extends Exception {
protected $model;
public function __construct($model) {
$this->model = $model;
}
public function render($request) {
return response()->json([
'error' => 'already_exists',
'message' => 'Ya existe la ' . $this->model
], 400);
}
}

View File

@@ -11,7 +11,7 @@ class ModelNotFoundException extends Exception {
public function __construct($modelName, $id) {
$this->modelName= $modelName;
$this->id = $id;
$this->id = is_array($id) ? implode(', ', $id) : $id;
}
public function render($request) {

View File

@@ -0,0 +1,167 @@
<?php
namespace App\Http\Controllers;
use App\Models\Restaurante;
use App\Models\Producto;
use App\Models\Categoria;
use App\Models\ZonaProduccion;
use App\Models\Ingrediente;
use App\Models\Receta;
use App\Services\PaginatorService;
use App\Services\UuidService;
use App\Exceptions\GenericException;
use App\Exceptions\ModelNotFoundException;
use Illuminate\Http\JsonResponse;
use Illuminate\Http\Request;
use Illuminate\Validation\ValidationException;
use Ramsey\Uuid\Uuid;
class ProductosController extends Controller {
/**
* Obtiene de forma paginada los productos registrados en el backend
*/
public function all(Request $request, $restaurante_id) {
app(UuidService::class)->validOrFail($restaurante_id);
$restaurante = Restaurante::findOrFail($restaurante_id);
$productos = $restaurante->productos();
$paginate = app(PaginatorService::class)->paginate(
perPage: $request->input('per_page', 15),
page: $request->input('page', 1),
total: $productos->count(),
route: 'restaurant.all',
data: ['restaurante_id' => $restaurante_id]
);
$data = $productos->get()
->skip($paginate['from'] - 1)
->take($paginate['per_page'])
->all();
return response()->json([
'pagination' => $paginate,
'data' => $data
]);
}
/**
* Obtiene un producto por su id
*/
public function get(Request $request, $restaurante_id, $id) {
app(UuidService::class)->validOrFail($restaurante_id);
app(UuidService::class)->validOrFail($id);
$restaurante = Restaurante::findOrFail($restaurante_id);
$producto = Producto::findOrFail($id);
if($producto->restaurante != $restaurante) {
throw new ModelNotFoundException("producto", $id);
}
return response()->json($producto);
}
/**
* Crea un nuevo producto
*/
public function create(Request $request, $restaurante_id) {
$this->validate($request, [
'nombre' => 'required',
'precio_venta' => 'required|numeric',
'categoria_id' => 'required|exists:categorias,id',
'zona_produccion_id' => 'required|exists:zonas_produccion,id',
]);
app(UuidService::class)->validOrFail($restaurante_id);
app(UuidService::class)->validOrFail($request->input('categoria_id'));
app(UuidService::class)->validOrFail($request->input('zona_produccion_id'));
$restaurante = Restaurante::findOrFail($restaurante_id);
$categoria = Categoria::findOrFail($request->input('categoria_id'));
$zonaProduccion = ZonaProduccion::findOrFail($request->input('zona_produccion_id'));
if($categoria->restaurante != $restaurante) {
throw new ModelNotFoundException("categoria", $id);
}
if($zonaProduccion->restaurante != $restaurante) {
throw new ModelNotFoundException("zona_produccion", $id);
}
$producto = Producto::create([
'id' => Uuid::uuid4(),
'nombre' => $request->input('nombre'),
'precio_venta' => $request->input('precio_venta'),
'categoria_id' => $categoria->id,
'zona_produccion_id' => $zonaProduccion->id,
'restaurante_id' => $restaurante->id
]);
return response()->json($producto, 201);
}
/**
* Actualiza un producto
*/
public function update(Request $request, $restaurante_id, $id) {
$this->validate($request, [
'nombre' => 'required',
'precio_venta' => 'required|numeric',
'categoria_id' => 'required|exists:categorias,id',
'zona_produccion_id' => 'required|exists:zonas_produccion,id',
]);
app(UuidService::class)->validOrFail($restaurante_id);
app(UuidService::class)->validOrFail($request->input('categoria_id'));
app(UuidService::class)->validOrFail($request->input('zona_produccion_id'));
app(UuidService::class)->validOrFail($id);
$restaurante = Restaurante::findOrFail($restaurante_id);
$categoria = Categoria::findOrFail($request->input('categoria_id'));
$zonaProduccion = ZonaProduccion::findOrFail($request->input('zona_produccion_id'));
$producto = Producto::findOrFail($id);
if($categoria->restaurante != $restaurante) {
throw new ModelNotFoundException("categoria", $id);
}
if($zonaProduccion->restaurante != $restaurante) {
throw new ModelNotFoundException("zona_produccion", $id);
}
if($producto->restaurante != $restaurante) {
throw new ModelNotFoundException("ingrediente", $id);
}
$producto->nombre = $request->input('nombre');
$producto->precio_venta = $request->input('precio_venta');
$producto->categoria_id = $categoria->id;
$producto->zona_produccion_id = $zonaProduccion->id;
$producto->save();
return response()->json($producto);
}
/**
* Elimina un producto
*/
public function delete(Request $request, $restaurante_id, $id) {
app(UuidService::class)->validOrFail($restaurante_id);
app(UuidService::class)->validOrFail($id);
$restaurante = Restaurante::findOrFail($restaurante_id);
$producto = Producto::findOrFail($id);
if($producto->restaurante != $restaurante) {
throw new ModelNotFoundException("producto", $id);
}
$producto->delete();
return response()->json([], 204);
}
}

View File

@@ -0,0 +1,188 @@
<?php
namespace App\Http\Controllers;
use App\Models\Restaurante;
use App\Models\Producto;
use App\Models\Ingrediente;
use App\Models\Receta;
use App\Services\PaginatorService;
use App\Services\UuidService;
use App\Exceptions\GenericException;
use App\Exceptions\AlreadyExistsException;
use App\Exceptions\ModelNotFoundException;
use Illuminate\Http\JsonResponse;
use Illuminate\Http\Request;
use Illuminate\Validation\ValidationException;
use Ramsey\Uuid\Uuid;
class RecetasController extends Controller {
/**
* Obtiene los ingredientes de la receta de un producto
*/
public function all(Request $request, $restaurante_id, $producto_id) {
app(UuidService::class)->validOrFail($restaurante_id);
app(UuidService::class)->validOrFail($producto_id);
$restaurante = Restaurante::findOrFail($restaurante_id);
$producto = Producto::findOrFail($producto_id);
if($producto->restaurante != $restaurante) {
throw new ModelNotFoundException("producto", $producto_id);
}
$recetas = Receta::where('producto_id', $producto->id)->with('ingrediente');
$paginate = app(PaginatorService::class)->paginate(
perPage: $request->input('per_page', 15),
page: $request->input('page', 1),
total: $recetas->count(),
route: 'productos.receta.all',
data: ['restaurante_id' => $restaurante_id, 'producto_id' => $producto_id]
);
$data = $recetas->get()
->skip($paginate['from'] - 1)
->take($paginate['per_page'])
->all();
return response()->json([
'pagination' => $paginate,
'data' => $data
]);
}
/**
* Obtiene los datos de un ingrediente de una receta
*/
public function get(Request $request, $restaurante_id, $producto_id, $ingrediente_id) {
app(UuidService::class)->validOrFail($restaurante_id);
app(UuidService::class)->validOrFail($ingrediente_id);
app(UuidService::class)->validOrFail($producto_id);
$restaurante = Restaurante::findOrFail($restaurante_id);
$ingrediente = Ingrediente::findOrFail($ingrediente_id);
$producto = Producto::findOrFail($producto_id);
if($ingrediente->restaurante != $restaurante) {
throw new ModelNotFoundException("ingrediente", $ingrediente_id);
}
if($producto->restaurante != $restaurante) {
throw new ModelNotFoundException("producto", $producto_id);
}
$receta = Receta::where('producto_id', $producto->id)
->where('ingrediente_id', $ingrediente->id)
->with('ingrediente')
->first();
if(!$receta) {
throw new ModelNotFoundException("receta", [$ingrediente_id, $producto_id]);
}
return response()->json($receta);
}
/**
* Agrega un ingrediente a la receta del producto
*/
public function create(Request $request, $restaurante_id, $producto_id, $ingrediente_id) {
$this->validate($request, [
'unidades' => 'required|numeric'
]);
app(UuidService::class)->validOrFail($restaurante_id);
app(UuidService::class)->validOrFail($ingrediente_id);
app(UuidService::class)->validOrFail($producto_id);
$restaurante = Restaurante::findOrFail($restaurante_id);
$ingrediente = Ingrediente::findOrFail($ingrediente_id);
$producto = Producto::findOrFail($producto_id);
if($ingrediente->restaurante != $restaurante) {
throw new ModelNotFoundException("ingrediente", $ingrediente_id);
}
if($producto->restaurante != $restaurante) {
throw new ModelNotFoundException("producto", $producto_id);
}
$receta = Receta::where('producto_id', $producto->id)
->where('ingrediente_id', $ingrediente->id)
->first();
if($receta) throw new AlreadyExistsException("receta");
$receta = Receta::create([
'id' => Uuid::uuid4(),
'unidades' => $request->input('unidades'),
'producto_id' => $producto->id,
'ingrediente_id' => $ingrediente->id,
]);
return response()->json($receta);
}
/**
* Modifica el ingrediente de una receta
*/
public function update(Request $request, $restaurante_id, $producto_id, $ingrediente_id) {
$this->validate($request, [
'unidades' => 'required|numeric'
]);
app(UuidService::class)->validOrFail($restaurante_id);
app(UuidService::class)->validOrFail($ingrediente_id);
app(UuidService::class)->validOrFail($producto_id);
$restaurante = Restaurante::findOrFail($restaurante_id);
$ingrediente = Ingrediente::findOrFail($ingrediente_id);
$producto = Producto::findOrFail($producto_id);
if($ingrediente->restaurante != $restaurante) {
throw new ModelNotFoundException("ingrediente", $ingrediente_id);
}
if($producto->restaurante != $restaurante) {
throw new ModelNotFoundException("producto", $producto_id);
}
$receta = Receta::where('producto_id', $producto->id)
->where('ingrediente_id', $ingrediente->id)
->first();
$receta->unidades = $request->input('unidades');
$receta->save();
return response()->json($receta);
}
/**
* Elimina un ingrediente de la receta del producto
*/
public function delete(Request $request, $restaurante_id, $producto_id, $ingrediente_id) {
app(UuidService::class)->validOrFail($restaurante_id);
app(UuidService::class)->validOrFail($producto_id);
app(UuidService::class)->validOrFail($ingrediente_id);
$restaurante = Restaurante::findOrFail($restaurante_id);
$producto = Producto::findOrFail($producto_id);
$ingrediente = Ingrediente::findOrFail($ingrediente_id);
if($producto->restaurante != $restaurante) {
throw new ModelNotFoundException("producto", $producto_id);
}
if($ingrediente->restaurante != $restaurante) {
throw new ModelNotFoundException("ingrediente", $ingrediente_id);
}
$receta = Receta::where('producto_id', $producto->id)
->where('ingrediente_id', $ingrediente->id)
->first();
$receta->delete();
return response()->json([], 204);
}
}

View File

@@ -11,6 +11,16 @@ class Producto extends Model {
use UuidPrimaryKey, SoftDeletes;
protected $table = 'productos';
protected $fillable = [
'id', 'nombre', 'precio_venta', 'categoria_id',
'zona_produccion_id', 'restaurante_id'
];
public static function findOrFail($id) {
$producto = Producto::find($id);
if(!$producto) throw new ModelNotFoundException("producto", $id);
return $producto;
}
public function recetas() {
return $this->hasMany(Receta::class, 'producto_id');

View File

@@ -10,6 +10,7 @@ class Receta extends Model {
use UuidPrimaryKey;
protected $table = 'recetas';
protected $fillable = ['unidades', 'producto_id', 'ingrediente_id'];
public function ingrediente() {
return $this->belongsTo(Ingrediente::class);

View File

@@ -8,6 +8,7 @@ use App\Models\ZonaProduccion;
use App\Models\Categoria;
use App\Models\Proveedor;
use App\Models\Ingrediente;
use App\Models\Producto;
use App\Traits\UuidPrimaryKey;
use App\Exceptions\ModelNotFoundException;
use Illuminate\Database\Eloquent\Model;
@@ -55,4 +56,8 @@ class Restaurante extends Model {
public function ingredientes() {
return $this->hasMany(Ingrediente::class, 'restaurante_id');
}
public function productos() {
return $this->hasMany(Producto::class, 'restaurante_id');
}
}