Hey Malcolm,

Thank you very much for your thoughts on those questions!

I will definitely be referring to your advice when I'm writing this
thing.

I had been thinking about those questions when I was on spring break
(about a week or so) and couldn't seem to reach a conclusion, but, I
think I'll be a bit better off now.

Thank you again.

-Sean

On Apr 12, 11:16 pm, Malcolm Tredinnick <malc...@pointy-stick.com>
wrote:
> On Sun, 2009-04-12 at 20:41 -0700, Sean Neilan wrote:
> > I'm building a large web application & I'm trying to figure out ways
> > to organize my business logic (just the queries). I figure I should
> > either put all my queries inside Model functions or ModelManager
> > functions. I've searched all over the internet for documentation on
> > where the business logic goes, but, didn't find what I was looking
> > for.
>
> > I have a couple questions:
>
> Opinions vary a bit on these sorts of things. What follows are mine...
>
>
>
> > 1) Should Model methods not contain any queries? Only calculations
> > based on the attributes of that model. Much like
> >http://docs.djangoproject.com/en/dev/topics/db/models/#id4
>
> When you have a model instance, it represents a single row in the
> database. Methods on a Python class instance tend to act on that
> instance, so it makes sense to have model methods act on the particular
> data for that instance, not be more general.
>
> Now, it could well be that "acting on the instance" really means
> "related to that instance" and does other queries to pull in
> information. For example, my blog code currently has the world's lamest
> tagging system (a very simple tag model with a name and a pointer to
> itself for the parent) and I have methods on the model that are "get all
> the descendents of this instance" and "get the ancestors of this
> instance". They are methods that are specific to the instance at hand.
>
>
>
> > 2) Is it a good idea to encapsulate _all_ queries as methods inside of
> > a manager class? Thus making it slightly easier to reuse queries.
>
> Abstracting everything to the n-th degree can often make code a lot
> harder to read, so curb your enthusiasm a little bit here.
>
> Model managers tend to be a good place to put methods that act on the
> collection of model instances. For example, using my lame tag example
> again, a method to query all the tags matching a particular name prefix.
> The documentation describes these as table-level methods, which tends to
> be the way I've thought of them over the years.
>
> For genuinely reusable query fragments, I find myself writing normal
> Python functions that accept a queryset as an argument. Then they aren't
> tied to any particular model, although I have some implicit contract
> with myself (as the user of those functions) that they querysets I pass
> in will be for objects that, say, have a "title" attribute so I can
> filter on the title.
>
> I will point out that some people like using classmethods for this sort
> of stuff. For model class-level queries -- the table-level stuff -- I
> find this looks very odd in code. It's one of those cases of not looking
> like almost all other Django code.
>
> In general, I'm fairly negative about classmethods in Python, though,
> since they're fairly unnecessary as Python already has ample namespacing
> capabilities. Other languages have classmethod equivalents because
> they're namespacing isn't as good. So you won't see me using classmethod
> style operations and there's swearing involved when I have to use
> somebody else's code that does (something that's happening in a
> side-project at the moment -- the other app is making my code looking
> fugly!)
>
>
>
> > 3) Is it a bad thing if a query inside of a Manager function uses
> > filter() to join with or even return another object type/list? This
> > obviously couples the query to the name of a model, but, also couples
> > the manager to an object that it doesn't manage. (The object that it
> > doesn't manage being joined in the query.)
>
> Trying to frame things as "bad" or "good" is probably not going to help
> very much, since it leads to discussions about what is really bad or
> good. I personally don't write things like that, since I like my
> managers methods on model X to returns things about model X.
>
> However, I'm not a slave to "everything must be in a class" and normal
> Python module-level functions are my good friends. So if I'm got
> something that is related to model X and returns something that isn't a
> queryset, I'll often just make it a function. The import statements
> elsewhere in the code namespace it usefully and using the function is
> pretty easy and not overly verbose.
>
> > 4) Also, Is it possible for a ModelManager object to gain access to
> > request.user so that the objects returned depend on who's logged in?
>
> Not unless you pass it in. Models are completely independent of the
> request/response cycle. They are only concerned with the persistent
> storage of data (not even necessarily business rules -- they're not the
> capital-M, MVC models). Request.user isn't a data storage thing.
>
> > Perhaps, if this is not a good design pattern (coupling the
> > authentication mechanisms to the ModelManager), should I simply take a
> > User object as a parameter on the ModelManager functions?
>
> I prefer that approach. Explicit over implicit. Some people shove
> request.user into threadlocals and use that. I personally don't like it,
> but I've used it from time to time as a last resort (or because the
> existing code did). The problem there is that threadlocals are one of
> the least "local" style of objects in all of Python, so it's not too
> hard to end up with a real mess there.
>
> Hopefully that gives you some ideas to think about. Realise there isn't
> (and shouldn't be) a unique solution to most of these questions. The
> above are what has worked for me over a few years and probably a few
> hundred thousand lines of Django application coding and reading, but I
> might not be doing things the same way others do.
>
> Regards,
> Malcolm
--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups 
"Django users" group.
To post to this group, send email to django-users@googlegroups.com
To unsubscribe from this group, send email to 
django-users+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/django-users?hl=en
-~----------~----~----~----~------~----~------~--~---

Reply via email to