简体   繁体   中英

How to index a foreign key CharField using Haystack/Whoosh with Django?

Using prepare_FOO(self, object) method, I'm trying to index a ForeignKey to get the name attribute of my tags (travel, family, ...)

This is my model

class Blog(models.Model):
    title = models.CharField(max_length=500)
    description = models.TextField(blank=True, null=True)
    tag = models.ForeignKey(Tag)
    #...

And in my search_index.py, that's what I have:

class BlogIndex(indexes.SearchIndex, indexes.Indexable):

    text = indexes.CharField(document=True, use_template=True)
    title = indexes.CharField(model_attr='title')
    description = indexes.CharField(model_attr='description')

    tag_name = indexes.CharField()
    def get_model(self):
        return Blog

    def prepare_tag_name(self, obj):
        return obj.tag.name

    def index_queryset(self, using=None):
        return self.get_model().objects.all().select_related('blog__tag')

... And my blog_text:

{{ object.title }}
{{ object.description }}

Any help would be appreciated, thank you!

You only need to add the following in your blog_text file blog_text and rebuild your index. and it works!

{{ object.title }}
{{ object.description }}
{{ object.tag.name }}

you don't need this in your class BlogIndex

tag_name = indexes.CharField()
def prepare_tag_name(self, obj):
    return obj.tag.name

similar answer is here Search over multiple fields a nice explanation is here haystack multiple field search In your index you should define one field with document=True , which is the document haystack will search on. By convention this field is named text. You add extra fields if you plan to do filtering or ordering on their values.

So essentially, the fields you include in your Index class are mainly for sorting or filtering. the search fields are defined in blog_text file.

Another solution is here which is more complicated. haystack - how you display data from multiple models with ForeignKeys?

This is a very old question but given answer does not really answer to the problem (even this is a correct answer anyway) Pompeyo, I think haystack require (required ?) a "model_attr" arg. You should defined your tag_name like this :

tag_name = indexes.CharField(model_attr='tag')

And your prepare_foo method :

def prepare_tag_name(self, obj):
    return '' if not obj.tag else obj.tag.name

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM