

Shortcomings in the Django ORM and a look at Peewee, a lightweight alternative - coleifer
http://charlesleifer.com/blog/shortcomings-in-the-django-orm-and-a-look-at-peewee-a-lightweight-alternative/

======
shuzchen
Is there a reason you didn't use SQLAlchemy, as that's what I turn to when I'm
not in Django-land. It's also closer to a competitor to Peewee than Django's
ORM is.

I mean, when I use Django, even though I could switch out the ORM, I'd be
ditching a lot of freebies (integration with auth, forms, South, all the
reusable apps in the wild). Thus, you really don't see people ripping out the
Django ORM except in the very extreme cases. It also explains why it'll be
really difficult to switch out the Django ORM, as there is just so much
integration to rewrite and legacy apps to lose.

If I wanted/needed/was willing to reinvent all of that, I'd probably start
with a smaller framework (like Tornado, Flask) where the only stable game - so
far - is SQLAlchemy.

Thus, I don't think it's in your benefit to consider/advertise yourself a
lightweight alternative to the Django ORM, as there aren't many folks looking
for an alternative (and even though most people aren't 100% happy with
Django's ORM the bar to competing is really high). Your users are most likely
not using Django, and deciding between Peewee and SQLAlchemy.

~~~
mattdawson
I've looked at Peewee (albeit before the rewrite mentioned here), and, more to
the point, my first response was "why didn't he write this _in_ SQLAlchemy."
SQLAlchemy is a battle hardened toolkit that's both broad and deep. At its
lowest levels, its a toolkit _for building ORMs_. IMHO, if you're doing SQL in
python, there's almost no reason to look anywhere else. That's how good it is.

------
ashray
I wouldn't call these shortcomings of Django's ORM as much as design decisions
that may or may not be agreed with. I've found Django's ORM pretty useful in
that, it reduces the amount of typing you need to do.
BlogPost.objects.filter() is shorter than "SELECT * from BlogPost where ....".
Of-course, Django's ORM gives you a few ways to implement complex SQL
statements. However, ORMs in my opinion aren't that great with dealing with
complexity. They can take you only so far before you realize that "Hey, I
could write this query much better manually". At the point where you need
that, ORMs are pretty useless. There've been times that I've manually enforced
database level constraints and enforced uniqueness on 2 or more columns with a
replace statement to avoid race conditions. An ORM wouldn't be able to handle
that kind of thing. Not at the moment anyway.

But that brings me to my point. Do we need to keep running after abstraction
(ORMs) when the needs become sufficiently complex and the abstraction ends up
making things more opaque ?

ORMs are great for simple stuff. Raw SQL rules for complex stuff. Yes/No ?

~~~
pplante
I agree with you about the use of raw SQL when a query gets too complex. Often
I find that the ORM is capable of expressing a query I have in mind, but it
might do it inefficiently. Sometimes I will rewrite this using SQL. Usually
what limits me is how much post processing I will have to do on the results to
attain my desired goal.

Often I avoid putting any work on my db beyond filtering and grouping of
results. Its typically much easier to scale out app/web servers than it is to
scale out databases to support a heavy query workload.

------
mburst
I think it's cool that you wrote a solution to a problem that was affecting
you. For me I've been using the Django ORM for quite some time now and have
been able to use it in 99% of situations. For the situations where it doesn't
fit Django allows me to drop down to raw SQL for a solution.

I do think it would be nice though to get rid of things like Q objects and
move to something else. Maybe something such as objects.filter(text='hello' |
text='goodbye'). Either way Q objects are extremely useful and the Django
documentation does a nice job of showing how to use all the queryset features.

~~~
mattdeboard
It's weird to single out Q objects since they're the most functional,
composable, flexible parts of that API. Passing around clauses lets you do
things like build a list of them then reduce that list into a single query via
|. There's a lot of mental gymnastics involved in learning Django's ORM but
the Q object is not something I would ever suggest as a candidate for
dismissal.

------
Nate75Sanders
As far as I can tell, neither this article nor Alex Gaynor's slides mention
another big problem with Django's ORM: lack of support for composite primary
keys and composite foreign keys.

We were layering some web stuff on top of a database that worked flawlessly
with SQLAlchemy and ended up changing our data model to accommodate Django's
weaknesses.

------
megaman821
I mostly like Peewee's API, it is like a mixture of the Django ORM and
SQLAlchemy. It could be a sane path forward for Django's ORM, but backwards
compatibility will still be hard. Django's ORM has a lot in it's API that are
hard to or shouldn't really be replicated like extra(), annotate(),
aggregate(), F(), exclude(), raw().

