1 # dyn-nsupdate: Self-made DynDNS
5 Welcome to [dyn-nsupdate](https://www.ralfj.de/projects/dyn-nsupdate),
6 a collection of tools using
7 [BIND](https://www.isc.org/downloads/bind/),
8 [CGI](https://en.wikipedia.org/wiki/Common_Gateway_Interface) and
9 [Python](https://www.python.org/) to provide DynDNS services with your
10 own nameserver. Both IPv4 and IPv6 are fully supported.
12 dyn-nsupdate consists of two pieces: The server part provides a way to update IP
13 addresses in Bind's DNS zones via CGI, in a safe manner. The client part uses CGI
14 to update some domain to the current address(es) of the machine it is running
15 on. Alternatively, some routers can be configured to do this themselves. The
16 FritzBox is known to be supported.
20 In the following, replace `dyn.example.com` by whatever domain will be managed
21 through DynDNS. I assume that BIND has already been set up for
22 `dyn.example.com` as a dynamic zone that can be updated through `nsupdate
23 -l`. This can be achieved by setting `update-policy local;` in the zone
24 configuration. Furthermore, I assume the directory `/var/lib/bind/` exists.
26 There are two pieces that have to be installed: A setuid wrapper which checks
27 the passwords, and applies the updates; and some CGI scripts offered through a
28 webserver. Please read this guide carefully and make sure you understand the
29 security implications of what you are doing. setuid wrappers are not toys!
31 Let's first set up the setuid wrapper. To compile it, you will need cmake and
32 boost, including the regex and program_options boost packages. Starting in the
33 source directory, run::
39 cmake .. -DCMAKE_BUILD_TYPE=Release -DDYNNSUPDATE_CONFIG_FILE=$DIR/dyn-nsupdate.conf
42 This should compile the binary `dyn-nsupdate`. Notice that the path to the
43 configuration file will be hard-coded into the binary. If it were run-time
44 configurable, then a user could call the script with her own configuration file,
45 gaining access to all domains BIND lets you configure. If you want to put the
46 files in another directory, change the configuration file name accordingly. Make
47 sure the file (and all of the directories it is in) can *not be written by
48 non-root*. The setuid wrapper trusts that file. You can now install it and the
49 sample configuration file, and set their permissions::
51 sudo install dyn-nsupdate $DIR/dyn-nsupdate -o bind -g bind -m +rx,u+ws
52 sudo install ../../dyn-nsupdate.conf.dist $DIR/dyn-nsupdate.conf -o bind -g bind -m u+rw
54 Finally, edit the config file. The format should be pretty self-explanatory. In
55 particular, **change the password**!
57 Now, let's go on with the CGI scripts. They are using Python 2, so make sure you
58 have that installed. There are two scripts: One is used for clients to detect
59 their current external IP address, and one is used to do the actual update of
60 the domain. The first script is used by the "web" IP detection method (see
61 client configuration below). It should be available on a domain that is
62 available only through a single protocol, i.e., IPv4 only or IPv6 only. This is
63 required to reliably detect the current address of the given protocol. If you
64 want to support both IPv4 and IPv6, I suggest you have three domains
65 `ipv4.ns.example.com`, `ipv6.ns.example.com` and `ns.example.com` where
66 only the latter is available via both protocols (this is something you have to
67 configure in your `example.com` DNS zone). All can serve the same scripts
68 (e.g. via a `ServerAlias` in the apache configuration). I also **strongly
69 suggest** you make these domains *HTTPS-only*, as the client script will send a
72 Choose some directory (e.g., `/srv/ns.example.com`) for the new domain, and
73 copy the content of `server-scripts` there. Now configure your webserver
74 appropriately for CGI scripts to be executed there. You can find a sample
75 configuration for apache in `apache-ns.example.com.conf`. If you used a
76 non-default location for the `dyn-nsupdate` wrapper, you have to change the
77 path in the `update` CGI script accordingly.
79 That's it! Your server is now configured. You can use `curl` to test your
82 DOMAIN=test.dyn.example.com
83 PW=some_secure_password
84 curl 'https://ns.example.com/update?domain=$DOMAIN&password=$PW&ip=127.0.0.1'
87 ## Client setup (using the script)
89 You can find the client script at `client-scripts/dyn-ns-client`. It requires
90 Python 3. Copy that script to the machine that should be available under the
91 dynamic domain. Also copy the sample configuration file
92 `dyn-ns-client.conf.dist` to `$HOME/.config/dyn-nsupdate/dyn-ns-client.conf`.
93 You can choose another name, but then you will have to tell the script about it.
94 Call `dyn-ns-client --help` for this and other options the script accepts. An
95 important aspect of configuration is how to detect the current addresses of the
96 machine the script is running on. For IPv4, this can only be "web", which can
97 deal with NAT. For IPv6, the script can alternatively attempt to detect the
98 correct local address to use. The sample file contains comments that should
101 Note that the script can update a list of domain names, in case you need the
102 machine to have several names. It is preferable to use a CNAME instead, this
103 will reduce the number of updates performed in the zone.
105 To run the script regularly, simply set up a cronjob. You can do so by running
106 `crontab -e`, and add a line as follows::
108 */15 * * * * /home/user/dyn-ns-client
110 This sets the update interval to 15min. If your IP address changes daily, you
111 may want to reduce this to 5min to have a smaller timeframe during which your
112 server is not available.
114 If you want to be emailed about changes in your IP address, pass `-v` as
115 argument. The script will then only produce output if it has to update the DNS
118 ## Client setup (using a router)
120 Some routers are able to perform the update of the domain names themselves. The
121 FritzBox is known to be supported. To configure it to tell your server about the
122 current IP address, go to the DynDNS configuration section of the FritzBox and
123 choose the "custom" DynDNS provider. Then enter the following settings:
125 - Update-URL: `https://ns.example.com/update?domain=<domain>&password=<pass>&ip=<ipaddr>`
126 - Domain Name: `test.dyn.example.com`
127 - User Name: `just_something`
128 - Password: `some_secure_password`
130 Note that the user name is ignored.
136 You can find the sources in the
137 [git repository](http://www.ralfj.de/git/dyn-nsupdate.git) (also
138 available [on GitHub](https://github.com/RalfJung/dyn-nsupdate). They
140 [2-clause BSD license](http://opensource.org/licenses/bsd-license.php). See
141 the file `LICENSE-BSD` for more details.
145 If you found a bug, or want to leave a comment, please
146 [send me a mail](mailto:post-AT-ralfj-DOT-de). All sorts of feedback are