Django 모델 내부에 슬러그 필드 추가

## Django의 Slug Field란?

일반적으로 이미 얻은 데이터를 사용하여 유효한 URL을 생성하는 방법입니다. 예를 들어 기사 제목을 사용하여 URL을 생성합니다. 블로그에 제목이 My First Post이고 기본 키 ID가 2인 게시물이 있다고 가정해 보겠습니다. 이 게시물을 다음과 같이 참조할 수 있습니다.
www.example.com/posts/2
또는 다음과 같은 제목을 참조할 수 있습니다.
www.example.com/posts/my first post
그러나 문제는 공백이 URL에서 유효하지 않기 때문에 보기 흉한 %20으로 대체해야 한다는 것입니다.
www.example.com/posts/my%20first%20post
그러나 의미있는 URL을 해결하지 않습니다. 다른 옵션은 다음과 같습니다.
www.example.com/posts/my-first-post
그래서 민달팽이는 이제 내 첫 번째 게시물입니다. 모든 문자는 소문자로 표시되고 공백은 하이픈 -으로 대체됩니다. 이러한 URL은 매우 SEO 친화적입니다.

Blog Post 모델이 이와 유사하다고 가정합니다.
프로젝트에 Slugify 추가:

STATUS_CHOICES = (
('draft', 'Draft'),
('published', 'Published'),
)class Post(models.Model):
title = models.CharField(max_length = 250)
slug = models.SlugField(max_length = 250, null = True, blank = True)
text = models.TextField()
published_at = models.DateTimeField(auto_now_add = True)
updated = models.DateTimeField(auto_now = True)status = models.CharField(max_length = 10, choices = STATUS_CHOICES,
             default ='draft')class Meta:
 ordering = ('-published_at', )def __str__(self):
 return self.title


이제 제목을 슬러그로 자동 변환하는 방법을 찾아야 합니다. Post 모델의 새 인스턴스가 생성될 때마다 이 스크립트가 트리거되기를 원합니다. 이를 위해 신호를 사용합니다.

참고: settings.py 파일이 저장된 동일한 디렉터리에 새 파일 util.py를 추가합니다.

import string, random
from django.db.models.signals import pre_save
from django.dispatch import receiver
from django.utils.text import slugify
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)
 Klass = instance.__class__
 max_length = Klass._meta.get_field('slug').max_length
 slug = slug[:max_length]
 qs_exists = Klass.objects.filter(slug = slug).exists()

 if qs_exists:
  new_slug = "{slug}-{randstr}".format(
   slug = slug[:max_length-5], randstr = random_string_generator(size = 4))

  return unique_slug_generator(instance, new_slug = new_slug)
 return slug



Django의 신호:



대부분의 경우 모델 인스턴스에 수정 사항이 있는 경우 일부 작업을 실행해야 합니다. Django는 이러한 상황을 처리할 수 있는 우아한 방법을 제공합니다. 신호는 이벤트와 조치를 연관시킬 수 있는 유틸리티입니다. 신호가 호출할 때 실행할 함수를 개발할 수 있습니다.
Post Model이 정의된 posts 앱의 models.py 파일에서 동일한 파일에 다음을 추가합니다.

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


pre_save_receiver 함수는 Post 모델 외부에 별도로 배치해야 합니다.

참고: urls.py에서 경로('posts/', detail)로 세부 경로를 편집합니다. views.py에서 세부 기능을 다음과 같이 편집합니다.

def detail(request, slug):
 q = Post.objects.filter(slug__iexact = slug)
if q.exists():
 q = q.first()
else:
 return HttpResponse('<h1>Post Not Found</h1>')
context = {'post': q
}
return render(request, 'posts/details.html', context)



마지막 단계는 HTML 파일에 링크를 추가하는 것입니다View. 이제 127.0.0.1:8000/posts/title-you-have- added로 이동할 준비가 되었으며 페이지 details.html이 표시됩니다.

Note: You Might have to import the modules into your models.py too.

그게 다야!


이제 블로그가 자동으로 제목을 슬러그로 변환합니다.

좋은 웹페이지 즐겨찾기