Django pattern prefix in URL isn't spreading to included views: Bug or misunderstanding?

StackOverflow https://stackoverflow.com/questions/22737639

  •  23-06-2023
  •  | 
  •  

Question

If I do that:

urlpatterns += patterns('datasets.views',                                  
    url(r'^$', 'home', name="home"),                 
    url(r'^(?P<slug>\w+)/', include(patterns('',#HERE I OMIT THE PREFIX                    
        url(r'^edit/', 'edit_api', name="edit_api"),                                            
    ))),
)

I will get a ``TypeError at /my-slug-name/ 'str' object is not callable

But If I include the prefix a second time, It's working.

urlpatterns += patterns('datasets.views',                                  
    url(r'^$', 'home', name="home"),                 
    url(r'^(?P<slug>\w+)/', include(patterns('datasets.views', #HERE THE PREFIX IS REPEATED                      
        url(r'^edit/', 'edit_api', name="edit_api"),                                            
    ))),
) 

Do I misunderstand how include works ? Should I report this as a bug ?

Was it helpful?

Solution

It's not how include() works, but how patterns works. Without the prefix, edit_api is just a string to pattern, it cannot resolve it to a view. Providing prefix to the first pattern doesn't make it implicitly include in the nested one. The way you are using patterns is a bit ugly. You need to consider each patterns() individually. The prefix is there to make your url configs clean, Consider this -

api_patterns = patterns('datasets.views',
        url(r'^edit/', 'edit_api', name="edit_api"),
        # --------------^ Here edit_api is actually datasets.views.edit_api
        # if you don't want to provide the prefix, you write the full path to the view
        # url(r'^edit/', 'datasets.views.edit_api', name="edit_api"),
)
urlpatterns += patterns('datasets.views',
    url(r'^$', 'home', name="home"),
    url(r'^(?P<slug>\w+)/', include(api_patterns)),
    # ------------------------------^
    # Here include doesn't use the pattern prefix you used 3 lines above
)

The reason is, include is designed to include patterns from various places like apps etc. And each of them might have individual pattern prefix. So to keep things simple, you either provide a pattern prefix and write relative view names or you omit pattern prefix and write complete view path.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top