Imagina que compramos uma barraca de acampar e ao chegar em casa montamos. Provavelmente não vamos conseguir carregar a barraca montada, por esse motivo desmontamos, transportamos e depois realizamos a montagem novamente. Quando estamos falando de programação em algumas situações precisamos realizar basicamente o mesmo processo. Em ciência da computação geralmente chamamos de serialização o ato de converter uma estrutura de dados para um formato de transporte ou armazenamento que pode ser reconstruído depois.
Quando trabalhamos com desenvolvimento de APIs é comum precisarmos serializar para o formato no qual eles serão transportados. Na maioria dos casos as APIs utilizam o formato JSON, porém pode ser qualquer outro como XML ou YAML.
Ao falarmos de serialização o Laravel possui algumas características que nos ajuda a realizar a serialização de forma automática e recursos que nos permite personalizar os dados na serialização.
Curso Laravel - Desenvolvimento de APIs REST
Conhecer o cursoSerialização automática no Controller
Alguns frameworks como Symfony esperam que o retorno de um método do controller seja sempre uma instância da classe response, contudo no caso do Laravel isso é um pouco diferente. Quando retornamos qualquer estrutura iterável em um controller automaticamente ele tenta serializar para JSON e enviar na resposta. Inclusive ele indica no cabeçalho da resposta que estamos retornando application/json
.
Faça um teste retornando um array simples ou mesmo o resultado de uma busca com Eloquent:
public function action()
{
return ["Escola" => "Treinaweb Cursos"];
}
Ao acessar terá:
Mesma coisa também acontece se retornarmos o resultado de uma consulta no banco de dados com Eloquent:
public function action()
{
return AppProduct::all();
}
Serialização manual
O Laravel também nos permite serializar os dados manualmente. Basta chamarmos o método toJson
em uma collection. Como os models do Eloquent sempre retornam uma collection quando buscamos por mais de um registro, podemos trabalhar do seguinte modo:
$products = AppProduct::all();
$json = $products->toJson();
Um detalhe importante! Quando fazemos a serialização o resultado é uma string simples com uma marcação no formato JSON. No caso acima, se retornarmos a variável $json
em um controller o content-type
será text/html
. O correto então é montar a resposta informando manualmente que estamos retornando um application/json
.
Curso Silex - Framework PHP
Conhecer o cursoEscolhendo os dados que não serão serializados
Muitas vezes não podemos retornar todos os dados do nosso model para a resposta. Imagine que o produto tem um campo preço de custo, não é nada legal enviar isso para um revendedor, por exemplo.
Nesses casos podemos declarar um atributo no model informando quais propriedades não devem ser incluídas quando realizarmos a serialização:
<?php
namespace App;
use IlluminateDatabaseEloquentModel;
class Product extends Model
{
/**
* Atributos que não serão serializados
*
* @var array
*/
protected $hidden = ['cost'];
}
Se por algum motivo em uma serialização específica quiser usar um dos campos escondidos temos um método específico:
$product->makeVisible('cost')->toJson();
Escolhendo os dados que serão serializados
Ao contrário temos também o atributo que indica apenas os campos que serão usados na serialização:
<?php
namespace App;
use IlluminateDatabaseEloquentModel;
class Product extends Model
{
/**
* Atributos que serão serializados
*
* @var array
*/
protected $visible = ['id', 'name', 'price'];
}
Podemos usar um método para esconder as propriedades que estão nessa lista:
return $product->makeHidden('price')->toJson();
Outros recursos
Outros dois recursos podem ajudar muito dependendo da situação. O primeiro nos permite usar um acessor na serialização, basta indicarmos o nome dele no atributo appends
do model. Além disso podemos formatar propriedades do tipo data com atributo casts
.