Q 객체
를 잘 활용하여 오늘 작성한 코드를 다듬어 보았다.
0:8000/films?genre=드라마&sort=random
0:8000/films?country=미국&sort=random
0:8000/films?time=100&sort=time-ascending
중간에 화면이 바뀌는 것은 새로고침을 하였을 때이다.
확실히 Q 객체
를 하니 오후에 짠 코드보다 몇 배로 간결해졌다.
from django.http import JsonResponse
from django.views import View
from django.db.models import Q
from films.models import Film
class FilmView(View):
def get(self, request):
try:
genre = request.GET.get('genre', None)
country = request.GET.get('country', None)
running_time_min = request.GET.get('time', None)
sort = request.GET.get('sort')
offset = int(request.GET.get('offset', 0))
limit = int(request.GET.get('limit', 10))
q = Q()
if genre:
q &= Q(genres__name = genre)
if country:
q &= Q(countries__name = country)
if running_time_min:
q &= Q(running_time_min__lte = int(running_time_min))
sort_set = {
'random' : '?',
'ascending-time' : 'running_time_min',
'descending-time' : '-running_time_min',
'score' : 'rate_set__score'
}
order_key = sort_set.get(sort, 'id')
films = Film.objects.filter(q).order_by(order_key)[offset:offset+limit]
results = [{
'id' : film.id,
'name' : film.name,
'release_date' : film.release_date.year,
'image_url' : film.image_url,
'country' : [country.name for country in film.countries.all()],
'running_time_min' : film.running_time_min,
} for film in films]
return JsonResponse({'results': results}, status = 200)
except KeyError:
return JsonResponse({'message': 'KEY_ERROR'}, status = 400)
order_by
또한 변수로 들어갈 수 있기에, order_key
라는 변수로 두고, default
값을 id
로 두었다.order_key
는 다시 sort_set
이라는 딕셔너리에 들어 있는데, 쿼리로 입력한 sort
의 값이 sort_set
의 키에 있으면 해당 값을 받는다.order_by
에 '?'
를 넣으면 랜덤 정렬!-
를 앞에 내림차순으로 정렬이다. 제외 시 오름차순이 기본