okTurtles / dnschain

A blockchain-based DNS + HTTP server that fixes HTTPS security, and more!
https://okturtles.com
Other
1.73k stars 169 forks source link

Enable CORS headers for HTTP API #162

Closed bumi closed 9 years ago

bumi commented 9 years ago

Setting the Cross-Origin Resource Sharing (CORS) headers in a global express middleware. This allows pure client side JS applications to retrieve data from the public REST API. (api.dnschain.net)

Please note that I am very new to the DNSchain code, looking forward to your feedback :)

taoeffect commented 9 years ago

Hmm, we'd be OK doing this if we were monetizing that API. And while we might consider doing that (as donations to the foundation), at the moment that's low on our priority list.

Also, we should not be making this call for everyone who uses DNSChain. This would be acceptable if it were implemented as an option tied to a variable in the config file (and disabled by default).

taoeffect commented 9 years ago

Also, it's not clear that it makes sense to implement at all.

DNSChain should not be contacted via pure client side JS (i.e. that's served in a webpage).

That would defeat the purpose of our security model since the call would be authenticated using X.509, and the point of DNSChain is to replace X.509. :P

Calls to DNSChain should be made from a native app or from a browser extension, both of which don't need CORS.

taoeffect commented 9 years ago

Closing for now unless there's a compelling reason not to. Sorry for having misunderstood your question on Twitter!

bumi commented 9 years ago

thanks for your feedback! What do you mean with monetizing the API?

As far as I understand the API it exposes an HTTP interface to entries stored in namecoin/etc. I don't really see a difference between "native" and pure browser based clients. So far I am not aware of any security issues enabling CORS for publicly available read-only HTTP APIs. We could limit the available only to GET requests - are there any non GET endpoints?

also related: https://fetch.spec.whatwg.org/#basic-safe-cors-protocol-setup

As background information: I was working on a contacts/social network application that stores contact references in remotestorage and collects profile information from namecoin. A read-only version similar to onename.io. This would be super simple with the DNSchain API.

Thanks again!

taoeffect commented 9 years ago

What do you mean with monetizing the API?

My understanding is that CORS will allow the API to be accessible from arbitrary website JavaScript. Doing so could put a heavy load on our server. We would not want to pay for all of that bandwidth, and so if were to monetize the API, that would discourage the use of our DNSChain server and encourage the installation of other DNSChain servers.

As far as I understand the API it exposes an HTTP interface to entries stored in namecoin/etc.

Yes.

I don't really see a difference between "native" and pure browser based clients. So far I am not aware of any security issues enabling CORS for publicly available read-only HTTP APIs.

This entire project is about creating an alternative to X.509 (used by HTTPS to authenticate connections). JS in web pages is authenticated over X.509 (currently), so using a system that we deem to be insecure, to access its more secure replacement, just doesn't make sense.

See the video on the homepage for details.

As background information: I was working on a contacts/social network application that stores contact references in remotestorage and collects profile information from namecoin. A read-only version similar to onename.io. This would be super simple with the DNSchain API.

Well, there are two possibilities:

  1. Re-implement your PR as an optional feature that's enabled via the config file (ideally outputting a warning in the log if it's enabled, mentioning that using DNSChain from a webpage JS relies on X.509 and therefore does not have the security properties of Namecoin).
  2. Just use your fork of DNSChain to run your own CORS based API.
SGrondin commented 9 years ago

I disagree with @taoeffect

I think that it's not up to us to force our point of view onto users in how DNSChain should be used.

I think there's a perfectly valid reason to expose it to browsers. Organizations might want to have a local DNSChain that is not accessible from the Internet, for example, to use in their intranet.

If you're worried about load, adjust the rate limiter settings, that's why they're there!

In my opinion, the more accessible DNSChain is, the more people will engage with it and the more the project will grow, gaining traction and developers in the process. We have no idea of how many valid and creative ways to use DNSChain there is out there, so let's not kill those innovations before they can be created. We should be making it easier to use it, not harder.

taoeffect commented 9 years ago

@SGrondin wrote:

I think that it's not up to us to force our point of view onto how DNSChain should be used.

Do you feel that in my asking that CORS be implemented as an optional feature we are "forcing" our POV on anything?

Or are you saying the answer is to "force" CORS on the project and thereby undermine its security model for everyone?

If you're worried about load, adjust the rate limiting settings, that's why they're there!

Fair point. I forgot about that. That doesn't mean I have to enable CORS on my DNSChain server.

In my opinion, the more accessible DNSChain is, the more people will engage with it and the more the project will grow, gaining traction and developers in the process. We should be making it easier, not harder to use it.

Sure, but I will not accept a PR that, in its current state, totally undermines the point of the project.

Implement it as an option (as I mentioned), and that should satisfy everyone's preferences, and it would grow the project as well.

SGrondin commented 9 years ago

Good points. Let's just make it optional. A boolean in the config should do it. Best of both worlds.

bumi commented 9 years ago

OK cool, I will add a config flag to optionally enable CORS.

If you are interested I could look into rate-limiting. There are some tools that could be used: express-limiter or pacer. But because these are only express middlewares anyway we could simly describe a standard way on how add some middlewares to the stack. This would make it very configurable for anybody running DNSchain. (that would also include the CORS middleware)

A quick question to better understand what is important/welcome: you say it is undermining the point of the project because the JS app is delivered from a server to the users's browser authenticated using HTTPS but respecting the browser's root certs and can not be trusted. In a non browser environment you have more control - for example also if you use some python/ruby/whatever script. Sorry, for this beginner question. thanks for the feedback!

SGrondin commented 9 years ago

There's already rate limiting in place, I was saying if he's worried about load then he can use the features in place to reduce it.

I'll let @taoeffect explain the security model

taoeffect commented 9 years ago

There's already rate limiting in place, I was saying if he's worried about load then he can use the features in place to reduce it.

Yeah, we use @SGrondin's awesome bottleneck for it. :smile:

A quick question to better understand what is important/welcome: you say it is undermining the point of the project because the JS app is delivered from a server to the users's browser authenticated using HTTPS but respecting the browser's root certs and can not be trusted. In a non browser environment you have more control - for example also if you use some python/ruby/whatever script. Sorry, for this beginner question. thanks for the feedback!

Well, in both a non-browser environment, and in a browser environment (but in the context of a browser extension only), you can ignore the root certs (and all their intermediates) for authentication and only trust the DNSChain server (if you have reason to trust it), which in turn will relay info from a blockchain.

The video on the homepage should make this clear. And our research efforts are now focused on exploring thin client protocols because they reduce the amount of trust you need to place in any one entity (include a DNSChain server, which could become compromised). Proof of Transition (explained in that post), for example, would detect if an honest DNSChain server became dishonest.

bumi commented 9 years ago

sorry for my late reply. I've made a new PR #166 and made CORS configurable and disabled by default.