This is the sanest Rails design-advice that I've read in a long time.
It counters the misguided "implicit over explicit"-mantra that is both very prevalent in the rails-community and also the source of most problems.
I.e. when you watch any random RailsCast it is usually filled to the rim with obscure incantations and "look how we need only one LoC to perform $excessive_magic"!
The end-result are those deeply entangled "piles of rails" that we've all seen and suffered from. Hopelessly overloaded models and a dense mesh of hidden interdependencies that nobody grasps anymore because many of them are not even explicitly declared.
Personally I've largely given up hope on rails and am waiting for the successor. The rails-team just seems too fixated on digging their rabbit hole ever deeper, rather than re-visiting design mistakes that were made early on.
However, if you are stuck with a Rails-app for the time being (and who isn't..) I'd definitely recommend to follow a pattern like the one outlined in this post. The best way to use Rails nowadays is to steer clear from most of the entrenched practices and packages (e.g. devise and related trainwrecks) and to use it like a library rather than a framework - as much as that is possible.
This eases the migration to the rails-successor when it manifests, and helps preserve the sanity of your older self and his successor.
I agree, although I'd add that the "magic" can be both the best and the worst part of Rails.
The "magic" is what makes Rails extremely fast to prototype with. For me, at least, it's what makes working with Rails fun, since it lets you spend time writing application code instead of repetitive business logic.
It's also what leads a less-experienced developer to get in over their head quite quickly. My only problem with programs like Dev Bootcamp is that complete newbies shouldn't be learning Rails, they should first be building an application with a much-less robust framework so that they truly appreciate (and are wary of) how much "magic" is in a framework like Rails.
As a side note, if you haven't done so already, take a look at express for node.js. You say you're "waiting for the successor", and it seems like you want something less all-encompassing than Rails.
steer clear from most of the entrenched practices and packages (e.g. devise and related trainwrecks)
I agree with your sentiment in general, but what do you suggest to use in place of devise? Surely you're not suggesting to write all the code for handling mail confirmation, password changes etc. yourself?
In fact for serious apps that are expected to grow I do recommend to write the auth yourself. It's not a lot of code, from the second time it's mostly copy/paste, and most importantly you'll fully understand what your code does and when, there will be no guesswork in one of the most important areas of your app.
Furthermore you usually end up heavily customizing whatever auth-code you start with anyway. The shrinkwrapped gems never cover even half of what an app eventually needs. Thus another advantage is that you won't have to reverse engineer devise or authlogic when you arrive at that point (and trust me, you really don't want to look at their code and the SQL they emit).
That all said, in a recent project I've found the 'sorcery'-gem to provide a reasonable baseline for rolling your own. It's one of the first "second generation" Rails-gems that refrain from most of the magic and instead provide a set of primitives that you wire up yourself.
It still suffers from a bit of rails-smell (code-generators...), but overall the level of abstraction looks about right.
So you're one of those guys. I inherited a Rails app that used roll-your-own auth instead of Devise or similar — it added a significant amount of mental overhead, plus a bunch of additional logic for Facebook login.
Task that with another product I just launched: over 100K users, on Devise, no customization needed, and Login with Facebook took 1 additional library, 3 lines of code and 15 minutes.
I used to be the roll-your-own-everything guy, years ago. After maintaining dozens and dozens of Rails apps, I'm not anymore. I'm much happier when logic is pushed into libraries and I can ignore it until it matters.
> In fact for serious apps that are expected to grow I do recommend to write the auth yourself.
No, no, no, just no. If you don't grow, you just wasted time you should have spent shipping real features. If you do grow, refactor in your own authentication later if you have to.
> you'll fully understand what your code does and when
You will, for sure. When you leave for another project and I'm brought into maintain $app, I won't, straight away.
> there will be no guesswork in one of the most important areas of your app.
There is no guesswork with 3rd-party libraries. `bundle open gem-name` is your friend. If you read through the code, you'll understand what it's doing, just like I'll have to read through your code if you roll-your-own library.
One of the major benefits to standardized libraries is that I only have to read the library for Devise or AuthLogic once across a dozen apps. I have to learn each customized solution 100% of the time.
> It still suffers from a bit of rails-smell (code-generators...)
I get the feeling that you work on really large apps with a lot of custom logic, and end up wishing you had complete control over everything. In such situations I'd probably end up agreeing with you 90% of the time if you suggested throwing out a 3rd-party library and rolling your own.
I just strongly disagree that you should start out that way. Your app should have a single selling point: "Schedule my tweets", "Remind me to pay bills", "keep track of my tasks", or whatever. Not "Log in with our unique authentication code."
No app ever became a million dollar company because a developer thought the most important job was to roll their own authentication scheme before they even scored a thousand users.
I think our opinions are not as far apart as it seems.
You are of course right that rolling your own auth won't be the first priority in your initial PoC. Neither is it needed for very simple apps or when you're dead-certain that you won't need more flexibility than the common gems provide.
However in my experience the latter almost never applies in a commercial app. Suddenly you need OmniAuth in addition to devise, and some form of ACLs. Then you grow an API that also needs some sort of auth-tokens. Then there's this other site you want to interface with which needs yet another bridge. Then one day you run that ad on TV and learn the hard way that those extra-lookups devise makes on every request are not free after all...
So what I'm saying is that the design of (in particular) devise and authlogic is just not a very good one to start from if you can already predict that you'll need customizations (beyond templating) in the future.
A frankensteined devise can be a lot harder to understand than a straightforward impl from scratch - but in the end it of course also boils down to who wrote it and whether he wrote it for the first time.
I think Rails developers made some deal with the devil where every line of code they write makes them more his dark Servant in exchange for the ability to write Ruby code. (They rarely know any others. Shoulda negotiated for some Erlang.)
Thereby, they seek to write as few lines of code as possible, at the expense of the sanity of everyone else.