terça-feira, 11 de abril de 2017

Defql: Consultas SQL como funções Elixir

PorMichał Kalbarczyk em

O mundo Elixir é funcional. Não há objetos ou instâncias. Nesse caso, eu me fiz uma pergunta.

Preciso de ORM?

Minha resposta a essa pergunta é não.

Preciso de dados. Dados puros que vêm diretamente do banco de dados. Outra pergunta que vem à minha mente.

Preciso de um DSL para consultar banco de dados?

Outra resposta negativa.

Temos uma ótima linguagem criada para consultar o banco de dados. SQL, lembra?

E se eu pudesse criar uma função Elixir que tenha um corpo SQL? E se eu pudesse usar essa função exatamente como qualquer outra função do Elixir? Seria ótimo, não é?

Podemos arquivar isso usando o sistema macro muito poderoso do Elixir. No entanto, essa também é uma boa maneira de aprender como as macros do Elixir funcionam.

Para arquivar isso, eu comecei a escrever Defql. Defql é um pacote Elixir que fornece uma maneira simples de definir funções com linguagem SQL. Como ele funciona?
Consultando banco de dados

Esse pacote fornece a macro defquery. Com ela, você pode definir a função que contém uma consulta SQL. Por exemplo:

1 defmodule UserQuery do


2 use Defql




4 defquery get_by_blocked(blocked) do


5 "SELECT * FROM users WHERE blocked = $blocked"


6 end


7 end


Parece muito limpo, é fácil de ler e a melhor parte dele é que ele suporta parâmetros. Brilhante!

Chamar essa função também é muito simples.

Dependendo do parâmetro fornecido, obteremos usuários bloqueados ou desbloqueados.

1 UserQuery.get_user(false) # => {:ok, []} 


2 UserQuery.get_user(true) # => {:ok, []}


Agora nós podemos consultar facilmente nosso banco de dados e encontrar um resultado.

E quanto a INSERT, UPDATE e DELETE? Boa pergunta! Você pode criar essas consultas com defquery, mas há outro método.
CRUD

Esse pacote também contém outras macros. Dê uma olhada neste exemplo:

1 defmodule UserQuery do


2 use Defql




4 defselect get(conds), table: :users


5 definsert add(params), table: :users


6 defupdate update(params, conds), table: :users


7 defdelete delete(conds), table: :users


8 end


O que eles farão? Essas macros irão criar funções CRUD comuns. Então, você não precisa escrever cada consulta com o SQL. Algumas simples são criadas para você, como esta. Como posso invocá-las? Aqui está um exemplo:

1 UserQuery.get(id: "3") # => {:ok, [%{...}]}


2 UserQuery.add(name: "Smbdy") # => {:ok, [%{...}]}


3 UserQuery.update([name: "Other"],[id: "2"]) # => {:ok, [%{...}]}


4 UserQuery.delete(id: "2") # => {:ok, [%{...}]}

Configuração

A configuração também é uma tarefa fácil. Agora mesmo você pode usá-la de duas maneiras.

Com conexão Ecto existente:

1 config :defql, connection: [


2 adapter: Defql.Adapter.Ecto.Postgres,


3 repo: Taped.Repo


4 ]


Como uma conexão autônoma:

CÓDIGO
O que falta?

Claro, é um estágio muito inicial, mas o suporte para postgres funciona bem. Há poucas coisas que estão faltando:
Suporte para MySQL
Suporte para IN com array % {id: [1,2,3]}
Adaptador ECTO de limpeza
Suporte para erros de banco de dados
Resumo

Usando Defql, temos uma maneira muito clara, simples e poderosa de interagir com um banco de dados.
Links
Repositório GitHub: https://github.com/fazibear/defql
Pacote hexadecimal: https://hex.pm/packages/defql
Documentação: https://hexdocs.pm/defql

Espero que tenha sido útil para você. Obrigado por ler!

***

Michał Kalbarczyk faz parte do time de colunistas internacionais do iMasters. A tradução do artigo é feita pela redação iMasters, com autorização do autor, e você pode acompanhar o artigo em inglês no link: https://blog.fazibear.me/sql-queries-as-elixir-functions-5f8b1d67169e.

Nenhum comentário:

Postar um comentário