Applications, Models, Properties, and Circular Imports

I’ve been fighting a problem in my Django project for a while, and the solution I came up with seemed like I was settling for practicality over elegance.  This post is an attempt to rationalize my choices.

First, I love the idea of reusable applications.  I have incorporated a few from open source, including django photologue for the gallery, and the ease of use was amazing.  While I know that my work may not be general enough for public use, I do hope to be able to reuse some code in different parts of my project.  And who knows, maybe something useful to the world will come from it.

So, I divided my project into what seemed to be mostly independent applications, and started coding.

My problem came when I started heavy use of the @property decorator in my models.  Being able to reference a function using the dot notation is very handy (even though they aren’t available in functions that reference fields internally – like the ORM).  However, I found myself referencing models and fields in these two certain applications often, and I ended up with a circular import error.

I’d like to take a moment to point out that my Internet search on circular imports did not yield much help.  Several sites merely pointed out that a circular import was the result of poor coding, but offered no advice.  Finally, one post suggested moving the import to the end of models.py.  This solved the problem in my laptop development environment, but the same code would not run on my Dreamhost server (maybe it is importing in a different order).

Next, I tried to rewrite my property functions to reference the models from the other application only through the ORM – to avoid the need for an import.  This helped on the less complicated functions, but I couldn’t do it for the really useful, complicated ones.

My solution was to combine these two applications together.  The two are obviously very connected, and it was easy to make the case.  However, one of them could have been used in a more general setting, and now it is too specific to be presented to the public.  I guess I’ll have to earn my open source cred with something else.

The important thing here is that I am past this and am once again able to work on features instead of back end problems.

Am I being too theoretical? Are properties not the way to go? The comment section is waiting for your thoughts.