(16) 981791110 contato@policast.studio

O que é o FOSRestBundle?

O FOSRestBundle é um bundle para o Symfony que facilita a criação de uma API RESTful. Ele suporta formatos de resposta como JSON, XML e outros, além de fornecer ferramentas para lidar com autenticação, autenticação OAuth, CORS e algumas outras coisas úteis.

O FOSRestBundle é fácil de usar, seguindo a filosofia do Symfony: crie uma configuração simples no arquivo app/config/config.yml e comece a escrever suas ações de controle.

O FOSRestBundle requer um pouco de configuração para começar, mas depois que você entender tudo, não precisa mais se preocupar com muitas coisas, apenas crie suas ações de controle e deixe o FOSRestBundle cuidar do resto.

Como instalar o FOSRestBundle no Symfony?

Instalar o FOSRestBundle é fácil, basta adicionar o seguinte à configuração do seu projeto:

composer require friendsofsymfony/rest-bundle 

Em seguida, vá para o arquivo app/AppKernel.php e adicione o FOSRestBundle às suas coleções de bundles. O código deverá ficar assim:

 $bundles = array(
// ...
new FOSRestBundleFOSRestBundle(),
);

Por último, mas não menos importante, adicione o seguinte código ao arquivo app/config/config.yml:

 fos_rest:
view:
view_response_listener: true

Com esses três passos, você já terá instalado e configurado o FOSRestBundle em seu projeto Symfony.

Como usar o FOSRestBundle?

O FOSRestBundle é fácil de usar. Ele fornece um conjunto de ferramentas para facilitar a criação de uma API RESTful. A primeira coisa a fazer é criar uma ação de controle.

Aqui está um exemplo de uma ação de controle que retorna uma lista de usuários:

 namespace AppBundleController;

use FOSRestBundleControllerFOSRestController;
use FOSRestBundleControllerAnnotations as Rest;
use AppBundleEntityUser;

class UserController extends FOSRestController
{
/**
* @RestGet("/users")
*/
public function getUsersAction()
{
$users = $this->getDoctrine()->getRepository(User::class)->findAll();

return $this->view($users);
}
}

Neste exemplo, estamos usando as anotações do FOSRestBundle para indicar que estamos criando uma ação de controle que responde ao método GET em “/users”. Observe que estamos usando o método $this->view () para retornar os usuários em um formato JSON, que é o padrão para o FOSRestBundle, mas podemos retornar outros formatos, como XML.

Criar uma ação de controle é a primeira etapa para usar o FOSRestBundle. Depois, podemos continuar na configuração de rotas, parâmetros de rota, autenticação etc.

Como configurar rotas no FOSRestBundle?

No FOSRestBundle, as rotas são configuradas usando anotações. A seguir, um exemplo de como configurar uma rota para uma ação de controle:

 namespace AppBundleController;

use FOSRestBundleControllerFOSRestController;
use FOSRestBundleControllerAnnotations as Rest;
use AppBundleEntityUser;

class UserController extends FOSRestController
{
/**
* @RestGet("/users/{id}")
*/
public function getUserAction($id)
{
$user = $this->getDoctrine()->getRepository(User::class)->find($id);

return $this->view($user);
}
}

Nesse exemplo, estamos configurando uma rota para a ação de controle getUserAction (). Observe que o parâmetro $ id é incluído na rota.

O FOSRestBundle suporta muitos outros tipos de anotações de rota, incluindo POST, PUT, DELETE e PATCH. Também é possível configurar rotas usando arquivos de configuração YAML. O FOSRestBundle é muito flexível e você pode configurar rotas da maneira que preferir.

Como usar autenticação no FOSRestBundle?

O FOSRestBundle suporta vários tipos de autenticação, incluindo autenticação de formulário, autenticação OAuth e autenticação JWT. Aqui está um exemplo de como usar a autenticação de formulário no FOSRestBundle:

Primeiro, precisamos criar uma ação de controle para login:

 namespace AppBundleController;

use FOSRestBundleControllerFOSRestController;
use FOSRestBundleControllerAnnotations as Rest;
use SymfonyComponentHttpFoundationRequest;

class SecurityController extends FOSRestController
{
/**
* @RestPost("/login")
*/
public function loginAction(Request $request)
{
// do your authentication here

return $this->view(['token' => 'your_token']);
}
}

Neste exemplo, criamos uma ação de controle que responde ao método POST em “/login”. Observe que estamos retornando um token que será usado para autenticação posterior.

Depois de criada a ação de controle, podemos continuar configurando a autenticação globalmente em nosso arquivo config.yml:

 security:
providers:
in_memory:
memory:
users:
username:
password: password
roles:
- ROLE_USER

firewalls:
api:
pattern: ^/api
stateless: true
anonymous: true
provider: in_memory
guard:
authenticators:
- app.token_authenticator
logout: false
http_basic: ~

access_control:
- { path: ^/api/login, roles: IS_AUTHENTICATED_ANONYMOUSLY }
- { path: ^/api, roles: ROLE_USER }

Neste exemplo, configuramos o FOSRestBundle para usar o provedor de autenticação embutido do Symfony (in_memory). Em seguida, configuramos um firewall para nossas rotas “/api” e adicionamos um autenticador para autenticar nossos tokens.

Com essas configurações, já é possível usar a autenticação em seu projeto Symfony com o FOSRestBundle.

Como usar o serializador no FOSRestBundle?

O FOSRestBundle inclui o JMS Serializer Bundle, que é um serializador poderoso e flexível para o Symfony. Ele suporta muitos tipos de formato, incluindo XML, JSON, YAML etc.

Para usar o serializador, primeiro precisamos serializar nossa saída de dados. Aqui está um exemplo:

 namespace AppBundleController;

use FOSRestBundleControllerFOSRestController;
use FOSRestBundleControllerAnnotations as Rest;
use SymfonyComponentHttpFoundationRequest;
use AppBundleEntityUser;

class UserController extends FOSRestController
{
/**
* @RestGet("/users/{id}")
*/
public function getUserAction($id)
{
$user = $this->getDoctrine()->getRepository(User::class)->find($id);

$data = $this->get('serializer')->serialize($user, 'json');

return new Response($data);
}
}

Neste exemplo, estamos usando o método $this->get(‘serializer’)->serialize() para serializar nossos dados de usuário em formato JSON.

Além disso, podemos editar e configurar as opções do Serializer nos arquivos de configuração. Com as opções que vêm junto com o Serializer, podemos personalizar como queremos que nossos dados sejam serializados.

Como usar o ViewHandler no FOSRestBundle?

O ViewHandler é útil quando precisamos personalizar-nos na forma como apresentamos nossas respostas. O ViewHandler é uma ferramenta que ajuda a guiar o nosso controle na escolha do melhor tipo de resposta para a ação.

Ao devolver uma resposta, podemos simplesmente chamar o método $this->view() e deixar a responsabilidade de formatá-la para o ViewHandler e é possível editar/enxergar opções, como por exemplo, o código HTTP que será retornado, o formato, o serializer, etc.

Veja um exemplo:

 namespace AppBundleController;

use FOSRestBundleControllerFOSRestController;
use FOSRestBundleControllerAnnotations as Rest;
use SymfonyComponentHttpFoundationRequest;
use AppBundleEntityUser;

class UserController extends FOSRestController
{
/**
* @RestGet("/users/{id}")
*/
public function getUserAction($id)
{
$user = $this->getDoctrine()->getRepository(User::class)->find($id);

$view = $this->view($user);
$view->setTemplate("MyBundle:User:getUser.html.twig");
$view->setTemplateVar('user');

return $this->handleView($view);
}
}

Neste exemplo, estamos usando o método $this->handleView() para formatar a resposta. Estamos definindo um modelo, um nome de variável para o nosso modelo e estamos passando essa resposta para o ViewHandler para que ocorra a devida formatação.

Como lidar com erros no FOSRestBundle?

O FOSRestBundle pode ajudar a lidar com erros ao criar uma API RESTful. Ele fornece um manipulador de exceção que pode manipular exceções e retornar uma resposta formatada em JSON. Com o manipulador de exceção, podemos retornar mensagens de erro personalizadas para os usuários da nossa API.

Aqui está um exemplo de como lidar com exceções no FOSRestBundle:

 namespace AppBundleController;

use FOSRestBundleControllerFOSRestController;
use FOSRestBundleControllerAnnotations as Rest;
use SymfonyComponentHttpFoundationRequest;
use AppBundleEntityUser;

class UserController extends FOSRestController
{
/**
* @RestGet("/users/{id}")
*/
public function getUserAction($id)
{
$user = $this->getDoctrine()->getRepository(User::class)->find($id);

if (!$user) {
throw $this->createNotFoundException('The user does not exist');
}

return $this->view($user);
}
}

Neste exemplo, estamos lançando uma exceção se não encontrarmos nenhum usuário com o id dado. Isso fará com que o FOSRestBundle entre no manipulador de exceção e retorne uma resposta de erro em JSON.

A configuração do manipulador de exceção pode ser compreendida nas documentações do FOSRestBundle e permite personalizar mensagens de erro para exceções específicas, além de codigos de respostas HTTP adequados que serão retornados na resposta da API.

Como lidar com CORS no FOSRestBundle?

O CORS é uma regra de segurança do navegador que impede que um site acesse recursos em outro site. Isso pode ser um problema quando estamos desenvolvendo uma API RESTful, onde os clientes vêm de outros domínios. O FOSRestBundle fornece uma solução simples para o CORS no Symfony.

Para configurar o FOSRestBundle para lidar com o CORS, precisamos editar o arquivo de configuração do Symfony:

 nelmio_cors:
defaults:
allow_credentials: false
allow_origin: ['*']
allow_headers: ['*']
allow_methods: ['GET', 'POST', 'PUT', 'DELETE', 'OPTIONS']
max_age: 3600

Neste exemplo, estamos permitindo todos os domínios, cabeçalhos e métodos HTTP. Também estamos definindo um tempo máximo de cache de 3600 segundos. Essa configuração é suficiente para a maioria das situações e torna a API RESTful do Symfony mais flexível.

Como usar o FOSRestBundle com autenticação JWT?

O FOSRestBundle suporta autenticação JWT (JSON Web Token), que é um padrão de autenticação amplamente utilizado na comunidade de desenvolvimento web.

Para usar autenticação JWT, precisamos instalar algumas dependências adicionais:

 composer require jwt-auth 

Em seguida, podemos configurar a autenticação nas nossas rotas:

 namespace AppBundleController;

use FOSRestBundleControllerFOSRestController;
use FOSRestBundleControllerAnnotations as Rest;
use SymfonyComponentHttpFoundationRequest;
use AppBundleEntityUser;
use LexikBundleJWTAuthenticationBundleServicesJWTTokenManagerInterface;

class SecurityController extends FOSRestController
{
/**
* @RestPost("/auth/login")
*/
public function loginAction(Request $request, JWTTokenManagerInterface $jwtManager)
{
// do your authentication here

$token = $jwtManager->create($user);

return $this->view(['token' => $token]);
}
}

Neste exemplo, estamos usando a biblioteca jwt-auth para gerar um token JWT que pode ser usado para autenticação posterior. Observe que estamos injetando o serviço JWTTokenManagerInterface em nossa ação de controle para criar o token.

Depois de criar o token, podemos usá-lo para autenticar nossas rotas:

 security:
providers:
in_memory:
memory:
users:
username:
password: password
roles:
- ROLE_USER

firewalls:
api:
pattern: ^/api
stateless: true
anonymous: true
provider: in_memory
guard:
authenticators:
- lexik_jwt_authentication.jwt_token_authenticator
logout: false
http_basic: ~

access_control:
- { path: ^/api/login, roles: IS_AUTHENTICATED_ANONYMOUSLY }
- { path: ^/api, roles: ROLE_USER }

Neste exemplo, estamos configurando o FOSRestBundle para usar o provedor de autenticação embutido do Symfony (in_memory) e adicionando um autenticador JWT. Novamente, estamos configurando um firewall para nossas rotas “/api” e adicionando um autenticador para autenticar nossos tokens.

Como usar a serialização de grupos no FOSRestBundle?

O FOSRestBundle suporta serialização de grupos, que é a capacidade de serializar apenas um subconjunto dos dados de uma entidade.

Para usar a serialização de grupos, primeiro precisamos criar um grupo no nosso modelo:

 namespace AppBundleEntity;

use DoctrineORMMapping as ORM;
use SymfonyComponentSerializerAnnotationGroups;

/**
* @ORMEntity()
*/
class User
{
/**
* @ORMId
* @ORMColumn(type="integer")
* @ORMGeneratedValue(strategy="AUTO")
*/
private $id;

/**
* @ORMColumn(type="string", length=255)
* @Groups({"public"})
*/
private $username;

/**
* @ORMColumn(type="string", length=255)
* @Groups({"private"})
*/
private $password;

// getters and setters...
}

Observe que estamos usando a anotação @Groups para definir dois grupos: “public” e “private”. O campo “username” é público e será incluído na serialização do grupo “public”, enquanto o campo “senha” é privado e será incluído na serialização do grupo “private”.

Para serializar apenas um grupo de dados, podemos usar o método $this->view() do FOSRestBundle e passar o grupo para o método serialize:

 namespace AppBundleController;

use FOSRestBundleControllerFOSRestController;
use FOSRestBundleControllerAnnotations as Rest;
use SymfonyComponentHttpFoundationRequest;
use AppBundleEntityUser;

class UserController extends FOSRestController
{
/**
* @RestGet("/users/{id}")
*/
public function getUserAction($id)
{
$user = $this->getDoctrine()->getRepository(User::class)->find($id);

return $this->view($user, 200, [], ['groups' => ['public']]);
}
}

Neste exemplo, estamos usando o método $this->view() para serializar apenas o grupo “public” de dados do usuário. Isso garante que a senha do usuário não seja incluída na resposta.

Como usar o mapeamento de formato no FOSRestBundle?

O FOSRestBundle suporta muitos formatos de saída, incluindo JSON, XML e YAML. No entanto, podemos adicionar nossos próprios formatos com o mapeamento de formato.

Para adicionar um novo formato, precisamos criar uma nova classe de formatador e configurar o FOSRestBundle para usá-la. Aqui está um exemplo: