20 ms·
After a year of using Node.js in production
- sb8244 11y agoI mused on similar things after getting a very small project shipped. It is based on my experience with Node, Ruby, and Node as of 4 years ago (when I first learned it). https://medium.com/@yoooodaaaa/reflections-on-node-698abecce1b3 https://medium.com/@yoooodaaaa/reflections-on-node-698abecce...
- mrgalaxy 11y agoI have used Node.js in production for about 5 years now and I must agree with the sentiment that JavaScript is "Easy to learn, impossible to master". Yes, error handling is a little confusing at first but it stems from JavaScript's asynchronous nature which is naturally complex for the linear mind. My personal sentiment is to just use Promises, like everywhere. ES7 async/await will really help with this too.
- spion 11y ago> Coming from other languages such as Python, Ruby or PHP you’d expect throwing and catching errors, or even returning an error from a function would be a straightforward way of handling errors. Not so with Node. Instead, you get to pass your errors around in your callbacks (or promises) - thats right, no throwing of exceptions. Promises let you throw errors normally. They will propagate up the call stack in a similar manner. With bluebird, you will also get full stack traces in development mode and the performance penalty for that isn't too bad. > The last thing that I found frustrating was the lack of standards. Everyone seems to have their own idea of how the above points should be handled. Callbacks? Promises? Error handling? Build scripts? Promises are in ES6 (i don't think it gets more standard than that) and have well defined semantics, including error handling, shared between libraries: https://promisesaplus.com/ https://promisesaplus.com/ I know that Bluebird's promisifyAll might seem like a bit of a hack, but just try it out. It works surprisingly well, and its really painstaikingly tuned for near-zero performance loss. It will probably be both less painful to do and more performant than any manual attempt to wrap a callback based API into a promise one.
- pjungwir 11y agoI gave a talk about handling errors in Node a few years ago: https://github.com/pjungwir/node-errors-talk https://github.com/pjungwir/node-errors-talk At the time the solution was "use domains", but I think domains are deprecated now. It was painful enough that I have stuck with Rails since then. I'm glad to hear that Promises are an improvement!
- koolba 11y agoDomains have been deprecated since at least 0.10. As of yet there's no replacement for them and all node apps should be using them. There's no other way to catch "But ... but ... that can't happen!" type errors.
- spion 11y agoThere is no replacement because they're a fundamentally broken idea. They require the following to happen, in that order: * V8 needs to optimize try-finally * Node core needs to add try-finally at every single place where callbacks are invoked and make sure all state and resource cleanup is properly done to support domains * Popular libraries need to also add try-finally handlers for the above. As to why this is a problem in node and not so much in other languages, its because with node callbacks, the call stack goes both ways. In other languages, libraries mostly call their dependencies' code. In node's CPS style, you call the library but the library also calls your closure code. The semantics for the 2nd part aren't well defined in node - the loose law basically says: I wont call you twice, I'll try not to call you synchronously, and you wont throw (and if you do the behavior is undefined). With promises there is a contract and its enforced by the promise implementation. Since Promises actually have error semantics, you can build resource management strategies on top of them. http://promise-nuggets.github.io/articles/21-context-managers-transactions.html http://promise-nuggets.github.io/articles/21-context-manager... - and consequently there is no reason to crash your server on errors.
- lobster_johnson 11y agoDomains are used for another reason: To emulate thread-local variables. I hope that support is not going away, because it's really handy.
- eldude 11y agoI train enterprise node.js for a living. My recommendation is to just use songbird (which exposes the forthcoming promise API from core, built on bluebird), async/await and the async `trycatch` library so you don't have to worry about a 3rd party package's choice of asynchrony. It also comes with optional long stack traces.
- o_____________o 11y ago> Songbird mixes promise into Function.prototype > Songbird adds promise to Object.prototype Eek
- eldude 11y agoMeh. Non-enumerable. You can opt instead for bluebird's promisifyAll when you require.
- snappy173 11y ago>async/await in my experience, async/await is a great way to layer indirection and obfuscation over what is still callback hell. it may look better in the editor, but it's hell to debug.
- eldude 11y ago<removed> EDIT: Oops, I misread the parent. You're right, async/await isn't easy to debug, but it's getting better, and it's a tradeoff. For now, I recommend debugging the compiled code (using generators) without source maps to avoid some of the quirks of source maps. In my experience, the tradeoff is worth it for new node.js developers because it offloads the asynchrony contract (e.g., calling a callback OAOO) to the language.
- raarts 11y agoWhen I initially encountered event -based processing (libevent in C), those callbacks were indeed difficult to wrap my mind around. But I learned to structure the code in the editor, keeping everything together which made it manageable. I 've worked with node for a couple of months now, and I find promises to be more confusing, because it obfuscates the callback in my mind, and makes it look like ordinary function calls.
- kcorbitt 11y agoI've spent a lot of time writing Javascript on the front-end in the last year using both React and React Native. I've found the React ecosystem to be a sane, productive and enjoyable development environment. Interested in sharing more model logic between our front- and backends, I also investigated writing some new backend features using Node (we're currently developing with Rails). But after days of research and playing around with the available options, I came to a conclusion similar to Gavin's -- any reasonably complex backend requires you to either roll your own everything, or try to cobble together literally hundreds of tiny dependencies that weren't built to go together, and then somehow keep track of all of their regressions and breaking changes. Node's fantastic performance and unique ability to share logic between client and server are enticing, but I just don't trust the community and "best practices" around it enough to bet the farm on it for now.
- wrong_variable 11y agoThe same problems you cite for node.js are the reasons why a lot of devs love node.js. Its much easier to do your own research and find the best module to solve a particular problem you are having then to shoehorn into some larger monolithic framework. Also its a lot more fundamental then that - Node.js has prolly the fastest iteration cycle for any platform out there since its so easy to create your own module - it leads to some sort of Cambrian explosion of innovation and experimentation. EDIT: Also OP seems to think callback hell and async programming is bad. The important thing is those things are problems for python/.... too ! Its just that python doesn't have a good programming model to even begin to address those concerns. JavaScript at-least tries to say - "hey this is a problem we need to deal with - concurrency is a issues we all face " So when devs complain about callback hell - its just that they have never tried to use python to do async in a neat way.
- empthought 11y ago> python doesn't have a good programming model to even begin to address those concerns This isn't even close to true. Anything JavaScript has to express logic in the face of asynchrony, Python has too. There are a half-dozen asynchronous web servers written in Python. There's not as much of a culture of writing APIs that way in Python because it's generally a terrible way to program, and threads/OS processes are good enough for basically everything except HTTP servers with absurd numbers of concurrent connections.
- wizard_class 11y agodoesnt node support modules? thats a way to avoid callback hell
- fredrb 11y agoHow so?
- JabavuAdams 11y agoThanks for this. The Node / Javascript ecosystem just seems like one I don't want to be a part of. I feel so lucky to have avoided the whole disgusting web stack.
- bdcravens 11y agoLike the author said, Node isn't a great fit for certain apps. It sounds like yours is one of them.
- joshmanders 11y agoThese types of articles make me laugh. Typically a dev with many many years experience with one language, learned all it's quirks, standards, etc decides to try Node.js because it's the "new hot fun toy", and expect it to work like their old language, and realize that is not how it works, doesn't know where to find what and fails real hard to realize that JavaScript in general is in a huge influx of updating at this moment, which by nature propagates to Node.js. The end result is they get frustrated and go back to their old language.
- eva1984 11y agoYeah, so some js devs might need to stop overselling javascript to everyone, pretending it is the one language that people are waiting for years...Just saying.
- joshmanders 11y agoYou should try to surround yourself with developers who don't have such attitudes. I am a fan of JavaScript, I love Node.js and I will often times suggest it to newbies. But I don't pretend it's the be all/end all of languages. Just like any other language it has its strengths and weaknesses. It's up to you to decide if it's the right choice for you.
- Silhouette 11y agoYou should try to surround yourself with developers who don't have such attitudes. The trouble is that while you can do this for yourself to some extent, you can't necessarily do it for the people you have to work with. I've worked on a project where one guy came in to do a simple database back-end for an embedded system and decided Node and its ecosystem were appropriate. He seemed to have some experience with those tools, so the rest of the team went along with his decision. A year later, there was still little useful code actually running on the required platforms. One of the other guys got fed up and wrote the basic case using C and SQLite in less than a day. That guy did have some relevant experience and had been questioning the use of Node for that project from early on, but because the Node hype was so high-profile, management hadn't known which developer to believe. This is why it's useful to have articles like the one we're discussing, where people who have actually tried a tool in real life for a significant period of time share their experiences, even if those experiences weren't quite what they'd hoped for at the start.
- eknkc 11y agoTLDR; Author actually wants to use Python. Used Node.JS regardless, for whatever reason.. It did not work the way Python works. Author is frustrated. Complains that JavaScript is not Python.
- fredrb 11y agoThis. You can't apply some other language paradigms in every programming language just because it's the only thing you know how to do.
- paulddraper 11y agoI love Python and hate JS as much as the next guy. But complaining that JS idioms do errors differently than Python idioms is stupid. It's like saying "JS is stupid because people use braces and whitespace to denote flow control" Adopt the paradigm and see how well the technology fits it
- vacri 11y agoSmall company ops guy here - a bit over a year ago, I used to joke with my devs, asking them "So, what's this month's recommended way of installing node?". More recently we've been experiencing dependency hell, which is exacerbated by our small team not having enough time to upgrade to the latest LTS release. Node is definitely a language that you have to manage. It doesn't sit in the background and let you get on with writing stuff. Is it the right tool for X or Y? I can't say, I'm not a dev. But it does require a lot of hand-holding and keeping current with the zeitgeist.
- deedubaya 11y agoFor all the comments on here about how unfair the author was, there sure is minimal feedback on the problems they highlighted.
- snappy173 11y agothe feedback is: stop expecting javascript to act like python
- deedubaya 11y agoHow productive!
- snappy173 11y agosorry if that came off harsh, but that is actually the feedback, and it's valid. whether or not javascript/node is better or worse than python, it's pretty clear that bringing a python style approach to nodejs is going to cause problems, especially with error handling and async stuff.
- q3k 11y agoWhat does that even mean? What behaviors are you talking about?
- deleted 11y ago[deleted]
- SiVal 11y agoReally, just learn to use callbacks properly. Well, wait, actually, you should skip that and start getting used to using promises instead--a big improvement. Well, I mean, until next version is ready, and we can start using async/await...until wasm makes better thought-out languages available. Despite the sounds of this, I do like the idea of having an experimental platform with which to gain experience using wildly different approaches to the wildly changing world of web apps. I don't take it for granted that old language concepts will turn out to be the most useful for the web platform. So, I'm okay building a website for the PTA or ceramics club with this, and I'm very interested in the experiences of others using a wide variety of technologies and approaches, but I'm not sure Node.js would be a sensible foundation to build a business on.
- Touche 11y agoA lot of this is residual effects of the (slow) evolution of JavaScript. It was thrust into the spotlight missing a lot of features and these features have only recently been fixed by the language itself. But Node has been around since 2009. 2009 JavaScript was missing a lot of features. It was basically a runtime only advanced users should use. The Node maintainers had to make a lot of decisions that now conflict (to some degree) with fixes that have come later to the language. They chose their callback style; now we have Promises. They chose to throw in methods rather than return an error in the callback (this makes it awkward to use fs with Promises without a wrapper library). They chose to implement their version of CommonJS, now we have the .mjs issue arise.
- firasd 11y agoI've been on a similar learning curve with Node over the last year, and it has certainly been a rougher incline than other languages I've used. The whole async situation needs to settle down, it's completely unacceptable to write code with callbacks, promises, etc. This is because they are not just challenging to deal with, but intrinsically wrong in concept. I have to wait for a database query to complete, then pass the next thing to do to the callback of the query? That can't be right. Interesting article I found: "Async/Await: The Hero JavaScript Deserved" https://www.twilio.com/blog/2015/10/asyncawait-the-hero-javascript-deserved.html https://www.twilio.com/blog/2015/10/asyncawait-the-hero-java...
- sockgrant 11y agoAgreed. Checkout RxJS to hold you over while you're in Javascript land.
- Touche 11y agoPlease don't use event streams for handling asynchronous code, that's not what it's for.
- sockgrant 11y agoCan you elaborate?
- Touche 11y agoEvent streams are similar to Promises in that they provide a value for something that will happen in the future. In the case of event streams it is a value for an event. In the browser this might be a user clicking a button. This event can occur many times. It might never occur. Promises are values for something that will happen in the future, but only once. Use Promises for things that happen once, event streams for things that happen 0 to many times.
- rescripting 11y ago
- mrmondo 11y agoWe couldn't even stand 6 months let alone a year. Broken pack depts make it hard to CI, poor performance, memory leaks, huge docker base images due to deps, lots of single cpu only tasks that were too hard to scale out, an ugly language compared to ruby or Python and on top of all that how poor the package management with NPM has been. We've just ditched it and gone back to Python/Django/flask and ruby for the ops tooling.
- Wintamute 11y ago> You use Grunt!? Everyone uses Gulp!? Wait no, use native NPM scripts! Although couched as a criticism this is actually the community fixing itself. The evolution from Grunt > Gulp > npm scripts is movement away from needless complexity towards simplicity. Npm scripts are effectively just Bash commands that build and manage your project, which sometimes employ small, unixy tools written in Node. This self correction was pretty quick, it happened within a few years. > Unfortunately, there isn’t any one “standard” (like everything else in Javascript) for implementing or using Promises. Yes there is. It's called the Promises/A+ spec, and its built into ES6.
- Touche 11y agoNPM scripts are just a different problem. See: https://twitter.com/sindresorhus/status/724259780676575232?lang=en https://twitter.com/sindresorhus/status/724259780676575232?l... https://github.com/ReactiveX/rxjs/blob/a3ec89605a24a6f54e577d21773dad11f22fdb14/package.json#L14-L96 https://github.com/ReactiveX/rxjs/blob/a3ec89605a24a6f54e577... Already people are coming up with new "solutions" to this problem that looks more like Grunt. It's a repetitive circle. Personally I just use Make.
- Wintamute 11y agoSo somebody found a project somewhere on the internet with an exceptionally complicated build process, and you use it to say npm scripts are broken? Sorry, that's absurd. Looking at that particular build process, I don't think a Makefile could have been crafted to make it much simpler or smaller. In that example, the problem lies with the complexity of what they're having to do, not the tool. Npm scripts are really just shell scripting, which means all the real progress happens in the unixy Node tools that do the heavy lifting, where it should be. It's a future proof and scalable approach for the vast majority of projects imo.
- Touche 11y agoIt's an inflated example of what all npm script projects become, imo. First you just have "test", then you add "build", then you separate your "test" into one for the browser, one for Node, one for CI, then you need scripts that combine those together; then you create different "start" versions depending on environment... It blows up quickly. > Npm scripts are really just shell scripting, which means all the real progress happens in the unixy Node tools that do the heavy lifting, where it should be. That's fine, but you're missing critical features that Make provides; make won't even rebuild a target if no files have changed.
- bricss 11y agoAuthor plz, uninstall Node.js, use your so lovely Python and don't make people concerned.
- tobltobs 11y agoBecause being concerned is a bad thing?
- tylerlh 11y agoThe Netflix.com site and webapp runs on Node (and talks to a number of services written in mostly JVM based languages). While we encounter challenges just as we would with any other language -- it works for us and I would argue that it's a pretty big application. There's always a multitude of ways to get something done, and it's up to you to decide what tool will do it best. Don't treat any one language as an end-all-be-all and you might find yourself much happier and more productive. Of course, YMMV.
- ChrisAntaki 11y ago> There's always a multitude of ways to get something done, and it's up to you to decide what tool will do it best Well said. By the way, what is Netflix's take on Promises vs RxJS?
- ZoeZoeBee 11y agoI'm pretty sure Netflix is in the Observables camp, as Ben Lesh over at Netflix is RxJs
- Akkuma 11y agoI watched one of the recent Netflix engineering videos where they moved to a customized version of React and I could have sworn in that talk they actually moved away from Observables[1]. What was confusing is that the other talked released at the same time they talk about enhancing RxJS. [1]: https://youtu.be/5sETJs2_jwo?t=5m32s https://youtu.be/5sETJs2_jwo?t=5m32s
- clessg 11y agoFor web applications, I've been very happy with the up-and-coming Phoenix[0], a framework for the Elixir language. Very well-designed and thought-out, fast, productive. Leans functional and immutable rather than object-oriented and mutable. It's kind of like Rails but without most of the problems. [0] http://www.phoenixframework.org/ http://www.phoenixframework.org/
- deedubaya 11y agoI've found Elixir to be a delightful language with very palatable syntax compared to ruby. It has been a really enjoyable transition, with some vague reminders of the parts I really like about JavaScript.
- deleted 11y ago[deleted]
- Chris911 11y agoMost of the problems described in the articles can be solved by simply using promises. Error handling is centralized in your chain and any function can throw and just like Python or Ruby you can catch anywhere you want. As for consistency between callbacks, promises and generators, just pick one. We switched from callbacks to promises and it was a great move. Error handling greatly improved and the code looks a lot nicer. No more callbacks hell. Ever. We switched our backend from Python to Node almost 2 years ago now and it was a great decision for us. If you handle a code base that deals with a lot of async requests Node is definitely a top contender.
- cyberpanther 11y agoI think by reading the comments here and the article, its apparent that Node.js just isn't as mature yet. If you know what you're doing, it can be great, but for the noobs the right way to do things is not easily apparent. Couple this with the huge choice in libraries and frameworks, makes Node.js harder for now. I think the base is good though and given more time it will become more easy to wield. This is typical of any new tool. And yes Node.js has been around the block for a while, but it is still newish compared to Python, Ruby, PHP, etc. So you're going to pay a new adopter tax still.
- billmalarky 11y agoJust FYI, the Koa framework makes node sane again. Callback hell and error handling are no longer issues in node if you just embrace generators or async/await. We use Koa in production and serve billions of requests just fine. If I had to go back to Express I'd say no.
- beders 11y agoNow all of a sudden, having types and some standards to gather around doesn't sound like a bad idea anymore ;) I agree with one of the commenters: Lessons already learned by older engineers (who went through similar woes with other languages/tools) are being re-learned again and again. The software industry is in a sorry state. Unless you are a very disciplined team with a very strong sense of writing modular code, don't use Node.js for any larger project. And even then, the single-most useful function in an IDE 'Show Call Hierarchy' will never be available when using a dynamically typed language. That is not an issue for smaller projects. However, long before you even get close to the the million lines of code project size, your tools will fail you. Your debugging/refactoring times will explode and adding a new feature will seem unsurmountable. Instead, let's just re-write everything from scratch because the cool hipster that wrote your backend a year ago has left for greener pastures... I won't even try to guess the amount of technical debt produced with Node.js and the likes each day in the bay area. And, yes, I just used Node.js to write a Slack-bot. It was fun, took me two hours and got me up and running quickly. That's the beauty of it. Just be aware of the dangers.
- spion 11y agoWith node, at least you have the option to easily migrate to TypeScript and get excellent tooling.
- beders 11y agoif all the libraries you are using are as well...maybe.
- spion 11y agoYou can write definition files for libraries. A lot of libraries already have such files: https://github.com/borisyankov/DefinitelyTyped https://github.com/borisyankov/DefinitelyTyped If a particular library doesn't have one, you can write it yourself. In that case theres no need to model the entire library - you can only model the subset of functions / methods that you use.
- dustinlakin 11y agoI think the switch to an async back-end can be more initial work than many expect. It may take some time to feel as productive, but promises become powerful and became a game changer for me over my previous work with callbacks. Error handling also becomes manageable. What I really enjoy is jumping into new community and getting to work with tools that have built. Choosing the right ones can make or break an experience. I personally enjoyed working with Express and Bookshelf.js/Knex. I appreciate the authors perspective, but I also don't think this should deter anyone from trying out Node. I personally have no overwhelming preference to using a Python or Javascript stack.
- xentronium 11y ago> Bookshelf.js/Knex After ruby orms, Bookshelf felt very, very underdeveloped. Anything I tried to do beyond "hello world" only brought me pain, especially dealing with associations, but honestly just about everything. I guess I've been spoiled, but getting anything done in express/bookshelf combo seemed like a chore.
- silviogutierrez 11y agoSame experience as the author. Tons of reinventing the wheel, and hundreds of dependencies. The majority of established companies that say they use Node in production are doing so as a fancy proxy. All the "serious" stuff is done on backend services written in other languages. Moreover, asynchrony is a concept far more advanced than most people think. We will likely continue to leverage Node as a fancy proxy. Adding Typescript will only help. But it's likely that as Node grows into a mature platform, other platforms will continue to fill in the gaps that Node filled. See for example Node constantly adding [foo]Sync versions of methods, while Python adds first class sync support.
- hasenj 11y agoEveryone and their aunt wants to publish an npm module. That's why you get a ton of badly written poorly thought-out packages.
- peterashford 11y agoI think the basic problem is that JS is not the right solution for every task but for the web, it's often the only tool available. I had similar experiences to the OP. I had lots of code written in JS that I was happy with to some extent, but all of it would have been easier / cleaner / more maintainable in a less crap language.
- nodesocket 11y agoI prefer to just use async (https://github.com/caolan/async https://github.com/caolan/async) for all control and error flow. Namely async.auto() can do almost any crazy flow.
- narrator 11y agoI'm using NodeJS on a pretty big project. Things I like: * Async libraries make it easy to make things high performance. * I like Sequelize as an ORM, once I figured out how the async everything works. * The testing support is pretty good, both mocha and e2e testing using selenium * The angular-fullstack generator was really helpful for getting started and setting up the deploy to Heroku. * everything is open source. If I get confused with what a library is doing while I'm debugging I can just stick a print in the lib temporarily. Things I don't like: * "undefined is not a function". When something goes wrong. This is the error I get 80% of the time. * async stuff silently swallows exceptions unless I put try{} catch(err) { console.trace(err) } everywhere * There's a bit of a learning curve with promises. * Needs a lot more automated testing than a really strongly typed language like Scala. * Single Threaded. I know how to program using threads, so I view this as a disadvantage. * No types. I have a lot of type checking asserts at the beginning of dao functions. If I did it all again and my teammates would oblige, I would have probably chosen Play/Scala. I actually reimplemnted things from a Play/Scala project I did a while back (login/signup/forgot password/confirm account) and it took less time in Play/Scala, even without passportJS and friends. I have about a years worth of experience learning Scala before I started that project, so it would probably take longer for a new Scala developer.
- rhinoceraptor 11y ago> async stuff silently swallows exceptions unless I put try{} catch(err) { console.trace(err) } everywhere Huh? That's not how async errors work in Node. Try/Catch is not async, the catch block will not magically transfer to your callback function. You check for the error as the first parameter in your callback, that's the standard way of error handling. Throwing errors in Node is considered by most to be an anti-pattern.
- narrator 11y agoThat's nice in theory, but third party libraries may throw exceptions if unexpected things happen at runtime. You'd still have to put the try catch block there and call the callback in the catch block everywhere.
- nevi-me 11y agoBeen on Node and Mongo for 4 years now. Both have worked well for me. JS has evolved a lot in the past few years, and with it came all the new shiny tools that left us confused. I think a year was too short for the author. Sounds like they were chasing after every cool thing to make life easy. Error handling is a pain yea, I've seen amateur folk try catch this and that, I think that lends itself to being terrible. One of the things I appreciate the most about JS is JSON. Crafting tens of classes in Java irritates me. I find Python sometimes tricky also when dealing with structs VA lists. I've always stuck to the basics when I was learning how to JavaScript with Node. I used only callbacks for 2 years until I understood what my code was doing. Granted, I'd have spaghetti at the end of complex async queries, but I understood what was going on. I moved to caolan::async and have been using async whenever necessary. I barely use promises as I got confused by the early adoption craze. I learnt how to use Backbonejs, and a bit of Angular+React+Ember, but I found myself comfortable using vanilla JavaScript. Only thing I use is Underscore templates. I know I could benefit from shadow DOMs etc, but I'm content where I am. I think a good way to learn is to take things at bite sized chunks. I've started using RxJS recently, and I'm loving it! I'll keep using JS as my primary tool, but I'm slowly moving to Kotlin.
- jrapdx3 11y agoCan't fully agree with the article re: using nodejs in production. A couple of years ago I decided to use nodejs for a rewrite of a web/database app that had gotten to be complex and hard to maintain. As so often said, it was true for me that the abundance of modules and choices in node was at first very confusing. I eventually figured out that keeping things as simple as possible was my best approach. What I came up was a server relying on very few module dependencies and written using consistent if not so elegant components. Sure it's kind of verbose and far from totally DRY but fairly easy to understand, modify and extend. Key issue was node's "callback hell" style of async programming. Of course, it's not just node, other languages (Scheme, FP, etc.) can be mind-bending in a similar way. The callback "inside-out" locality inversion was initially hard to grasp, but once I caught on it was possible to get the server working the way I needed it to. The more recent development of promises, etc., certainly provides reasonable ways to reduce the high barriers implicated in using the nodejs style of async programming.
- zyxley 11y agoCallbacks definitely become much, much less of a problem once you can turn everything into promises.
- placebo 11y agoI usually don't respond to anything which I feel is just another "language war" provocation, but whenever I see these type of reviews I'm mystified. I've developed in many languages and frameworks, both well known and lesser known - decades of client and server side of C/C++, Javascript, Lua, Java, Python, PHP, Perl, Lisp. Pascal (just to name a few) in projects of all sizes, and not once did I have the thought "this language sucks". I think there are a few reasons for this: 1) Even after all these years, I'm still passionate and excited at the ability to sculpt logic, regardless of the "material" I need to use. 2) A "keep it simple" approach - no way to overemphasise this. Know the advantages and limitations of the language and stick to what works. Keeping things simple should be like a fractal - existing at all levels of abstraction. 3) I'm very wary of hype. New, shiny and trendy does not necessarily mean better, especially when the hype is in conflict with keeping things simple. I find that when you understand the playing field, mark the areas to avoid and keep things as simple as possible, the elegance of the design and implementation usually makes the advantage of language X over Y insignificant, and I feel that blaming failure on the language used is like blaming a bad novel on the word processor used to write it.
- stormbeta 11y agoThe article doesn't appear to be blaming Javascript as a language, but rather the Node.js ecosystem as a server platform. Not all tools are appropriate for all niches. The author made it clear they don't have an issue with Javascript as a whole or even with Node.js necessarily, but rather the use of Node.js as a major server platform or as a platform for large applications.
- qwer 11y agoAll of his arguments actually apply to all of javascript, and are not actually specific to node.js though.
- adevine 11y agoBut there is a good argument that your server components (or at least a good portion of them) should be built in a language that requires some more up front work because it makes maintenance easier down the line.
- Clobbersmith 11y agoWe use NodeJS pretty extensively at Yahoo for both front end and back end services and it works well. While some of the complaints are valid, it's not worth flipping tables over. Promises are standard in ES6 and it is "the way" to handle errors. At least if you want to stay sane.
- santoshalper 11y agoNode.js, meteor, et al. is a great example of what happens when you let inexperienced developers design a platform and run an ecosystem. Almost every ounce of focus in this community goes to increasing developer productivity. Operational concerns like scalability, security, monitoring, are given the bare minimum of focus. In many years of programming in many languages on many platforms I have never seen a worse platform and ecosystem than Node.js in a very popular language (obviously some obscure languages hardly have anything built around them at all). I really think it is setting the programming world back a lot. Not to mention what a thoroughly shitty language JavaScript is. Being able to code your web app in one language is a neat trick, and the ability to talk back and forth between client and server so seamlessly does kind of feel like magic, but otherwise, this is a meaningfully worse language/platform that Visual Basic.
- programmarchy 11y agoNever had the problems with Node described in the article. Node forces thinking about modularity and composition though, which I'd wager is what the author is actually struggling with. Write functions that do one thing and they're pretty easy to compose, even if they're asynchronous. It's really not hard to debug what went wrong in the stack trace when you name your functions. And I think exception handling is much worse than passing errors up through callbacks. It forces you to think about edge cases. Not sure how python handles this, but I can't tell you how many times I've seen Java or C# code swallow exceptions which is much harder to debug IMO. People really seem to have a problem with there not being "the one true path" in Javascript, but it's not something that gives me much anxiety. Javascript is incredibly moldable, which is part of what makes it so powerful.
- emilong 11y agoI've been using Node in production for a few months now, having come from Ruby (Rails & Sinatra) immediately before, but having used JavaEE and PHP before that. I find it... fine. For error handling, bluebird's typed error catching (http://bluebirdjs.com/docs/api/catch.html http://bluebirdjs.com/docs/api/catch.html) is working well for me and I'm finding it analogous to my experiences with Java and Ruby. I'm rather used to using ORMs as well and I use Bookshelf (http://bookshelfjs.org http://bookshelfjs.org) on top of Postgres for this as well. It definitely has room to grow, but it's also fine. I've also gained a dependency injection container (Bottle.js, see my write up here: https://blog.boldlisting.com/declarative-dependencies-for-unit-testing-node-js-services-45542ceb5703#.gaf9om7zj https://blog.boldlisting.com/declarative-dependencies-for-un...), which I sorely missed in my Rails days and which gives a lot of structure to the application. I think the biggest concerns on which I'd agree with the author are the pace of the community and lack of agreement on things which are well-decided in other, more well-established development environments. That being said, there's huge potential with Node because of that. There are more coders in the world than ever (I'm assuming) and Javascript is a great low barrier to entry language that encourages people to explore various runtimes. In 20+ years of coding, I've not seen this level of excitement and engagement in a development environment. While it may be rocky for another few years yet, I suspect we'll end up with a very productive platform, simply because of the amount of involvement. Of course, it's totally understandable to want to wait for that before jumping in. :) As a relatively new Node developer, I'm much more concerned about the single-threaded nature than the development environment, but so far even that hasn't been a problem.
- EdSharkey 11y agoIn my opinion, JavaScript is a toy language. Looking at it, and the Node.js ecosystem by-extension, that way has really helped me be effective with it. Tooling has never been more important to my productivity with a language as it has been with JS. I constantly search for tools to paper over the warts and potholes.
- jv22222 11y agoUber has done pretty well using node as their core dispatch architecture.
- jtchang 11y agoNode is one of those platforms that makes me shudder every time I go looking for solid best practices. It seems to change every 3 months. It's scary (and cool) how fast things are changing.
- jondubois 11y ago- The dependency instability can be avoided by specifying specific versions of your dependencies inside your package.json. - The fact that the ecosystem is evolving quickly is a good thing. Node.js is still one of the fastest growing software development platforms according to Google trends so you should expect it to change faster than other ecosystems. - ORMs suck (in every language) - They always sucked; ORMs are a massive hack intended to fix the impedence mismatch between relational DBs and RESTful APIs. If you used a NoSQL DB with Node.js (such as RethinkDB), your life would be much easier. Nobody in the Node.js community except your grandma cares about ORMs because they're considered legacy technology. If you don't like it, then you can stick to your COBOL and Oracle database. - Node.js lets you choose how you want to handle errors. JavaScript offers an Error class which exposes a name property (which you can overwrite for each error type) and you can also attach custom properties to Error objects (to carry back more detailed info specific to each Error type). JavaScript is really easy to serialize/deserialize so you can even design your error handling system to be isomorphic (same error handling on the client/browser and server). I really enjoy error handling in Node.js/JavaScript - You just have to put some thought into it. - The way of writing async logic is changing. The fact that Node.js is keeping up is a good thing. There is no single right way to handle async logic. Most well-maintained libraries will keep slowly evolving to use the newer features of the language but it's mostly backwards compatible (many libraries support both callbacks and promises). - The standards are not bad; they're evolving and you can choose your own styleguides for your projects. Most JS developers will adapt to new styleguides as they move between companies/projects.
- flamethroeaway 11y agoIs package.json webscale?
- stevebmark 11y agojesus this guy is a boring loser
- dang 11y agoThis comment breaks the HN guidelines. Please post civilly and substantively, or not at all. https://news.ycombinator.com/newsguidelines.html https://news.ycombinator.com/newsguidelines.html https://news.ycombinator.com/newswelcome.html https://news.ycombinator.com/newswelcome.html
- stevebmark 11y agogot it!
- z3t4 11y agoI think the problem is they chased the latest and greatest. tips: Always throw errors! Use named functions!
- Corrado 11y agoI agree with this article and find the Node.js community, and to a lesser extent Javascript itself, exhausting. It seems like every 2 minutes there is a "more" proper way to do something, which tells me that the architecture is not yet mature, even though it's pretty old by now. On a related note, it seems like every time you find something that doesn't quite work correctly or conveniently in Node.js there is a "fix". Don't like callbacks? Force Node.js to look more like other "normal" code and use Promises. Having trouble getting Node.js to concentrate on one thing at a time? Force Node.js to look more like other "normal" languages and use the "async" library. And it just goes on and on and on. If I have to use all of these other pieces and parts to be productive in Node.js I may as well just use some other language. I really wanted to like and use Node.js, but Javascript and the community are holding it back.
- Kequc 11y agoI'm still not all the way on board with promises - from the sounds of it this article says there is already a successor down the pipe. As you've pointed out some of these libraries make things behave a lot more similarly to other languages. And in such a case you may be better off just using one of them. However you're giving up on a lot of the power and benefits javascript provides, so of course you'd want to use something else. For all of its pitfalls and annoyances, javascript is too powerful a language to ignore. Asynchronous operations and streams are just too good. They are difficult to balance but once mastered you can really do a lot with them. My recommendation would be to skip libraries where possible. Use raw ES6, or Typescript. Something javascript has been suffering from for a long time is bloat from external libraries. You don't really need to use them, especially now that the language has more or less settled down. All of the best libraries were used to normalise things and that's not really needed anymore.
- MichaelGG 11y agoHow is JavaScript so special with async and streams? JS lacks any syntax for async, so it's not on par with languages that do. What's special there? Same for streams: they're implementable in any language, and JS has no special capability there. Or am I unaware of something JS has that other languages lack (besides popularity)?
- gedrap 11y agoThe only clear, objective advantage of using nodejs is that if your application is I/O heavy (e.g. tons of sql queries which can be executed in parallel), nodejs event system is helpful and everything you need is pretty much out of the box. Other thing... it largely depends on personal taste and a matter of convention. Reading his "Why I’m switching from Python to Node.js", doesn't seem like he was having an issue with that. And I don't really buy into the "same language everywhere" argument because come on, how hard is it to learn python, ruby, etc enough so that you can be productive? Not hard at all, unless you have hundreds of cubicles filled with drones. Anyway, it's good to see that he made some reasonable conclusions after the experiment. That's a good sign :)
- MichaelGG 11y agoSame language, in theory, is great. Reuse structure definitions. Reuse rendering logic or even validation logic (perform checks on both, but make it easy to get into client-side). In general, keeping things "in sync". Also can make it easier to write in SPA style but offload rendering to the server when you need it (particularly first-page or reloads). Whether or not tooling is good enough to allow this (either with JS or compilers) is another issue.
- spriggan3 11y agoThe biggest problem is dealing with callbacks (and yes even promises use callbacks , and generators need to be wrapped in a cor-routine framework in order to work as cor-routines ). I want to write a quick script doing some busy work , I now have to think about synchronicity even though the script does not need to be non blocking. Of course in these circumstances, I want to move back to Ruby or Python, which actually let me code the thing I want to code without forcing callbacks on me. So when you have to do 20 i/o operations in sequence, using nodejs becomes really tedious.
- ldehaan 11y agoFrom reading the comments there are Still a lot of misconceptions about Js. javascript is not new, it's been around since before most of the web devs out there started working in computers. nodejs supports multiple CPUs. nodejs is stable. JavaScript is retarded fast, and it's not c or c++ or any Compiled language, and shouldn't be compared to them because that's unhelpful as a measure. it is the only language for the web which enables you to work in the same language on both fronts. frameworks aren't JavaScript. nodejs isn't JavaScript. JavaScript is so flexible that it can be changed to suit the needs of those writing it, so much so that you get whole new dsl's like typescript. there are more conversations on the internet about JavaScript than any other language being used today. oh and nothing scales if you don't know how to write scalable software, that's on you, not the language.
- tempodox 11y agoI find this a valid assessment of Node and JS.
- kartickv 11y agoIf this article is true, it paints a concerning picture. I don't want to research libraries, understand the pros and cons of them, run into problems, then switch to another library, and so on. I want there to be a default that works out of the box for the majority of use cases. There can be alternatives, as long as there's a default that works out of the box for most people and most use cases.
- bschwindHN 11y agoInteresting analysis. I just finished a year of using Node for implementing an HTTP API and a chat server, and found it to be actually pretty pleasant. I'm not chasing the latest and greatest things, there's no ES6, no ORM, and I'm on an older version of Node. But it works and has actually been quite stable! The things I've missed are static type checking at compile time, and execution speed (which is less of an issue when you're talking with databases all the time). I'd be happy to write in more detail if anyone has any questions, but I found I had the opposite experience of this author. The situation makes all the difference though.
- paulftw 11y agoA year ago one of the reasons to leave Python was poor MongoDB & JSON support, 12 months later the same author complains about the lack of a decent SQL ORM library in js <scratching my head/> while JS is far from perfect, his problem was he was a little bit ahead of time- babel, standard promises & sequelize solve most of the problems. I think Python is still superior for serverside, but JS isn't as bad as portrayed in this post, if you slowdown for a couple of weeks to learn how to use it properly (just like any other popular language or framework).
- igl 11y agoAsync-functions are the answer to all his problems. I generally agree on his conclusion though: Do small things, don't build big systems. I hate that JS trys to be this OO-FP hybrid. Jack of all trades, master of none.
- tonyjstark 11y agoThis article definitely matches with my experience. I did two not all too complicated projects on the side with Node.js and the the first steps where so easy that it completely convinced me to go with it. After a while I tried to dig deeper and went to meetups to see whether I do things right as in a community accepted way and if I use the right tools and so on. Since then I refer to the Nodejs community as the most hipster programmer community I've ever seen. As soon as a framework was getting near a 1.0 version nobody wanted to use it anymore, experimental features were used in production code, it was horrifying. For me that ended this endeavour, I just could not keep up with the pace. I always wondered if it would be different if I would have worked full-time on Nodejs projects.
- btomar 11y agoThough I agree with what you all explained with the big issues with NodeJS, you have to understand its not all of Javascript. Its only server side JS. The creators have clarified, for heavy CPU intensive services, go away from NodeJS. As far as frontend is concerned, AngularJS and React are just sugar candy for user interaction and structure. Node filled the gap with an async network application in pure JS without the heaviness of Python or traditional languages. It is a hack as in every day people are finding new ways to use NodeJS but I agree, there has to be best practices and less boilerplate (plus less silly npm packages for trivial JS tasks).
- throwanem 11y agotl;dr: "I really miss Python's bondage and discipline, so I'm going back to it, and I'm going to hate on Node on my way out because I genuinely can't wrap my head around the idea of a paradigm other than the one with which I'm familiar and comfortable." It's not even about Node. It's about anything that isn't Python, and doesn't have the Python community's strong "there is exactly one way to do it" tradition. I'm glad OP has realized that's what works for him. It's a shame he lacks the perspective to understand that it's about him.
- velox_io 11y agoThere's a very fine line between between removing too much essential complexity, and leaving programmers with too many limitations. Or the other end where the language overhead overshadows the original task at hand. For instance multithreading should be handled by languages and frameworks 99.9% of the time. Take reading a file (something that should be handled by the language/ framework). Read it asynchronously, structure any dependant code clearly (which JavaScript does pretty well), if any problems are detected they display/ log the appropriate error. You shouldn't be kneck-deep in callbacks.
- co_dh 11y agowelcome back :)
- swivelmaster 11y agoThis articulates my fears around switching to node very clearly. I've played with it in the past and felt like it would become too difficult to manage with a large project and lots of contributors.
- deleted 11y ago[deleted]
- arisAlexis 11y agoUsing babel without async await is a mistake IMO should solve almost all your problems and errors. Also the main argument for using js in the back end is that you have the same team working in the front-end too and in any case in the same langage.