code: def runSearchRequest(
              self, requestStr, requestClass, responseClass, objectGenerator):
          
          self.startProfile()
          try:
              request = protocol.fromJson(requestStr, requestClass)
          except protocol.json_format.ParseError:
              raise exceptions.InvalidJsonException(requestStr)
          # TODO How do we detect when the page size is not set?
          if not request.page_size:
              request.page_size = self._defaultPageSize
          if request.page_size < 0:
              raise exceptions.BadPageSizeException(request.page_size)
          responseBuilder = response_builder.SearchResponseBuilder(
              responseClass, request.page_size, self._maxResponseLength)
          nextPageToken = None
          for obj, nextPageToken in objectGenerator(request):
              responseBuilder.addValue(obj)
              if responseBuilder.isFull():
                  break
          responseBuilder.setNextPageToken(nextPageToken)
          responseString = responseBuilder.getSerializedResponse()
          self.endProfile()
          return responseString
docs: Runs the specified request. The request is a string containing
          a JSON representation of an instance of the specified requestClass.
          We return a string representation of an instance of the specified
          responseClass in JSON format. Objects are filled into the page list
          using the specified object generator, which must return
          (object, nextPageToken) pairs, and be able to resume iteration from
          any point using the nextPageToken attribute of the request object.