Ruby Next: A Transpiler for Ruby
evilmartians.com
evilmartians.com
I do see the author’s point with regards to writing gems, though. Just because it’s easy to upgrade to 2.7 doesn’t mean I rush to do it. Usually the new language features added are nice, but not mind-blowing. It’s a mature language.
One thing that has been great is steady performance improvement every year. We usually see a few percent reduction in compute after a ruby bump, which is good for a smile. I’ve heard and am hoping that the 3.0 bump will be a little bigger.
I’m totally in favour of using transpilers to support older platforms.
What has happened though in JS land is developers started using them in reverse - writing to future standards that are not supported by the current underlying interpreter.
Hoping here the same thing does not happen in Ruby
But wow, when the ES6 features hit, and I could use them NOW, in spite of having to support IE? That was huge, and made the code so much nicer in so many ways.
I was really glad that I could, as the snaky folks say, "import from future".
It's not the worst problem for an ecosystem to have, but as someone who wants to ship smaller JS bundles, I find it annoying.
This is somewhat mitigated by the use of babel-preset-env and browserslist.
https://github.com/browserslist/browserslist
Where I work, our build tool uses a list that's (very slowly) getting reduced to evergreen browsers. On some projects, a simpler list can be used for little to no polyfills.
> transpiling in Node, which makes no damn sense
A legitimate use case would be for server-rendered apps, where it's advantageous to share code with client-side, namely transpiling module import/export (rather than CommonJS) and JSX. I do enjoy how recent versions of Node.js are embracing modern language features, even pipeline operator. Still, there are situations where transpiling server-side code makes sense.
Another maybe more relevant reason is using TypeScript, which arguably provides a leap in developer experience and code quality, beyond what browsers (or the V8 engine) would implement in the foreseeable future.
May as well pick the JavaScript/TypeScript flavor with the best developer ergonomics.
It's awesome to be able to use new features and kick their tires before the core engine dev teams invest resources in building them out.
It seems like a win / win situation here.
js devs get to use and reason about tomorrow's features today and help guide whether or not they are a good idea or even more easily come up with new ones.
Js engine devs get to see how features are used and whether or not to invest.
Honestly what is not to like about this?
JavaScript's a bit unique in this regard though, in that you don't have the option to upgrade the underlying interpreter. In most contexts where Ruby is used, it'd be much simpler just upgrade to a newer version of Ruby than start using a transpiler.
My bigger issue is that this shifts control over the language from Matz and the community to the maintainers of this transpiler. Maybe they decide they want to support something like the ++ operator as a workaround to Matz's insistence that it should not be the language. Then what?
On the JS side, sure, you don't control the env that'll eventually run it, so a source to source compiler makes sense.
On the ruby side, why is this just not in the standard runtime? Are people trying to run newer code on older VMs that they control the deployment of?
If you mean “don't control”, probably, at least, they might be given this tooling: e.g., Ruby on App Engine Standard is 2.5, not the current 2.7.
What is the problem here? You can't expect billions of browsers to be updated so soon and I'd be hairless if I still had to write in ES5 just because there are still IE out there.
Currently I favor in writing TypeScript but if Ruby Next starts supporting type hinting for Ruby 3, then I'd like to give it a go as soon as possible which can even be deployed on current environment. The only problem would be the lack of editor support for the new syntax.
> What has happened though in JS land is developers started using them in reverse - writing to future standards that are not supported by the current underlying interpreter.
Why is that in reverse. A transpiler is, after all, and using a compiler to be able to write in a language more expressive than the language to which your code is compiled is rather normal.
Actually, that's not even “in reverse” compared to “to support older platforms”, that's how trabspilers are used to support older platforms.
If I'm using Babel to support, say, IE9 (an older platform), what I am doing is using it to compile JS not supported by IE9, largely because it's a newer standard than IE9 supported, and compiling it to what IE9 understands.
If there a difference between doing that with language features from ES6 on IE9 vs ES2019 on IE11 vs something that is a currently a Stage 3 proposal on current Chrome, sure, but none of those is the reverse of the other, they are all variations on a theme in the same direction.
A bit shocking to see how much ancient Ruby is in use. It is not like they massively change the language with every release like e.g. Swift. Probably breaking changes in Rails are a bigger blocker for updating to a new Ruby than Ruby itself?
I can see a number of companies sticking on Ruby 2.2 because you can happily upgrade Rails from 3.2 to 5.2 while only changing to a minor bugfix release of 2.2.10.
Rails 6 locks in at 2.5.0 which was over a year old at the time of the Rails 6 release.
https://stackoverflow.com/questions/9087116/which-ruby-on-ra...
Thus, there's always the desire to use third-party gems to achieve pretty basic stuff (localization, decent networking/REST, database drivers, etc). These then tend to go out of date. It's pretty common to find well-used gems that haven't been updated in 5, even 10 years. This puts the developer in a tough spot - reinvent the gem/wheel? Or be forced to stay on an EOL version of Ruby?
Compared to which other language?
Java, for one, but obviously it's subjective
I'd love to think that Raku (formerly Perl 6) would be that language, but it doesn't seem like the trajectory is there.
The community is us. Ruby is what we make it. So let's make it better.
I'm leaning towards a full TypeScript stack for my next project. The idea of sharing types & code between client & server is incredibly seductive. But there's no Rails for TS/Node, so I know it's going to be a shit show assembling all of my chosen libraries into a cohesive whole.
Although looking at your previous comment, perhaps I should give Kotlin / Ktor a try?
You can fork any gem in github, fix whatever issue it has, and point your Gemfile at your fork on github. Bundler treats it as the same package so it doesn't break your dependency tree either above or below it. I've used this to fix an incompatibility in the middle of my dep tree before. It's annoying, but it's not exactly a big deal.
Ruby, between versions, doesn't have many breaking changes, if any. They're more additive changes than they are subtractive. That obscure gem that has a last commit date of 2 years ago? Probably still works. Bundler complaining the Ruby version isn't supported in the gemspec? Fork, edit, push, bundle, success.
When you say basic stuff, I think of "busy work that's already solved by someone else, probably in a more complete than my half-assed attempt would be just so I can focus on more domain-specific problems and implement business logic." That's a fine tradeoff. My clients don't pay me to implement things like authentication or design an ORM: They pay me to do business logic. `bundle add devise; rails g devise:install; rails g devise User; rake db:migrate` gets me rock-solid authentication and I didn't have to think twice about it.
"Look at all the things I'm not doing" was something DHH said when he released Rails. A lot of Ruby is the same way. That's fine with me, and a lot of others.
There's a lot to love with Ruby in 2020. I still find it to be the most hyper-productive ecosystem and it doesn't change daily (see: Javascript's ecosystem). It's a language that's expressive, enjoyable, and plain fun. And for the very vast majority of web applications — which are CRUD-centric — Rails is still an extremely valuable means to get up and running. Scale? 99% of us won't need to worry about scale, and when we do, that's a great problem. Speed? For 99% of us, our database will be the slowest part of our application — even when indexed and tuned.
Sure, it may not be 2020 sexy. The socks you're wearing probably aren't either, but they still get the job done.
Personally I don't mind magic or hidden state that much but then again I came from perl.
- Rails is the monolith that gives you all of that auth/database/etc capability, and it's very non-trivial to upgrade
- Refactoring a large codebase with a dynamic, untyped language like Ruby is extremely difficult without 100% test coverage
- Unusual syntax conventions which can get you into trouble (y = x.blah vs x.blah!), strings vs symbols, magical naming conventions for Rails, etc etc
- Auto-loading is a mess
- ActiveRecord is great until you care about DB performance, and then you end up continually working around it's quirks (the N+1 problem, indexes failing due to int/string type conversion, etc)
- Everything in Rails is convention over configuration. File paths, names of classes, names of routes, mapping of AR to DB table, etc. Sure it "just works", but when it doesn't, it's not always easy to figure out why.
- Monkey-patching is cute, but, seriously? Hot-patching system library functions?
- What's a variable? What's an accessor? What's a function? Parentheses are optional, return is optional (yet @ is required for class/instance vars?)
Again, none of this prevents you from building a quick and easy CRUD app, but I've found the deeper I go, the less I like it.
It sounds like you had to dive head-first into a mess where it was hacked together by non-Rubyists who learned "just enough" to push to production, and were by no means diligent about following Rails conventions.
Obviously, this issue is agnostic of what language one chooses. But it certainly leaves a bad taste when there's all this "magic" happening (see: metaprogramming). That magic is what makes working with Rails so productive.
Rails makes it easy to do bad things because of how magical it is. `@post.comments.each { }` when you didn't preload `comments` is bad. This is fixed with `Post.includes(:comments)`.
Similarly, if you avoid its conventions — overriding `table_name` on your model, in your example — and try work against it, rather than with it — it becomes more of a chore than it does a treat.
Like all frameworks, they require a little bit of diligence and care and understanding to really get the full effect. Rails is great because it makes a lot of assumptions at the cost of brainpower, and for the vast majority of things this is good. It's not always the right tool, and it doesn't need to be. But when it is — again, a large majority of web apps are just CRUD — and when it's written with a little bit of care, it's great.
And Rails itself is less monolithic than you think. You can swap out most of the components for other gems, like ActiveRecord vs. DataMapper (though I am not aware of anyone who does this anymore and the level of support for Rails gems generally outclasses everyone else) or remove those components entirely.
Much of the "Rails magic" is inside ActiveSupport, which you can import without bringing in all of Rails proper. Personally I think much of the stuff in ActiveSupport should go core.
FYI see Zeitwerk gem for autoloading improvements.
Also, type hinting is coming to ruby 3.
> magical naming conventions for Rails
That's rails' problem. I don't like it either but nothing to do with ruby.
Seems like half your problem comes from rails.
Rails is neither the language nor the standard library, so the “unless” part seems superfluous.
> These then tend to go out of date. It's pretty common to find well-used gems that haven't been updated in 5, even 10 years. This puts the developer in a tough spot - reinvent the gem/wheel?
If it's open source, why would reinvention rather than forking and assuming maintenance (for one's own needs, not necessarily publicly) be an issue?
Also, I found this statement hilarious:
> Unlike front-end developers, we, Rubyists, usually do not need to “build” code (unless you’re using mruby, Opal, etc.).
It wasn't that long ago that front-end developers used to say the reverse.