rubydns 1.0.3 → 2.0.0.pre.rc1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.rspec +4 -0
- data/.travis.yml +9 -12
- data/Gemfile +4 -1
- data/README.md +49 -151
- data/Rakefile +2 -7
- data/examples/basic-dns.rb +24 -0
- data/examples/cname.rb +25 -0
- data/examples/flakey-dns.rb +2 -2
- data/examples/simple.rb +25 -0
- data/examples/soa-dns.rb +82 -0
- data/examples/test-dns-1.rb +83 -0
- data/examples/test-dns-2.rb +83 -0
- data/examples/wikipedia-dns.rb +4 -18
- data/lib/rubydns.rb +9 -23
- data/lib/rubydns/{server.rb → rule_based_server.rb} +2 -160
- data/lib/rubydns/version.rb +1 -1
- data/rubydns.gemspec +3 -6
- data/spec/rubydns/daemon_spec.rb +26 -22
- data/spec/rubydns/injected_supervisor_spec.rb +10 -7
- data/spec/rubydns/passthrough_spec.rb +31 -24
- data/spec/spec_helper.rb +43 -0
- metadata +21 -100
- data/lib/rubydns/chunked.rb +0 -34
- data/lib/rubydns/extensions/resolv.rb +0 -85
- data/lib/rubydns/extensions/string.rb +0 -28
- data/lib/rubydns/handler.rb +0 -188
- data/lib/rubydns/logger.rb +0 -31
- data/lib/rubydns/message.rb +0 -76
- data/lib/rubydns/resolver.rb +0 -294
- data/lib/rubydns/system.rb +0 -146
- data/lib/rubydns/transaction.rb +0 -204
- data/lib/rubydns/transport.rb +0 -75
- data/spec/rubydns/celluloid_bug_spec.rb +0 -92
- data/spec/rubydns/ipv6_spec.rb +0 -70
- data/spec/rubydns/message_spec.rb +0 -56
- data/spec/rubydns/origin_spec.rb +0 -106
- data/spec/rubydns/resolver_performance_spec.rb +0 -110
- data/spec/rubydns/resolver_spec.rb +0 -152
- data/spec/rubydns/server/bind9/generate-local.rb +0 -25
- data/spec/rubydns/server/bind9/local.zone +0 -5014
- data/spec/rubydns/server/bind9/named.conf +0 -14
- data/spec/rubydns/server/bind9/named.run +0 -0
- data/spec/rubydns/server/million.rb +0 -85
- data/spec/rubydns/server/rubydns.stackprof +0 -0
- data/spec/rubydns/server_performance_spec.rb +0 -136
- data/spec/rubydns/slow_server_spec.rb +0 -89
- data/spec/rubydns/socket_spec.rb +0 -77
- data/spec/rubydns/system_spec.rb +0 -60
- data/spec/rubydns/transaction_spec.rb +0 -138
- data/spec/rubydns/truncation_spec.rb +0 -59
@@ -0,0 +1,83 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# Copyright, 2009, 2012, by Samuel G. D. Williams. <http://www.codeotaku.com>
|
4
|
+
#
|
5
|
+
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
+
# of this software and associated documentation files (the "Software"), to deal
|
7
|
+
# in the Software without restriction, including without limitation the rights
|
8
|
+
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
# copies of the Software, and to permit persons to whom the Software is
|
10
|
+
# furnished to do so, subject to the following conditions:
|
11
|
+
#
|
12
|
+
# The above copyright notice and this permission notice shall be included in
|
13
|
+
# all copies or substantial portions of the Software.
|
14
|
+
#
|
15
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
+
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
+
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
+
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
+
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
20
|
+
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
21
|
+
# THE SOFTWARE.
|
22
|
+
|
23
|
+
require 'rubygems'
|
24
|
+
require 'rubydns'
|
25
|
+
require 'rubydns/system'
|
26
|
+
|
27
|
+
# You can specify other DNS servers easily
|
28
|
+
# $R = Resolv::DNS.new(:nameserver => ["xx.xx.1.1", "xx.xx.2.2"])
|
29
|
+
|
30
|
+
R = RubyDNS::Resolver.new(RubyDNS::System.nameservers)
|
31
|
+
Name = Resolv::DNS::Name
|
32
|
+
IN = Resolv::DNS::Resource::IN
|
33
|
+
INTERFACES = [
|
34
|
+
[:udp, '0.0.0.0', 5300],
|
35
|
+
[:tcp, '0.0.0.0', 5300],
|
36
|
+
# [:udp, '::0', 5300],
|
37
|
+
# [:tcp, '::0', 5300],
|
38
|
+
]
|
39
|
+
|
40
|
+
RubyDNS.run_server(listen: INTERFACES) do
|
41
|
+
# % dig +nocmd +noall +answer @localhost ANY dev.mydomain.org
|
42
|
+
# dev.mydomain.org. 16000 IN A 10.0.0.80
|
43
|
+
# dev.mydomain.org. 16000 IN MX 10 mail.mydomain.org.
|
44
|
+
match(/dev.mydomain.org/, IN::ANY) do |transaction|
|
45
|
+
transaction.append_question!
|
46
|
+
|
47
|
+
[IN::A, IN::CNAME, IN::MX].each do |resource_class|
|
48
|
+
logger.debug "Appending query for #{resource_class}..."
|
49
|
+
transaction.append!(transaction.name, resource_class)
|
50
|
+
end
|
51
|
+
end
|
52
|
+
|
53
|
+
# For this exact address record, return an IP address
|
54
|
+
match('dev.mydomain.org', IN::A) do |transaction|
|
55
|
+
transaction.respond!('10.0.0.80')
|
56
|
+
end
|
57
|
+
|
58
|
+
match('80.0.0.10.in-addr.arpa', IN::PTR) do |transaction|
|
59
|
+
transaction.respond!(Name.create('dev.mydomain.org.'))
|
60
|
+
end
|
61
|
+
|
62
|
+
match('dev.mydomain.org', IN::MX) do |transaction|
|
63
|
+
transaction.respond!(10, Name.create('mail.mydomain.org.'))
|
64
|
+
end
|
65
|
+
|
66
|
+
match(/^test([0-9]+).mydomain.org$/, IN::A) do |transaction, match_data|
|
67
|
+
offset = match_data[1].to_i
|
68
|
+
|
69
|
+
if offset > 0 && offset < 10
|
70
|
+
logger.info "Responding with address #{'10.0.0.' + (90 + offset).to_s}..."
|
71
|
+
transaction.respond!('10.0.0.' + (90 + offset).to_s)
|
72
|
+
else
|
73
|
+
logger.info "Address out of range: #{offset}!"
|
74
|
+
false
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
# Default DNS handler
|
79
|
+
otherwise do |transaction|
|
80
|
+
logger.info 'Passing DNS request upstream...'
|
81
|
+
transaction.passthrough!(R)
|
82
|
+
end
|
83
|
+
end
|
@@ -0,0 +1,83 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
|
3
|
+
# Copyright, 2009, 2012, by Samuel G. D. Williams. <http://www.codeotaku.com>
|
4
|
+
#
|
5
|
+
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
+
# of this software and associated documentation files (the "Software"), to deal
|
7
|
+
# in the Software without restriction, including without limitation the rights
|
8
|
+
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
+
# copies of the Software, and to permit persons to whom the Software is
|
10
|
+
# furnished to do so, subject to the following conditions:
|
11
|
+
#
|
12
|
+
# The above copyright notice and this permission notice shall be included in
|
13
|
+
# all copies or substantial portions of the Software.
|
14
|
+
#
|
15
|
+
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
+
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
+
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
+
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
+
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
20
|
+
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
21
|
+
# THE SOFTWARE.
|
22
|
+
|
23
|
+
require 'rubydns'
|
24
|
+
require 'process-daemon'
|
25
|
+
|
26
|
+
# To run this command, use the standard daemon syntax as root
|
27
|
+
# ./daemon2.rb start
|
28
|
+
|
29
|
+
# You should be able to see that the server has dropped priviledges
|
30
|
+
# # ps aux | grep daemon2.rb
|
31
|
+
# daemon 16555 0.4 0.0 81392 2024 ?? S 3:35am 0:00.28 ruby ../test/daemon2.rb start
|
32
|
+
|
33
|
+
# Test using the following command
|
34
|
+
# dig @localhost test.mydomain.org
|
35
|
+
# dig +tcp @localhost test.mydomain.org
|
36
|
+
|
37
|
+
# You might need to change the user name "daemon". This can be a user name or a user id.
|
38
|
+
RUN_AS = 'daemon'
|
39
|
+
|
40
|
+
INTERFACES = [
|
41
|
+
[:udp, '0.0.0.0', 53],
|
42
|
+
[:tcp, '0.0.0.0', 53]
|
43
|
+
]
|
44
|
+
|
45
|
+
# We need to be root in order to bind to privileged port
|
46
|
+
if RExec.current_user != 'root'
|
47
|
+
$stderr.puts 'Sorry, this command needs to be run as root!'
|
48
|
+
exit 1
|
49
|
+
end
|
50
|
+
|
51
|
+
# The Daemon itself
|
52
|
+
class Server < Process::Daemon
|
53
|
+
Name = Resolv::DNS::Name
|
54
|
+
IN = Resolv::DNS::Resource::IN
|
55
|
+
|
56
|
+
# Use upstream DNS for name resolution.
|
57
|
+
UPSTREAM = RubyDNS::Resolver.new([[:udp, '8.8.8.8', 53], [:tcp, '8.8.8.8', 53]])
|
58
|
+
|
59
|
+
def startup
|
60
|
+
# Don't buffer output (for debug purposes)
|
61
|
+
$stderr.sync = true
|
62
|
+
|
63
|
+
# Start the RubyDNS server
|
64
|
+
RubyDNS.run_server(listen: INTERFACES) do
|
65
|
+
on(:start) do
|
66
|
+
RExec.change_user(RUN_AS)
|
67
|
+
end
|
68
|
+
|
69
|
+
match('test.mydomain.org', IN::A) do |transaction|
|
70
|
+
transaction.respond!('10.0.0.80')
|
71
|
+
end
|
72
|
+
|
73
|
+
# Default DNS handler
|
74
|
+
otherwise do |transaction|
|
75
|
+
logger.info "Passthrough: #{transaction}"
|
76
|
+
transaction.passthrough!(UPSTREAM)
|
77
|
+
end
|
78
|
+
end
|
79
|
+
end
|
80
|
+
end
|
81
|
+
|
82
|
+
# RExec daemon runner
|
83
|
+
Server.daemonize
|
data/examples/wikipedia-dns.rb
CHANGED
@@ -22,7 +22,6 @@
|
|
22
22
|
# THE SOFTWARE.
|
23
23
|
|
24
24
|
require 'rubydns'
|
25
|
-
require 'rubydns/extensions/string'
|
26
25
|
|
27
26
|
require 'process/daemon'
|
28
27
|
require 'process/daemon/privileges'
|
@@ -33,6 +32,8 @@ require 'json'
|
|
33
32
|
|
34
33
|
require 'digest/md5'
|
35
34
|
|
35
|
+
require 'http'
|
36
|
+
|
36
37
|
# You might need to change the user name "daemon". This can be a user name
|
37
38
|
# or a user id.
|
38
39
|
RUN_AS = 'daemon'
|
@@ -42,19 +43,6 @@ if Process::Daemon::Privileges.current_user != 'root'
|
|
42
43
|
exit 1
|
43
44
|
end
|
44
45
|
|
45
|
-
require 'http'
|
46
|
-
|
47
|
-
# Celluloid::IO fetcher to retrieve URLs.
|
48
|
-
class HttpFetcher
|
49
|
-
include Celluloid::IO
|
50
|
-
|
51
|
-
def get(url)
|
52
|
-
# Note: For SSL support specify:
|
53
|
-
# ssl_socket_class: Celluloid::IO::SSLSocket
|
54
|
-
HTTP.get(url, socket_class: Celluloid::IO::TCPSocket)
|
55
|
-
end
|
56
|
-
end
|
57
|
-
|
58
46
|
# Encapsulates the logic for fetching information from Wikipedia.
|
59
47
|
module Wikipedia
|
60
48
|
def self.summary_url(title)
|
@@ -81,9 +69,6 @@ class WikipediaDNS < Process::Daemon
|
|
81
69
|
|
82
70
|
stats = { requested: 0 }
|
83
71
|
|
84
|
-
# Use a Celluloid supervisor so the system recovers if the actor dies
|
85
|
-
fetcher = HttpFetcher.supervise
|
86
|
-
|
87
72
|
# Start the RubyDNS server
|
88
73
|
RubyDNS.run_server do
|
89
74
|
on(:start) do
|
@@ -103,7 +88,8 @@ class WikipediaDNS < Process::Daemon
|
|
103
88
|
title = match_data[1]
|
104
89
|
stats[:requested] += 1
|
105
90
|
|
106
|
-
|
91
|
+
url = Wikipedia.summary_url(title)
|
92
|
+
response = HTTP.get(url) # socket_class: ... is not yet supported.
|
107
93
|
|
108
94
|
summary =
|
109
95
|
Wikipedia.extract_summary(response).force_encoding('ASCII-8BIT')
|
data/lib/rubydns.rb
CHANGED
@@ -18,33 +18,19 @@
|
|
18
18
|
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
19
19
|
# THE SOFTWARE.
|
20
20
|
|
21
|
-
|
21
|
+
require 'async/dns'
|
22
22
|
|
23
|
-
require_relative 'rubydns/
|
24
|
-
require_relative 'rubydns/
|
25
|
-
require_relative 'rubydns/resolver'
|
26
|
-
require_relative 'rubydns/handler'
|
27
|
-
require_relative 'rubydns/logger'
|
23
|
+
require_relative 'rubydns/version'
|
24
|
+
require_relative 'rubydns/rule_based_server'
|
28
25
|
|
29
26
|
module RubyDNS
|
27
|
+
# Backwards compatibility:
|
28
|
+
Resolver = Async::DNS::Resolver
|
29
|
+
|
30
30
|
# Run a server with the given rules.
|
31
|
-
def self.run_server (
|
32
|
-
|
33
|
-
|
34
|
-
supervisor = server_class.supervise(options, &block)
|
31
|
+
def self.run_server (server_class: RuleBasedServer, **options, &block)
|
32
|
+
server = server_class.new(**options, &block)
|
35
33
|
|
36
|
-
|
37
|
-
if options[:asynchronous]
|
38
|
-
return supervisor
|
39
|
-
else
|
40
|
-
read, write = IO.pipe
|
41
|
-
|
42
|
-
trap(:INT) {
|
43
|
-
write.puts
|
44
|
-
}
|
45
|
-
|
46
|
-
IO.select([read])
|
47
|
-
supervisor.terminate
|
48
|
-
end
|
34
|
+
server.run
|
49
35
|
end
|
50
36
|
end
|
@@ -18,166 +18,11 @@
|
|
18
18
|
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
19
19
|
# THE SOFTWARE.
|
20
20
|
|
21
|
-
require '
|
22
|
-
|
23
|
-
require_relative 'transaction'
|
24
|
-
require_relative 'logger'
|
21
|
+
require 'async/dns/server'
|
25
22
|
|
26
23
|
module RubyDNS
|
27
|
-
class UDPSocketWrapper < Celluloid::IO::UDPSocket
|
28
|
-
def initialize(socket)
|
29
|
-
@socket = socket
|
30
|
-
end
|
31
|
-
end
|
32
|
-
|
33
|
-
class TCPServerWrapper < Celluloid::IO::TCPServer
|
34
|
-
def initialize(server)
|
35
|
-
@server = server
|
36
|
-
end
|
37
|
-
end
|
38
|
-
|
39
|
-
class Server
|
40
|
-
include Celluloid::IO
|
41
|
-
|
42
|
-
finalizer :shutdown
|
43
|
-
|
44
|
-
# The default server interfaces
|
45
|
-
DEFAULT_INTERFACES = [[:udp, "0.0.0.0", 53], [:tcp, "0.0.0.0", 53]]
|
46
|
-
|
47
|
-
# Instantiate a server with a block
|
48
|
-
#
|
49
|
-
# server = Server.new do
|
50
|
-
# match(/server.mydomain.com/, IN::A) do |transaction|
|
51
|
-
# transaction.respond!("1.2.3.4")
|
52
|
-
# end
|
53
|
-
# end
|
54
|
-
#
|
55
|
-
def initialize(options = {})
|
56
|
-
@handlers = []
|
57
|
-
|
58
|
-
@logger = options[:logger] || Celluloid.logger
|
59
|
-
@interfaces = options[:listen] || DEFAULT_INTERFACES
|
60
|
-
|
61
|
-
@origin = options[:origin] || '.'
|
62
|
-
end
|
63
|
-
|
64
|
-
# Records are relative to this origin:
|
65
|
-
attr_accessor :origin
|
66
|
-
|
67
|
-
attr_accessor :logger
|
68
|
-
|
69
|
-
# Fire the named event as part of running the server.
|
70
|
-
def fire(event_name)
|
71
|
-
end
|
72
|
-
|
73
|
-
def shutdown
|
74
|
-
fire(:stop)
|
75
|
-
end
|
76
|
-
|
77
|
-
# Give a name and a record type, try to match a rule and use it for processing the given arguments.
|
78
|
-
def process(name, resource_class, transaction)
|
79
|
-
raise NotImplementedError.new
|
80
|
-
end
|
81
|
-
|
82
|
-
# Process an incoming DNS message. Returns a serialized message to be sent back to the client.
|
83
|
-
def process_query(query, options = {}, &block)
|
84
|
-
start_time = Time.now
|
85
|
-
|
86
|
-
# Setup response
|
87
|
-
response = Resolv::DNS::Message::new(query.id)
|
88
|
-
response.qr = 1 # 0 = Query, 1 = Response
|
89
|
-
response.opcode = query.opcode # Type of Query; copy from query
|
90
|
-
response.aa = 1 # Is this an authoritative response: 0 = No, 1 = Yes
|
91
|
-
response.rd = query.rd # Is Recursion Desired, copied from query
|
92
|
-
response.ra = 0 # Does name server support recursion: 0 = No, 1 = Yes
|
93
|
-
response.rcode = 0 # Response code: 0 = No errors
|
94
|
-
|
95
|
-
transaction = nil
|
96
|
-
|
97
|
-
begin
|
98
|
-
query.question.each do |question, resource_class|
|
99
|
-
begin
|
100
|
-
question = question.without_origin(@origin)
|
101
|
-
|
102
|
-
@logger.debug {"<#{query.id}> Processing question #{question} #{resource_class}..."}
|
103
|
-
|
104
|
-
transaction = Transaction.new(self, query, question, resource_class, response, options)
|
105
|
-
|
106
|
-
transaction.process
|
107
|
-
rescue Resolv::DNS::OriginError
|
108
|
-
# This is triggered if the question is not part of the specified @origin:
|
109
|
-
@logger.debug {"<#{query.id}> Skipping question #{question} #{resource_class} because #{$!}"}
|
110
|
-
end
|
111
|
-
end
|
112
|
-
rescue Celluloid::ResumableError
|
113
|
-
raise
|
114
|
-
rescue StandardError => error
|
115
|
-
@logger.error "<#{query.id}> Exception thrown while processing #{transaction}!"
|
116
|
-
RubyDNS.log_exception(@logger, error)
|
117
|
-
|
118
|
-
response.rcode = Resolv::DNS::RCode::ServFail
|
119
|
-
end
|
120
|
-
|
121
|
-
end_time = Time.now
|
122
|
-
@logger.debug {"<#{query.id}> Time to process request: #{end_time - start_time}s"}
|
123
|
-
|
124
|
-
return response
|
125
|
-
end
|
126
|
-
|
127
|
-
#
|
128
|
-
# By default the server runs on port 53, both TCP and UDP, which is usually a priviledged port and requires root access to bind. You can change this by specifying `options[:listen]` which should contain an array of `[protocol, interface address, port]` specifications.
|
129
|
-
#
|
130
|
-
# INTERFACES = [[:udp, "0.0.0.0", 5300]]
|
131
|
-
# RubyDNS::run_server(:listen => INTERFACES) do
|
132
|
-
# ...
|
133
|
-
# end
|
134
|
-
#
|
135
|
-
# You can specify already connected sockets if need be:
|
136
|
-
#
|
137
|
-
# socket = UDPSocket.new; socket.bind("0.0.0.0", 53)
|
138
|
-
# Process::Sys.setuid(server_uid)
|
139
|
-
# INTERFACES = [socket]
|
140
|
-
#
|
141
|
-
def run
|
142
|
-
@logger.info "Starting RubyDNS server (v#{RubyDNS::VERSION})..."
|
143
|
-
|
144
|
-
fire(:setup)
|
145
|
-
|
146
|
-
# Setup server sockets
|
147
|
-
@interfaces.each do |spec|
|
148
|
-
if spec.is_a?(BasicSocket)
|
149
|
-
spec.do_not_reverse_lookup
|
150
|
-
protocol = spec.getsockopt(Socket::SOL_SOCKET, Socket::SO_TYPE).unpack("i")[0]
|
151
|
-
ip = spec.local_address.ip_address
|
152
|
-
port = spec.local_address.ip_port
|
153
|
-
|
154
|
-
case protocol
|
155
|
-
when Socket::SOCK_DGRAM
|
156
|
-
@logger.info "<> Attaching to pre-existing UDP socket #{ip}:#{port}"
|
157
|
-
link UDPSocketHandler.new(self, UDPSocketWrapper.new(spec))
|
158
|
-
when Socket::SOCK_STREAM
|
159
|
-
@logger.info "<> Attaching to pre-existing TCP socket #{ip}:#{port}"
|
160
|
-
link TCPSocketHandler.new(self, TCPServerWrapper.new(spec))
|
161
|
-
else
|
162
|
-
raise ArgumentError.new("Unknown socket protocol: #{protocol}")
|
163
|
-
end
|
164
|
-
elsif spec[0] == :udp
|
165
|
-
@logger.info "<> Listening on #{spec.join(':')}"
|
166
|
-
link UDPHandler.new(self, spec[1], spec[2])
|
167
|
-
elsif spec[0] == :tcp
|
168
|
-
@logger.info "<> Listening on #{spec.join(':')}"
|
169
|
-
link TCPHandler.new(self, spec[1], spec[2])
|
170
|
-
else
|
171
|
-
raise ArgumentError.new("Invalid connection specification: #{spec.inspect}")
|
172
|
-
end
|
173
|
-
end
|
174
|
-
|
175
|
-
fire(:start)
|
176
|
-
end
|
177
|
-
end
|
178
|
-
|
179
24
|
# Provides the core of the RubyDNS domain-specific language (DSL). It contains a list of rules which are used to match against incoming DNS questions. These rules are used to generate responses which are either DNS resource records or failures.
|
180
|
-
class RuleBasedServer < Server
|
25
|
+
class RuleBasedServer < Async::DNS::Server
|
181
26
|
# Represents a single rule in the server.
|
182
27
|
class Rule
|
183
28
|
def initialize(pattern, callback)
|
@@ -247,9 +92,6 @@ module RubyDNS
|
|
247
92
|
end
|
248
93
|
end
|
249
94
|
|
250
|
-
# Don't wrap the block going into initialize.
|
251
|
-
execute_block_on_receiver :initialize
|
252
|
-
|
253
95
|
# Instantiate a server with a block
|
254
96
|
#
|
255
97
|
# server = Server.new do
|
data/lib/rubydns/version.rb
CHANGED