コード例 #1
0
def test_ordered_multidict():
    """Test the OrderedMultiDict"""
    d = OrderedMultiDict()
    assert not d
    d.add("foo", "bar")
    assert len(d) == 1
    d.add("foo", "baz")
    assert len(d) == 1
    assert d.items() == [("foo", "bar")]
    assert list(d) == ["foo"]
    assert d.items(multi=True) == [("foo", "bar"), ("foo", "baz")]
    del d["foo"]
    assert not d
    assert len(d) == 0
    assert list(d) == []

    d.update([("foo", 1), ("foo", 2), ("bar", 42)])
    d.add("foo", 3)
    assert d.getlist("foo") == [1, 2, 3]
    assert d.getlist("bar") == [42]
    assert d.items() == [("foo", 1), ("bar", 42)]
    assert d.keys() == list(d) == list(d.iterkeys()) == ["foo", "bar"]
    assert d.items(multi=True) == [("foo", 1), ("foo", 2), ("bar", 42), ("foo", 3)]
    assert len(d) == 2

    assert d.pop("foo") == 1
    assert d.pop("blafasel", None) is None
    assert d.pop("blafasel", 42) == 42
    assert len(d) == 1
    assert d.poplist("bar") == [42]
    assert not d

    d.get("missingkey") is None

    d.add("foo", 42)
    d.add("foo", 23)
    d.add("bar", 2)
    d.add("foo", 42)
    assert d == MultiDict(d)
    id = ImmutableOrderedMultiDict(d)
    assert d == id
    d.add("foo", 2)
    assert d != id

    d.update({"blah": [1, 2, 3]})
    assert d["blah"] == 1
    assert d.getlist("blah") == [1, 2, 3]

    # setlist works
    d = OrderedMultiDict()
    d["foo"] = 42
    d.setlist("foo", [1, 2])
    assert d.getlist("foo") == [1, 2]

    assert_raises(OrderedMultiDict.KeyError, d.pop, "missing")
    assert_raises(OrderedMultiDict.KeyError, d.__getitem__, "missing")

    # popping
    d = OrderedMultiDict()
    d.add("foo", 23)
    d.add("foo", 42)
    d.add("foo", 1)
    assert d.popitem() == ("foo", 23)
    assert_raises(OrderedMultiDict.KeyError, d.popitem)
    assert not d

    d.add("foo", 23)
    d.add("foo", 42)
    d.add("foo", 1)
    assert d.popitemlist() == ("foo", [23, 42, 1])
    assert_raises(OrderedMultiDict.KeyError, d.popitemlist)
コード例 #2
0
def test_ordered_multidict():
    """Test the OrderedMultiDict"""
    d = OrderedMultiDict()
    assert not d
    d.add('foo', 'bar')
    assert len(d) == 1
    d.add('foo', 'baz')
    assert len(d) == 1
    assert d.items() == [('foo', 'bar')]
    assert list(d) == ['foo']
    assert d.items(multi=True) == [('foo', 'bar'), ('foo', 'baz')]
    del d['foo']
    assert not d
    assert len(d) == 0
    assert list(d) == []

    d.update([('foo', 1), ('foo', 2), ('bar', 42)])
    d.add('foo', 3)
    assert d.getlist('foo') == [1, 2, 3]
    assert d.getlist('bar') == [42]
    assert d.items() == [('foo', 1), ('bar', 42)]
    assert d.keys() == list(d) == list(d.iterkeys()) == ['foo', 'bar']
    assert d.items(multi=True) == [('foo', 1), ('foo', 2), ('bar', 42),
                                   ('foo', 3)]
    assert len(d) == 2

    assert d.pop('foo') == 1
    assert d.pop('blafasel', None) is None
    assert d.pop('blafasel', 42) == 42
    assert len(d) == 1
    assert d.poplist('bar') == [42]
    assert not d

    d.get('missingkey') is None

    d.add('foo', 42)
    d.add('foo', 23)
    d.add('bar', 2)
    d.add('foo', 42)
    assert d == MultiDict(d)
    id = ImmutableOrderedMultiDict(d)
    assert d == id
    d.add('foo', 2)
    assert d != id

    d.update({'blah': [1, 2, 3]})
    assert d['blah'] == 1
    assert d.getlist('blah') == [1, 2, 3]

    # setlist works
    d = OrderedMultiDict()
    d['foo'] = 42
    d.setlist('foo', [1, 2])
    assert d.getlist('foo') == [1, 2]

    assert_raises(OrderedMultiDict.KeyError, d.pop, 'missing')
    assert_raises(OrderedMultiDict.KeyError, d.__getitem__, 'missing')

    # popping
    d = OrderedMultiDict()
    d.add('foo', 23)
    d.add('foo', 42)
    d.add('foo', 1)
    assert d.popitem() == ('foo', 23)
    assert_raises(OrderedMultiDict.KeyError, d.popitem)
    assert not d

    d.add('foo', 23)
    d.add('foo', 42)
    d.add('foo', 1)
    assert d.popitemlist() == ('foo', [23, 42, 1])
    assert_raises(OrderedMultiDict.KeyError, d.popitemlist)
コード例 #3
0
ファイル: test_datastructures.py プロジェクト: d1on/werkzeug
def test_ordered_multidict():
    """Test the OrderedMultiDict"""
    d = OrderedMultiDict()
    assert not d
    d.add('foo', 'bar')
    assert len(d) == 1
    d.add('foo', 'baz')
    assert len(d) == 1
    assert d.items() == [('foo', 'bar')]
    assert list(d) == ['foo']
    assert d.items(multi=True) == [('foo', 'bar'),
                                   ('foo', 'baz')]
    del d['foo']
    assert not d
    assert len(d) == 0
    assert list(d) == []

    d.update([('foo', 1), ('foo', 2), ('bar', 42)])
    d.add('foo', 3)
    assert d.getlist('foo') == [1, 2, 3]
    assert d.getlist('bar') == [42]
    assert d.items() == [('foo', 1), ('bar', 42)]
    assert d.keys() == list(d) == list(d.iterkeys()) == ['foo', 'bar']
    assert d.items(multi=True) == [('foo', 1), ('foo', 2),
                                   ('bar', 42), ('foo', 3)]
    assert len(d) == 2

    assert d.pop('foo') == 1
    assert d.pop('blafasel', None) is None
    assert d.pop('blafasel', 42) == 42
    assert len(d) == 1
    assert d.poplist('bar') == [42]
    assert not d

    d.get('missingkey') is None

    d.add('foo', 42)
    d.add('foo', 23)
    d.add('bar', 2)
    d.add('foo', 42)
    assert d == MultiDict(d)
    id = ImmutableOrderedMultiDict(d)
    assert d == id
    d.add('foo', 2)
    assert d != id

    d.update({'blah': [1, 2, 3]})
    assert d['blah'] == 1
    assert d.getlist('blah') == [1, 2, 3]

    # setlist works
    d = OrderedMultiDict()
    d['foo'] = 42
    d.setlist('foo', [1, 2])
    assert d.getlist('foo') == [1, 2]

    assert_raises(OrderedMultiDict.KeyError, d.pop, 'missing')
    assert_raises(OrderedMultiDict.KeyError, d.__getitem__, 'missing')

    # popping
    d = OrderedMultiDict()
    d.add('foo', 23)
    d.add('foo', 42)
    d.add('foo', 1)
    assert d.popitem() == ('foo', 23)
    assert_raises(OrderedMultiDict.KeyError, d.popitem)
    assert not d

    d.add('foo', 23)
    d.add('foo', 42)
    d.add('foo', 1)
    assert d.popitemlist() == ('foo', [23, 42, 1])
    assert_raises(OrderedMultiDict.KeyError, d.popitemlist)
コード例 #4
0
class Request(object):
    """
    A Request object.

    This should not be manually created. Instead, it is automatically provided by Kyokai.

    If you must create one, use :meth:`from_data` or :meth:`parse`.

    :ivar method: The HTTP method (GET, POST, PUT, etc)
    :ivar path: The full path of the request (``/api/v1/whatever``)
    :ivar headers: A :class:`IOrderedDict` representing the headers of the request.
    :ivar query: The raw query string (``a=b&c=d``)
    :ivar body: The raw body of the request.

    :ivar cookies: A :class:`cookies.SimpleCookie` containing the cookies of the request.

    :ivar args: The arguments from the query string, parsed out.
    :ivar form: The form data for the request. If the request was JSON, this is automatically parsed out.
    :ivar values: THe arguments and the form combined.

    :ivar source: The source IP of the request.
    """
    def __init__(self):
        """
        Creates a new request.

        The request is probably useless right now, but the HTTP parser will then go on to set the right attributes on
        it.
        """
        # Empty values.
        self.method = ""

        # This differs from path/query because it's the full `/a/b/?c=d`.
        # This is then urlsplit into a path and query string in _parse_path.
        self.full_path = b""

        self.path = ""
        self.query = ""
        self.version = ""

        # Empty body, as this isn't known until it's passed in.
        self.body = ""

        self.cookies = cookies.SimpleCookie()

        # We use a Headers object here as it serves our purposes the best.
        self.headers = Headers()

        # Args, values, and forms are OrderedMultiDicts.
        # So are files.
        self.args = OrderedMultiDict()
        self._form = OrderedMultiDict()
        self.values = OrderedMultiDict()
        self.files = OrderedMultiDict()

        # Protocol-specific data.
        self.ip = ""
        self.port = 0

        # Extra values, for hooks.
        self.extra = {}

        self.should_keep_alive = False

    @property
    def form(self) -> dict:
        """
        Returns the form data for the specified request.
        JSON forms are lazy loaded. This means that parsing is done in the first call to `.form`, rather than when
        the request is created.
        """
        if self._form:
            return self._form
        # Parse JSON, otherwise.
        if self.headers.get("Content-Type") == "application/json":
            self._form = json.loads(self.body)
            self.values.update(self._form if self._form else {})
        return self._form

    def _parse_path(self):
        """
        urlsplits the full path.
        """
        split = uparse.urlsplit(self.full_path.decode())
        self.path = split.path
        self.query = split.query

    def _parse_query(self):
        """
        Parses the query string, and updates `args` with it as appropriate.
        """
        new_args = uparse.parse_qs(self.query)
        # Unpack the urlparsed arguments.
        for name, value in new_args.items():
            if len(value) == 1:
                self.args[name] = value[0]
            elif len(value) == 0:
                self.args[name] = None
            else:
                self.args[name] = value

    def _parse_body(self):
        """
        Parses the body data.
        """
        if self.headers.get("Content-Type") != "application/json":
            # Parse the form data out.
            f_parser = formparser.FormDataParser()

            # Wrap the body in a BytesIO.
            body = BytesIO(self.body.encode())

            # The headers can't be directly passed into Werkzeug.
            # Instead, we have to get a the custom content type, then pass in some fake WSGI options.
            mimetype, c_t_args = parse_options_header(
                self.headers.get("Content-Type"))

            if mimetype:
                # We have a valid mimetype.
                # This is good!
                # Now parse the body.

                # Construct a fake WSGI environment.
                env = {
                    "Content-Type": self.headers.get("Content-Type"),
                    "Content-Length": self.headers.get("Content-Length")
                }

                # Take the boundary out of the Content-Type, if applicable.
                boundary = c_t_args.get("boundary")
                if boundary is not None:
                    env["boundary"] = boundary

                # Get a good content length.
                content_length = self.headers.get("Content-Length")
                try:
                    content_length = int(content_length)
                except ValueError:
                    content_length = len(self.body)
                except TypeError:
                    # NoneType...
                    raise HTTPException(411)

                # Then, the form body itself is parsed.

                data = f_parser.parse(body,
                                      mimetype,
                                      content_length,
                                      options=env)

                # Extract the new data from the form parser.
                self._form.update(data[1])
                self.files.update(data[2])

    def parse_all(self):
        """
        Called when all data is parsed.

        This tells the request to re-parse everything based off of the raw data.

        This is an internal method.

        .. versionadded:: 1.9
        """
        # Call _parse_path to parse the path.
        self._parse_path()
        # Call _parse_query to parse the query string.
        self._parse_query()
        # Call _parse_body to parse the body.
        self._parse_body()

        # Load cookies.
        cookie_header = self.headers.get_all("Cookie")
        for c in cookie_header:
            self.cookies.load(c)