std.net.dns.Resolver
type pub inline Resolver
A type for performing DNS queries.
Backends
The Resolver
type uses a different backend/implementation depending on the
underlying platform. These are as follows:
Platform | Backend | Fallback |
---|---|---|
FreeBSD | getaddrinfo() | None |
macOS | getaddrinfo() | None |
Linux | systemd-resolve (using its varlink API) | getaddrinfo() |
Due to the blocking nature of getaddrinfo()
, it's possible for a call to
this function to block the OS thread for a long period of time. While such
threads are marked as blocking and are replaced with a backup thread whenever
necessary, the number of available threads is fixed and thus it's possible to
exhaust all these threads by performing many slow DNS queries.
In contrast, the systemd-resolve backend is able to take advantage of Inko's
non-blocking network IO and thus doesn't suffer from the same problem. For
this reason it's highly recommended to ensure systemd-resolve is available
when deploying to a Linux environment. If systemd-resolve isn't available, the
Linux implementation falls back to using getaddrinfo()
.
When using the getaddrinfo()
backend, the following ai_flags
flags are
set:
AI_ADDRCONFIG
AI_V4MAPPED
These flags are set to ensure consistent behaviour across platforms and libc implementations.
Deadlines
A Resolver
supports setting a deadline using Resolver.timeout_after=
.
However, this timeout might be ignored based on the backend in use. Most
notably, getaddrinfo()
backends don't support timeouts/deadlines and instead
use a system-wide timeout, ignoring any deadlines set using
Resolver.timeout_after=
.
Examples
Resolving a hostname and using it to connect a socket:
import std.net.dns (Resolver)
import std.net.socket (TcpClient)
let dns = Resolver.new
let ips = dns.resolve('example.com').or_panic('DNS lookup failed')
ips.try(fn (ip) { TcpClient.new(ip, port: 80) }).or_panic('failed to connect')
Static methods
new
Show source codeHide source code
fn pub static new -> Resolver {
Resolver(sys.resolver)
}
fn pub static new -> Resolver
Returns a new Resolver
.
Instance methods
reset_deadline
Show source codeHide source code
fn pub mut reset_deadline {
@inner.reset_deadline
}
fn pub mut reset_deadline
Resets the deadline stored in self
.
resolve
Show source codeHide source code
fn pub mut resolve(host: String) -> Result[Array[IpAddress], Error] {
@inner.resolve(host)
}
fn pub mut resolve(host: String) -> Result[Array[IpAddress], Error]
Resolves the given hostname into a list of IP addresses.
Upon success an array of IpAddress
values is returned, storing them in the
order in which they should be used based on the underlying platform's
preferences.
Errors
If the host doesn't resolve to anything, an Error.InvalidHost
error is
returned.
If the DNS server produced some sort of internal error (e.g. it's
overloaded), an Error.ServerError
is returned.
For any other kind of error (e.g. a timeout), a Error.Other
is returned
that wraps an std.io.Error
value.
Examples
Resolving a hostname and using it to connect a socket:
import std.net.dns (Resolver)
import std.net.socket (TcpClient)
let dns = Resolver.new
let ips = dns.resolve('example.com').or_panic('DNS lookup failed')
ips
.try(fn (ip) { TcpClient.new(ip, port: 80) })
.or_panic('failed to connect')
timeout_after=
Show source codeHide source code
fn pub mut timeout_after=[T: ToInstant](deadline: ref T) {
@inner.timeout_after = deadline
}
fn pub mut timeout_after=[T: ToInstant](deadline: ref T)
Sets the point in time after which IO operations must time out.
Depending on the implementation of the resolver, the deadline might be ignored.