如何在Django Web应用程序中添加Slug 编辑编辑2(更多说明)

这是问题所在:我正试图“刷新”我的Django网络博客,因此,我不想拥有/post/2/的那条链接就像我的标题一样(像这样:{{1} }

这里有一些代码,我已经尝试了几件事,但是没有任何效果:

models.py

/post/today-is-friday

urls.py

from django.db import models
from django.utils import timezone
from django.contrib.auth.models import User
from django.urls import reverse
from django.template.defaultfilters import slugify

class Post(models.Model):
    title = models.CharField(max_length=200)
    content = models.TextField()
    date_posted = models.DateTimeField(default=timezone.now)
    author = models.ForeignKey(User,on_delete=models.CASCADE)
    categories = models.ManyToManyField('Category',related_name='posts')
    image = models.ImageField(upload_to='images/',default="images/None/no-img.jpg")
    slug= models.SlugField(max_length=500,unique=True,null=True,blank=True)

    def save(self,*args,**kwargs):
        self.url= slugify(self.title)
        super(Post,self).save(*args,**kwargs)

    def __str__(self):
        return self.title

    def get_absolute_url(self):
        return reverse('post-detail',kwargs={'pk': self.pk})


class Category(models.Model):
    name = models.CharField(max_length=20)

    def __str__(self):
        return self.name

user_posts.html (用于访问博客本身)

from django.urls import path
from django.conf.urls import include,url
from . import views
from .views import PostListView,PostDetailView,PostCreateView,PostUpdateView,PostDeleteView,UserPostListView

urlpatterns = [
    #Blog section
    path("",PostListView.as_view(),name='blog-home'),path("user/<str:username>",UserPostListView.as_view(),name='user-posts'),path("<slug:slug>/",PostDetailView.as_view(),name='post-detail'),path("post/new/",PostCreateView.as_view(),name='post-create'),path("<slug:slug>/update/",PostUpdateView.as_view(),name='post-update'),path("<slug:slug>/delete/",PostDeleteView.as_view(),name='post-delete'),path("about/",views.about,name="blog-about"),path("<category>/",views.blog_category,name="blog_category"),]

post_form.html (用于创建新帖子,创建帖子后无法重定向)

{% extends 'blog/base.html' %}
{% block content %}
  <h1 class='mb-3'>Post by {{ view.kwargs.username }} ({{ page_obj.paginator.count }})</h1>
  {% for post in posts %}
    <article class="media content-section">
      <img class="rounded-circle article-img" src="{{ post.author.profile.image.url }}" alt="">
      <div class="media-body">
        <div class="article-metadata">
          <a class="mr-2 author_title" href="{% url 'user-posts' post.author.username %}">@{{ post.author }}</a>
          <small class="text-muted">{{ post.date_posted|date:"N d,Y" }}</small>
          <div>
            <!-- category section -->
            <small class="text-muted">
              Categories:&nbsp;
              {% for category in post.categories.all %}
              <a href="{% url 'blog_category' category.name %}">
                {{ category.name }}
              </a>&nbsp;
              {% endfor %}
            </small>
          </div>


        </div>
        <h2><a class="article-title" href="{% url 'post-detail' post.id %}">{{ post.title }}</a></h2>
        <p class="article-content">{{ post.content|slice:200 }}</p>
      </div>
    </article>
    {% endfor %}
{% endblock content %}
jiangpingshe 回答:如何在Django Web应用程序中添加Slug 编辑编辑2(更多说明)

如果要在保存之前更改slug字段的值,则可以使用信号。

django的slugify方法也位于django.utils.text而非django.template.defaultfilters中。

urls.py

# ...
path('post/<slug:slug>/',PostDetailView.as_view(),name='post-detail'),# ...

models.py

from django.db.models.signals import pre_save
from django.dispatch import receiver
from django.utils.text import slugify
import string


class Post(models.Model):
    # ...
    slug= models.SlugField(max_length=500,unique=True,null=True,blank=True)
    # do not override save method here 


def random_string_generator(size=10,chars=string.ascii_lowercase + string.digits):
    return ''.join(random.choice(chars) for _ in range(size))


def unique_slug_generator(instance,new_slug=None):
    if new_slug is not None:
        slug = new_slug
    else:
        slug = slugify(instance.title)

    class_ = instance.__class__
    qs_exists = class_.objects.filter(slug=slug).exists()
    if qs_exists:
        new_slug = f"{slug}-{random_string_generator(size=5)}"
        return unique_slug_generator(instance,new_slug=new_slug)
    return slug


@receiver(pre_save,sender=Post)
def post_pre_save_receiver(sender,instance,*args,**kwargs):
    if not instance.slug:
        instance.slug = unique_slug_generator(instance)

这两个函数unique_slug_generatorrandom_string_generator共同保证您在两个帖子上不会有相同的意思,即使这些帖子的标题相同! (它将在末尾添加一些随机生成的字符串)

编辑

user_posts.html的html模板中,替换

<h2><a class="article-title" href="{% url 'post-detail' post.id %}">{{ post.title }}</a></h2>

使用

<h2><a class="article-title" href="{% url 'post-detail' post.slug %}">{{ post.title }}</a></h2>

此外,在post_form视图(不是模板)中,您应像这样覆盖get_success_url

    def get_success_url(self):
        return reverse('post-detail',kwargs={'slug': self.object.slug})

编辑2(更多说明)

首先,每个帖子都需要一个网址,我们将其实现为:

path('post/<slug:slug>/',

接下来,您应该将以前的链接更改为post-detail。这些包括您的1)模板链接和2)视图/模型中的链接:

在模板中,无论您有{% url 'post-detail' post.pk %},都应将其更改为{% url 'post-detail' post.slug %}

在视图/模型中,您应该更改reverse('post-detail',kwargs={'pk': self.pk}) tp reverse('post-detail',kwargs={'slug': self.slug})(而不是self.object.slug

本文链接:https://www.f2er.com/3116347.html

大家都在问