Giter Site home page Giter Site logo

fxbox / dns-server Goto Github PK

View Code? Open in Web Editor NEW
4.0 4.0 2.0 33 KB

Server that helps the Box to announce its local IP address without relying on mDNS, and to register its LetsEncrypt cert for use on its local IP address.

JavaScript 26.85% Shell 73.15%

dns-server's People

Contributors

fabricedesre avatar ferjm avatar michielbdejong avatar samgiles avatar

Stargazers

 avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar

dns-server's Issues

Store logs on the server

Yesterday, the E2E test started to fail for no obvious reasons. Locally, I noticed that sometimes 2 boxes are visible from http://fxbox.github.io/app/ . I'm suspecting Travis to share the same internal IP address on many VMs.

I got the live logs on the knilxof (ssh login then pm2 logs $APP_NAME - thanks @samgiles ๐Ÿ˜ƒ) machine, but I couldn't find if the logs are already stored on the hard drive. If not, that's something we could improve. What do you think @michielbdejong @samgiles ?

cc @isabelrios @npark-mozilla

Check client cert

As we will be generating TLS certs on the Box anyway, authentication via TLS client certs seems like an appropriate option. This server should be configured with the root cert to trust, and the Box should have a signing certificate signed with that same root cert, and a TLS certificate signed with the Box's own signing certificate.

Additionally, the Box should only be allowed to set records under /v1/dns/org/knilxof/<hash>, where <hash> is the first 32 hex chars of the sha256 of its signing cert.

Support ip-ip-ip-ip scheme

Maybe have a special API end-point that sets all subdomains of format ip-ip-ip-ip at once.

Although at this point I don't see a reason why we need this, the Box can just explicitly set each record it needs.

Cannot run on high port

When changing DNS_PORT from 53 to 5353 in both src/server.js and src/client.js. the tests start failing. Have to figure out whether this is a server- or a client-problem.

Add client

By way of documentation, it would be good to add an API client to this repo, with some documented examples of how to set the server up and use it from that example client.

Find a way to make client cert auth use the actual LetsEncrypt

Looking back at how we made this work, it seems that the client creates a self-signed cert whose hash determines its URL under .box.knilxof.org, but then it serves the LetsEncrypt cert, which will have a different hash altogether. It would be better if we use the hash of the actual LetsEncrypt cert, but the client already needs to edit DNS when only a csr exists, so not sure if/how we can extract the public key hash from the csr. Will have a look at which files letsencrypt.sh produces.

Return CNAMEs in response to A queries

Follow-up to #8:

For CNAMEs to work, you should return them not only in response to 'CNAME'-queries, but also include them in all responses to all query types, for instance like this:

Michiels-Laptop:~ Michiel$ dig A www.michielbdejong.com @meera.ns.cloudflare.com
[...]
;; ANSWER SECTION:
www.michielbdejong.com. 191 IN  CNAME   michielbdejong.com.
michielbdejong.com. 191 IN  A   104.27.176.52
michielbdejong.com. 191 IN  A   104.27.177.52

Michiels-Laptop:~ Michiel$ dig NS www.michielbdejong.com @meera.ns.cloudflare.com
[...]
;; ANSWER SECTION:
www.michielbdejong.com. 296 IN  CNAME   michielbdejong.com.
michielbdejong.com. 86400   IN  NS  meera.ns.cloudflare.com.
michielbdejong.com. 86400   IN  NS  beau.ns.cloudflare.com.

Michiels-Laptop:~ Michiel$ dig www.michielbdejong.com @meera.ns.cloudflare.com
[...]
;; ANSWER SECTION:
www.michielbdejong.com. 300 IN  CNAME   michielbdejong.com.
michielbdejong.com. 300 IN  A   104.27.177.52
michielbdejong.com. 300 IN  A   104.27.176.52

Local IP addresses stripped from DNS response by some home routers

The names created in this server fail to resolve with the DNS server supplied in the DHCPACK from the BT Home Hub 5:

Succesful resolution bypassing the DHCP supplied DNS server

$ nslookup local.006c824eb59a3422e543d708d2d0a2e576f896b4.box.knilxof.org 8.8.8.8
Server:     8.8.8.8
Address:    8.8.8.8#53

Non-authoritative answer:
Name:   local.006c824eb59a3422e543d708d2d0a2e576f896b4.box.knilxof.org
Address: 192.168.1.67

Fails using the DNS server response from the router configured via DHCP:

.$ nslookup local.006c824eb59a3422e543d708d2d0a2e576f896b4.box.knilxof.org
Server:     192.168.1.254
Address:    192.168.1.254#53

Non-authoritative answer:
*** Can't find local.006c824eb59a3422e543d708d2d0a2e576f896b4.box.knilxof.org: No answer

Routers known to prevent DNS rebinding attacks by stripping local IPs rom responses:

  • BT Home Hub 5

Initial exploration

There is a lot of room for improvement here (e.g. use a rest API instead of the scp command to upload the challenge string, and the native-dns package is currently inbetween maintainers), but I got the following working on my machine:

./letsencrypt.sh --cron --domain my-link-box.knilxof.org --challenge dns-01 --hook ./deploy-challenges.sh
  • deploy-challenges.sh contains:
echo deploying challenge
echo $4 > ./tmp.txt
scp tmp.txt [email protected]:/root/dns-server/challenge.txt
  • my-link-box.knilxof.org DNS is served by ns.knilxof.org
  • On ns.knilxof.org, run something like:
var fs = require('fs'),
  dns = require('native-dns'),
  server = dns.createServer();

server.on('request', function (request, response) {
  //console.log(request) 
  response.answer.push(dns.A({
    name: request.question[0].name,
    address: '127.0.0.1',
    ttl: 600,
  }));
  response.answer.push(dns.TXT({
    name: request.question[0].name,
    data: [fs.readFileSync('./challenge.txt').toString().trim()],
    ttl: 600,
  }));
  response.send();
});

server.on('error', function (err, buff, req, res) {
  console.log(err.stack);
});

server.serve(53);

Productify this

  • add more tests
  • make it robust across reboots (currently data is only stored in memory)
  • make it possible to run multi-threaded, or even multi-server
  • consider using Bind for answering the DNS queries, and only leave the part of this nodejs script for the API, to make database edits in Bind's database backend.

Support CNAME

For query type 'A', if a 'CNAME' record exists, it should be returned (including the resolving A record?) in the answer section, even though the query type didn't match.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.