Así como con la creación de registros, actualizar registros también requiere típicamente de dos acciones: una para mostrar el formulario de edición y otra para procesar la actualización del registro. En esta lección te enseñaré cómo obtener un registro usando Eloquent y enlace de modelos a rutas, y luego actualizarlo con los datos provenientes del usuario.
Esta lección incluye un video premium
Regístrate para ver este video y cientos de lecciones exclusivas.
Mira el código en GitHub: actual, resultado, comparación.
Declarar la ruta para actualizar registros
Vamos a comenzar declarando la ruta para procesar la actualización del registro:
<?php // routes/web.php Route::put('notas/{note}', 'NoteController@update')->name('notes.update');
Nota que la URL de esta ruta es la misma que en la ruta para mostrar los detalles de una nota, lo que cambia es el método HTTP:
- Mostramos los detalles de un registro utilizando el método
GET
- Actualizamos los datos del registro a través del método
PUT
Es importante notar que en ambos casos necesitaremos el ID de la nota – para saber cuál registro mostrar o actualizar.
Si presionamos el botón de actualizar nota una vez más, veremos el siguiente error:
Debido a que el método update
no existe en NoteController
.
Es importante familiarizarnos con los errores que pueden arrojar Laravel y otros frameworks. Aprender a leer e interpretar los errores, nos permitirá solucionar los problemas de manera más rápida e independiente.
Acciones con enlace de modelos a rutas
Vamos a proceder a declarar este método, además utilizaremos Enlace de modelos a rutas en Laravel para obtener la nota directamente como un argumento de dicha acción:
<?php class NoteController { //... public function update(Note $note) { return "Actualizando nota: {$note->title}"; } }
Deberías un mensaje como «Actualizando nota: Una nueva nota». Si el título de la nota aparece vacío, verifica que el parámetro de la ruta ({note}
) tenga el mismo nombre que el parámetro del método ($note
).
Esta característica se llama «Enlace de modelos a rutas«, Laravel utiliza la declaración del método para verificar que deseas cargar una nota (Note
) y luego utiliza el ID pasado por el usuario a través de la URL para buscar y encontrar dicha nota. Puedes ver la lección enlazada para más información.
Reglas de validación para editar un registro
A continuación, voy a colocar las reglas de validación, copiando y pegando las que escribimos para crear el registro:
<?php class NoteController { //... public function update(Note $note, Request $request) { $request->validate([ 'title' => ['required', 'min:3', Rule::unique('notes')], 'content' => 'required', ]); return "Actualizando nota: {$note->title}"; } }
Si cambiamos el título de la nota, la validación va a pasar y veremos el texto «Actualizando nota…». Pero si no cambiamos el título de la nota, vamos a ver el siguiente error:
Esto sucede por la regla de validación Rule::unique('notes')
, debemos indicar que queremos que se ignore la nota actual, para no vernos obligados a tener que actualizar el título cada vez que queramos editar el contenido de la nota. Esto se logra de forma muy sencilla:
<?php $request->validate([ 'title' => ['...', Rule::unique('notes')->ignore($note)], ]);
Fíjate que he encadenado el método ignore
pasando como primer argumento el modelo de la nota. Laravel se encargará del resto. Ten cuidado con la posición de los paréntesis y los corchetes.
Puedes aprender más sobre cómo encadenar métodos en PHP con la lección Constructores semánticos e interfaces fluidas de nuestro Curso de programación orientada a objetos con PHP.
Si presionamos «Actualizar nota» una vez más, veremos el texto «Actualizando nota…» lo que quiere decir que la validación ya ha pasado.
Actualizar un registro con Eloquent
Actualizar un modelo es muy sencillo. Podemos llamar al método update
del modelo en cuestión y pasar un arreglo asociativo con los atributos que queremos actualizar. Por supuesto dichos atributos pueden provenir de la petición del usuario, solamente asegúrate de validarlos antes:
<?php $note->update([ 'title' => $request->input('title'), 'content' => $request->input('content'), ]);
Estos atributos deben estar en la propiedad $fillable
de lo contrario serán ignorados u obtendrás un error de asignación masiva como vimos previamente.
Además, quiero mencionar que el método validate
del objeto $request
retorna un arreglo asociativo con los campos validados, por lo que podríamos simplificar nuestro código aún más:
<?php $data = $request->validate([ 'title' => ['required', 'min:3', Rule::unique('notes')->ignore($note)], 'content' => 'required', ]); $note->update($data);
Redirigir a la URL anterior
Finalmente vamos a colocar la redirección, puedes redirigir a la URL que prefieras. Yo utilizaré la página de inicio una vez más:
<?php return redirect('/');
Enlaces Relacionados
- Constructores semánticos e interfaces fluidas
- Asignación masiva en Eloquent ORM a fondo (uso de fillable, guarded, fill, forceFill y atributos dinámicos)
- Nueva sintaxis para las reglas de validación: dimensions, exists, unique, in y not_in en Laravel 5.3
- Helper global ddd en Laravel
Regístrate hoy en Styde y obtén acceso a todo nuestro contenido.
Lección anterior Formulario para editar registros en Laravel 6 Lección siguiente Eliminar registros en Laravel 6