Skip to content

Instantly share code, notes, and snippets.

@dcramer
Created June 23, 2011 09:59
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save dcramer/09980581b269a45f60a2 to your computer and use it in GitHub Desktop.
Save dcramer/09980581b269a45f60a2 to your computer and use it in GitHub Desktop.
class PostSort(models.Model):
"""
You must create the following index by hand:
create index forums_postsort_sort on forums_postsort (thread_id, sort, value, depth);
>>> post_ids = PostSort.objects.filter(thread_id=2, sort=0)\
.order_by('value', 'depth')\
.values_list('post_id', flat=True)[:25]
"""
SORT_CHOICES = dict((
(0, 'newest'),
(1, 'oldest'),
))
thread_id = models.PositiveIntegerField()
post_id = models.PositiveIntegerField()
depth = models.PositiveIntegerField(default=1)
sort = models.PositiveIntegerField(choices=SORT_CHOICES.items())
value = NumericArrayField()
class Meta:
unique_together = (('thread_id', 'post_id', 'sort'),)
@classmethod
def get_sort(cls, flat, sort, instance):
try:
ts = float(instance.date.strftime('%s.%f'))
except ValueError:
ts = 0
if sort == 0: # oldest
value = [ts]
elif sort == 1: # newest
value = [-ts]
else:
raise ValueError
value.append(instance.parent_post_id or instance.pk)
return value
@classmethod
def post_save(cls, instance, created=True, **kwargs):
if not switches.for_forum('post_sort_paginator_index', instance.forum):
return
if not created:
return
for flat in (True, False):
for sort in cls.SORT_CHOICES.keys():
if instance.parent_post_id and not flat:
value = cls.objects.filter(
thread_id=instance.thread_id,
post_id=instance.parent_post_id,
sort=sort,
).values_list('value', flat=True).get()
else:
value = []
this_value = cls.get_sort(flat, sort, instance)
depth = 1
if instance.parent_post_id:
depth += len(value) / len(this_value)
cls.objects.create(
thread_id=instance.thread_id,
post_id=instance.pk,
sort=sort,
depth=depth,
value=value + this_value,
)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment