def __dispatch_url(self): self.__log.info('Stream connection to {url}', url=self.transport.location) _scheme, _netloc, path_bytes, _params, query_bytes, _fragment = urlparse( bytes_or_ascii(self.transport.location)) # py2/3: unquote returns str in either version but we want Unicode path = [ six.text_type(urllib.parse.unquote(x)) for x in path_bytes.split(b'/') ] assert path[0] == '' path[0:1] = [] cap_string = path[0] if cap_string in self._caps: root_object = self._caps[cap_string] path[0:1] = [] else: raise Exception('Unknown cap') # TODO better error reporting if path == [AUDIO_STREAM_PATH_ELEMENT]: options = parse_audio_stream_options(parse_qs(query_bytes, 1)) self.inner = AudioStreamInner(the_reactor, self.__send, root_object, options.sample_rate) elif len(path) >= 1 and path[0] == CAP_OBJECT_PATH_ELEMENT: # note _lookup_block may throw. TODO: Better error reporting root_object = _lookup_block(root_object, path[1:]) self.inner = StateStreamInner( self.__send, root_object, path_bytes.decode('utf-8'), self.__subscription_context ) # note reuse of WS path as HTTP path; probably will regret this else: raise Exception('Unknown path: %r' % (path, ))
def get_stream_head(test_case, url): agent = client.Agent(the_reactor) response = yield agent.request( method=b'GET', uri=bytes_or_ascii(url)) prefix_reader = _PrefixReaderProtocol() response.deliverBody(prefix_reader) defer.returnValue((response, prefix_reader))
def http_request(reactor, url, method, body=None, accept=None, more_headers=None): agent = client.Agent(reactor) headers = Headers() if accept is not None: headers.addRawHeader('Accept', bytes_or_ascii(accept)) if more_headers: for k, v in six.iteritems(more_headers): headers.addRawHeader(bytes_or_ascii(k), bytes_or_ascii(v)) d = agent.request( method=bytes_or_ascii(method), uri=bytes_or_ascii(url), headers=headers, bodyProducer=client.FileBodyProducer(six.BytesIO(bytes_or_ascii(body))) if body else None) return _handle_agent_response(d)
def _coerce_and_validate_base_url(url_value, label, allowed_schemes, allow_path=False): """Convert url_value to string or None and validate it is a suitable base URL.""" if url_value is not None: url_value = str(url_value) scheme, _netloc, path_bytes, _params, _query_bytes, _fragment = urlparse(bytes_or_ascii(url_value)) # Ensure that the protocol is compatible. if scheme.lower() not in allowed_schemes: raise ConfigException('config.serve_web: {} must be a {} URL but was {}'.format(label, ' or '.join(repr_no_string_tag(s + ':') for s in allowed_schemes), repr_no_string_tag(url_value))) # Ensure that there are no path components. There are two reasons for this: # 1. The client makes use of host-relative URLs. # 2. Because ShinySDR makes heavy use of localStorage, and may in the future use other origin-scoped features, it is not safe to run ShinySDR on the same origin as another web application as they might collide with each other. Trying to reverse-proxy with an added path component does not _necessarily_ indicate an attempt to do this, but it'd be more work to support it so let's not bother. # However, neither reason applies to WebSocket addresses, so those are allowed to have directory paths. if allow_path: if not path_bytes.endswith(b'/'): raise ConfigException('config.serve_web: {}\'s path must end in a slash, but had {}'.format(label, repr_no_string_tag(path_bytes))) else: if path_bytes != b'/': raise ConfigException('config.serve_web: {} must not have any path components, but had {}'.format(label, repr_no_string_tag(path_bytes))) return url_value
def get_stream_head(test_case, url): agent = client.Agent(the_reactor) response = yield agent.request(method=b'GET', uri=bytes_or_ascii(url)) prefix_reader = _PrefixReaderProtocol() response.deliverBody(prefix_reader) defer.returnValue((response, prefix_reader))