Есть ли простой способ заполнить SlugField из CharField?

StackOverflow https://stackoverflow.com/questions/141487

  •  02-07-2019
  •  | 
  •  

Вопрос

class Foo(models.Model):
    title = models.CharField(max_length=20)
    slug = models.SlugField()

Есть ли встроенный способ заставить поле slug автоматически заполняться на основе заголовка?Возможно, в Админке и за ее пределами.

Это было полезно?

Решение

для администрирования в Django 1.0 и выше вам нужно будет использовать

prepopulated_fields = {'slug': ('title',), }

в вашем admin.py

Ваш ключ в словаре prepopulated_fields - это поле, которое вы хотите заполнить, а значение - это кортеж полей, которые вы хотите объединить.

За пределами admin вы можете использовать slugify функционируйте в ваших представлениях.В шаблонах вы можете использовать |slugify Фильтр.

Существует также этот пакет, который позаботится об этом автоматически: https://pypi.python.org/pypi/django-autoslug

Другие советы

За пределами администратора смотрите этот фрагмент django.Положи это в свой .save(), и это будет работать с объектами, созданными программно.Внутри администратора, как уже говорили другие, используйте prepopulated_fields.

Для версии до версии 1.0:

slug = models.SlugField(prepopulate_from=('title',))

должно сработать просто отлично

Для версии 1.0 используйте камфланский

Вы также можете использовать pre_save django signal для заполнения slug вне кода администратора django.Видишь Документация по сигналам Django.

Проверка уникальности Ajax slug также будет полезна, см. Проверка уникальности Слага по мере ввода @ Иррациональное изобилие

автослюнявчик в прошлом это работало у меня довольно хорошо.Хотя я никогда не пробовал использовать его с приложением admin.

Подумал, что хотел бы добавить полный и актуальный ответ с упомянутыми ошибками:

1.Автоматическое заполнение форм в Django Admin

Если вас интересует только добавление и обновление данных в admin, вы могли бы просто использовать предварительно заполненные поля атрибут

class ArticleAdmin(admin.ModelAdmin):
    prepopulated_fields = {"slug": ("title",)}

admin.site.register(Article, ArticleAdmin)

2.Автоматическое заполнение пользовательских форм в шаблонах

Если вы создали свой собственный серверный интерфейс с формами, вы могли бы автоматически заполнять поля, используя либо |слизнуть накладной фильтр или слизывать утилита при сохранении формы (is_valid).

3.Автоматическое заполнение полей slugfields на уровне модели с помощью django-autoslug

Вышеупомянутые решения будут автоматически заполнять slugfield (или любое другое поле) только тогда, когда данные обрабатываются через эти интерфейсы (администратор или пользовательская форма).Если у вас есть API, команды управления или что-то еще, что также манипулирует данными, вам нужно перейти на уровень модели.

django-автоматический сервис предоставляет AutoSlugField-поля, которые расширяют SlugField и позволяют вам установить, какое поле оно должно аккуратно заполнять:

class Article(Model):
    title = CharField(max_length=200)
    slug = AutoSlugField(populate_from='title')

Поле использует сигналы pre_save и post_save для достижения своей функциональности, поэтому, пожалуйста, ознакомьтесь с текстом gotcha в нижней части этого ответа.

4.Автоматическое заполнение полей slugfields на уровне модели путем переопределения функции save()

Последний вариант - реализовать это самостоятельно, что предполагает переопределение метода save() по умолчанию:

    class Article(Model):
        title = CharField(max_length=200)
        slug = SlugField()

    def save(self, *args, **kwargs):
        self.slug = slugify(self.title)
        super(Job, self).save(*args, **kwargs)

ПРИМЕЧАНИЕ:Массовые обновления будут обходить ваш код (включая сигналы)

Это распространенное непонимание новичками в Django.Во-первых, вы должны знать, что сигналы pre_save и post_save напрямую связаны с методом save().Во-вторых, все различные способы выполнения массовых обновлений в Django обходят метод save() для достижения высокой производительности, работая непосредственно на SQL-уровне.Это означает, что для примера модели, используемой в решении 3 или 4 выше:

  • Article.objects.all().update(заголовок='Новое сообщение') будет НЕТ обновите заголовок любой статьи
  • Используя bulk_create - создать или объемное обновление на модели статьи будет НЕТ обновите заголовок любой статьи.
  • Поскольку метод save()-не вызывается, сигналы pre_save или post_save отправляться не будут.

Чтобы выполнять массовые обновления и по-прежнему использовать ограничения на уровне кода, единственным решением является повторение объектов один за другим и вызов его метода save(), который имеет значительно меньшую производительность, чем массовые операции на уровне SQL.Конечно, вы могли бы использовать триггеры в своей базе данных, хотя это совершенно другая тема.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top