nodes: 0, module; 1, function_definition; 2, function_name:process_params; 3, parameters; 4, block; 5, identifier:request; 6, default_parameter; 7, default_parameter; 8, default_parameter; 9, expression_statement; 10, if_statement; 11, expression_statement; 12, if_statement; 13, expression_statement; 14, for_statement; 15, if_statement; 16, if_statement; 17, return_statement; 18, identifier:standard_params; 19, identifier:STANDARD_QUERY_PARAMS; 20, identifier:filter_fields; 21, None; 22, identifier:defaults; 23, None; 24, comment:"""Parse query params.
  
      Parses, validates, and converts query into a consistent format.
  
      :keyword request: the bottle request
      :keyword standard_params: query params that are present in most of our
          (opinionated) APIs (ex. limit, offset, sort, q, and facets)
      :keyword filter_fields: list of field names to allow filtering on
      :keyword defaults: dict of params and their default values
      :retuns: dict of query params with supplied values (string or list)
      """; 25, not_operator; 26, block; 27, assignment; 28, identifier:unfilterable; 29, block; 30, assignment; 31, identifier:key; 32, attribute; 33, block; 34, comparison_operator:'sort' in request.query; 35, block; 36, comparison_operator:'q' in request.query; 37, block; 38, identifier:query_fields; 39, identifier:filter_fields; 40, expression_statement; 41, identifier:unfilterable; 42, parenthesized_expression; 43, expression_statement; 44, identifier:query_fields; 45, boolean_operator; 46, identifier:request; 47, identifier:query; 48, if_statement; 49, string; 50, attribute; 51, expression_statement; 52, expression_statement; 53, expression_statement; 54, string; 55, attribute; 56, expression_statement; 57, expression_statement; 58, expression_statement; 59, assignment; 60, binary_operator:set(request.query.keys()) - set(filter_fields) -
                      set(standard_params); 61, call; 62, identifier:defaults; 63, dictionary; 64, comparison_operator:key in filter_fields; 65, comment:# turns ?netloc=this.com&netloc=that.com,what.net into; 66, comment:# {'netloc': ['this.com', 'that.com', 'what.net']}; 67, block; 68, string_content:sort; 69, identifier:request; 70, identifier:query; 71, assignment; 72, assignment; 73, assignment; 74, string_content:q; 75, identifier:request; 76, identifier:query; 77, assignment; 78, assignment; 79, assignment; 80, identifier:filter_fields; 81, list; 82, binary_operator:set(request.query.keys()) - set(filter_fields); 83, call; 84, attribute; 85, argument_list; 86, identifier:key; 87, identifier:filter_fields; 88, expression_statement; 89, expression_statement; 90, if_statement; 91, identifier:sort; 92, call; 93, identifier:sort; 94, call; 95, subscript; 96, identifier:sort; 97, identifier:search; 98, call; 99, identifier:search; 100, call; 101, subscript; 102, identifier:search; 103, call; 104, call; 105, identifier:set; 106, argument_list; 107, identifier:bottle; 108, identifier:abort; 109, integer:400; 110, binary_operator:"The following query params were invalid: %s. "
                       "Try one (or more) of %s." %
                       (", ".join(unfilterable),
                        ", ".join(filter_fields)); 111, assignment; 112, assignment; 113, comparison_operator:len(matches) > 1; 114, block; 115, else_clause; 116, attribute; 117, argument_list; 118, identifier:list; 119, argument_list; 120, identifier:query_fields; 121, string; 122, attribute; 123, argument_list; 124, identifier:list; 125, argument_list; 126, identifier:query_fields; 127, string; 128, identifier:set; 129, argument_list; 130, identifier:set; 131, argument_list; 132, identifier:standard_params; 133, concatenated_string; 134, tuple; 135, identifier:matches; 136, call; 137, identifier:matches; 138, call; 139, call; 140, integer:1; 141, expression_statement; 142, block; 143, attribute; 144, identifier:getall; 145, string; 146, call; 147, string_content:sort; 148, attribute; 149, identifier:getall; 150, string; 151, call; 152, string_content:q; 153, call; 154, identifier:filter_fields; 155, string:"The following query params were invalid: %s. "; 156, string:"Try one (or more) of %s."; 157, call; 158, call; 159, attribute; 160, argument_list; 161, identifier:list; 162, argument_list; 163, identifier:len; 164, argument_list; 165, assignment; 166, expression_statement; 167, identifier:request; 168, identifier:query; 169, string_content:sort; 170, attribute; 171, argument_list; 172, identifier:request; 173, identifier:query; 174, string_content:q; 175, attribute; 176, argument_list; 177, attribute; 178, argument_list; 179, attribute; 180, argument_list; 181, attribute; 182, argument_list; 183, attribute; 184, identifier:getall; 185, identifier:key; 186, call; 187, identifier:matches; 188, subscript; 189, identifier:matches; 190, assignment; 191, identifier:itertools; 192, identifier:chain; 193, list_splat; 194, identifier:itertools; 195, identifier:chain; 196, list_splat; 197, attribute; 198, identifier:keys; 199, string:", "; 200, identifier:join; 201, identifier:unfilterable; 202, string:", "; 203, identifier:join; 204, identifier:filter_fields; 205, identifier:request; 206, identifier:query; 207, attribute; 208, argument_list; 209, identifier:query_fields; 210, identifier:key; 211, subscript; 212, subscript; 213, generator_expression; 214, generator_expression; 215, identifier:request; 216, identifier:query; 217, identifier:itertools; 218, identifier:chain; 219, list_splat; 220, identifier:query_fields; 221, identifier:key; 222, identifier:matches; 223, integer:0; 224, call; 225, for_in_clause; 226, call; 227, for_in_clause; 228, if_clause; 229, generator_expression; 230, identifier:comma_separated_strings; 231, argument_list; 232, identifier:k; 233, identifier:sort; 234, identifier:comma_separated_strings; 235, argument_list; 236, identifier:k; 237, identifier:search; 238, identifier:k; 239, call; 240, for_in_clause; 241, call; 242, identifier:k; 243, attribute; 244, argument_list; 245, identifier:k; 246, identifier:matches; 247, identifier:str; 248, argument_list; 249, identifier:k; 250, identifier:split; 251, string; 252, identifier:k; 253, string_content:,
code: def process_params(request, standard_params=STANDARD_QUERY_PARAMS,
                     filter_fields=None, defaults=None):
      """Parse query params.
  
      Parses, validates, and converts query into a consistent format.
  
      :keyword request: the bottle request
      :keyword standard_params: query params that are present in most of our
          (opinionated) APIs (ex. limit, offset, sort, q, and facets)
      :keyword filter_fields: list of field names to allow filtering on
      :keyword defaults: dict of params and their default values
      :retuns: dict of query params with supplied values (string or list)
      """
      if not filter_fields:
          filter_fields = []
      unfilterable = (set(request.query.keys()) - set(filter_fields) -
                      set(standard_params))
      if unfilterable:
          bottle.abort(400,
                       "The following query params were invalid: %s. "
                       "Try one (or more) of %s." %
                       (", ".join(unfilterable),
                        ", ".join(filter_fields)))
      query_fields = defaults or {}
      for key in request.query:
          if key in filter_fields:
              # turns ?netloc=this.com&netloc=that.com,what.net into
              # {'netloc': ['this.com', 'that.com', 'what.net']}
              matches = request.query.getall(key)
              matches = list(itertools.chain(*(k.split(',') for k in matches)))
              if len(matches) > 1:
                  query_fields[key] = matches
              else:
                  query_fields[key] = matches[0]
      if 'sort' in request.query:
          sort = request.query.getall('sort')
          sort = list(itertools.chain(*(
              comma_separated_strings(str(k)) for k in sort)))
          query_fields['sort'] = sort
      if 'q' in request.query:
          search = request.query.getall('q')
          search = list(itertools.chain(*(
              comma_separated_strings(k) for k in search
              if k)))
          query_fields['q'] = search
      return query_fields