def test_resultset_list_filter_by_date(webapp, test_repository, sample_resultset, jm, test_project): """ test retrieving a resultset list, filtered by a date range """ sample_resultset[3]["push_timestamp"] = utils.to_timestamp("2013-08-09") sample_resultset[4]["push_timestamp"] = utils.to_timestamp("2013-08-10") sample_resultset[5]["push_timestamp"] = utils.to_timestamp("2013-08-11") sample_resultset[6]["push_timestamp"] = utils.to_timestamp("2013-08-12") sample_resultset[7]["push_timestamp"] = utils.to_timestamp("2013-08-13") jm.store_result_set_data(sample_resultset) resp = webapp.get( reverse("resultset-list", kwargs={"project": jm.project}), {"startdate": "2013-08-10", "enddate": "2013-08-13"} ) assert resp.status_int == 200 results = resp.json["results"] meta = resp.json["meta"] assert len(results) == 4 assert set([rs["revision"] for rs in results]) == { u"ce17cad5d554cfffddee13d1d8421ae9ec5aad82", u"7f417c3505e3d2599ac9540f02e3dbee307a3963", u"a69390334818373e2d7e6e9c8d626a328ed37d47", u"f361dcb60bbedaa01257fbca211452972f7a74b2", } assert meta == { u"count": 4, u"enddate": u"2013-08-13", u"filter_params": {u"push_timestamp__gte": 1376118000.0, u"push_timestamp__lt": 1376463600.0}, u"repository": test_project, u"startdate": u"2013-08-10", }
def to_representation(self, job): return { 'build_architecture': job.build_platform.architecture, 'build_os': job.build_platform.os_name, 'build_platform': job.build_platform.platform, 'build_platform_id': job.build_platform_id, 'build_system_type': job.signature.build_system_type, 'end_timestamp': to_timestamp(job.end_time), 'failure_classification_id': job.failure_classification_id, 'id': job.id, 'job_coalesced_to_guid': job.coalesced_to_guid, 'job_group_description': job.job_type.job_group.description, 'job_group_id': job.job_type.job_group_id, 'job_group_name': job.job_type.job_group.name, 'job_group_symbol': job.job_type.job_group.symbol, 'job_guid': job.guid, 'job_type_description': job.job_type.description, 'job_type_id': job.job_type_id, 'job_type_name': job.job_type.name, 'job_type_symbol': job.job_type.symbol, 'last_modified': job.last_modified, 'machine_name': job.machine.name, 'machine_platform_architecture': job.machine_platform.architecture, 'machine_platform_os': job.machine_platform.os_name, 'option_collection_hash': job.option_collection_hash, 'platform': job.machine_platform.platform, 'push_id': job.push_id, 'reason': job.reason, 'ref_data_name': job.signature.name, 'result': job.result, 'result_set_id': job.push_id, 'running_eta': job.running_eta, 'signature': job.signature.signature, 'start_timestamp': to_timestamp(job.start_time), 'state': job.state, 'submit_timestamp': to_timestamp(job.submit_time), 'tier': job.tier, 'who': job.who }
def test_resultset_list_filter_by_date(webapp, initial_data, sample_resultset, jm): """ test retrieving a resultset list, filtered by a date range """ sample_resultset[3]["push_timestamp"] = utils.to_timestamp("2013-08-09") sample_resultset[4]["push_timestamp"] = utils.to_timestamp("2013-08-10") sample_resultset[5]["push_timestamp"] = utils.to_timestamp("2013-08-11") sample_resultset[6]["push_timestamp"] = utils.to_timestamp("2013-08-12") sample_resultset[7]["push_timestamp"] = utils.to_timestamp("2013-08-13") jm.store_result_set_data(sample_resultset) resp = webapp.get( reverse("resultset-list", kwargs={"project": jm.project}), {"startdate": "2013-08-10", "enddate": "2013-08-13"} ) assert resp.status_int == 200 results = resp.json['results'] meta = resp.json['meta'] assert len(results) == 4 assert set([rs["revision"] for rs in results]) == set( ["909f55c626a8", "71d49fee325a", "bb57e9f67223", "668424578a0d"] ) assert(meta == { u'count': 4, u'enddate': u'2013-08-13', u'filter_params': { u'push_timestamp__gte': 1376118000.0, u'push_timestamp__lt': 1376463600.0 }, u'repository': u'test_treeherder', u'startdate': u'2013-08-10'} ) jm.disconnect()
def test_push_list_filter_by_date(client, test_repository, sample_push): """ test retrieving a push list, filtered by a date range """ for (i, datestr) in zip([3, 4, 5, 6, 7], ["2013-08-09", "2013-08-10", "2013-08-11", "2013-08-12", "2013-08-13"]): sample_push[i]['push_timestamp'] = utils.to_timestamp( utils.to_datetime(datestr)) store_push_data(test_repository, sample_push) resp = client.get( reverse("push-list", kwargs={"project": test_repository.name}), {"startdate": "2013-08-10", "enddate": "2013-08-13"} ) assert resp.status_code == 200 # The .json() method of the Django test client doesn't handle unicode properly on # Python 2, so we have to deserialize ourselves. TODO: Clean up once on Python 3. data = json.loads(resp.content) results = data['results'] meta = data['meta'] assert len(results) == 4 assert set([rs["revision"] for rs in results]) == { u'ce17cad5d554cfffddee13d1d8421ae9ec5aad82', u'7f417c3505e3d2599ac9540f02e3dbee307a3963', u'a69390334818373e2d7e6e9c8d626a328ed37d47', u'f361dcb60bbedaa01257fbca211452972f7a74b2' } assert(meta == { u'count': 4, u'enddate': u'2013-08-13', u'filter_params': { u'push_timestamp__gte': 1376092800.0, u'push_timestamp__lt': 1376438400.0 }, u'repository': test_repository.name, u'startdate': u'2013-08-10'} )
def test_push_list_filter_by_date(webapp, test_repository, sample_push): """ test retrieving a push list, filtered by a date range """ for (i, datestr) in zip([3, 4, 5, 6, 7], ["2013-08-09", "2013-08-10", "2013-08-11", "2013-08-12", "2013-08-13"]): sample_push[i]['push_timestamp'] = utils.to_timestamp( utils.to_datetime(datestr)) store_push_data(test_repository, sample_push) resp = webapp.get( reverse("push-list", kwargs={"project": test_repository.name}), {"startdate": "2013-08-10", "enddate": "2013-08-13"} ) assert resp.status_int == 200 results = resp.json['results'] meta = resp.json['meta'] assert len(results) == 4 assert set([rs["revision"] for rs in results]) == { u'ce17cad5d554cfffddee13d1d8421ae9ec5aad82', u'7f417c3505e3d2599ac9540f02e3dbee307a3963', u'a69390334818373e2d7e6e9c8d626a328ed37d47', u'f361dcb60bbedaa01257fbca211452972f7a74b2' } assert(meta == { u'count': 4, u'enddate': u'2013-08-13', u'filter_params': { u'push_timestamp__gte': 1376092800.0, u'push_timestamp__lt': 1376438400.0 }, u'repository': test_repository.name, u'startdate': u'2013-08-10'} )
def list(self, request, project): """ GET method for list of ``resultset`` records with revisions """ # What is the upper limit on the number of resultsets returned by the api MAX_RESULTS_COUNT = 1000 # make a mutable copy of these params filter_params = request.query_params.copy() # This will contain some meta data about the request and results meta = {} # support ranges for date as well as revisions(changes) like old tbpl for param in ["fromchange", "tochange", "startdate", "enddate", "revision"]: v = filter_params.get(param, None) if v: del(filter_params[param]) meta[param] = v try: repository = Repository.objects.get(name=project) except Repository.DoesNotExist: return Response({ "detail": "No project with name {}".format(project) }, status=HTTP_404_NOT_FOUND) pushes = Push.objects.filter(repository=repository).order_by('-time') for (param, value) in meta.iteritems(): if param == 'fromchange': frompush_time = Push.objects.values_list('time', flat=True).get( repository=repository, revision__startswith=value) pushes = pushes.filter(time__gte=frompush_time) filter_params.update({ "push_timestamp__gte": to_timestamp(frompush_time) }) elif param == 'tochange': topush_time = Push.objects.values_list('time', flat=True).get( repository=repository, revision__startswith=value) pushes = pushes.filter(time__lte=topush_time) filter_params.update({ "push_timestamp__lte": to_timestamp(topush_time) }) elif param == 'startdate': pushes = pushes.filter(time__gte=to_datetime(value)) filter_params.update({ "push_timestamp__gte": to_timestamp(to_datetime(value)) }) elif param == 'enddate': real_end_date = to_datetime(value) + datetime.timedelta(days=1) pushes = pushes.filter(time__lte=real_end_date) filter_params.update({ "push_timestamp__lt": to_timestamp(real_end_date) }) elif param == 'revision': # revision can be either the revision of the push itself, or # any of the commits it refers to pushes = pushes.filter(commits__revision__startswith=value) rev_key = "revisions_long_revision" \ if len(meta['revision']) == 40 else "revisions_short_revision" filter_params.update({rev_key: meta['revision']}) for param in ['push_timestamp__lt', 'push_timestamp__lte', 'push_timestamp__gt', 'push_timestamp__gte']: if filter_params.get(param): # translate push timestamp directly into a filter try: value = datetime.datetime.fromtimestamp( float(filter_params.get(param))) except ValueError: return Response({ "error": "Invalid timestamp specified for {}".format( param) }, status=HTTP_400_BAD_REQUEST) pushes = pushes.filter(**{ param.replace('push_timestamp', 'time'): value }) for param in ['id__lt', 'id__lte', 'id__gt', 'id__gte', 'id']: try: value = int(filter_params.get(param, 0)) except ValueError: return Response({ "error": "Invalid timestamp specified for {}".format( param) }, status=HTTP_400_BAD_REQUEST) if value: pushes = pushes.filter(**{param: value}) id_in = filter_params.get("id__in") if id_in: try: id_in_list = [int(id) for id in id_in.split(',')] except ValueError: return Response({"error": "Invalid id__in specification"}, status=HTTP_400_BAD_REQUEST) pushes = pushes.filter(id__in=id_in_list) author = filter_params.get("author") if author: pushes = pushes.filter(author=author) count = int(filter_params.get("count", 10)) if count > MAX_RESULTS_COUNT: msg = "Specified count exceeds api limit: {}".format(MAX_RESULTS_COUNT) return Response({"error": msg}, status=HTTP_400_BAD_REQUEST) # we used to have a "full" parameter for this endpoint so you could # specify to not fetch the revision information if it was set to # false. however AFAIK no one ever used it (default was to fetch # everything), so let's just leave it out. it doesn't break # anything to send extra data when not required. pushes = pushes.select_related('repository').prefetch_related('commits')[:count] serializer = PushSerializer(pushes, many=True) meta['count'] = len(pushes) meta['repository'] = project meta['filter_params'] = filter_params resp = { 'meta': meta, 'results': serializer.data } return Response(resp)
def list(self, request, project, jm): """ GET method for list of ``resultset`` records with revisions """ # What is the upper limit on the number of resultsets returned by the api MAX_RESULTS_COUNT = 1000 # make a mutable copy of these params filter_params = request.query_params.copy() # This will contain some meta data about the request and results meta = {} # support ranges for date as well as revisions(changes) like old tbpl for param in ["fromchange", "tochange", "startdate", "enddate", "revision"]: v = filter_params.get(param, None) if v: del(filter_params[param]) meta[param] = v # create a timestamp lookup based on the from/to change params that may # exist. This means we only make 1 DB query rather than 2, if we have # both a ``fromchange`` and a ``tochange`` value. ts_lookup = jm.get_resultset_all_revision_lookup( [meta[x] for x in ['fromchange', 'tochange'] if x in meta] ) # translate these params into our own filtering mechanism if 'fromchange' in meta: filter_params.update({ "push_timestamp__gte": ts_lookup[meta['fromchange']]["push_timestamp"] }) if 'tochange' in meta: filter_params.update({ "push_timestamp__lte": ts_lookup[meta['tochange']]["push_timestamp"] }) if 'startdate' in meta: filter_params.update({ "push_timestamp__gte": to_timestamp(meta['startdate']) }) if 'enddate' in meta: # add a day because we aren't supplying a time, just a date. So # we're doing ``less than``, rather than ``less than or equal to``. filter_params.update({ "push_timestamp__lt": to_timestamp(meta['enddate']) + 86400 }) if 'revision' in meta: # Allow the user to search by either the short or long version of # a revision. rev_key = "revisions_long_revision" \ if len(meta['revision']) == 40 else "revisions_short_revision" filter_params.update({rev_key: meta['revision']}) meta['filter_params'] = filter_params filter = UrlQueryFilter(filter_params) offset_id = int(filter.pop("id__lt", 0)) count = int(filter.pop("count", 10)) if count > MAX_RESULTS_COUNT: msg = "Specified count exceeds api limit: {}".format(MAX_RESULTS_COUNT) return Response({"error": msg}, status=HTTP_400_BAD_REQUEST) full = filter.pop('full', 'true').lower() == 'true' results = jm.get_result_set_list( offset_id, count, full, filter.conditions ) for rs in results: rs["revisions_uri"] = reverse("resultset-revisions", kwargs={"project": jm.project, "pk": rs["id"]}) meta['count'] = len(results) meta['repository'] = project resp = { 'meta': meta, 'results': results } return Response(resp)
def list(self, request, project, jm): """ GET method for list of ``resultset`` records with revisions """ # make a mutable copy of these params filter_params = request.query_params.copy() # This will contain some meta data about the request and results meta = {} # support ranges for date as well as revisions(changes) like old tbpl for param in ["fromchange", "tochange", "startdate", "enddate", "revision"]: v = filter_params.get(param, None) if v: del(filter_params[param]) meta[param] = v # translate these params into our own filtering mechanism if 'fromchange' in meta: filter_params.update({ "push_timestamp__gte": jm.get_revision_timestamp(meta['fromchange']) }) if 'tochange' in meta: filter_params.update({ "push_timestamp__lte": jm.get_revision_timestamp(meta['tochange']) }) if 'startdate' in meta: filter_params.update({ "push_timestamp__gte": to_timestamp(meta['startdate']) }) if 'enddate' in meta: # add a day because we aren't supplying a time, just a date. So # we're doing ``less than``, rather than ``less than or equal to``. filter_params.update({ "push_timestamp__lt": to_timestamp(meta['enddate']) + 86400 }) if 'revision' in meta: # TODO: modify to use ``short_revision`` or ``long_revision`` fields # when addressing Bug 1079796 # It ends up that we store sometimes long, sometimes short # revisions in the ``revision`` field, depending on the repo/source. # (gaia, for instance). So we must search # for EITHER the short or long, when long is passed in. if len(meta['revision']) > 12: filter_params.update( {"revision__in": "{},{}".format(meta['revision'], meta['revision'][:12])} ) else: filter_params.update({"revision": meta['revision']}) meta['filter_params'] = filter_params filter = UrlQueryFilter(filter_params) offset_id = int(filter.pop("id__lt", 0)) count = min(int(filter.pop("count", 10)), 1000) full = filter.pop('full', 'true').lower() == 'true' results = jm.get_result_set_list( offset_id, count, full, filter.conditions ) for rs in results: rs["revisions_uri"] = reverse("resultset-revisions", kwargs={"project": jm.project, "pk": rs["id"]}) meta['count'] = len(results) meta['repository'] = project resp = { 'meta': meta, 'results': results } return Response(resp)
def list(self, request, project, jm): """ GET method for list of ``resultset`` records with revisions """ # make a mutable copy of these params filter_params = request.QUERY_PARAMS.copy() # This will contain some meta data about the request and results meta = {} # support ranges for date as well as revisions(changes) like old tbpl for param in ["fromchange", "tochange", "startdate", "enddate"]: v = filter_params.get(param, None) if v: del(filter_params[param]) meta[param] = v # translate these params into our own filtering mechanism if 'fromchange' in meta: filter_params.update({ "push_timestamp__gte": jm.get_revision_timestamp(meta['fromchange']) }) if 'tochange' in meta: filter_params.update({ "push_timestamp__lte": jm.get_revision_timestamp(meta['tochange']) }) if 'startdate' in meta: filter_params.update({ "push_timestamp__gte": to_timestamp(meta['startdate']) }) if 'enddate' in meta: # add a day because we aren't supplying a time, just a date. So # we're doing ``less than``, rather than ``less than or equal to``. filter_params.update({ "push_timestamp__lt": to_timestamp(meta['enddate']) + 86400 }) meta['filter_params'] = filter_params filter = UrlQueryFilter(filter_params) offset_id = int(filter.pop("id__lt", 0)) count = min(int(filter.pop("count", 10)), 1000) full = filter.pop('full', 'true').lower() == 'true' results = jm.get_result_set_list( offset_id, count, full, filter.conditions ) for rs in results: rs["revisions_uri"] = reverse("resultset-revisions", kwargs={"project": jm.project, "pk": rs["id"]}) meta['count'] = len(results) meta['repository'] = project resp = { 'meta': meta, 'results': results } return Response(resp)
def get_push_timestamp(self, push): return to_timestamp(push.time)
def to_representation(self, value): return to_timestamp(value.time)
def list(self, request, project, jm): """ GET method for list of ``resultset`` records with revisions """ # make a mutable copy of these params filter_params = request.QUERY_PARAMS.copy() # This will contain some meta data about the request and results meta = {} # support ranges for date as well as revisions(changes) like old tbpl for param in ["fromchange", "tochange", "startdate", "enddate"]: v = filter_params.get(param, None) if v: del (filter_params[param]) meta[param] = v # translate these params into our own filtering mechanism if 'fromchange' in meta: filter_params.update({ "push_timestamp__gte": jm.get_revision_timestamp(meta['fromchange']) }) if 'tochange' in meta: filter_params.update({ "push_timestamp__lte": jm.get_revision_timestamp(meta['tochange']) }) if 'startdate' in meta: filter_params.update( {"push_timestamp__gte": to_timestamp(meta['startdate'])}) if 'enddate' in meta: # add a day because we aren't supplying a time, just a date. So # we're doing ``less than``, rather than ``less than or equal to``. filter_params.update( {"push_timestamp__lt": to_timestamp(meta['enddate']) + 86400}) meta['filter_params'] = filter_params filter = UrlQueryFilter(filter_params) offset_id = filter.pop("id__lt", 0) count = min(int(filter.pop("count", 10)), 1000) full = filter.pop('full', 'true').lower() == 'true' with_jobs = filter.pop('with_jobs', 'true').lower() == 'true' debug = request.QUERY_PARAMS.get('debug', None) objs = jm.get_result_set_list(offset_id, count, full, filter.conditions) if with_jobs: results = self.get_resultsets_with_jobs(jm, objs, full, {}, debug) else: for rs in objs: rs["revisions_uri"] = reverse("resultset-revisions", kwargs={ "project": jm.project, "pk": rs["id"] }) results = objs meta['count'] = len(results) meta['repository'] = project resp = { 'meta': meta, 'results': results, } if with_jobs: resp['job_property_names'] = JOB_PROPERTY_RETURN_KEY return Response(resp)
def get_duration(submit_time, start_time, end_time): endtime = end_time if to_timestamp(end_time) else datetime.datetime.now() starttime = start_time if to_timestamp(start_time) else submit_time seconds = max((endtime - starttime).total_seconds(), 60) return max(round(seconds / 60), 1)
def list(self, request, project): """ GET method for list of ``push`` records with revisions """ # What is the upper limit on the number of pushes returned by the api MAX_PUSH_COUNT = 1000 # make a mutable copy of these params filter_params = request.query_params.copy() # This will contain some meta data about the request and results meta = {} # support ranges for date as well as revisions(changes) like old tbpl for param in [ "fromchange", "tochange", "startdate", "enddate", "revision" ]: v = filter_params.get(param, None) if v: del filter_params[param] meta[param] = v try: repository = Repository.objects.get(name=project) except Repository.DoesNotExist: return Response( {"detail": "No project with name {}".format(project)}, status=HTTP_404_NOT_FOUND) pushes = Push.objects.filter(repository=repository).order_by('-time') for (param, value) in iteritems(meta): if param == 'fromchange': frompush_time = Push.objects.values_list( 'time', flat=True).get(repository=repository, revision__startswith=value) pushes = pushes.filter(time__gte=frompush_time) filter_params.update( {"push_timestamp__gte": to_timestamp(frompush_time)}) elif param == 'tochange': topush_time = Push.objects.values_list('time', flat=True).get( repository=repository, revision__startswith=value) pushes = pushes.filter(time__lte=topush_time) filter_params.update( {"push_timestamp__lte": to_timestamp(topush_time)}) elif param == 'startdate': pushes = pushes.filter(time__gte=to_datetime(value)) filter_params.update( {"push_timestamp__gte": to_timestamp(to_datetime(value))}) elif param == 'enddate': real_end_date = to_datetime(value) + datetime.timedelta(days=1) pushes = pushes.filter(time__lte=real_end_date) filter_params.update( {"push_timestamp__lt": to_timestamp(real_end_date)}) elif param == 'revision': # revision can be either the revision of the push itself, or # any of the commits it refers to pushes = pushes.filter(commits__revision__startswith=value) rev_key = "revisions_long_revision" \ if len(meta['revision']) == 40 else "revisions_short_revision" filter_params.update({rev_key: meta['revision']}) for param in [ 'push_timestamp__lt', 'push_timestamp__lte', 'push_timestamp__gt', 'push_timestamp__gte' ]: if filter_params.get(param): # translate push timestamp directly into a filter try: value = datetime.datetime.fromtimestamp( float(filter_params.get(param))) except ValueError: return Response( { "detail": "Invalid timestamp specified for {}".format(param) }, status=HTTP_400_BAD_REQUEST) pushes = pushes.filter( **{param.replace('push_timestamp', 'time'): value}) for param in ['id__lt', 'id__lte', 'id__gt', 'id__gte', 'id']: try: value = int(filter_params.get(param, 0)) except ValueError: return Response( { "detail": "Invalid timestamp specified for {}".format(param) }, status=HTTP_400_BAD_REQUEST) if value: pushes = pushes.filter(**{param: value}) id_in = filter_params.get("id__in") if id_in: try: id_in_list = [int(id) for id in id_in.split(',')] except ValueError: return Response({"detail": "Invalid id__in specification"}, status=HTTP_400_BAD_REQUEST) pushes = pushes.filter(id__in=id_in_list) author = filter_params.get("author") if author: pushes = pushes.filter(author=author) try: count = int(filter_params.get("count", 10)) except ValueError: return Response({"detail": "Valid count value required"}, status=HTTP_400_BAD_REQUEST) if count > MAX_PUSH_COUNT: msg = "Specified count exceeds api limit: {}".format( MAX_PUSH_COUNT) return Response({"detail": msg}, status=HTTP_400_BAD_REQUEST) # we used to have a "full" parameter for this endpoint so you could # specify to not fetch the revision information if it was set to # false. however AFAIK no one ever used it (default was to fetch # everything), so let's just leave it out. it doesn't break # anything to send extra data when not required. pushes = pushes.select_related('repository').prefetch_related( 'commits')[:count] serializer = PushSerializer(pushes, many=True) meta['count'] = len(pushes) meta['repository'] = project meta['filter_params'] = filter_params resp = {'meta': meta, 'results': serializer.data} return Response(resp)
def list(self, request, project, jm): """ GET method for list of ``resultset`` records with revisions """ # make a mutable copy of these params filter_params = request.query_params.copy() # This will contain some meta data about the request and results meta = {} # support ranges for date as well as revisions(changes) like old tbpl for param in [ "fromchange", "tochange", "startdate", "enddate", "revision" ]: v = filter_params.get(param, None) if v: del (filter_params[param]) meta[param] = v # create a timestamp lookup based on the from/to change params that may # exist. This means we only make 1 DB query rather than 2, if we have # both a ``fromchange`` and a ``tochange`` value. ts_lookup = jm.get_resultset_all_revision_lookup( [meta[x] for x in ['fromchange', 'tochange'] if x in meta]) # translate these params into our own filtering mechanism if 'fromchange' in meta: filter_params.update({ "push_timestamp__gte": ts_lookup[meta['fromchange']]["push_timestamp"] }) if 'tochange' in meta: filter_params.update({ "push_timestamp__lte": ts_lookup[meta['tochange']]["push_timestamp"] }) if 'startdate' in meta: filter_params.update( {"push_timestamp__gte": to_timestamp(meta['startdate'])}) if 'enddate' in meta: # add a day because we aren't supplying a time, just a date. So # we're doing ``less than``, rather than ``less than or equal to``. filter_params.update( {"push_timestamp__lt": to_timestamp(meta['enddate']) + 86400}) if 'revision' in meta: # Allow the user to search by either the short or long version of # a revision. rev_key = "revisions_long_revision" \ if len(meta['revision']) == 40 else "revisions_short_revision" filter_params.update({rev_key: meta['revision']}) meta['filter_params'] = filter_params filter = UrlQueryFilter(filter_params) offset_id = int(filter.pop("id__lt", 0)) count = min(int(filter.pop("count", 10)), 1000) full = filter.pop('full', 'true').lower() == 'true' results = jm.get_result_set_list(offset_id, count, full, filter.conditions) for rs in results: rs["revisions_uri"] = reverse("resultset-revisions", kwargs={ "project": jm.project, "pk": rs["id"] }) meta['count'] = len(results) meta['repository'] = project resp = {'meta': meta, 'results': results} return Response(resp)