使用get_absolute_url()时出现NoReverseMatch错误

1 投票
2 回答
792 浏览
提问于 2025-04-18 07:02

我正在尝试使用 get_absolute_url 来遵循 DRY 原则(即“不要重复自己”)。如果我直接从 slug(一个简短的标识符)构建链接,代码运行得很好。虽然看起来很丑,结构也很乱,但至少能工作……

所以我想用 get_absolute_url() 正确地实现这个功能,但我遇到了一个 NoReverseMatch 的错误,使用下面的代码时就出现了这个问题。我知道这肯定是某种新手错误,但我已经在文档和论坛上翻来覆去找了好几天,还是搞不定这个问题!

我遇到的错误是:

NoReverseMatch at /calendar
Reverse for 'pEventsCalendarDetail' with arguments '()' and keyword arguments '{u'slug': u'Test-12014-05-05'}' not found. 0 pattern(s) tried: []
Request Method: GET
Request URL:    http://127.0.0.1:8000/calendar
Django Version: 1.6
Exception Type: NoReverseMatch
Exception Value:    
Reverse for 'pEventsCalendarDetail' with arguments '()' and keyword arguments '{u'slug': u'Test-12014-05-05'}' not found. 0 pattern(s) tried: []
Exception Location: /usr/local/lib/python2.7/site-packages/django/core/urlresolvers.py in _reverse_with_prefix, line 429
Python Executable:  /usr/local/opt/python/bin/python2.7
Python Version: 2.7.6

使用以下的 models.py 代码片段:

@python_2_unicode_compatible
class Event(models.Model):
    eventName = models.CharField(max_length=40)
    eventDescription = models.TextField()
    eventDate = models.DateField()
    eventTime = models.TimeField()
    eventLocation = models.CharField(max_length=60, null=True, blank=True)
    creationDate = models.DateField(auto_now_add=True)
    eventURL = models.URLField(null=True, blank=True)
    slug = AutoSlugField(populate_from=lambda instance: instance.eventName + str(instance.eventDate),
                         unique_with=['eventDate'],
                         slugify=lambda value: value.replace(' ','-'))

    @models.permalink
    def get_absolute_url(self):
        from django.core.urlresolvers import reverse
        path = reverse('pEventsCalendarDetail', (), kwargs={'slug':self.slug})
        return "http://%s" % (path)

完整的 urls.py 文件:

from django.conf.urls import patterns, include, url

from django.contrib import admin
admin.autodiscover()

urlpatterns = patterns('',
    # Examples:
    url(r'^$', 'electricphoenixfll.views.home', name='home'),
    url(r'^home$', 'electricphoenixfll.views.home', name='home'),
    url(r'^calendar$', 'electricphoenixfll.views.calendar', name='calendar'),
    url(r'^forum$', 'electricphoenixfll.views.forum', name='forum'),
    url(r'^donate$', 'electricphoenixfll.views.donate', name='donate'),
    url(r'^donate_thanks$', 'electricphoenixfll.views.donate_thanks', name='donate_thanks'),
    url(r'^what_is_fll$', 'electricphoenixfll.views.what_is_fll', name='what_is_fll'),
    url(r'^core_values$', 'electricphoenixfll.views.core_values', name='core_values'),
    url(r'^follow_the_phoenix$', 'electricphoenixfll.views.follow_the_phoenix', name='follow_the_phoenix'),
    url(r'^followEnter/$', 'electricphoenixfll.views.followEnter', name='followEnter'),
    url(r'^followList/$', 'electricphoenixfll.views.followList', name='followList'),
    url(r'^about_us$', 'electricphoenixfll.views.about_us', name='about_us'),
    url(r'^calendarDetail/(?P<slug>[\w-]+)/$', 'phoenixEvents.views.calendarDetail', name='pEventsCalendarDetail'),

    url(r'^admin/', include(admin.site.urls)),
)

2 个回答

1

不要同时使用 permalink 装饰器和 reverse() 函数。它们的作用是一样的。建议去掉装饰器,因为它已经不再推荐使用了。

1

reverse()这个函数的第二个位置参数是urlconf参数:

reverse(viewname[, urlconf=None, args=None, kwargs=None, current_app=None])

要让它正常工作,可以使用关键字参数来设置args

path = reverse('pEventsCalendarDetail', args=(), kwargs={'slug':self.slug})

或者,根本就不设置args

path = reverse('pEventsCalendarDetail', kwargs={'slug':self.slug})

撰写回答