dns
Version, currently 0.1.02 versions
- 0.1.1latestApr 26, 2020
- 0.1.0not indexedJan 31, 2020
gitlab.com/jgillich/crystal-dns
DNS protocol library
Nothing has been indexed for 0.1.0 yet. The tag is recorded, its shard.yml has not been read, so the manifest and dependency list below are empty because they are unknown rather than because they are absent.
Installation
# Add this to your shard.yml
dependencies:
dns:
gitlab: jgillich/crystal-dns
version: ~> 0.1.0Then run:
shards installshard.yml
No shard.yml has been indexed for 0.1.0. You can read it on the repository.
Dependencies
Unknown: the shard.yml for this version has not been read yet.
README
This README is the one indexed from the repository at its latest ref, not from the tag for this version.
DNS for Crystal
crystal-dns implements the DNS protocol and provides a resolver. It can also be used to implement a name server, but there might be some missing pieces.
This is beta quality software. The API is not stable and some features are missing. Further testing is needed. No support for DNSSEC and DNS-over-TLS at this time.
crystal-dns was developed for Everbase, our Crystal-powered API that makes you a more productive developer. Check it out!
Installation
Add this to your project's shard.yml:
dependencies:
dns:
gitlab: jgillich/crystal-dns
Resolver Usage
resolver = DNS::Resolver.new
response = resolver.query("example.com", DNS::RecordType::AAAA)
response.answers.each do |answer|
puts "got ipv6 address #{answer.data}"
end
resolver.close
Advanced Usage
If you are already familiar with DNS, most of this library should be self-explanatory. The main
information carrier in DNS is a Message. The format is identical for both queries and responses,
but some fields vary. In a nutshell, a message contains:
- A header. This includes information about the message (is it a query or a response, number of results, etc)
- A question. It consists of a domain name, a record type (A, CNAME, MX etc) and a record class (in most cases IN for internet). Technically DNS allows for more than one question, but very few name servers support this.
- A number of records with a data payload. If your question's record type is A, the payload is an IPv4 address.
First we need a Socket to communicate over. This can be either a client or a
server, but for this example we'll talk to a server.
require "socket"
require "dns"
socket = UDPSocket.new
socket.connect("8.8.8.8", 53)
Now we build a message with the format from above:
header = DNS::Header.new(op_code: DNS::OpCode::Query, recursion_desired: true)
message = DNS::Message.new(header: header)
message.questions << DNS::Question.new(name: DNS::Name.new("www.example.com"), query_type: DNS::ResourceType::A)
This is a valid DNS query that will return the IPv4 address for the domain www.example.com.
Message implements #to_io(IO, IO::ByteFormat) and .from_io(IO, IO::ByteFormat), but they do
not work well with a Socket. We need IO#seek to resolve pointers, but sockets do not implement
this method. There are also some slight variations in the data format between UDP and TCP. So
instead, we provide #to_socket(Socket, IO::ByteFormat) and Message.from_socket(Socket, IO::ByteFormat).
Let's use them to send our message:
message.to_socket socket
Done! Now we can read the response:
response = Message.from_socket socket
response.answers.each do |answer|
puts "got ipv4 address #{answer.data}"
end
Links
Documentation
Built from the current release. The first visit to a release nobody has asked for starts its build.
Links
This release
- Version
0.1.0- Tagged
- Jan 31, 2020
- Commit
41ae9c180d95- Indexed
- not yet
Dependents
Repository
gitlab.com/jgillich/crystal-dns
Metadata
- Created
- Aug 16, 2026
- Updated
- Oct 14, 2026
- Synced
- Oct 14, 2026
- Versions
- 2