0

I'm using haystack and I follow the tutorials. I add haystack to settings, migrate, then I create this

class PostIndex(indexes.SearchIndex, indexes.Indexable):
  text = indexes.CharField(document=True, use_template=True)
  publish = indexes.DateTimeField(model_attr='publish')

  def get_model(self):
      return Post

  def index_queryset(self, using=None):
      """Used when the entire index for model is updated."""
      return self.get_model().objects.all()

in templates I create

search/indexes/blog/post_text.txt

and add this to it

{{ object.title }}
{{ object.tags.all|join:", " }}
{{ object.body }}

in my views.py i add

from haystack.query import SearchQuerySet

then in a view function

def post_search(request):

  form = request.GET.get('q')
  results = SearchQuerySet().models(Post).filter(content=form)
  # count total results
  total_results = results.count()
  template = 'blog/post/search.html',
  context = {
      'form': form,
      'results': results,
      'total_results': total_results

  }
  return render(request, template, context)

and in a search template

{% for result in results %}
  <p>{{result.publish}}</p>

  <a href="{{ result.object.get_absolute_url }}">{{ result.object.title }}</a>

but the only thing that gets returned is the publish. If I inspect the a element the href is blank. if I do this

{{results}}

I get something like this

[blog.post.pk(2)] or something like that

these will not work

 {{result.object.publish}}<br>

but this will {{result.publish}}

and to access these

 {{result.object.body}}<br>
 {{result.object.title}}<br>
 {{result.object.slug}}<br>

I go back and add this

 class PostIndex(indexes.SearchIndex, indexes.Indexable):
  text = indexes.CharField(document=True, use_template=True)
  publish = indexes.DateTimeField(model_attr='publish')

  # added this
  title = indexes.CharField(model_attr='title')
  body = indexes.CharField(model_attr='body')
  slug = indexes.CharField(model_attr='slug')

  def get_model(self):
      return Post

  def index_queryset(self, using=None):
      """Used when the entire index for model is updated."""
      return self.get_model().objects.all()

which is nothing like the the tutorials say What am I doing wrong?

I get my results buy doing this

result.title

not

result.object.title

and from the tutorials I watch and read all they do is this

 class PostIndex(indexes.SearchIndex, indexes.Indexable):
  text = indexes.CharField(document=True, use_template=True)
  publish = indexes.DateTimeField(model_attr='publish')

  def get_model(self):
      return Post

  def index_queryset(self, using=None):
      """Used when the entire index for model is updated."""
      return self.get_model().objects.all()

but can access everything like this

result.object.title
result.object.publish
result.object.get_absolute_url

they are obviously accessing the whole object but for some reason I am not. any guidance or a suggestion to something that I could possibly see like a video would be appreciated. I really don't get why I'm not accessing the whole object.

Edit :

my models.py

class Post(models.Model):

STATUS_CHOICES = (
   ('draft', 'Draft'),
   ('published', 'Published'),
)
title = models.CharField(max_length=250)
slug = models.SlugField(max_length=250,
                        unique_for_date='publish')
image = models.ImageField(null=True, blank=True)
author = models.ForeignKey(User,
                           related_name='blog_posts')
body = models.TextField()
publish = models.DateTimeField(default=timezone.now)
created = models.DateTimeField(auto_now_add=True)
updated = models.DateTimeField(auto_now=True)
status = models.CharField(max_length=10,
                          choices=STATUS_CHOICES,
                          default='draft')
video = models.BooleanField(default=False)
video_path = models.CharField(max_length=320,
                              null=True,
                              blank=True,)

class Meta:
    ordering = ('-publish',)

def __str__(self):
    return self.title

def get_absolute_url(self):
        return reverse('blog:post_detail',
                       args=[self.publish.year,
                             self.publish.strftime('%m'),
                             self.publish.strftime('%d'),
                             self.slug])

objects = models.Manager() # The default manager.
published = PublishedManager() # Our custom manager.
tags = TaggableManager()

I'm using

Django==1.9.4
django-crispy-forms==1.6.0
django-haystack==2.4.1
django-taggit==0.18.0
Pillow==3.1.1
pysolr==3.4.0
pytz==2016.1
requests==2.9.1
python 3.5

Ive updated and rebuilt my schema and I followed Mike Hibbert and read a book called django by example follwed them verbatim and still cant figure it out. Is this some kinf=d of bug?

losee
  • 2,190
  • 3
  • 29
  • 55
  • I think you have to define this method on your model. Haystack can't guess the url by itself, so you should build the url with `reverse()` and return it. – Antoine Fontaine Mar 20 '16 at 20:07
  • Thanks for the response. None of the videos I've watched have done what you said nor any of the tuts i've read – losee Mar 20 '16 at 20:27
  • After a quick search, I've found someone with the same problem as you: http://stackoverflow.com/questions/27968892/haystack-whoosh-result-object-get-absolute-url-is-not-working. I guess the documentation needs an update. – Antoine Fontaine Mar 20 '16 at 20:40
  • thanks again for the response. This is what I already had defined def get_absolute_url(self): return reverse('blog:post_detail', args=[self.publish.year, self.publish.strftime('%m'), self.publish.strftime('%d'), self.slug]) – losee Mar 20 '16 at 21:27
  • @AntoineFontaine I added my models.py so you could see what I already had. maybe you can see the problem – losee Mar 20 '16 at 21:33

2 Answers2

0

after researching this for about 3 day now, I have come across information that django 1.9 isnt fully supported so this may be the issue hopefully. Hope this spares someone the anguish that I've went through.

losee
  • 2,190
  • 3
  • 29
  • 55
0

I had a similar or probably even the same problem.

For some reason, reverse lookups within my get_absolute_url method failed after I'd accessed the HaystackSearchQueryset containing the results. It seemed as though the reverse mechanism didn't have any patterns to analyze ("...patterns tried: []").

Your suggestion pointing towards Django 1.9 incompatibilities helped me a lot as I just installed the lastest master and everything seems to work just fine now.Django 1.9 compatibility was added here by Claude Peroz. Yay :-)

Samuel Blattner
  • 303
  • 4
  • 10