Packages
rambla
1.1.4
1.5.0
1.4.2
1.4.1
1.4.0
1.3.0
1.2.6
1.2.5
1.2.4
1.2.3
1.2.2
1.2.1
1.2.0
1.1.5
1.1.4
1.1.3
1.1.2
1.1.1
1.1.0
1.0.1
1.0.0
0.16.6
0.16.5
0.16.4
0.16.3
0.16.2
0.16.1
0.16.0
0.15.0
0.14.4
0.14.3
0.14.2
0.14.1
0.14.0
0.13.1
0.13.0
0.12.2
0.12.1
0.11.1
0.11.0
0.10.0
0.9.3
0.9.2
0.9.1
0.9.0
0.8.4
0.8.3
0.8.2
0.8.1
0.8.0
0.7.0
0.6.5
0.6.4
0.6.3
0.6.2
0.6.1
0.6.0
0.5.5
0.5.4
0.5.3
0.5.2
0.5.1
0.5.0
0.4.0
0.3.0
0.2.0
0.1.0
Easy publishing to many different targets. Supported back-ends: - Rabbit [Amqp](https://hexdocs.pm/amqp/) - Redis [Redix](https://hexdocs.pm/redix) - Http [:httpc](http://erlang.org/doc/man/httpc.html) - Smtp [:gen_smtp](https://hexdocs.pm/gen_smtp) - Slack [Envío](https://hexdocs.pm/envio)
Current section
Files
Jump to
Current section
Files
lib/rambla/connections/smtp.ex
defmodule Rambla.Smtp do
@moduledoc """
Default connection implementation for 📧 SMTP.
It expects a message to be a map containing the following fields:
`:to`, `:subject`, `:body` _and_ the optional `:from` that otherwise would be
taken from the global settings (`releases.mix`) from `[]:rambla, :pools, Rambla.Smtp]`.
For instance, this call would send an email to email:am@example.com with the
respective subject and body.
```elixir
Rambla.publish(
Rambla.Smtp,
%{to: "am@example.com", subject: "Hi there", body: "I ❤ SMTP"}
}
```
"""
@behaviour Rambla.Connection
@conn_params ~w|relay username password auth ssl tls tls_options hostname retries|a
@impl Rambla.Connection
def connect(params) when is_list(params) do
if is_nil(params[:hostname]),
do:
raise(Rambla.Exceptions.Connection,
value: params,
source: __MODULE__,
reason: "inconsistent params",
expected: "📧 configuration with :host key"
)
[defaults, opts] =
params
|> Keyword.split(@conn_params)
|> Tuple.to_list()
|> Enum.map(&Map.new/1)
%Rambla.Connection{
conn: %Rambla.Connection.Config{conn: params[:hostname], opts: opts, defaults: defaults},
conn_type: __MODULE__,
conn_pid: self(),
conn_params: params,
errors: []
}
end
@impl Rambla.Connection
def publish(%Rambla.Connection.Config{} = conn, message) when is_binary(message),
do: publish(conn, Jason.decode!(message))
@impl Rambla.Connection
def publish(%Rambla.Connection.Config{} = conn, message) when is_list(message),
do: publish(conn, Map.new(message))
@impl Rambla.Connection
def publish(%Rambla.Connection.Config{opts: opts, defaults: defaults}, message)
when is_map(opts) and is_map(message) do
{to, message} = Map.pop(message, :to)
{from, message} = Map.pop(message, :from, Map.get(opts, :from, []))
{subject, message} = Map.pop(message, :subject, Map.pop(opts, :subject, ""))
{body, _message} = Map.pop(message, :body, Map.pop(opts, :body, ""))
from_with_name = for {name, email} <- from, do: "#{name} <#{email}>"
smtp_message =
["Subject: ", "From: ", "To: ", "\r\n"]
|> Enum.zip([subject, hd(from_with_name), to, body])
|> Enum.map_join("\r\n", &(&1 |> Tuple.to_list() |> Enum.join()))
apply(:gen_smtp_client, :send, [
{to, Map.values(from), smtp_message},
defaults
|> Map.merge(Map.take(opts, @conn_params))
|> Map.to_list()
])
end
end