For the exact example in the article, both the try/catch version and the "nullcheck" version seem much simpler to understand (even if they are admittedly a bit "ugly" looking). And while I get that the author is using a simplistic example to help teach, it really doesn't seem like a more complex example would change things.
When I've felt the best writing JS was back when it was a much worse language (which is saying something) and I wrote it about as close to C as I could manage. But then I've always thought the prototypal object model is a giant footgun with little legitimate purpose and any "clever" use of it's simply a bad idea, so maybe I'm just inflexible. I also think modern classes are entirely fine, even good, for Reactjs, and adding more patterns just to be more "functional" (but not really—look under the hood) is a very bad idea, but I seem to be nearly alone in that.
[EDIT] never got why in JS specifically. I get how in a language with proper support for it functional style can be nice. And it's fine in certain narrow cases of course—a little recursive function or simple list processing code, for instance, just not as a broad, principled pattern to apply to as much of a JS codebase as you can manage.
Forcing sum types onto a language that does not support them is bound to end in awkwardness and reduced readability without providing the real benefits of increased
This is a great example. std::option from C++ is another one.
If someone did this at work, I'd wonder why they are trying to add so much complexity to something that is rather simple and already well understood by most.
It would be hard to convince me to sign off on a code review where this was added tbh. I'd love to hear how/why I'm wrong here though.
Maybe there are better use cases for it? But in my case, the major thing I care about is that code is simple and readable.
That said, I work with quite a few juniors. You should absolutely not use this in production.
But, generally, functional programming really shines when you have build-time type enforcement so you're not guessing as to whether things will work together.
In dynamically typed languages, all you know about a function is that its arguments have names and it returns a value. You can have some wonderful free-monads, but you're left to run the code, see it crash, and ponder stack traces or reason through why it failed. (Assuming it's nice enough to fail obviously.)
So you get lured in by how cool it is, but then the moment you use functional techniques beyond what you can fit in your head, you find your tooling gives you no support whatsoever.
On the other hand, in a dynamic language if you pass the wrong number of arguments to a curried function the error will only show up when the result of that is called, at which point the stack trace is useless.
Improving the error messages for things like this in the presence of dynamic typing is only possible with lots of help from the language runtime and doing it without ruining performance is still an open research question.
Reason is more popular but it lacks the category theory centric rigor. The syntax also is not as nice as the Haskell style. I'd rather go with something that fits the FP model better than syntax that is more familiar.
Ramda is beautiful and works pretty well in isolation, until you start to use 3rd party code that doesn't work with it well, or you need to interface with non-ramda code in your system, or working with built-in DOM functions or any other number of reasons why you'd need to hop out of the ramda ecosystem.
Then I end up spending most of my time trying to figure out the best way to shove X, Y, and Z into the "ramda way", and often fucking stuff up in the process producing more harder to understand and track down bugs.
Then without perfect buy-in from the entire team, we end up with 3 different ways of filtering exceptions, people using native .map and mixing it with ramda's R.map, uncurrying, reordering, and re-currying functions, and places where the nice control flow is interrupted when it had to dive into 3rd party or native code.
It just ends up hurting every time I go for it, even though the functional style works amazingly in OCaml or Haskell or Rust.
I used it also on greenfield projects where I then brought juniors in, and the learning curve for them was hard - at least..
So I kinda avoid it now, though using it taught me much. Even for my embedded C code.