Индексирование тегов Taggit с помощью Algolia для Django: у объекта _TaggableManager нет атрибута name
У меня возникли проблемы с использованием интеграции Algolia Django с одной из моих моделей, которая содержит TaggitManager()
поле. В настоящее время я получаю следующую ошибку при запуске этой команды:
$ python manage.py algolia_reindex
AttributeError: '_TaggableManager' object has no attribute 'name'
Я взглянул на документацию Taggit, но я просто не уверен, как именно жениться на методе, описанном в методе поискового индекса Algolia.
index.py:
import django
django.setup()
from algoliasearch_django import AlgoliaIndex
class BlogPostIndex(AlgoliaIndex):
fields = ('title')
settings = {'searchableAttributes': ['title']}
index_name = 'blog_post_index'
models.py:
from taggit.managers import TaggableManager
class Post(models.Model):
...some model fields...
tags = TaggableManager()
3 ответа
Индексировать taggit
теги с вашими полями поста, вам нужно будет предоставить вызываемый элемент, который возвращает теги поста блога в виде списка строк.
Лучший вариант - хранить их как _tags
, который позволит вам фильтровать теги во время запроса.
Ваш PostIndex
будет выглядеть так:
class PostIndex(AlgoliaIndex):
fields = ('title', '_tags')
settings = {'searchableAttributes': ['title']}
index_name = 'Blog Posts Index'
should_index = 'is_published'
Что касается Post
:
class Post(models.Model):
# ...some model fields...
tags = TaggableManager()
def _tags(self):
return [t.name for t in self.tags.all()]
Следуя этим инструкциям, ваши записи будут проиндексированы с соответствующими тегами:
Вы можете проверить taggit
ветка нашего демо Django, которое демонстрирует эти шаги.
Чтобы ответить на мой собственный вопрос. Теперь я передал и модель, и модельный индекс, так что теперь Алголия знает, что индексировать, а что нет. Хотя я хотел бы, чтобы метод Algolia позволял индексировать теги taggit, увы, это, вероятно, невозможно.
Мой файл apps.py:
import algoliasearch_django as algoliasearch
from django.apps import AppConfig
from .index import PostIndex
class BlogConfig(AppConfig):
name = 'blog'
def ready(self):
Post = self.get_model('Post')
algoliasearch.register(Post, PostIndex)
Мой файл index.py:
from algoliasearch_django import AlgoliaIndex
class PostIndex(AlgoliaIndex):
fields = ('title')
settings = {'searchableAttributes': ['title']}
index_name = 'Blog Posts Index'
should_index = 'is_published'
И это должно сработать! Просто, когда вы знаете, как, или после попытки около 10 различных вариантов!
Это может вам помочь, если вы используете django==2+
Проблема в get_queryset()
метод TaggableManager
Откройте с ним файл (мой путь был: Pipenv(project_name)/lib/site-packages/taggit/manager.py
) Найти _TaggableManager
класс и изменить имя метода get_queryset
к get_query_set
Готово. Я хочу, чтобы разработчики taggit исправили это в будущих обновлениях
Так как никто не отвечает, я расскажу вам, как я решил эту проблему, но я должен сказать, что это не хороший путь и не "чистое" решение вообще. Итак, что я сделал, это зашел в "менеджеры taggit" в пакетах сайта (env->lib->python2.x/3.x-> site_packages->taggit-> Manager.py) В файле Manager.py вы будете найдите в строке 394 этот прекрасный фрагмент кода:
def __get__(self, instance, model):
if instance is not None and instance.pk is None:
raise ValueError("%s objects need to have a primary key value "
"before you can access their tags." % model.__name__)
manager = self.manager(
through=self.through,
model=model,
instance=instance,
prefetch_cache_name=self.name, # this is the line I comment out when building the index,
name=self.name #this is the line I added and needs to be commented out after the index is build.
)
return manager
Поэтому, когда я хочу перестроить поисковый индекс, я закомментирую (поместив "#" перед строкой) prefetch_cache_name=self.name,
и заменить его на name=self.name
, Таким образом, построение индекса будет работать. После завершения построения индекса вы должны вернуть все, как было раньше (переключите "#" на name=self.name
снова и уходи prefetch_cache_name=self.name,
опять видно).
Как уже упоминалось, это, вероятно, не лучший способ, но у меня была такая же боль, и это работает для меня. Это занимает одну минуту, когда у вас есть рутина. Поскольку мне приходится перестраивать индекс, может быть, раз в две недели, это не такая уж проблема для меня, но если вам приходится делать это очень часто, это может раздражать...
В любом случае, я надеюсь, что это поможет вам.