Packages

Gleam bindings for Erlang's built-in DNS resolution modules.

Current section

Files

Jump to
nessie_2 src nessie_2.erl
Raw

src/nessie_2.erl

-module(nessie_2).
-compile([no_auto_import, nowarn_unused_vars, nowarn_unused_function, nowarn_nomatch, inline]).
-define(FILEPATH, "src/nessie_2.gleam").
-export([ip_decoder/0, getbyname/3, getbyname_soa/2, getbyname_ipv4/2, getbyname_ipv6/2, getbyname_mx/2, gethostbyaddr/2, lookup_ipv4/3, lookup_ipv6/3, lookup/4, lookup_soa/3, lookup_mx/3, ip_to_string/1, string_to_ip/1]).
-export_type([dns_class/0, resolver_option/0, s_o_a_record/0, error_reason/0, m_x_record/0, timeout_/0, hostent/1, i_p_address/0, string_record_type/0]).
-if(?OTP_RELEASE >= 27).
-define(MODULEDOC(Str), -moduledoc(Str)).
-define(DOC(Str), -doc(Str)).
-else.
-define(MODULEDOC(Str), -compile([])).
-define(DOC(Str), -compile([])).
-endif.
?MODULEDOC(
" A collection of functions for resolving DNS names in Gleam programs targeting Erlang.\n"
"\n"
" The functions in this module are implemented using Erlang's built-in\n"
" `inet_res` and `inet` modules. Most of the functions and types are simply\n"
" Gleam representations of their Erlang counterparts.\n"
).
-type dns_class() :: in | chaos | hs | any.
-type resolver_option() :: {nameservers, list({i_p_address(), integer()})} |
{i_net6, boolean()} |
{recurse, boolean()} |
{retry, integer()} |
{timeout_millis, integer()} |
{nxdomain_reply, boolean()}.
-type s_o_a_record() :: {s_o_a_record,
binary(),
binary(),
integer(),
integer(),
integer(),
integer(),
integer()}.
-type error_reason() :: formerr |
qfmterr |
servfail |
nxdomain |
notimp |
refused |
badvers |
timeout_err |
{other, binary()}.
-type m_x_record() :: {m_x_record, integer(), binary()}.
-type timeout_() :: {timeout, integer()} | infinity.
-type hostent(EAR) :: {hostent,
binary(),
list(binary()),
binary(),
integer(),
list(EAR)}.
-type i_p_address() :: {i_p_v4, {integer(), integer(), integer(), integer()}} |
{i_p_v6,
{integer(),
integer(),
integer(),
integer(),
integer(),
integer(),
integer(),
integer()}}.
-type string_record_type() :: cname | txt | ns.
-file("src/nessie_2.gleam", 144).
?DOC(" Returns a `gleam/dynamic.Decoder` for decoding an IP address tuple.\n").
-spec ip_decoder() -> gleam@dynamic@decode:decoder(i_p_address()).
ip_decoder() ->
Ipv4_decoder = begin
gleam@dynamic@decode:field(
0,
{decoder, fun gleam@dynamic@decode:decode_int/1},
fun(I1) ->
gleam@dynamic@decode:field(
1,
{decoder, fun gleam@dynamic@decode:decode_int/1},
fun(I2) ->
gleam@dynamic@decode:field(
2,
{decoder, fun gleam@dynamic@decode:decode_int/1},
fun(I3) ->
gleam@dynamic@decode:field(
3,
{decoder,
fun gleam@dynamic@decode:decode_int/1},
fun(I4) ->
gleam@dynamic@decode:success(
{i_p_v4, {I1, I2, I3, I4}}
)
end
)
end
)
end
)
end
)
end,
Ipv6_decoder = begin
gleam@dynamic@decode:field(
0,
{decoder, fun gleam@dynamic@decode:decode_int/1},
fun(I1@1) ->
gleam@dynamic@decode:field(
1,
{decoder, fun gleam@dynamic@decode:decode_int/1},
fun(I2@1) ->
gleam@dynamic@decode:field(
2,
{decoder, fun gleam@dynamic@decode:decode_int/1},
fun(I3@1) ->
gleam@dynamic@decode:field(
3,
{decoder,
fun gleam@dynamic@decode:decode_int/1},
fun(I4@1) ->
gleam@dynamic@decode:field(
4,
{decoder,
fun gleam@dynamic@decode:decode_int/1},
fun(I5) ->
gleam@dynamic@decode:field(
5,
{decoder,
fun gleam@dynamic@decode:decode_int/1},
fun(I6) ->
gleam@dynamic@decode:field(
6,
{decoder,
fun gleam@dynamic@decode:decode_int/1},
fun(I7) ->
gleam@dynamic@decode:field(
7,
{decoder,
fun gleam@dynamic@decode:decode_int/1},
fun(I8) ->
gleam@dynamic@decode:success(
{i_p_v6,
{I1@1,
I2@1,
I3@1,
I4@1,
I5,
I6,
I7,
I8}}
)
end
)
end
)
end
)
end
)
end
)
end
)
end
)
end
)
end,
gleam@dynamic@decode:one_of(Ipv6_decoder, [Ipv4_decoder]).
-file("src/nessie_2.gleam", 293).
-spec to_erl_resolver_option(resolver_option()) -> {gleam@erlang@atom:atom_(),
gleam@dynamic:dynamic_()}.
to_erl_resolver_option(Option) ->
{Opt_name, Opt_value} = case Option of
{i_net6, Inet6} ->
{<<"inet6"/utf8>>, gleam_stdlib:identity(Inet6)};
{recurse, Recurse} ->
{<<"recurse"/utf8>>, gleam_stdlib:identity(Recurse)};
{retry, Retry} ->
{<<"retry"/utf8>>, gleam_stdlib:identity(Retry)};
{timeout_millis, Timeout} ->
{<<"timeout"/utf8>>, gleam_stdlib:identity(Timeout)};
{nxdomain_reply, Nxdomain_reply} ->
{<<"nxdomain_reply"/utf8>>, gleam_stdlib:identity(Nxdomain_reply)};
{nameservers, Nameservers} ->
Erl_nameservers = gleam@list:map(
Nameservers,
fun(Ip_port) ->
{Ip, Port} = Ip_port,
Ip@1 = begin
Ints = case Ip of
{i_p_v4, {N1, N2, N3, N4}} ->
[N1, N2, N3, N4];
{i_p_v6, {N1@1, N2@1, N3@1, N4@1, N5, N6, N7, N8}} ->
[N1@1, N2@1, N3@1, N4@1, N5, N6, N7, N8]
end,
_pipe = gleam@list:map(
Ints,
fun gleam_stdlib:identity/1
),
gleam_stdlib:identity(_pipe)
end,
erlang:list_to_tuple([Ip@1, gleam_stdlib:identity(Port)])
end
),
{<<"nameservers"/utf8>>, gleam_stdlib:identity(Erl_nameservers)}
end,
{erlang:binary_to_atom(Opt_name), Opt_value}.
-file("src/nessie_2.gleam", 347).
-spec to_dns_err(gleam@erlang@atom:atom_()) -> error_reason().
to_dns_err(E) ->
E@1 = erlang:atom_to_binary(E),
case E@1 of
<<"formerr"/utf8>> ->
formerr;
<<"qfmterror"/utf8>> ->
qfmterr;
<<"servfail"/utf8>> ->
servfail;
<<"nxdomain"/utf8>> ->
nxdomain;
<<"notimp"/utf8>> ->
notimp;
<<"refused"/utf8>> ->
refused;
<<"badvers"/utf8>> ->
badvers;
<<"timeout"/utf8>> ->
timeout_err;
_ ->
{other, E@1}
end.
-file("src/nessie_2.gleam", 379).
-spec from_dns_name(gleam@dynamic:dynamic_()) -> binary().
from_dns_name(Dyn) ->
Atom_from_dynamic = fun() -> _pipe = Dyn,
_pipe@1 = gleam_erlang_ffi:identity(_pipe),
_pipe@2 = erlang:atom_to_binary(_pipe@1),
{ok, _pipe@2} end,
_pipe@3 = Dyn,
_pipe@4 = nessie_inet_res_ffi:charlist_from_dynamic(_pipe@3),
_pipe@5 = gleam@result:map(_pipe@4, fun unicode:characters_to_binary/1),
_pipe@6 = gleam@result:lazy_or(_pipe@5, Atom_from_dynamic),
gleam@result:unwrap(_pipe@6, <<""/utf8>>).
-file("src/nessie_2.gleam", 363).
-spec to_hostent(
{gleam@erlang@atom:atom_(),
gleam@dynamic:dynamic_(),
list(gleam@dynamic:dynamic_()),
gleam@erlang@atom:atom_(),
integer(),
list(ECC)},
fun((ECC) -> ECE)
) -> hostent(ECE).
to_hostent(Erl_hostent, Addr_list_transform) ->
{_, Name, Aliases, Addrtype, Length, Addr_list} = Erl_hostent,
Gleam_aliases = gleam@list:map(Aliases, fun from_dns_name/1),
{hostent,
from_dns_name(Name),
Gleam_aliases,
erlang:atom_to_binary(Addrtype),
Length,
gleam@list:map(Addr_list, Addr_list_transform)}.
-file("src/nessie_2.gleam", 394).
-spec to_mx({integer(), gleam@dynamic:dynamic_()}) -> m_x_record().
to_mx(Erl_mx) ->
{Priority, Exchange} = Erl_mx,
{m_x_record, Priority, from_dns_name(Exchange)}.
-file("src/nessie_2.gleam", 399).
-spec to_soa(
{gleam@dynamic:dynamic_(),
gleam@dynamic:dynamic_(),
integer(),
integer(),
integer(),
integer(),
integer()}
) -> s_o_a_record().
to_soa(Erl_soa) ->
{Mname, Rname, Serial, Refresh, Retry, Expire, Minimum} = Erl_soa,
{s_o_a_record,
from_dns_name(Mname),
from_dns_name(Rname),
Serial,
Refresh,
Retry,
Expire,
Minimum}.
-file("src/nessie_2.gleam", 228).
?DOC(" Looks up a DNS record of the given type for the given name.\n").
-spec getbyname(binary(), string_record_type(), timeout_()) -> {ok,
hostent(binary())} |
{error, error_reason()}.
getbyname(Name, Srt, Timeout) ->
_pipe = nessie_inet_res_ffi:getbyname(Name, Srt, Timeout),
_pipe@1 = gleam@result:map(
_pipe,
fun(_capture) ->
to_hostent(_capture, fun unicode:characters_to_binary/1)
end
),
gleam@result:map_error(_pipe@1, fun to_dns_err/1).
-file("src/nessie_2.gleam", 261).
?DOC(" Looks up a SOA record for the given name.\n").
-spec getbyname_soa(binary(), timeout_()) -> {ok, hostent(s_o_a_record())} |
{error, error_reason()}.
getbyname_soa(Name, Timeout) ->
_pipe = Name,
_pipe@1 = nessie_inet_res_ffi:getbyname_soa(_pipe, Timeout),
_pipe@2 = gleam@result:map(
_pipe@1,
fun(_capture) -> to_hostent(_capture, fun to_soa/1) end
),
gleam@result:map_error(_pipe@2, fun to_dns_err/1).
-file("src/nessie_2.gleam", 239).
?DOC(" Looks up an `A` record for the given name.\n").
-spec getbyname_ipv4(binary(), timeout_()) -> {ok,
hostent({integer(), integer(), integer(), integer()})} |
{error, error_reason()}.
getbyname_ipv4(Name, Timeout) ->
_pipe = Name,
_pipe@1 = nessie_inet_res_ffi:getbyname_ipv4(_pipe, Timeout),
_pipe@2 = gleam@result:map(
_pipe@1,
fun(_capture) -> to_hostent(_capture, fun gleam@function:identity/1) end
),
gleam@result:map_error(_pipe@2, fun to_dns_err/1).
-file("src/nessie_2.gleam", 250).
?DOC(" Looks up an `AAAA` record for the given name.\n").
-spec getbyname_ipv6(binary(), timeout_()) -> {ok,
hostent({integer(),
integer(),
integer(),
integer(),
integer(),
integer(),
integer(),
integer()})} |
{error, error_reason()}.
getbyname_ipv6(Name, Timeout) ->
_pipe = Name,
_pipe@1 = nessie_inet_res_ffi:getbyname_ipv6(_pipe, Timeout),
_pipe@2 = gleam@result:map(
_pipe@1,
fun(_capture) -> to_hostent(_capture, fun gleam@function:identity/1) end
),
gleam@result:map_error(_pipe@2, fun to_dns_err/1).
-file("src/nessie_2.gleam", 272).
?DOC(" Looks up a DNS MX record for the given name.\n").
-spec getbyname_mx(binary(), timeout_()) -> {ok, hostent(m_x_record())} |
{error, error_reason()}.
getbyname_mx(Name, Timeout) ->
_pipe = Name,
_pipe@1 = nessie_inet_res_ffi:getbyname_mx(_pipe, Timeout),
_pipe@2 = gleam@result:map(
_pipe@1,
fun(_capture) -> to_hostent(_capture, fun to_mx/1) end
),
gleam@result:map_error(_pipe@2, fun to_dns_err/1).
-file("src/nessie_2.gleam", 283).
?DOC(" Looks up a host by IP address.\n").
-spec gethostbyaddr(i_p_address(), timeout_()) -> {ok, hostent(binary())} |
{error, error_reason()}.
gethostbyaddr(Address, Timeout) ->
_pipe = Address,
_pipe@1 = nessie_inet_res_ffi:gethostbyaddr(_pipe, Timeout),
_pipe@2 = gleam@result:map(
_pipe@1,
fun(_capture) ->
to_hostent(_capture, fun unicode:characters_to_binary/1)
end
),
gleam@result:map_error(_pipe@2, fun to_dns_err/1).
-file("src/nessie_2.gleam", 185).
?DOC(" Looks up an `A` record for the given name.\n").
-spec lookup_ipv4(binary(), dns_class(), list(resolver_option())) -> list({integer(),
integer(),
integer(),
integer()}).
lookup_ipv4(Name, Class, Options) ->
Erl_options = gleam@list:map(Options, fun to_erl_resolver_option/1),
nessie_inet_res_ffi:lookup_ipv4(Name, Class, Erl_options).
-file("src/nessie_2.gleam", 195).
?DOC(" Looks up an `AAAA` record for the given name.\n").
-spec lookup_ipv6(binary(), dns_class(), list(resolver_option())) -> list({integer(),
integer(),
integer(),
integer(),
integer(),
integer(),
integer(),
integer()}).
lookup_ipv6(Name, Class, Options) ->
Erl_options = gleam@list:map(Options, fun to_erl_resolver_option/1),
nessie_inet_res_ffi:lookup_ipv6(Name, Class, Erl_options).
-file("src/nessie_2.gleam", 171).
?DOC(" Looks up a record of the specified type for the given name.\n").
-spec lookup(
binary(),
dns_class(),
string_record_type(),
list(resolver_option())
) -> list(binary()).
lookup(Name, Class, Srt, Options) ->
Erl_options = gleam@list:map(Options, fun to_erl_resolver_option/1),
_pipe = Name,
_pipe@1 = nessie_inet_res_ffi:lookup(_pipe, Class, Srt, Erl_options),
gleam@list:map(_pipe@1, fun unicode:characters_to_binary/1).
-file("src/nessie_2.gleam", 205).
?DOC(" Looks up a SOA record for the given name.\n").
-spec lookup_soa(binary(), dns_class(), list(resolver_option())) -> list(s_o_a_record()).
lookup_soa(Name, Class, Options) ->
Erl_options = gleam@list:map(Options, fun to_erl_resolver_option/1),
_pipe = Name,
_pipe@1 = nessie_inet_res_ffi:lookup_soa(_pipe, Class, Erl_options),
gleam@list:map(_pipe@1, fun to_soa/1).
-file("src/nessie_2.gleam", 216).
-spec lookup_mx(binary(), dns_class(), list(resolver_option())) -> list(m_x_record()).
lookup_mx(Name, Class, Options) ->
Erl_options = gleam@list:map(Options, fun to_erl_resolver_option/1),
_pipe = Name,
_pipe@1 = nessie_inet_res_ffi:lookup_mx(_pipe, Class, Erl_options),
gleam@list:map(_pipe@1, fun to_mx/1).
-file("src/nessie_2.gleam", 112).
?DOC(
" Converts an IP address to a string.\n"
"\n"
" For more detail, see the `inet` module's [ntoa/1 function docs](https://www.erlang.org/doc/man/inet#ntoa-1)\n"
).
-spec ip_to_string(i_p_address()) -> {ok, binary()} | {error, binary()}.
ip_to_string(Ip_addr) ->
_pipe = Ip_addr,
_pipe@1 = nessie_inet_ffi:ntoa(_pipe),
_pipe@2 = gleam@result:map(_pipe@1, fun unicode:characters_to_binary/1),
gleam@result:map_error(_pipe@2, fun erlang:atom_to_binary/1).
-file("src/nessie_2.gleam", 124).
?DOC(
" Converts a string to an IP address.\n"
"\n"
" If the given string is not a valid IP address, this function returns an error.\n"
"\n"
" For more detail, see the `inet` module's [parse_address/1 function docs](https://www.erlang.org/doc/man/inet#parse_address-1).\n"
).
-spec string_to_ip(binary()) -> {ok, i_p_address()} | {error, binary()}.
string_to_ip(Ip_addr) ->
_pipe = Ip_addr,
_pipe@1 = nessie_inet_ffi:parse_address(_pipe),
_pipe@2 = gleam@result:map_error(_pipe@1, fun erlang:atom_to_binary/1),
_pipe@4 = gleam@result:map(
_pipe@2,
fun(Dyn) -> _pipe@3 = gleam@dynamic@decode:run(Dyn, ip_decoder()),
gleam@result:replace_error(_pipe@3, <<"decode_error"/utf8>>) end
),
gleam@result:flatten(_pipe@4).