user1836831
user1836831

Reputation: 575

What is @permalink and get_absolute_url in Django?

What is @permalink and get_absolute_url in Django? When and why to use it?

Please a very simple example (a real practical example). Thanks

Upvotes: 43

Views: 25604

Answers (4)

Mark Chackerian
Mark Chackerian

Reputation: 23582

As of 2013, the Django documentation discouraged use of the permalink decorator and encouraged use of reverse() in the body of the get_absolute_url method. By 2015, the permalink decorator seemed to have vanished without a trace from the Django documentation, and it was finally removed in Django version 2.1 in 2018.

So, for a standard DRY way to create a permanent link to a single object view, use get_absolute_url() in your model like this:

from django.db import models
from django.urls import reverse
#  NOTE: pre Django 1.10+ this is "from django.core.urlresolvers import reverse"


class MyModel(models.Model):
    slug = models.SlugField()

    def get_absolute_url(self):
        return reverse('mymodel_detail', args=(self.slug,))

and then have an entry in urls.py that points to your view:

url(r'^(?P<slug>[-\w\d\_]+)/$',
    MyModelDetailView.as_view(),
    name='mymodel_detail'),

Another nice feature that you get from using get_absolute_url is when using the admin app to view the object-editing page, a “View on site” button links directly to this URL.

Upvotes: 95

Mehdi Zare
Mehdi Zare

Reputation: 1381

A better approach is to declare a name for your app in urls.py and then refer to that instead of hard coding anything:

in urls.py:

app_name = 'my_app'

urlpatterns = [
    path('blogs/<int:slug>', blog.views.blog_detail, name='mymodel_detail'),
    ]

and in models.py:

from django.urls import reverse


class BlogPost(models.Model):
    name = modelsCharField()
    slug = models.SlugField(...)

    def get_absolute_url(self):
        return ('my_app:mymodel_detail, args=[self.slug,])

Upvotes: 0

C.K.
C.K.

Reputation: 5528

in Django 2.1 The django.db.models.permalink() decorator is removed.

source

Upvotes: 6

Timmy O&#39;Mahony
Timmy O&#39;Mahony

Reputation: 53999

@permalink is a python decorator, while get_absolute_url is a method on a django model.

Both are concerned with allowing you to reverse the URL for a particular object and should be used together. They are used anytime you need to provide a link to a particular object or want to display that object's specific URL (if it has one) to the user

You could simply write your get_absolute_url method to return a hard coded string, but this wouldn't adhere to Django's philosophy of DRY (don't repeat yourself). Instead, there is the @permalink to make things more flexible.

If you read the docs on the subject you will see how they relate to each other. the @permalink decorator hooks into django's URLconf's backend, allowing you to write much more portable code by using named url patterns. This is preferable to just using get_absolute_url on it's own: your code becomes much DRYer as you don't have to specify paths.

class BlogPost(models.Model):
    name = modelsCharField()
    slug = models.SlugField(...)

    @permalink
    def get_absolute_url(self):
        return ("blog-detail", [self.slug,])

and in urls.py

    ...
    url(r'/blog/(?P<slug>[-w]+)/$', blog.views.blog_detail, name="blog-detail")

Upvotes: 38

Related Questions