10 ms·
Launching NginScript
- tootie 11y agoI've recently been leaning towards not using web servers like nginx or apache at all. There are non-blocking server platforms like node.js or vert.x that let you code your web server instead of configure it. I find that ou frequently hit a wall of opaque redirect rules that become unmaintainable for any complex project. Having your server written in testable code makes it more predictable. It looks like nginx is trying to meet in the middle.
- wasd 11y agoI'm not sure if this is great idea. Use of reverse proxies has lots of benefits. You can manage load balancing, SSL Termination, serving static content (much faster), caching, compression, centralized logging, and using different applications on the same ur space (foo.com/app1, foo.com/app2). They also have the added benefit of another layer of security (look for and prevent various HTTP exploits and prevent them from getting to the web server). I'm not saying you can't do this in node but nginx/apache are really good at what they do. EDIT: I've read through your comments and you seem like a pretty experienced developer. I don't think any of the information in my comment should be news to you so I'm curious to hear more about why you feel this way.
- happytrails 11y agoEven gods make mistakes
- ajacksified 11y agoTo play devil's advocate (not that OP is an devil), you want a CDN serving up static assets anyway, and maybe take care of SSL termination and security depending on your sensitivity needs; haproxy is great for load balancing and centralized logging; vulcand to handle reverse-proxying; and at that point, all you're left with is compression, which a reasonable web server should be able handle. Now you've got a suite of specialized tools that will do their jobs well, and you probably have most of them in your stack anyway. Granted, it's more complexity, but nginx certainly isn't the must-have that it used to be.
- polpo 11y agoHAProxy can do the SSL termination, reverse proxying, and compression jobs quite well by itself. Though vulcand's etcd-based runtime configuration looks friendlier than HAProxy's.
- sixdimensional 11y agoI don't know about the OP's reasons, but one of mine lately has simply been dependency management and simplicity of deployment. It's just handy to be able to package it all together, especially for packaged software where deploying another component would be more configuration. I suppose this is why docker containers (or in the past, virtual appliances/VMs) have become so much more popular. The good embeddable web servers are usually pretty lightweight, scalable and can be programmatically configured. Things like Jetty are popular, but look at languages like Go that have HTTP serving built in via libraries and scale nicely via coroutines. Vert.x etc. are cool for performance reasons, being lightweight and usually much less thread hungry (using async operations, sometimes in many less threads). That said, I do agree that reverse proxies are still really useful for all the reasons you mentioned. Reverse proxies on top of some of these high performing embedded HTTP serving engines is a good practice, when you need it. And there is no need to throw out the tried and true engines, like Apache, Nginx, etc. Just depends on the use case and needs I suppose.
- kyledrake 11y agoI use nginx at Neocities to serve all our static sites, and as a proxy for our front site. I like nginx, but it has way too much of a sacred cow treatment by the dev community. It has plenty of problems, the configuration is a psuedo-language that doesn't always make the right choices and is difficult to heavily customize, and I've gotten to it be -very- unstable under certain circumstances, including really bread-and-butter things like SSL caching. If there's a bug, you'll have a good old time debugging it's massive collection of C code. It's great, but it's not perfect. Making nginx do custom things that you'll probably need to do in a serious environment (example: dynamically programmable SSL SNI) requires craxy mods and hacks that have only recently been made available (by third parties) and heavily reduce nginx's performance. Further, they only provide purgable proxy caching via their commercial version, which costs an exorbitant amount of money. The free purger, naturally, makes nginx lock up. I wouldn't mind chipping in a bit for nginx because I want to support their team any way, but at their current prices ($100/node/month or something like that) we simply can't afford it. I realize this is not a popular opinion right now, but node.js is completely up to the task of running a reverse http proxy. They are basically (you likely won't notice the difference unless you're running the New York Times) competitive with nginx for performance, and as a tradeoff for an unnoticable slowdown you get a full, turing complete programming language to completely control the flow of your data. Nginx under the hood is just a reactor pattern with children that share a socket. Node.js has a cluster module that uses the exact same strategy. Mind you this is from someone that has done talks critical of reactor pattern scaling. Also, if you have blocking I/O apps, it doesn't matter what you configure nginx to do, it's still going to lock up when someone DDoSes it with slow loris connections. Make your ruby app thread safe and use Rainbows! instead of Unicorn, or you're going to have a bad time.
- bhouston 11y agoSo when are you going to release "node-ginx"? :)
- kyledrake 11y agoYou're on to me. ;) There is node-http-proxy available (https://github.com/nodejitsu/node-http-proxy https://github.com/nodejitsu/node-http-proxy), which also has some plugins available to do some of the advanced features nginx supports. I'll likely be writing a custom proxy server tailored to our needs such that it probably won't be useful as a general purpose proxy server, but if you're looking for something, that's a start. Making it more general purpose unfortunately would require more work, and I'm pretty time stretched right now. I'm not saying it's better than nginx, of course. I'm just saying that if you need to do some crazy programming that can't be done with nginx, you're free to use something else. Don't be fearful of treading your own path, just make sure you know well how HTTP works before doing it. Here's a stupid example I whipped up quickly for a reverse proxy for our IPFS nodes that demonstrates how quickly you can put together a custom reverse proxy to do something weird: https://github.com/neocities/hshca-proxy/blob/master/app.js https://github.com/neocities/hshca-proxy/blob/master/app.js. That flaming piece of junk hasn't crashed once since I deployed it.
- RyanZAG 11y ago> load balancing You'd rather use a dedicated load balancer like Route53 or haproxy. Don't think choosing Apache or Nginx is the right option for those really. Plus something like vert.x is very usable as a load balancer already. >SSL Termination Just about everything handles this already. Current best practice is to use SSL for all communication between your own servers anyway, so there's no gain. If you SSL terminate on your load balancer, these days you want to use a new SSL connection between your load balancer and application server anyway if possible. > serving static content, caching, compression New app servers like vert.x support Linux sendfile and handle very well for serving static content etc. Currently, nearly everyone uses Cloudflare to handle all of this anyway. No real reason to duplicate it if Cloudflare is set to handle it. > centralized logging Centralized logging is usually done by sending all of your logs off from each service/server to be aggregated on a dedicated box running Logstash or whatever. You don't use your reverse proxy for this? >using different applications on the same ur space From using the web, I don't think this is done anymore. In fact it seems to be the opposite - foo1.app.com, foo2.app.com seems to be the trend. Basically the opposite of multiple apps on 1 domain because of the big move towards microservices. Extra domains are the cheapest thing there is. > added benefit of another layer of security Security doesn't work that way in my experience. It's more about minimizing attack surface. If you use node and nginx and apache then any exploit that hits any of those 3 will hit you. If you only use node, then you can only get hit by exploits on node. So I'd argue it's the opposite. The more layers, the less secure. > nginx/apache are really good at what they do Sure, but you need to find the most efficient tool to handle your needs with the least amount of complexity. Only add something if it solves an issue that you can't solve in a simpler way just as well.
- derefr 11y ago> Current best practice is to use SSL for all communication between your own servers anyway, so there's no gain. I've never heard this. Who does this? Everyone I know of either just naively relies on the privacy of NAT-style non-routability in something like an AWS VPC, or, if they're more paranoid (or their provider has no private-networking feature, or they need HIPAA compliance, or whatever), uses IPSec—which is, happily, exactly the proper use-case for IPSec. (Unless what you actually mean is requests between separately-maintained microservices that are supposed to treat one-another as if they were produced by third parties, like AWS strives to do. But the "your machines" makes me doubt that; you wouldn't think of those other machines as "yours" in that case.) > From using the web, I don't think this is done anymore. In fact it seems to be the opposite - foo1.app.com, foo2.app.com seems to be the trend. Green-field applications, no matter the size, are usually deployed to separate subdomains, yes. For long-term maintenance, though, nothing beats being able to just mount a new backend (probably written in a different language, even) on top of your legacy app's /admin/ or whatever else. It's effectively about patching a resource space with new backends to handle parts of it, without having to touch the legacy code to get it proxying to the new server. Businesses that embrace the "cool URLs don't change" philosophy—for example, newspapers who want their heavily-linked-to story pages accessible forever—take this approach all the time. Their web servers are rats' nests of routing rules to different backends, to make everything seem, from outward appearance, to be the same as it always was, even when everything is now in the CMS-of-the-week. The other place this happens is API servers—you might want /1.1/ and /2.0/, or even /feeds and /emotes, going to different clusters. (If you're doing that in the path instead of using content negotiation.) That kind of business-policy-level routing is not the rightful domain of a load balancer, even if haproxy et al can be configured to do it; you want your load balancers to be dumb stateless infrastructure components, and your web servers to be maintained and configured and updated as part of the service you're deploying. > If you use node and nginx and apache then any exploit that hits any of those 3 will hit you. There are a bunch of clever things that genuine, battle-tested "web servers" do that "application web servers" don't. Preventing Slowloris attacks, for example—it's something every HTTP server would do in an ideal world, but since it complicates the code and prevents streaming parsing, you really only want to handle it once (by buffering requests) at the input end. There are umpteen other such attacks that web servers just abstract away. Even with, say, Erlang's "battle-tested" reputation, I wouldn't trust it sitting on the open web without nginx or something else in front. Usually, though, your load balancer is also a "web server"... if SSL has been terminated there so that it can actually parse the requests and responses. This tends to be why some people actually chain haproxy -> nginx -> their app server: they put haproxy in dumb TCP load-balancing mode, while nginx terminates SSL and thus gets to be the "web server."
- marcosdumay 11y agoHe's just saying that he prefers to configure his reverse proxy in Javascript, or some other mainstream language than in the Nginx configuration language. I can see where he's coming from. But I still slightly disagree with the feeling.
- tootie 11y agoFirstly, I'm flattered that I sound like not a n00b :) I should say that I haven't ever really tried this at production scale. My background is mostly consulting wherein my responsibility is to deliver a provably working solution for someone else to manage and operate. So there's my bias in this. Other commenters have made a lot of the points I would. You can easily handle TLS in Java or JavaScript. Or you can terminate with an ELB as I usually do. A lot of load can be pushed to a CDN. But really, I'm not convinced it would be that much slower. I know this dated, but a simple apache bench test shows Tomcat outperforming httpd for static assets [1]. I've never had a site that was remotely bottlenecked by static assets, but I've had many bugs due to obtuse mod_rewrite configs. It's cheaper to have to fewer bugs than to spin another server. [1] http://www.devshed.com/c/a/BrainDump/Tomcat-Benchmark-Procedure/ http://www.devshed.com/c/a/BrainDump/Tomcat-Benchmark-Proced...
- bhouston 11y agoFor handling load we find nginx amazing, and we run it in front of an ExpressJS server on Node.JS. The combination is pretty phenomenal for high traffic production sites that ExpressJS can not handle alone.
- untog 11y agoThere's no either/or here. Nginx in front of Node works great.
- Tenzer 11y agoThe post ends with "We look forward to your feedback as you try out nginScript [...]" but it doesn't mention where we can test it out. Does anybody know more about that?
- wut42 11y agoIt's here: http://hg.nginx.org/njs/ http://hg.nginx.org/njs/
- placeybordeaux 11y agoIt's sad to see lua get slowly replaced by javascript.
- ianlevesque 11y agoIt is. But JavaScript is the new assembly language, all you need is a Lua to JS compiler or a whatever to JS compiler.
- teacup50 11y agoI genuinely can't tell whether you're joking.
- ianlevesque 11y agoNot joking, just dying a little inside.
- hackcasual 11y agohttps://kripken.github.io/lua.vm.js/lua.vm.js.html https://kripken.github.io/lua.vm.js/lua.vm.js.html
- vardump 11y agoLast I checked Javascript implementations were slower than LuaJIT. Cost of implementing Lua tables, meta-tables, co-routines, etc. in Javascript will be rather high. Anywhere between 2-50x. If native Lua engine is removed, you can just forget about it then. So what you're saying doesn't make any sense for anything remotely performance sensitive.
- bryanlarsen 11y agolua compiled to asm.js is 64% of the speed of lua native https://kripken.github.io/lua.vm.js/lua.vm.js.html https://kripken.github.io/lua.vm.js/lua.vm.js.html
- 11y ago
- lxfontes 11y agoI'm really happy with openresty and curious to put them side by side. betting on lua here.
- marktangotango 11y agoTwo things; The big HUGE win for lua in this, in my view, is the plethora of packages on luarocks. With simple scripts, as presented in this blog posts, sure a javascript subset is fine. But suppose you want to interact with redis from your script? Where's the c ffi interface, and a prepared package you can use from nginscript? Grap hiredis bindings from luarocks, and your set. Second, great yet another javascript implementation. They're very open about supporting a subset out of the gate, who knows how long it would take to reach parity with es 5 or 6 even?
- bigtunacan 11y agoI think this depends on just how compatible NginScript is with JavaScript. Will it be possible to pull in the ffi node module, or one of the many node redis modules?
- neomantra 11y agoI agree with what you said -- although the node/npm ecosystem is much bigger. I'm not sure how it works with the nginScript subset. But network-related libraries shouldn't be pulled from luarocks (unless maybe they have resty in the name). One would want to use lua-resty-redis and not hiredis within OpenResty. The 'resty' libs use the nginx cosocket library so work asyncronously with nginx core. hiredis would block the worker threads.
- marktangotango 11y agoAh thanks, I was not aware of that. Also, unless they code nginscript to specifically support googles V8 api, there's no reason to expect node or any of it's packages to work with it.
- bungle 11y ago
- graniter 11y agoThis is a welcome improvement to me. I've spent many an hour trying to figure out how to put some logic in nginx but it was never very intuitive to me. I think a reverse proxy + ssl termination + web cache should be considered part of a normal web stack and developers should be proficient to use the full stack when they develop and implement sites. Rather than trying to do everything on the app server, once I started utilizing nginx my app design changed somewhat and of course the response times dropped and the app server load was reduced. I'm hoping nginscript just makes it all easier to do.
- stonogo 11y agonginx is driving very fast down the road to firefox.
- ticktocktick 11y agoMarginal bloat is always rational. Forest for the trees and all that.
- jordigh 11y agoOr Apache.
- wut42 11y agoFor anyone interested, it looks like it's available as a module on http://hg.nginx.org/njs/ http://hg.nginx.org/njs/
- stanleydrew 11y agoI can't help but think this is a bad idea. Jamming more stuff into what is a great tool puts nginx on a slow path to a bloaty death. Am I incorrect in assuming that you could implement your entire server-side js app now as an nginScript module? Do people think that is a good thing? Not to mention that putting more interpreters and more end-user code into a system that has access to your service's private key might not be terribly wise. I'm sure many people will tell me I'm wrong, and I guess I can see some benefit to simplifying configuration and perhaps deployment. But there's a reason we've mostly moved away from deploying embedded PHP applications inside of mod_php.
- bhouston 11y agoThere is already Lua support so this is just adding another language - thus if this is a bad idea, it is a continuation of an existing bad idea, rather that starting a new bad idea. If that makes a difference....
- stanleydrew 11y agoYeah I've been skeptical of nginx's Lua support in the past. I guess I discounted it because it was a relatively unknown feature and Lua is obviously not nearly as popular as JavaScript. I don't know of any production service written exclusively in Lua, though I'm sure there are some. So yes while this is just a continuation of a bad idea, it's a rather substantial continuation. I fear that a lot more people will make use of this than make use of nginx's Lua support.
- stock_toaster 11y agoI have read that cloudflare uses nginx lua a ton. Apparently so does taobao (via tengine?).
- Touche 11y agoOpenResty is built on Nginx's Lua support and is fairly popular. You're probably using websites that use it without knowing it.
- TazeTSchnitzel 11y agoThis seems like massive overkill. Instead of adding a limited domain-specific language which is tuned to nginx's requirements, they've added the behemoth that is JavaScript, along with all its flaws. A turing-complete behemoth, at that.
- ksherlock 11y agoIt's a subset of javascript, with a subset of flaws. The wiki entry specifically mentions that eval and closures aren't supported.
- harshreality 11y agoThe nginx config language already is a half-assed DSL with all sorts of unintuitive limitations (chiefly caused by its insane mix of declarative and procedural elements, and arbitrary precedence of declarative directives). The last thing nginx needs is a new DSL (that everyone has to learn from scratch) with a new set of unintuitive limitations and a new set of differences from common general purpose languages. There are plenty of good minimal languages, from embedded scheme varieties to luajit to io. If that's what you mean by a DSL (embedded minimalist scheme with some nginx-specific functions and variables, for instance) then I agree, but they chose the javascript path for a good reason: it has a healthy community and ecosystem, and while the performance won't be top notch, I don't think it'll matter.
- eknkc 11y agoI think it's a good addition. We have been using varnish on high traffic servers and one of the reasons was that it had "vcl", a javascript-like language to define request handling logic. (With a lot smaller feature set and more domain specific. But powerful enough). Having javascript on nginx would provide a lot of config options for people familiar with it. I believe nginx already has Lua support so not a big deal anyway.
- girishso 11y agoI agree. It will be more easier to write some custom request handling logic in Javascript.
- tambourine_man 11y agoWe run a separate virtual machine for each request, so there’s no need for garbage collection I'm curious to see the impact of this strategy on performance.
- Matthias247 11y agoI wondered about this sentence. If you would apply scripting functionality to serve long-running websocket or HTTP/2 connections I'm sure garbage collection would be necessary. However if the scripts are really per request and not per connection then it could work - but the capabilites would be much more limited then what you can do in other scripted-webserver-environments (e.g. node).
- sitkack 11y agoA VM context could be cheap to create and include an amount of memory above what that script uses for its lifetime. Meaning a single allocation and then the whole thing gets free'd at the end of execution. Analogous to how CGIs execute.
- Rygu 11y agoSlightly off-topic, but I wouldn't worry. Nowadays hypervisors can boot up complete OSes in ~800ms. https://insights.ubuntu.com/2015/05/18/lxd-crushes-kvm-in-density-and-speed/ https://insights.ubuntu.com/2015/05/18/lxd-crushes-kvm-in-de...
- ck2 11y agoas long as I can compile --without-nginscript, go nuts
- jnbiche 11y agoI wonder why they didn't use Duktape[1]. It seems like the obvious choice for this kind of effort (e.g., if the 2 main Lua implementations have any counterpart in JS, it's probably Duktape). It's possible that Duktape was still too early in its development to use when Nginx started this project, but even then it seems like they could have collaborated and saved a lot of man hours. I wonder if there a good reason why Nginx didn't use Duktape, or could this be a case of NiH where some Nginx dev got excited about the opportunity to build a new superfast JavaScript implementation just for Nginx? Surely it would have been less work to integrate the two event loops and use Duktape's (well-documented) API to build whatever features they wanted? That said, although I've built significant async programs in other languages, I've never done anything in C on this scale, so take my words with a grain of salt. 1. http://duktape.org/ http://duktape.org/
- jws 11y agoI've used duktape as an extension language and wholeheartedly recommend it. It does the job and caused me zero problems. I can't ask for more than that in software.
- acd 11y agoI think Nginx is open source crippleware. All the goddies are in the closed Nginxplus. Http2, load balancing with monitoring with application health checks. Do you get the source code of the closed features? Nginx already has LUA scripting support.
- pnommensen 11y agoThe HTTP/2 module of NGINX is (and has been) fully open source. https://www.nginx.com/blog/nginx-1-9-5/ https://www.nginx.com/blog/nginx-1-9-5/ Disclaimer: I work at NGINX.
- potatosareok 11y agotengine fork has application health checks, although I'd still probably recommend haproxy
- mulander 11y agoA web server with a JavaScript engine. What could ever go wrong? My eyes start to bleed when I imagine what some cowboys will implement on top of that.
- s369610 11y agoI wonder if this has anything to do with the call for a new maintainer for LuaJIT recently
- bungle 11y agoNo.
- vacri 11y agoI wonder if they'll have an "'nginscript' is evil" section in their wiki, like their "'if' is evil" one...
- paraboul 11y agoI think that most people missed the point here. The basic idea is a DSL that "happens" to have the same syntax than Javascript. I guess that this VM has a lot of optimisations related to its purpose toward nginx (.e.g. no GC overhead, since each JS context is supposed to be short lived and tied to a unique request).
- iamleppert 11y agoDislike.
- rwaldron 11y agohttps://www.youtube.com/watch?v=rX7wtNOkuHo https://www.youtube.com/watch?v=rX7wtNOkuHo
- jessaustin 11y agoShould Greenspun's Tenth Rule be updated with a note that "they might try adding javascript before they add common lisp"?
- fideloper 11y agoHN and it's predictable level of antipathy is a constant disappointment. Hating is the norm, do better. Put more thought into your opinions. Personal feelings of Javascript aside (not my favorite either!), I think this is a great business move (adoption, excitement, blog-o-sphere marketing, even if some users shoot themselves in the foot), and I think it opens up exciting possibilities, including creating Nginx+ features fo'free.
- striking 11y agoAnything you can do in nginScript, you can do in Lua. Except that Lua was lightweight to begin with. This isn't JS (as we know it), this doesn't get access to the Node/npm/bower/whatever ecosystems. The antipathy is a symptom of our JavaScript disease. We have grown tired of this affliction. We understand now what makes it less great than we once thought. The churn of rapidly growing and devolving JS frameworks, the slog of awful design-by-committee processes putting the language together... it is nothing compared to Lua's simplicity. And some clever fellows understood this long ago, on a site much like this one. Feel free to take a look. https://news.ycombinator.com/item?id=7890685 https://news.ycombinator.com/item?id=7890685
- _Codemonkeyism 11y agoI can understand the appeal, marketing Javascript to CIO/CTO is much easier than marketing Lua today. (Which obviously is sad as in my humble opionion for various reasons Lua is the better embedded language. I hoped it could become a widely adopted standard, we had great success with Lua in Redis in the past).
- namelezz 11y agoWhy did not they use Golang?
- kolev 11y agoWhy not write a JavaScript to Lua transpiler instead?!
- mrbig4545 11y agoso it's mod_perl, but javascript and nginx instead of apache and perl. seems like they've ignored history here, as mod_perl turned out to be a bad thing in the end, people messing with bits they really shouldn't leading to massive amounts of unmaintained legacy spaghetti code messing with all parts of apache. bearing in mind mod_perl's original use was not for writing applications, it was for messing with apache, for doing the things you can't easily do in the config. but where there's a way, abuse will follow, and before you know it whole apps will be written with this ah well, those who don't learn from history are doomed to repeat it. so, while it may seem like a good idea now, you can bet in 5-10 years it will no longer look so clever
- 59nadir 11y agoI think a countdown for a new 'in vogue' webserver just started. This is something I would've expected from a "Show HN: Embedded JS in Nginx" post, meaning it has potential to be a project done just to see what can be done, that everyone could say "Hey, that's cool" and then never use, because it's a terrible idea. Instead, it's presented as a reasonable way of moving forward, when they could've pushed for their own much more reasonable alternative. They've done more work for a worse idea, effectively out-competing their own feature with a much more popular but crappy alternative.
- elcct 11y agoIf you need that flexibility I think Go is much better solution.
- mkup 11y agoAdding Javascript support to high-performance reliable web server does not seem rational from the engineering point of view. I'd rather added support for the safe subset of some statically-typed, high performance language compiled to LLVM. This language must be without asyncronous GC, so its memory use will be predicatable under high load. Javascript on server side is so vogue-ish. Vogue will change soon but uglyness of architectural decision will stay with Nginx forever.
- jimjag 11y agoYeah, I am a known Apache fanboy, and so I'm sure that what I say will be discounted. But, imo, this just shows what happens when an open source project becomes the sales initiative of an Open Core model company. Instead of the design and future being under the control and guidance of the community, it is instead in the hands of the VCs and whatever "promises" future revenue growth. Believe me, I know; I used to work at Covalent which was billed as the "Red Hat of the Apache web server" so I know how hard it is to resist the push of VCs and those nasty quarterly numbers. And Covalent wasn't the only Apache shop around, unlike nginx.com today. The combination of FUD and marketing $$$ is being used to "encourage" more people to migrate (or use) nginx, as an "open source" alternative, when it's obvious that "open source" is being used mostly for the PR aspect and not so much for the community-focus and community-led aspects which is really core to "true" Open Source.
- totony 11y agoAs long as they add a --disable-js config flag i guess i'm okay with it