Nos últimos artigos discutimos, com muita paciência, sobre como padronizar APIs REST, porque, obviamente, isso não é algo que todo mundo entende facilmente (como já percebemos claramente). Já falamos das motivações e das boas práticas, mas agora, finalmente, chega de teoria! Vamos criar uma API RESTful que segue, vejam só, boas práticas. Impressionante, não é?
Sua API retorna sempre um 200 OK até quando o banco explode? Você usa POST onde deveria usar GET porque o cliente achou "mais simples"? Pois é, hoje você vai aprender como parar com essas barbaridades!
Neste tutorial faremos uma API que finalmente respeita os padrões RESTful. Sim, isso inclui erros decentes usando ProblemDetails, Status Codes corretos para GET, POST, PUT, PATCH e DELETE, e, claro, Swagger. Não adianta ter API bonitinha e não saber usá-la, né?
Ah, e leia o artigo anterior se não sabe nem o que é RESTful: API RESTful - Boas práticas
Padrões importam (quem diria, né?)
Uncle Bob disse em "Clean Code" que você passa 10 vezes mais tempo lendo código do que escrevendo. E ainda assim, você insiste em criar códigos ilegíveis, parabéns!
Indeed, the ratio of time spent reading vs. writing is well over 10:1.
Martin, Robert C.. Clean Code (Robert C. Martin Series) . Pearson Education.
Padrões existem para facilitar sua vida miserável. Já imaginou reaprender a dirigir todo dia? O caos seria pouco comparado ao que você gera com códigos sem padrão algum. Siga padrões e pare de reinventar a roda, por favor.
Swagger (para quem não gosta de sofrer)
OpenAPI com Swagger facilita sua vida para testar a API, ou seja, uma ferramenta útil, o que é raro na sua stack.
Instale via Nuget o pacote Swashbuckle.AspNetCore e configure no Startup.cs
:
Olha só que simples configurar, quase como apertar Ctrl+C e Ctrl+V!
Filtrar, paginar e ordenar (sem precisar rezar)
A vida não é só POST e GET sem parâmetros. Observe essa requisição detalhada:
GET /users?status=active&lives_in=brazil&older_than=18&younger_than=35&sort=firstname,-lastname&limit=10
Com a biblioteca AspNet.Core.RESTFul.Extensions
você cria filtros decentes, não aquela bagunça manual que você chama de "código personalizado":
E na Controller, você utiliza esse parâmetro no GET:
Pronto, QueryString organizada, quem diria, hein?
Respostas e Status Codes (o básico que você ignora)
- 200 Ok - sucesso. Parece simples, mas você insiste em errar.
- 201 Created - criado com sucesso (POST).
- 204 No Content - deu certo, mas não tem conteúdo (PUT, PATCH, DELETE).
- 202 Accepted - aceita, mas será processada depois (assíncrono).
GET (aquele que deveria ser simples)
POST (para criar algo útil)
Use CreatedAtAction()
, não retorne só um objeto jogado!
PUT (para quem ainda acha que "atualizar" é só substituir)
PATCH (para atualizar parcialmente sem destruir tudo)
DELETE (o comando que você mais usa acidentalmente)
Download (para copiar porque você não aguenta escrever tudo)

O projeto completo está no meu GitHub, para você copiar sem vergonha nenhuma.
Conclusão
Espero que esse artigo tenha ajudado e que pelo menos um dia você consiga fazer uma API decente. Deixe seus comentários, estou curioso para ver suas desculpas!
Texto original de 16/01/2020