This is an SDB back-end to the venerable BIND name server. It implements an interface to the CouchDB database, which is a distributed, schema-free document database.
Because it's cool. Because CouchDB replicates over port 80, whereas zone transfers (AXFR) use port 53. Because CouchDB is proxyable. Because it is fast enough for moderate use. And mainly, because I felt like doing it ever since I created a proof of concept using a pipe back-end to PowerDNS.
Yes, it does. A bit. Speed isn't bad at all. Due to limitations of the Bind SDB back-end, couch-sdb
cannot possibly be faster than .
The CouchDB portion doesn't use a view in any way. It's either the document for the zone is there, or it ain't. My first version queried a view to find the requested domain name, but I was getting an unecessary number of hits on the database per query, so I scrapped that.
Data in a CouchDB is JSON. If you didn't know that, you shouldn't be here. A zone is one document. (Look at zone.json while we speak.)
- The document's
_id
is the zone name. - If a
serial
value exists in thesoa
object, it must be an integer, which is used as the SOA serial. If it doesn't exist, the first integer value of the document's_rev
is used; now that is way cool! -- auto-incrementing serial! mname
andrname
are used, else hard-coded values.ns
is an array of name servers. Names, of course; not addresses!default_ttl
is just that; it is used for the NS RR and for records that don't have their own TTL.rr
is an array of RR objects. Each of these have:- A domain
name
, which must be unqualified. (I.e. usewww
only.) Use@
for the zone apex. - A
type
. Upper or lower case. data
is the rdata for the domain. It is either a single value or an array of similar values, in which case an RRset is built.- An optional
ttl
for this RRset.
- A domain
Yep, we do that too. The couch_allnodes
() function does that with a view walker (sorry, this is loose terminology of CDBC). It uses a view called axfr
in the dns
couchapp in the same database. The view does the hard work of producing the resource records to be included in the zone transfer.
-
Read my chapter on Bind's SDB! :)
-
Patch
bin/named/Makefile.in
withDBDRIVER_OBJS = couch-sdb.o DBDRIVER_SRCS = couch-sdb.c DBDRIVER_INCLUDES = DBDRIVER_LIBS = -lcdbc -lcurl -ljansson
-
Fix
bin/named/main.c
as per my book. -
./configure && make
-
Create a minimal
named.conf
containing something like this:controls { }; options { directory "/tmp"; listen-on port 9953 { 127.0.0.1; }; listen-on-v6 {none;}; allow-query {any;}; }; zone "example.org" { type master; database "couch http://couch-server.com:5984 dns"; ^ ^ ^^^ | | | | | + dbname | +---------------------- URL +---------------------------------- keyword allow-transfer { 127.0.0.1; }; };
-
Launch
named
in foreground./named -4 -n 1 -d 1 -g -c jp.conf
-
Query it
dig -p 9953 @127.0.0.1 www.example.org