API decorator for common tests (sessions open, etc.) and throttle
        limitation (calls per second).
3881
def _api(fn):
        """"""
        @_functools.wraps(fn)
        def _fn(self, *args, **kwargs):
            self._throttle_wait()
            if not self._SID:
                raise RuntimeError('Session closed. Invoke connect() before.')
            return fn(self, *args, **kwargs)
        return _fn
686513
function makeRequestCallFromTimer(callback) {
    return function requestCall() {
        // We dispatch a timeout with a specified delay of 0 for engines that
        // can reliably accommodate that request. This will usually be snapped
        // to a 4 milisecond delay, but once we're flushing, there's no delay
        // between events.
        var timeoutHandle = setTimeout(handleTimer, 0);
        // However, since this timer gets frequently dropped in Firefox
        // workers, we enlist an interval handle that will try to fire
        // an event 20 times per second until it succeeds.
        var intervalHandle = setInterval(handleTimer, 50);

        function handleTimer() {
            // Whichever timer succeeds will cancel both timers and
            // execute the callback.
            clearTimeout(timeoutHandle);
            clearInterval(intervalHandle);
            callback();
        }
    };
}
1238628
def timelimit(timeout):
    """"""
    def _1(function):
        def _2(*args, **kw):
            class Dispatch(threading.Thread):
                def __init__(self):
                    threading.Thread.__init__(self)
                    self.result = None
                    self.error = None

                    self.setDaemon(True)
                    self.start()

                def run(self):
                    try:
                        self.result = function(*args, **kw)
                    except:
                        self.error = sys.exc_info()

            c = Dispatch()
            c.join(timeout)
            if c.isAlive():
                raise TimeoutError, 'took too long'
            if c.error:
                raise c.error[0], c.error[1]
            return c.result
        return _2
    return _1
1374655
def decorate(self, func, limit, ttl, *anoop, **kwnoop):
        """"""
        return super(ratelimit, self).decorate(func, limit, ttl, *anoop, **kwnoop)
785111
def ultracache(timeout, *params):
    """"""

    def decorator(cls):
        class WrappedClass(cls):
            def __init__(self, *args, **kwargs):
                super(WrappedClass, self).__init__(*args, **kwargs)

            @cached_get(timeout, *params)
            def get(self, *args, **kwargs):
                return super(WrappedClass, self).get(*args, **kwargs)

        return WrappedClass
    return decorator
951626
private void throttledTransfer(MockResponse throttlePolicy, InputStream in, OutputStream out,
            long limit) throws IOException {
        byte[] buffer = new byte[1024];
        int bytesPerPeriod = throttlePolicy.getThrottleBytesPerPeriod();
        long delayMs = throttlePolicy.getThrottleUnit().toMillis(throttlePolicy.getThrottlePeriod());

        while (true) {
            for (int b = 0; b < bytesPerPeriod; ) {
                int toRead = (int) Math.min(Math.min(buffer.length, limit), bytesPerPeriod - b);
                int read = in.read(buffer, 0, toRead);
                if (read == -1) return;

                out.write(buffer, 0, read);
                out.flush();
                b += read;
                limit -= read;

                if (limit == 0) return;
            }

            try {
                if (delayMs != 0) Thread.sleep(delayMs);
            } catch (InterruptedException e) {
                throw new AssertionError();
            }
        }
    }
178754
def _request(self, method, endpoint, id=None, **kwargs):
        ""
        request = getattr(requests, method, None)
        if not callable(request):
            raise RequestError('Invalid method %s' % method)
        # Find files, separate them out to correct kwarg for requests.
        data = kwargs.get('data')
        if data:
            files = {}
            for name, value in list(data.items()):
                # Value might be a file-like object (with a read method), or it
                # might be a (filename, file-like) tuple.
                if hasattr(value, 'read') or isinstance(value, tuple):
                    files[name] = data.pop(name)
            if files:
                kwargs.setdefault('files', {}).update(files)
        path = ['api', self.version, endpoint]
        # If we received an ID, append it to the path.
        if id:
            path.append(str(id))
        # Join fragments into a URL
        path = '/'.join(path)
        if not path.endswith('/'):
            path += '/'
        while '//' in path:
            path = path.replace('//', '/')
        url = self.url + path
        # Add our user agent.
        kwargs.setdefault('headers', {}).setdefault('User-Agent',
                                                    HTTP_USER_AGENT)
        # Now try the request, if we get throttled, sleep and try again.
        trys, retrys = 0, 3
        while True:
            if trys == retrys:
                raise RequestError('Could not complete request after %s trys.'
                                   % trys)
            trys += 1
            try:
                return self._do_request(request, url, **kwargs)
            except ResponseError as e:
                if self.throttle_wait and e.status_code == 503:
                    m = THROTTLE_PATTERN.match(
                        e.response.headers.get('x-throttle', ''))
                    if m:
                        time.sleep(float(m.group(1)))
                        continue
                # Failed for a reason other than throttling.
                raise
310231
def __api_request(self, method, endpoint, params={}, files={}, headers={}, access_token_override=None, do_ratelimiting=True, use_json = False):
        
        response = None
        remaining_wait = 0
        # "pace" mode ratelimiting: Assume constant rate of requests, sleep a little less long than it
        # would take to not hit the rate limit at that request rate.
        if do_ratelimiting and self.ratelimit_method == "pace":
            if self.ratelimit_remaining == 0:
                to_next = self.ratelimit_reset - time.time()
                if to_next > 0:
                    # As a precaution, never sleep longer than 5 minutes
                    to_next = min(to_next, 5 * 60)
                    time.sleep(to_next)
            else:
                time_waited = time.time() - self.ratelimit_lastcall
                time_wait = float(self.ratelimit_reset - time.time()) / float(self.ratelimit_remaining)
                remaining_wait = time_wait - time_waited

            if remaining_wait > 0:
                to_next = remaining_wait / self.ratelimit_pacefactor
                to_next = min(to_next, 5 * 60)
                time.sleep(to_next)

        # Generate request headers
        headers = copy.deepcopy(headers)
        if not self.access_token is None:
            headers['Authorization'] = 'Bearer ' + self.access_token
        if not access_token_override is None:
            headers['Authorization'] = 'Bearer ' + access_token_override

        if self.debug_requests:
            print('Mastodon: Request to endpoint "' + endpoint + '" using method "' + method + '".')
            print('Parameters: ' + str(params))
            print('Headers: ' + str(headers))
            print('Files: ' + str(files))

        # Make request
        request_complete = False
        while not request_complete:
            request_complete = True

            response_object = None
            try:
                kwargs = dict(headers=headers, files=files,
                              timeout=self.request_timeout)
                if use_json == False:
                    if method == 'GET':
                        kwargs['params'] = params
                    else:
                        kwargs['data'] = params
                else:
                    kwargs['json'] = params
                    
                response_object = self.session.request(
                        method, self.api_base_url + endpoint, **kwargs)
            except Exception as e:
                raise MastodonNetworkError("Could not complete request: %s" % e)

            if response_object is None:
                raise MastodonIllegalArgumentError("Illegal request.")

            # Parse rate limiting headers
            if 'X-RateLimit-Remaining' in response_object.headers and do_ratelimiting:
                self.ratelimit_remaining = int(response_object.headers['X-RateLimit-Remaining'])
                self.ratelimit_limit = int(response_object.headers['X-RateLimit-Limit'])

                try:
                    ratelimit_reset_datetime = dateutil.parser.parse(response_object.headers['X-RateLimit-Reset'])
                    self.ratelimit_reset = self.__datetime_to_epoch(ratelimit_reset_datetime)

                    # Adjust server time to local clock
                    if 'Date' in response_object.headers:
                        server_time_datetime = dateutil.parser.parse(response_object.headers['Date'])
                        server_time = self.__datetime_to_epoch(server_time_datetime)
                        server_time_diff = time.time() - server_time
                        self.ratelimit_reset += server_time_diff
                        self.ratelimit_lastcall = time.time()
                except Exception as e:
                    raise MastodonRatelimitError("Rate limit time calculations failed: %s" % e)

            # Handle response
            if self.debug_requests:
                print('Mastodon: Response received with code ' + str(response_object.status_code) + '.')
                print('response headers: ' + str(response_object.headers))
                print('Response text content: ' + str(response_object.text))

            if not response_object.ok:
                try:
                    response = response_object.json(object_hook=self.__json_hooks)
                    if isinstance(response, dict) and 'error' in response:
                        error_msg = response['error']
                    elif isinstance(response, str):
                        error_msg = response
                    else:
                        error_msg = None
                except ValueError:
                    error_msg = None

                # Handle rate limiting
                if response_object.status_code == 429:
                    if self.ratelimit_method == 'throw' or not do_ratelimiting:
                        raise MastodonRatelimitError('Hit rate limit.')
                    elif self.ratelimit_method in ('wait', 'pace'):
                        to_next = self.ratelimit_reset - time.time()
                        if to_next > 0:
                            # As a precaution, never sleep longer than 5 minutes
                            to_next = min(to_next, 5 * 60)
                            time.sleep(to_next)
                            request_complete = False
                            continue

                if response_object.status_code == 404:
                    ex_type = MastodonNotFoundError
                    if not error_msg:
                        error_msg = 'Endpoint not found.'
                        # this is for compatibility with older versions
                        # which raised MastodonAPIError('Endpoint not found.')
                        # on any 404
                elif response_object.status_code == 401:
                    ex_type = MastodonUnauthorizedError
                elif response_object.status_code == 502:
                    ex_type = MastodonServerError
                else:
                    ex_type = MastodonAPIError

                raise ex_type(
                        'Mastodon API returned error',
                        response_object.status_code,
                        response_object.reason,
                        error_msg)

            try:
                response = response_object.json(object_hook=self.__json_hooks)
            except:
                raise MastodonAPIError(
                    "Could not parse response as JSON, response code was %s, "
                    "bad json content was '%s'" % (response_object.status_code,
                                                   response_object.content))

            # Parse link headers
            if isinstance(response, list) and \
                    'Link' in response_object.headers and \
                    response_object.headers['Link'] != "":
                tmp_urls = requests.utils.parse_header_links(
                    response_object.headers['Link'].rstrip('>').replace('>,<', ',<'))
                for url in tmp_urls:
                    if 'rel' not in url:
                        continue

                    if url['rel'] == 'next':
                        # Be paranoid and extract max_id specifically
                        next_url = url['url']
                        matchgroups = re.search(r"[?&]max_id=([^&]+)", next_url)

                        if matchgroups:
                            next_params = copy.deepcopy(params)
                            next_params['_pagination_method'] = method
                            next_params['_pagination_endpoint'] = endpoint
                            max_id = matchgroups.group(1)
                            if max_id.isdigit():
                                next_params['max_id'] = int(max_id)
                            else:
                                next_params['max_id'] = max_id
                            if "since_id" in next_params:
                                del next_params['since_id']
                            if "min_id" in next_params:
                                del next_params['min_id']
                            response[-1]._pagination_next = next_params

                    if url['rel'] == 'prev':
                        # Be paranoid and extract since_id or min_id specifically
                        prev_url = url['url']
                        
                        # Old and busted (pre-2.6.0): since_id pagination
                        matchgroups = re.search(r"[?&]since_id=([^&]+)", prev_url)
                        if matchgroups:
                            prev_params = copy.deepcopy(params)
                            prev_params['_pagination_method'] = method
                            prev_params['_pagination_endpoint'] = endpoint
                            since_id = matchgroups.group(1)
                            if since_id.isdigit():
                                prev_params['since_id'] = int(since_id)
                            else:
                                prev_params['since_id'] = since_id
                            if "max_id" in prev_params:
                                del prev_params['max_id']
                            response[0]._pagination_prev = prev_params
                            
                        # New and fantastico (post-2.6.0): min_id pagination
                        matchgroups = re.search(r"[?&]min_id=([^&]+)", prev_url)
                        if matchgroups:
                            prev_params = copy.deepcopy(params)
                            prev_params['_pagination_method'] = method
                            prev_params['_pagination_endpoint'] = endpoint
                            min_id = matchgroups.group(1)
                            if min_id.isdigit():
                                prev_params['min_id'] = int(min_id)
                            else:
                                prev_params['min_id'] = min_id
                            if "max_id" in prev_params:
                                del prev_params['max_id']
                            response[0]._pagination_prev = prev_params

        return response
798631
def check_throttles(self, request):
        
        for throttle in self.get_throttles():
            if not throttle.allow_request(request, self):
                self.throttled(request, throttle.wait())
523188
def as_session(name_or_func):  # decorator
    
    if callable(name_or_func):  # no name provided
        func = name_or_func
        name = func.__name__
        name = "".join([(' ' + x) if x.isupper() else x for x in name])
        name = name.replace('_', ' ')
        return as_session(name)(func)  # deco(func) -> deco(name)(func)
    else:
        name = name_or_func

    def get_func(func):
        @wraps(func)
        def wrapper(*args, **kwargs):
            start()
            title(name)
            result = func(*args, **kwargs)
            end()
            return result
        return wrapper
    return get_func
304633
def wrap_session_request(wrapped, instance, args, kwargs):
    """"""
    method = kwargs.get('method') or args[0]
    url = kwargs.get('url') or args[1]

    blacklist_hostnames = execution_context.get_opencensus_attr(
        'blacklist_hostnames')
    parsed_url = urlparse(url)
    if parsed_url.port is None:
        dest_url = parsed_url.hostname
    else:
        dest_url = '{}:{}'.format(parsed_url.hostname, parsed_url.port)
    if utils.disable_tracing_hostname(dest_url, blacklist_hostnames):
        return wrapped(*args, **kwargs)

    _tracer = execution_context.get_opencensus_tracer()
    _span = _tracer.start_span()

    _span.name = '[requests]{}'.format(method)
    _span.span_kind = span_module.SpanKind.CLIENT

    try:
        tracer_headers = _tracer.propagator.to_headers(
            _tracer.span_context)
        kwargs.setdefault('headers', {}).update(
            tracer_headers)
    except Exception:  # pragma: NO COVER
        pass

    # Add the requests url to attributes
    _tracer.add_attribute_to_current_span(HTTP_URL, url)

    result = wrapped(*args, **kwargs)

    # Add the status code to attributes
    _tracer.add_attribute_to_current_span(
        HTTP_STATUS_CODE, str(result.status_code))

    _tracer.end_span()
    return result
850766
function throttle(func) {
    var context,
      args,
      result,
      timeout = null,
      previous = 0,
      later = function() {
        previous = getNow()
        timeout = null
        result = func.apply(context, args)
        if (!timeout) {
          // eslint-disable-next-line no-multi-assign
          context = args = null
        }
      }

    return function() {
      var now = getNow()

      if (!previous) {
        previous = now
      }

      var remaining = throttledTimer - (now - previous)

      context = this
      args = arguments

      if (remaining <= 0 || remaining > throttledTimer) {
        if (timeout) {
          clearTimeout(timeout)
          timeout = null
        }

        previous = now
        result = func.apply(context, args)

        if (!timeout) {
          // eslint-disable-next-line no-multi-assign
          context = args = null
        }
      } else if (!timeout) {
        timeout = setTimeout(later, remaining)
      }

      return result
    }
  }
912503
def retry(func):
    
    def retried_func(*args, **kwargs):
        max_tries = 3
        tries = 0
        while True:
            try:
                resp = func(*args, **kwargs)

            except requests.exceptions.ConnectionError as exc:
                exc.msg = "Connection error for session; exiting"
                raise exc

            except requests.exceptions.HTTPError as exc:
                exc.msg = "HTTP error for session; exiting"
                raise exc

            if resp.status_code != 200 and tries < max_tries:
                logger.warning("retrying request; current status code: {}"
                               .format(resp.status_code))
                tries += 1
                # mini exponential backoff here.
                time.sleep(tries ** 2)
                continue

            break

        if resp.status_code != 200:
            error_message = resp.json()["error"]["message"]
            logger.error("HTTP Error code: {}: {}".format(resp.status_code, error_message))
            logger.error("Rule payload: {}".format(kwargs["rule_payload"]))
            raise requests.exceptions.HTTPError

        return resp

    return retried_func
559772
def _requests(self, url, method='GET', headers=None, params=None, data=None, errors=None):

        '''  '''

        title = '%s._requests' % self.__class__.__name__
    
    # import dependencies
        from time import time
        import requests

    # validate access token
        if not self._access_token:
            self.access_token()
            if self.retrieve_details:
                self._get_products()
    
    # refresh token
        current_time = time()
        if current_time > self.expires_at:
            self.access_token()
            if self.retrieve_details:
                self._get_products()

    # construct request kwargs
        request_kwargs = {
            'url': url,
            'headers': { 
                'Authorization': 'Bearer %s' % self._access_token,
                'Accept': 'application/json;v=2'
            },
            'params': {},
            'data': {}
        }
        if headers:
            request_kwargs['headers'].update(headers)
        if params:
            request_kwargs['params'].update(params)
        if data:
            request_kwargs['data'].update(data)

    # send request
        if method == 'POST':
            try:
                response = requests.post(**request_kwargs)
            except Exception:
                if self.requests_handler:
                    request_kwargs['method'] = 'POST'
                    request_object = requests.Request(**request_kwargs)
                    return self.requests_handler(request_object)
                else:
                    raise
        elif method == 'GET':
            try:
                response = requests.get(**request_kwargs)
            except Exception:
                if self.requests_handler:
                    request_kwargs['method'] = 'GET'
                    request_object = requests.Request(**request_kwargs)
                    return self.requests_handler(request_object)
                else:
                    raise
        else:
            raise ValueError('%s(method='') must be either GET or POST' % title)

    # handle response
        response_details = self.response_handler.handle(response, errors)
        
        return response_details
1205699
def decorate(self, func, limit=0, ttl=0, *anoop, **kwnoop):
        """"""
        self.limit = int(limit)
        self.ttl = int(ttl)
        return super(RateLimitDecorator, self).decorate(func, target=None, *anoop, **kwnoop)
292256
def CallLoggedAndAccounted(f):
  """"""

  @functools.wraps(f)
  def Decorator(*args, **kwargs):
    try:
      start_time = time.time()
      result = f(*args, **kwargs)
      latency = time.time() - start_time

      stats_collector_instance.Get().RecordEvent(
          "db_request_latency", latency, fields=[f.__name__])
      logging.debug("DB request %s SUCCESS (%.3fs)", f.__name__, latency)

      return result
    except db.Error as e:
      stats_collector_instance.Get().IncrementCounter(
          "db_request_errors", fields=[f.__name__, "grr"])
      logging.debug("DB request %s GRR ERROR: %s", f.__name__,
                    utils.SmartUnicode(e))
      raise
    except Exception as e:
      stats_collector_instance.Get().IncrementCounter(
          "db_request_errors", fields=[f.__name__, "db"])
      logging.debug("DB request %s INTERNAL DB ERROR : %s", f.__name__,
                    utils.SmartUnicode(e))
      raise

  return Decorator
963966
def scoped_session_decorator(func):
    """"""
    @wraps(func)
    def wrapper(*args, **kwargs):
        from wallace.db import session as wallace_session
        with sessions_scope(wallace_session) as session:
            from psiturk.db import db_session as psi_session
            with sessions_scope(psi_session) as session_psiturk:
                # The sessions used in func come from the funcs globals, but
                # they will be proxied thread locals vars from the session
                # registry, and will therefore be identical to those returned
                # by the context managers above.
                logger.debug('Running worker %s in scoped DB sessions',
                             func.__name__)
                return func(*args, **kwargs)
    return wrapper