mirror of
https://github.com/fergalmoran/dss.git
synced 2025-12-22 09:38:18 +00:00
235 lines
9.8 KiB
Python
Executable File
235 lines
9.8 KiB
Python
Executable File
from django.conf.urls import url
|
|
from django.core.exceptions import ObjectDoesNotExist
|
|
from django.core.paginator import Paginator, InvalidPage
|
|
from django.db.models import Count
|
|
from django.http import Http404
|
|
from django.template.loader import render_to_string
|
|
from tastypie import fields
|
|
from tastypie.authorization import Authorization
|
|
from tastypie.constants import ALL_WITH_RELATIONS
|
|
from tastypie.exceptions import ImmediateHttpResponse
|
|
from tastypie.fields import ToOneField
|
|
from tastypie.http import HttpGone, HttpUnauthorized
|
|
from tastypie.utils import trailing_slash
|
|
|
|
from spa.api.v1.BackboneCompatibleResource import BackboneCompatibleResource
|
|
from spa.api.v1.CommentResource import CommentResource
|
|
from spa.api.v1.ActivityResource import ActivityResource
|
|
from spa.models.mix import Mix
|
|
from spa.models.show import Show
|
|
|
|
|
|
class MixResource(BackboneCompatibleResource):
|
|
comments = fields.ToManyField('spa.api.v1.CommentResource.CommentResource',
|
|
'comments', null=True, full=True)
|
|
favourites = fields.ToManyField('spa.api.v1.UserResource.UserResource',
|
|
'favourites', related_name='favourites',
|
|
full=False, null=True)
|
|
likes = fields.ToManyField('spa.api.v1.UserResource.UserResource',
|
|
'likes', related_name='likes',
|
|
full=False, null=True)
|
|
genres = fields.ToManyField('spa.api.v1.GenreResource.GenreResource',
|
|
'genres', related_name='genres',
|
|
full=True, null=True)
|
|
|
|
class Meta:
|
|
queryset = Mix.objects.filter(is_active=True)
|
|
user = ToOneField('UserResource', 'user')
|
|
always_return_data = True
|
|
detail_uri_name = 'slug'
|
|
excludes = ['is_active', 'waveform-generated']
|
|
post_excludes = ['comments']
|
|
filtering = {'comments': ALL_WITH_RELATIONS,
|
|
'genres': ALL_WITH_RELATIONS,
|
|
'favourites': ALL_WITH_RELATIONS,
|
|
'likes': ALL_WITH_RELATIONS,
|
|
'title': ALL_WITH_RELATIONS,
|
|
'slug': ALL_WITH_RELATIONS, }
|
|
authorization = Authorization()
|
|
|
|
def prepend_urls(self):
|
|
return [
|
|
url(r"^(?P<resource_name>%s)/search%s$" %
|
|
(self._meta.resource_name, trailing_slash()),
|
|
self.wrap_view('get_search'),
|
|
name="api_get_search"),
|
|
url(r"^(?P<resource_name>%s)/(?P<id>[\d]+)/$" %
|
|
self._meta.resource_name, self.wrap_view('dispatch_detail'),
|
|
name="api_dispatch_detail"),
|
|
url(r"^(?P<resource_name>%s)/random/$" %
|
|
self._meta.resource_name, self.wrap_view('dispatch_random'),
|
|
name="api_dispatch_random"),
|
|
url(r"^(?P<resource_name>%s)/(?P<slug>[\w\d-]+)/$" %
|
|
self._meta.resource_name,
|
|
self.wrap_view('dispatch_detail'), name="api_dispatch_detail"),
|
|
url(r"^(?P<resource_name>%s)/(?P<slug>\w[\w/-]*)/comments%s$" %
|
|
(self._meta.resource_name, trailing_slash()),
|
|
self.wrap_view('get_comments'), name="api_get_comments"),
|
|
url(r"^(?P<resource_name>%s)/(?P<slug>\w[\w/-]*)/activity%s$" % (
|
|
self._meta.resource_name, trailing_slash()),
|
|
self.wrap_view('get_activity'), name="api_get_activity"),
|
|
]
|
|
|
|
def dispatch_random(self, request, **kwargs):
|
|
kwargs['pk'] = \
|
|
self._meta.queryset.values_list('pk', flat=True).order_by('?')[0]
|
|
return self.get_detail(request, **kwargs)
|
|
|
|
def get_comments(self, request, **kwargs):
|
|
try:
|
|
basic_bundle = self.build_bundle(request=request)
|
|
obj = self.cached_obj_get(bundle=basic_bundle,
|
|
**self.remove_api_resource_names(kwargs))
|
|
except ObjectDoesNotExist:
|
|
return HttpGone()
|
|
|
|
child_resource = CommentResource()
|
|
return child_resource.get_list(request, mix=obj)
|
|
|
|
def get_activity(self, request, **kwargs):
|
|
try:
|
|
basic_bundle = self.build_bundle(request=request)
|
|
obj = self.cached_obj_get(bundle=basic_bundle,
|
|
**self.remove_api_resource_names(kwargs))
|
|
except ObjectDoesNotExist:
|
|
return HttpGone()
|
|
|
|
child_resource = ActivityResource()
|
|
return child_resource.get_list(request, mix=obj)
|
|
|
|
def obj_create(self, bundle, **kwargs):
|
|
if 'is_featured' not in bundle.data:
|
|
bundle.data['is_featured'] = False
|
|
|
|
if 'download_allowed' not in bundle.data:
|
|
bundle.data['download_allowed'] = False
|
|
|
|
bundle.data['user'] = bundle.request.user.get_profile()
|
|
ret = super(MixResource, self).obj_create(
|
|
bundle,
|
|
user=bundle.request.user.get_profile(),
|
|
uid=bundle.data['upload-hash'],
|
|
extension=bundle.data['upload-extension'])
|
|
|
|
return ret
|
|
|
|
def obj_update(self, bundle, **kwargs):
|
|
#don't sync the mix_image, this has to be handled separately
|
|
bundle.data.pop('mix_image', None)
|
|
|
|
ret = super(MixResource, self).obj_update(bundle, bundle.request)
|
|
|
|
bundle.obj.update_favourite(bundle.request.user,
|
|
bundle.data['favourited'])
|
|
bundle.obj.update_liked(bundle.request.user,
|
|
bundle.data['liked'])
|
|
|
|
return ret
|
|
|
|
def apply_sorting(self, obj_list, options=None):
|
|
orderby = options.get('order_by', '')
|
|
if orderby == 'latest':
|
|
obj_list = obj_list.order_by('-id')
|
|
elif orderby == 'toprated':
|
|
obj_list = obj_list.annotate(
|
|
karma=Count('activity_likes')).order_by('-karma')
|
|
elif orderby == 'mostplayed':
|
|
obj_list = obj_list.annotate(
|
|
karma=Count('activity_plays')).order_by('-karma')
|
|
elif orderby == 'mostactive':
|
|
obj_list = obj_list.annotate(
|
|
karma=Count('comments')).order_by('-karma')
|
|
elif orderby == 'recommended':
|
|
obj_list = obj_list.annotate(
|
|
karma=Count('activity_likes')).order_by('-karma')
|
|
|
|
return obj_list
|
|
|
|
def apply_filters(self, request, applicable_filters):
|
|
semi_filtered = super(MixResource, self) \
|
|
.apply_filters(request, applicable_filters) \
|
|
.filter(waveform_generated=True)
|
|
|
|
f_user = request.GET.get('user', None)
|
|
|
|
if request.GET.get('stream'):
|
|
if request.user.is_anonymous():
|
|
raise ImmediateHttpResponse(
|
|
HttpUnauthorized("Only logged in users have a stream")
|
|
)
|
|
semi_filtered = semi_filtered.filter(
|
|
user__in=request.user.get_profile().following.all())
|
|
if request.GET.get('for_show'):
|
|
semi_filtered = semi_filtered.filter(show__isnull=True)
|
|
|
|
if f_user is not None:
|
|
semi_filtered = semi_filtered.filter(user__slug=f_user)
|
|
|
|
if len(applicable_filters) == 0:
|
|
semi_filtered = semi_filtered.filter(is_featured=True)
|
|
|
|
return semi_filtered
|
|
|
|
def dehydrate_mix_image(self, bundle):
|
|
return bundle.obj.get_image_url(size="160x110")
|
|
|
|
def dehydrate(self, bundle):
|
|
bundle.data['waveform_url'] = bundle.obj.get_waveform_url()
|
|
bundle.data['user_name'] = bundle.obj.user.get_nice_name()
|
|
bundle.data['user_profile_url'] = bundle.obj.user.get_absolute_url()
|
|
bundle.data['user_profile_image'] = \
|
|
bundle.obj.user.get_small_profile_image()
|
|
bundle.data['item_url'] = '/mix/%s' % bundle.obj.slug
|
|
bundle.data['download_allowed'] = bundle.obj.download_allowed
|
|
bundle.data['favourite_count'] = bundle.obj.favourites.count()
|
|
|
|
bundle.data['play_count'] = bundle.obj.activity_plays.count()
|
|
bundle.data['download_count'] = bundle.obj.activity_downloads.count()
|
|
bundle.data['like_count'] = bundle.obj.activity_likes.count()
|
|
|
|
bundle.data['tooltip'] = render_to_string('inc/player_tooltip.html',
|
|
{'item': bundle.obj})
|
|
bundle.data['comment_count'] = bundle.obj.comments.count()
|
|
|
|
bundle.data['liked'] = bundle.obj.is_liked(bundle.request.user)
|
|
|
|
if bundle.request.user.is_authenticated():
|
|
bundle.data['can_edit'] = bundle.request.user.is_staff or \
|
|
bundle.obj.user_id == bundle.request.user.get_profile().id
|
|
else:
|
|
bundle.data['can_edit'] = False
|
|
|
|
if bundle.request.user.is_authenticated():
|
|
bundle.data['favourited'] = bundle.obj.favourites.filter(
|
|
user=bundle.request.user).count() != 0
|
|
else:
|
|
bundle.data['favourited'] = False
|
|
|
|
return bundle
|
|
|
|
def get_search(self, request, **kwargs):
|
|
self.method_check(request, allowed=['get'])
|
|
self.is_authenticated(request)
|
|
self.throttle_check(request)
|
|
|
|
# Do the query.
|
|
sqs = Mix.objects.filter(title__icontains=request.GET.get('q', ''))
|
|
paginator = Paginator(sqs, 20)
|
|
|
|
try:
|
|
page = paginator.page(int(request.GET.get('page', 1)))
|
|
except InvalidPage:
|
|
raise Http404("Sorry, no results on that page.")
|
|
|
|
objects = []
|
|
|
|
for result in page.object_list:
|
|
bundle = self.build_bundle(obj=result, request=request)
|
|
bundle = self.full_dehydrate(bundle)
|
|
objects.append(bundle)
|
|
|
|
object_list = {'objects': objects, }
|
|
|
|
self.log_throttled_access(request)
|
|
return self.create_response(request, object_list)
|