Hacker News new | past | comments | ask | show | jobs | submit login

The problem is the ORM requires you to know its language, the underlying SQL for that database, as well as how the ORM maps to that underlying language.

It’s the worst of a leaky abstraction, and like 3x the conceptual overhead. But it’s better because … something something OOP.




> It’s the worst of a leaky abstraction, and like 3x the conceptual overhead.

I really think you hit the nail on the head with this sentence. For example, another commenter said "But the same SQL fanboys who believe every developer ought to memorize tri-state truth tables..."

Yes, I think it's fine to argue that the boolean logic with respect to NULL in SQL is a pain in the ass. But ORMs certainly don't hide that from you! The ways DBs treat nulls is a fundamental part of nearly all RDBMSes - if you don't understand that, you're (eventually) going to have a bad time. All ORMs really do is make it harder to understand when you may need to take special null logic into account.


Exactly. As unfortunate as those warts are, you can't pretend them away. Might as well be able to see them clearly.


“Something something OOP” - you reach enlightenment once you realize OOP itself is an anti-pattern.


OOP isn't an anti pattern, OOP as a _silver bullet_ is an anti pattern. Almost all of my programs end up to some degree multi paradigm of OOP, functional, and procedural.


I call that post-OOP. The outcome might even be very, very similar to what you might have implemented as an OOP believer, but the assessment has flipped: instead of assuming yourself "did I use enough OOPisms" you ask yourself "could it be better with less?"


I'm not gonna argue against OOP in general here, but in the context of ORMs, some of the most important characteristics of OOP (encapsulation and inheritance, especially) are the source of many anti-patterns.

Keeping methods that operate on data together with the data is the biggest problem with the Active Record pattern, and it's good that some new ORMs (like Ecto) are inspiring others to try other alternatives. Those alternatives invariably eschew the exaggerated use of method/data coupling and code-sharing via inheritance/mixins, among other things. They are either functional or procedural.

Not to mention that a lot of OOP-heavy codebases are already replacing a lot of OOP-heavy ORM code with procedural (Services) or functional-inspired ("Railway Oriented Programming", Trailblazer operations).

Sure, there are still classes being used. But I don't think it's fair to call "just using classes" as really as OOP, when they're used as structs, and especially in languages that make class usage mandatory.


I dunno I've been using rails for over a decade, its lovely.


I never said otherwise. “Lovely” and “the ORM is free of issues” is orthogonal. The issues are why there’s a lot of different alternative ways of writing domain logic in Rails.


I agree. We'd be better off with data structures and functions that work on those data structures, and packages/modules/namespaces (with public/private exposing) to do encapsulation.

OOP comes with the banana-gorilla-jungle problem, which I consider the fundamental issue with it.

https://softwareengineering.stackexchange.com/questions/3687...


> It’s the worst of a leaky abstraction

This stems from the fact that SQL itself is a very leaky abstraction: each RDBMS implementation is different, and the common part is shallow. There is no way to optimize a query in an RDBMS-agnostic way.

Actually, ORMs are worse than a leaky abstraction: they border on cheating! They actually abstract the easy, boring part away, but they run with their tail between their legs as soon as the issue becomes interesting.


> They actually abstract the easy, boring part away, but they run with their tail between their legs as soon as the issue becomes interesting.

This is the biggest offense, IMO. It's not just that ORMs are a leaky abstraction, it's that they're just a bad abstraction--leaky or not. We don't really need an abstraction to make easy things easier, and we certainly don't need/want an abstraction that makes hard things even harder!

There's a famous quote that always comes to mind when I encounter stuff like this. I've seen it attributed to several people, so I'm not positive, but I think it was from Larry Wall: "Make easy things easy and hard things possible."


Exactly!

The analogy I use is SQL is like two-wheeled motorbike - fast, nimble, elegant. Yes, it may be dangerous. Yes, you may need to wear a helmet. Yes, it cannot carry too much load. But it gets you very quickly very far, if you have skill!

Now, ORM sees deficiencies and presents you... two motorbikes welded together side-by-side by some iron sticks. They call it a "car". Four wheels are better than two, right? Two engines can push more load, right? No helmet needed, right?

But does it really become a "car", or it is just has most of deficiencies of the motorbike plus some spectacular new ones? And no benefits of a car whatsoever?

I run away in disgust.


Django's magic double underscored kwargs DSL is so awful.

Just let me write SQL, please. God I miss JDBI


> Django's magic is so awful.

Fixed that for you.

Granted, I haven't dove deep into Django, but from what I learned scratching the surface, it's slow, bloated, utterly un-Pythonic, and I just don't understand how it got so popular. Yeah, it's the most batteries-included web app framework for Python, but it just sucks to use.


Yep, fair fix. My favourite bit of Django metabollocks is when they mix in an override for __new__ on models, that won't let you instantiate an instance if the Django "app" the model or any of its dependencies belong to isn't in django.settings.INSTALLED_APPs.

I'm sure they had a good reason for doing this at some point, but I'm just trying to write a unit test for something that consumes a FooModel, no DB access needed, just a small test that doesn't involve starting up all the Django bits, but Django says no, best I can do is creating an SQLite DB and creating all your tables on it.

I have toyed with doing my own metabollocks hackery to circumvent this, but it just makes everything even more fragile.

(Oh, the Django test-runner won't discover tests that aren't subclasses of a Django test class, so no writing a unittest.TestCase for you! You might need Django in it!)




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: