views:

83

answers:

2

I'm trying to use one app to satisfy multiple url paths. That is to say, I want the url /blog/ and /job/ to use the same app, but different views. There are a number of ways to do this I'm sure, but none of them seem very clean. Here's what I'm doing right now

# /urls.py
urlpatterns = patterns("",
    (r"^(blog|job)/", include("myproject.myapp.urls")),
)

# /myapp/urls.py
urlpatterns = patterns("myproject.myapp.views",
    (r"^(?P<id>\d+)/edit/$",    "myproject.myapp.views.edit"),
    (r"^(?P<id>\d+)/delete/$",  "myproject.myapp.views.delete"),
    (r"^(?P<id>\d+)/update/$",  "myproject.myapp.views.update"),
    (r"^insert/$",              "myproject.myapp.views.insert"),
)

urlpatterns += patterns("",
    (r"^(?P<object_id>\d+)/$",  "django.views.generic.list_detail.object_detail", info_dict, "NOIDEA-detail"),
    (r"^/$",                    "django.views.generic.list_detail.object_list",   info_dict, "NOIDEA-community"),
)

# /myapp/views.py
def edit(request, type, id):
    if (type == "blog"):
        editBlog(request, id)
    else (type == "job")
        editJob(request, id)

def editBlog(request, id):
    # some code

def editJob(request, id):
    # some code

I've ended up breaking all of this into multiple model and view files to make the code cleaner but the above example doesn't account for things like reverse url lookups which breaks all of my template {% url %} calls.

Originally, I had blogs, jobs, events, contests, etc all living in their own apps, but all of their functionality is so similar, that it didn't make sense to leave it that way, so I attempted to combine them... and this happened. You see those "NOIDEA-detail" and "NOIDEA-community" url names on my generic views? Yeah, I don't know what to use there :-(

A: 

Looks pretty good to me. If you want reverse lookups, just have a different reverse name for each url format, even if they end up pointing to the same view.

Christian Oudard
+2  A: 

You can have more than one modules defining URLs. You can have /blog/ URLs in myapp/urls.py and /job/ URLs in myapp/job_urls.py. Or you can have two modules within a urls subpackage.

Alternatively you can manually prefix your url definitions:

urlpatterns = patterns("myproject.myapp.views",
    (r"^jobs/(?P<id>\d+)/edit/$",    "myproject.myapp.views.edit"),
    (r"^jobs/(?P<id>\d+)/delete/$",  "myproject.myapp.views.delete"),
    (r"^jobs/(?P<id>\d+)/update/$",  "myproject.myapp.views.update"),
    (r"^jobs/insert/$",              "myproject.myapp.views.insert"),
)

urlpatterns += patterns("",
    (r"^blog/(?P<object_id>\d+)/$",  "django.views.generic.list_detail.object_detail", info_dict, "NOIDEA-detail"),
    (r"^blog/$",                    "django.views.generic.list_detail.object_list",   info_dict, "NOIDEA-community"),
)

And then mount them as:

urlpatterns = patterns("",
    (r"", include("myapp.urls")),
)

Personally I would go for more RESTful URL definitions though. Such as blog/(?P<post_id>\d+)/edit/$.

muhuk