[英]Django models slug mixin with unique constraint handling
I have three models Book
, Part
, Chapter
, in my models.py
that uses the SlugField
.我在使用
SlugField
的models.py
中有三个模型Book
、 Part
、 Chapter
。
For the Book
class, I have written a slug handler in the custom save
method that checks if an object exists with the slug
.对于
Book
class,我在自定义save
方法中编写了一个 slug 处理程序,用于检查 object 是否与slug
一起存在。 And when it does, it makes it unique by appending a count
to it.当它这样做时,它会通过向它附加一个
count
来使其独一无二。
How do I rewrite the block inside Book
's to SlugMixin
so that I can use for the rest of the models?如何将
Book
中的块重写为SlugMixin
以便我可以用于模型的 rest?
models.py
...
class SlugMixin(models.Model):
slug = models.SlugField(max_length=50, unique=True)
class Meta:
abstract = True
class Book(models.Model):
title = models.CharField(max_length=50)
slug = models.SlugField(max_length=50, unique=True)
def save(self, *args, **kwargs):
if not self.pk and not self.slug:
slug = slugify(self.title, allow_unicode=True)
slug_exists = True
counter = 1
self.slug = slug
while slug_exists:
try:
slug_exists = Book.objects.get(slug=slug)
if slug_exists:
slug = self.slug + '_' + str(counter)
counter += 1
except Book.DoesNotExist:
self.slug=slug
break
class Part(models.Model):
book = models.ForeignKey(Book, on_delete=models.CASCADE, related_name='parts')
title = models.CharField(max_length=30)
slug = models.SlugField(max_length=30, unique=True)
class Chapter(models.Model):
part = models.ForeignKey(Part, on_delete=models.CASCADE, related_name='chapters')
title = models.CharField(max_length=40)
slug = models.SlugField(max_length=40, unique=True)
...
How about this这个怎么样
SLUG_LENGTH = 50
def get_unique_slug(model_instance):
slugify_title = slugify(model_instance.title, allow_unicode=True)
if len(slugify_title) > SLUG_LENGTH:
slug = slugify_title[:SLUG_LENGTH]
else:
slug = slugify_title
slug_copy = slug
num = 1
while model_instance.__class__.objects.filter(slug=slug).exists():
number_attached_slug = '{}-{}'.format(slug_copy, num)
if len(number_attached_slug) > SLUG_LENGTH:
trimmed_slug = slug_copy[:-(num + 1)] # adding 1 because there is hyphen in the slug
slug = '{}-{}'.format(trimmed_slug, num)
else:
slug = number_attached_slug
num += 1
return slug
class SomeLogicKlass:
def save(self, *args, **kwargs):
if not self.slug:
self.slug = get_unique_slug(self)
super().save(*args, **kwargs)
def __str__(self):
return self.slug
class Book(SomeLogicKlass, models.Model):
...
class Part(SomeLogicKlass, models.Model):
...
Note: make sure the value of SLUG_LENGTH
is same as the max_length
of models.SlugField(...)
注意:确保
SLUG_LENGTH
的值与models.SlugField(...)
的max_length
相同
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.