Herramientas de usuario

Herramientas del sitio


informatica:programacion:php:frameworks:laravel:formularios

Diferencias

Muestra las diferencias entre dos versiones de la página.

Enlace a la vista de comparación

Próxima revisión
Revisión previa
informatica:programacion:php:frameworks:laravel:formularios [2023/06/10 14:26] – creado tempwininformatica:programacion:php:frameworks:laravel:formularios [2023/06/10 15:30] (actual) tempwin
Línea 61: Línea 61:
 </code> </code>
  
 +Por tanto, cuando se envíe el formulario, se llamará al método ''store'' del ''ProductController'' mediante POST:
  
 +<code php>
 +public function store() 
 +{
 +    dd("Estamos en store");
 +}
 +</code>
  
 +Esto no nos funcionará porque, por defecto, Laravel tiene protección contra CSRF (//Cross-site request forgery//). Se asegura que las peticiones que se hagan a nuestra web, vengan realmente de nuestra web. 
  
 +Para solucionarlo, en nuestros formularios debemos añadir un token CSRF:
  
 +<code html5>
 +@extends("layout.master")
  
-===== Enviando y mostrando información en vistas =====+@section("content"
 +    <h1>Create a product</h1> 
 +     
 +    <form method="post" action="{{ route("products.store" }}"> 
 +    @csrf 
 +     
 +</code>
  
-Sabemos cómo crear una vista, cómo mostrar información en esa vista, pero ahora queremos añadir en la vista información que recuperamos de la base de datos a través de un controlador.+Esa instrucción de Blade incluye un campo HTML oculto en el formulario:
  
-Partimos de un método de nuestro ''ProductController'': +<code html5
- +<form method="postaction=""> 
-<code php+    <input type="hidden" name="_token" value="123h4jkl123khxvbnasd12"
-    // code +
-    public function show($product)  +
-    { +
-        $product Product::findOrFail($product); +
-         +
-        return view("products.show"); +
-         +
-    }+
 </code> </code>
  
-Para enviar información la vista usamos ''with'' y definimos qué nos llevaremos a la vista.+===== Datos provenientes de formularios ===== 
 + 
 +Vamos crear (almacenar) un producto partir de la información recibida desde un formulario:
  
 <code php> <code php>
-    // code +public function store()  
-    public function show($product)  +
-    +    $product = Product::create([ 
-        $product = Product::findOrFail($product); +        'title' => request()->title, 
-         +        'description' => request()->description, 
-        return view("products.show")->with([ +        'price' => request()->price, 
-            "product" =>  $product+        'stock' => request()->stock
-        ]); +        'status' => request()->status, 
-         +    ]); 
-    }+     
 +    return $product; 
 +}
 </code> </code>
  
-A la vista estaremos enviando la variable ''product'' con el valor ''$product''.+Veremos un string JSON con el producto creado a través del formulario.
  
-Si vamos a la vista (''resources/views/products/show.blade.php'': +Versión abreviada cogiendo todo lo que llegue de un formulario:
- +
-<code html5> +
-<!DOCTYPE html> +
-<html lang="en"> +
-  <head> +
-    <meta charset="utf-8" /> +
-    <title>Product</title> +
-  </head>+
  
-  <body+<code php
-    <h1>{{ $product->title }} ({{ $product->id }})</h1> +public function store()  
-    <p>{{ $product->description }}</p> +
-    <p>{{ $product->price }}</p> +    $product = Product::create(request()->all()); 
-    <p>{{ $product->stock }}</p> +     
-    <p>{{ $product->status }}</p>             +    return $product
-  </body> +}
-</html>+
 </code> </code>
  
-Usando [[https://laravel.com/docs/10.x/blade|Blade]], el motor de plantillas que incluye Laravel, interpretará las variables. Las encerramos entre llaves dobles (''%%{{%% %%}}%%'').+<WRAP center round important 60%> 
 +Los atributos que se asignarán a nuestro modelo a partir del formulario serán los que hayamos indicado en el array de ''$fillable''. 
 +</WRAP>
  
-===== Blade: motor de plantillas =====+===== Editando desde un formulario =====
  
-[[https://laravel.com/docs/10.x/blade|Blade]] es el motor de plantillas que incluye Laravel+Los métodos que modificaremos en nuestro ProductController serán ''edit'' y ''update''Uno mostrará el formulario de edición del producto y el otro hará efectiva la actualización.
  
-==== Variables ==== +<code php> 
- +public function edit($product)  
-Para mostrar el contenido de una variable en Blade:+
 +    return view("products.edit")->with([ 
 +        "product" => Product::findOrFail($product), 
 +    ]); 
 +}
  
-<code> +public function update($product)  
-{{ $variable }}+{ 
 +}
 </code> </code>
  
-Comentar para que no las procese ni las muestre:+Recordemos las rutas:
  
-<code> +<code php
-{{-- $variable --}+Route::get("products/{$product}/edit", "ProductController@edit")->name("products.edit");
-</code>+
  
-Si queremos que aparezca el texto tal cual (llaves incluidas)es decirque Blade no evalúe nada: +Route::match(["put""patch"]"products/{$product}", "ProductController@update")->name("products.update");
- +
-<code> +
-@{{ $variable }}+
 </code> </code>
  
-Esto es útil si estamos trabajando con un framework para el frontend como Vuejs, React o Angular ya que también utilizan la sintaxis de las dobles llaves para las variables. +Para el formulario de edicióncreamos la vista ''resources/views/products/edit.blade.php'':
- +
-==== Estructuras de control ==== +
- +
-Por ejemplosi tenemos en nuestro controlador: +
- +
-<code php> +
-    public function index() +
-    { +
-        $products = Product::all(); +
-         +
-        return view("products.index")->with([ +
-            "products" => $products, +
-        ]); +
-    } +
-</code> +
- +
-En la vista (''resources/views/products.blade.php''):+
  
 <code html5> <code html5>
-<!DOCTYPE html> +@extends("layout.master")
-<html lang="en"+
-  <head> +
-    <meta charset="utf-8" /> +
-    <title>Product</title> +
-  </head>+
  
-  <body> +@section("content") 
-    <h1>List of Products</h1>+    <h1>Edit a product</h1>
          
-    @if (empty($products)) +    <form method="post" action="{{ route("products.update", ["product" => $product->id]}}"> 
-        <div class="alert alert-warning"> +        @csrf 
-            This list of products is empty+        @method("PUT"
 +        <div class="form-row"> 
 +            <label>Title</label> 
 +            <input class="form-control" type="text" name="title" value="{{ $product->title }}" required>
         </div>         </div>
-    @else +        <div class="form-row"> 
-        <div class="table-responsive"> +            <label>Description</label
-            <table class="table table-striped"+            <input class="form-control" type="text" name="description" value="{{ $product->description }} required>
-                <thead class="thead-light"+
-                    <tr> +
-                        <th>ID</th> +
-                        <th>Title</th> +
-                        <th>Description</th> +
-                        <th>Price</th> +
-                        <th>Stock</th> +
-                        <th>Status</th> +
-                    </tr> +
-                </thead> +
-                <tbody> +
-                    @foreach ($products as $product) +
-                    <tr> +
-                        <td>{{ $product->id }}</td> +
-                        <td>{{ $product->title }}</td> +
-                        <td>{{ $product->description }}</td> +
-                        <td>{{ $product->price }}</td> +
-                        <td>{{ $product->stock }}</td> +
-                        <td>{{ $product->status }}</td>                         +
-                    </tr>       +
-                    @endforeach                   +
-                </tbody> +
-            </table>+
         </div>         </div>
-    @endif +        <div class="form-row"> 
-  </body+            <label>Price</label> 
-</html>+            <input class="form-control" type="number" min="1.00" step="0.01" name="price" value="{{ $product->price }} required> 
 +        </div>                 
 +        <div class="form-row"> 
 +            <label>Stock</label> 
 +            <input class="form-control" type="number" min="0" name="stock" value="{{ $product->stock }} required> 
 +        </div>                   
 +        <div class="form-row"> 
 +            <label>Status</label>       
 +            <select class="custom-select" name="status" required> 
 +                <option {{ $product->status == "available" ? "selected" : "" }} value="available">Available</option>                 
 +                <option {{ $product->status == "unavailable" ? "selected" : "" }} value="unavailable">Unavailable</option>                                 
 +            </select> 
 +        </div> 
 +        <div class="form-row"> 
 +            <button type="submit" class="btn btn-primary btn-lg">Edit product</button> 
 +        </div
 +    </form>
 </code> </code>
  
-Para el caso de comprobar vacíosexiste otra estructura dedicada::+Los navegadores solo procesan GET y POST, así que para forzar un tipo de peticiónusamos ''@method'' que añadirá una etiqueta ''input'' oculta con el valor que le pasemos.
  
-<code html5+Para realizar la actualización del producto, en el controlador: 
-    <h1>List of Products</h1>+ 
 +<code php> 
 +public function update($product)  
 +{ 
 +    $product = Product::findOrFail($product);
          
-    @empty ($products) +    $product->update(request()->all()); 
-        <div class="alert alert-warning"> +     
-            This list of products is empty +    return $product; 
-        </div+}
-    @else +
-    ... +
-    @endempty+
 </code> </code>
  
-===== Crear plantillas para las vistas =====+===== Eliminar de la base de datos =====
  
-Para cuando tengamos componentes que se repitan.+En Laravel tenemos que usar un formulario también para eliminar productosEn nuestro controlador, modificaremos el método ''destroy'':
  
-Creamos, por ejemplo, ''reseources/views/layouts/master.blade.php'':+<code php
 +public function destroy($product)  
 +
 +    $product = Product::findOrFail($product); 
 +     
 +    $product->delete(); 
 +
 +</code>
  
-<code html5> +Recordemos que debe existir una ruta:
-<!DOCTYPE html> +
-<html lang="en"> +
-  <head> +
-    <meta charset="utf-8" /> +
-    <title>Laravel Shop</title> +
-  </head>+
  
-  <body+<code php
-    @yield('content') +Route::delete("products/{product}", "ProductController@destroy")->name("products.destroy");
-  </body> +
-</html>+
 </code> </code>
  
-Con ''yield()'' marcamos una sección a la que podremos hacer luego referencia. +Finalmente, para dar la opción de eliminar un producto, basta con crear un enlace, pero debe ser usando el método DELETE:
- +
-Las vistas que quieran utilizar esta plantilla tendrían que...+
  
 <code html5> <code html5>
-@extends("layouts.master"+<form method="post" action="{{ route("products.destroy", ["product=> product->id]}}"
- +    @csrf 
-@section("content") +    @method("DELETE") 
- +    <button type="submit" class="btn btn-link">Delete</button
-    <h1>List of Products</h1+</form>
-     +
-    @if (empty($products)) +
-        <div class="alert alert-warning"+
-            This list of products is empty +
-        </div> +
-    @else +
-        <div class="table-responsive"+
-            <table class="table table-striped"> +
-                <thead class="thead-light"> +
-                    <tr> +
-                        <th>ID</th+
-                        <th>Title</th> +
-                        <th>Description</th> +
-                        <th>Price</th> +
-                        <th>Stock</th> +
-                        <th>Status</th> +
-                    </tr> +
-                </thead> +
-                <tbody> +
-                    @foreach ($products as $product) +
-                    <tr> +
-                        <td>{{ $product->id }}</td> +
-                        <td>{{ $product->title }}</td> +
-                        <td>{{ $product->description }}</td> +
-                        <td>{{ $product->price }}</td> +
-                        <td>{{ $product->stock }}</td> +
-                        <td>{{ $product->status }}</td>                         +
-                    </tr>       +
-                    @endforeach                   +
-                </tbody> +
-            </table> +
-        </div> +
-    @endif +
- +
-@endsection+
 </code> </code>
informatica/programacion/php/frameworks/laravel/formularios.1686399980.txt.gz · Última modificación: por tempwin