1News
2====
3
41.5.0a0 (2015-07-25)
5--------------------
6
7Backwards Incompatibilities
8~~~~~~~~~~~~~~~~~~~~~~~~~~~
9
10- ``Morsel`` will no longer accept a cookie value that does not meet RFC6265's
11  cookie-octet specification. Upon calling ``Morsel.serialize`` a warning will
12  be issued, in the future this will raise a ``ValueError``, please update your
13  cookie handling code. See https://github.com/Pylons/webob/pull/172
14
15  The cookie-octet specification in RFC6265 states the following characters are
16  valid in a cookie value:
17
18  ===============  =======================================
19  Hex Range        Actual Characters
20  ===============  =======================================
21  ``[0x21     ]``  ``!``
22  ``[0x25-0x2B]``  ``#$%&'()*+``
23  ``[0x2D-0x3A]``  ``-./0123456789:``
24  ``[0x3C-0x5B]``  ``<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[``
25  ``[0x5D-0x7E]``  ``]^_`abcdefghijklmnopqrstuvwxyz{|}~``
26  ===============  =======================================
27
28  RFC6265 suggests using base 64 to serialize data before storing data in a
29  cookie.
30
31- ``response.set_cookie`` now uses the internal ``make_cookie`` API, which will
32  issue warnings if cookies are set with invalid bytes. See
33  https://github.com/Pylons/webob/pull/172
34
35Features
36~~~~~~~~
37
38- Add support for some new caching headers, stale-while-revalidate and
39  stale-if-error that can be used by reverse proxies to cache stale responses
40  temporarily if the backend disappears. From RFC5861. See
41  https://github.com/Pylons/webob/pull/189
42
43Bug Fixes
44~~~~~~~~~
45
46- Response.status now uses duck-typing for integers, and has also learned to
47  raise a ValueError if the status isn't an integer followed by a space, and
48  then the reason. See https://github.com/Pylons/webob/pull/191
49
50- Fixed a bug in ``webob.multidict.GetDict`` which resulted in the
51  QUERY_STRING not being updated when changes were made to query
52  params using ``Request.GET.extend()``.
53
54- Read the body of a request if we think it might have a body. This fixes PATCH
55  to support bodies. See https://github.com/Pylons/webob/pull/184
56
57- Response.from_file returns HTTP headers as latin1 rather than UTF-8, this
58  fixes the usage on Google AppEngine. See
59  https://github.com/Pylons/webob/issues/99 and
60  https://github.com/Pylons/webob/pull/150
61
62- Fix a bug in parsing the auth parameters that contained bad white space. This
63  makes the parsing fall in line with what's required in RFC7235. See
64  https://github.com/Pylons/webob/issues/158
65
66- Use '\r\n' line endings in ``Response.__str__``. See:
67  https://github.com/Pylons/webob/pull/146
68
69Documentation Changes
70~~~~~~~~~~~~~~~~~~~~~
71
72- ``response.set_cookie`` now has proper documentation for ``max_age`` and
73  ``expires``. The code has also been refactored to use ``cookies.make_cookie``
74  instead of duplicating the code. This fixes
75  https://github.com/Pylons/webob/issues/166 and
76  https://github.com/Pylons/webob/issues/171
77
78- Documentation didn't match the actual code for the wsgify function signature.
79  See https://github.com/Pylons/webob/pull/167
80
81- Remove the WebDAV only from certain HTTP Exceptions, these exceptions may
82  also be used by REST services for example.
83
841.4 (2014-05-14)
85----------------
86
87Features
88~~~~~~~~
89
90- Remove ``webob.__version__``, the version number had not been kept in sync
91  with the official pkg version.  To obtain the WebOb version number, use
92  ``pkg_resources.get_distribution('webob').version`` instead.
93
94Bug Fixes
95~~~~~~~~~
96
97- Fix a bug in ``EmptyResponse`` that prevents it from setting self.close as
98  appropriate due to testing truthiness of object rather than if it is
99  something other than ``None``.
100
101- Fix a bug in ``SignedSerializer`` preventing secrets from containing
102  higher-order characters. See https://github.com/Pylons/webob/issues/136
103
104- Use the ``hmac.compare_digest`` method when available for constant-time
105  comparisons.
106
1071.3.1 (2013-12-13)
108------------------
109
110Bug Fixes
111~~~~~~~~~
112
113- Fix a bug in ``SignedCookieProfile`` whereby we didn't keep the original
114  serializer around, this would cause us to have ``SignedSerializer`` be added on
115  top of a ``SignedSerializer`` which would cause it to be run twice when
116  attempting to verify a cookie.  See https://github.com/Pylons/webob/pull/127
117
118Backwards Incompatibilities
119~~~~~~~~~~~~~~~~~~~~~~~~~~~
120
121- When ``CookieProfile.get_value`` and ``SignedCookieProfile.get_value`` fails
122  to deserialize a badly encoded value, we now return ``None`` as if the cookie
123  was never set in the first place instead of allowing a ``ValueError`` to be
124  raised to the calling code.  See https://github.com/Pylons/webob/pull/126
125
1261.3 (2013-12-10)
127----------------
128
129Features
130~~~~~~~~
131
132- Added a read-only ``domain`` property to ``BaseRequest``.  This property
133  returns the domain portion of the host value.  For example, if the
134  environment contains an ``HTTP_HOST`` value of ``foo.example.com:8000``,
135  ``request.domain`` will return ``foo.example.com``.
136
137- Added five new APIs: ``webob.cookies.CookieProfile``,
138  ``webob.cookies.SignedCookieProfile``, ``webob.cookies.JSONSerializer`` and
139  ``webob.cookies.SignedSerializer``, and ``webob.cookies.make_cookie``.  These
140  APIs are convenience APIs for generating and parsing cookie headers as well
141  as dealing with signing cookies.
142
143- Cookies generated via webob.cookies quoted characters in cookie values that
144  did not need to be quoted per RFC 6265.  The following characters are no
145  longer quoted in cookie values: ``~/=<>()[]{}?@`` .  The full set of
146  non-letter-or-digit unquoted cookie value characters is now
147  ``!#$%&'*+-.^_`|~/: =<>()[]{}?@``.  See
148  http://tools.ietf.org/html/rfc6265#section-4.1.1 for more information.
149
150- Cookie names are now restricted to the set of characters expected by RFC
151  6265.  Previously they could contain unsupported characters such as ``/``.
152
153- Older versions of Webob escaped the doublequote to ``\"`` and the backslash
154  to ``\\`` when quoting cookie values.  Now, instead, cookie serialization
155  generates ``\042`` for the doublequote and ``\134`` for the backslash. This
156  is what is expected as per RFC 6265.  Note that old cookie values that do
157  have the older style quoting in them will still be unquoted correctly,
158  however.
159
160- Added support for draft status code 451 ("Unavailable for Legal Reasons").
161  See http://tools.ietf.org/html/draft-tbray-http-legally-restricted-status-00
162
163- Added status codes 428, 429, 431 and 511 to ``util.status_reasons`` (they
164  were already present in a previous release as ``webob.exc`` exceptions).
165
166Bug Fixes
167~~~~~~~~~
168
169- MIMEAccept happily parsed malformed wildcard strings like "image/pn*" at
170  parse time, but then threw an AssertionError during matching.  See
171  https://github.com/Pylons/webob/pull/83 .
172
173- Preserve document ordering of GET and POST request data when POST data passed
174  to Request.blank is a MultiDict.  See https://github.com/Pylons/webob/pull/96
175
176- Allow query strings attached to PATCH requests to populate request.params.
177  See https://github.com/Pylons/webob/pull/106
178
179- Added Python 3.3 trove classifier.
180
1811.2.3
182------------
183
184* Maintainership transferred to `Pylons Project <http://www.pylonsproject.org/>`
185
186* Fix parsing of form submissions where fields have
187  transfer-content-encoding headers.
188
1891.2.2
190------------
191
192* Fix multiple calls to ``cache_expires()`` not fully overriding the
193  previously set headers.
194
195* Fix parsing of form submissions where fields have different encodings.
196
197
1981.2.1
199------------
200
201* Add index page (e.g., ``index.html``) support for
202  :class:`webob.static.DirectoryApp`.
203
204* Detect mime-type when creating a test request with file uploads
205  (``Request.blank("/", POST=dict(file1=("foo.jpg", "xxx")))``)
206
207* Relax parsing of ``Accept`` and ``Range`` headers to allow
208  uppercase and extra whitespace.
209
210* Fix docs references to some deprecated classes.
211
212
2131.2
214------------
215
216* Fix :mod:`webob.client` handling  of connection-refused on Windows.
217
218* Use ``simplejson`` in :mod:`webob.request` if present.
219
220* Fix ``resp.retry_after = <long>`` interpreting value as a UNIX timestamp
221  (should interpret as time delta in seconds).
222
223
2241.2rc1
225------------
226
227* Add ``Response.json`` and ``Request.json`` which reads and sets the
228  body using a JSON encoding (previously only the readable attribute
229  ``Request.json_body`` existed).  ``Request.json_body`` is still
230  available as an alias.
231
232* Rename ``Response.status_int`` to ``Response.status_code`` (the
233  ``.status_int`` name is still available and will be supported
234  indefinitely).
235
236* Add ``Request.text``, the unicode version of the request body
237  (similar to ``Response.text``).
238
239* Add :mod:`webob.client` which contains the WSGI application
240  ``send_request_app`` and ``SendRequest``.  All requests sent to this
241  application are turned into HTTP requests.
242
243* Renamed ``Request.get_response(app)`` to ``Request.send(app)``.  The
244  ``.get_response()`` name is still available.
245
246* Use ``send_request_app`` as the default application for
247  ``Request.send()``, so you can do:
248
249    ``resp = Request.blank("http://python.org").send()``
250
251* Add :mod:`webob.static` which contains two new WSGI applications,
252  :class:`FileApp` serve one static file and :class:`DirectoryApp` to serve
253  the content of a directory. They should provide a reusable implementation
254  of :doc:`file-example`.  It also comes with support for ``wsgi.file_wrapper``.
255
256  The implementation has been imported and simplified from
257  :mod:`PasteOb.fileapp`.
258
259* Add ``dev`` and ``docs`` setup.py aliases (to install development and docs
260  dependencies respectively, e.g. "python setup.py dev").
261
262
2631.2b3
264------------
265
266* Added ``request.host_port`` API (returns port number implied by HTTP_HOST,
267  falling back to SERVER_PORT).
268
269* Added ``request.client_addr`` API (returns IP address implied by
270  HTTP_X_FORWARDED_FOR, falling back to REMOTE_ADDR).
271
272* Fix corner-case ``response.status_int`` and ``response.status`` mutation
273  bug on py3 (use explicit floor division).
274
275* Backwards incompatibility: Request and BaseRequest objects now return
276  Unicode for ``request.path_info`` and ``request.script_name`` under Python
277  2.  Rationale: the legacy behavior of returning the respective raw environ
278  values was nonsensical on Python 3.  Working with non-ascii encoded environ
279  variables as raw WSGI values under Python 3 makes no sense, as PEP 3333
280  specifies that environ variables are bytes-tunneled-as-latin-1 strings.
281
282  If you don't care about Python 3, and you need strict backwards
283  compatibility, to get legacy behavior of returning bytes on Python 2 for
284  these attributes, use ``webob.LegacyRequest`` instead of ``webob.Request``.
285  Although it's possible to use ``webob.LegacyRequest`` under Python 3, it
286  makes no sense, and it should not be used there.
287
288* The above backwards incompatibility fixed nonsensical behavior of
289  ``request.host_url``, ``request.application_url``, ``request.path_url``,
290  ``request.path``, ``request.path_qs``, ``request.url``,
291  ``request.relative_url``, ``request.path_info_peek``,
292  ``request.path_info_pop`` under Python 3.  These methods previously dealt
293  with raw SCRIPT_NAME and PATH_INFO values, which caused nonsensical
294  results.
295
296* The WebOb Request object now respects an additional WSGI environment
297  variable: ``webob.url_encoding``.  ``webob.url_encoding`` will be used to
298  decode the raw WSGI PATH_INFO and SCRIPT_NAME variables when the
299  ``request.path_info`` and ``request.script_name`` APIs are used.
300
301* Request objects now accept an additional constructor parameter:
302  ``url_encoding``.  ``url_encoding`` will be used to decode PATH_INFO and
303  SCRIPT_NAME from its WSGI-encoded values. If ``webob.url_encoding`` is not
304  set in the environ and ``url_encoding`` is not passed to the Request
305  constructor, the default value ``utf-8`` will be used to decode the
306  PATH_INFO and SCRIPT_NAME.
307
308  Note that passing ``url_encoding`` will cause the WSGI environment variable
309  ``webob.url_encoding`` to be set.
310
311* Fix ``webob.response._request_uri`` internal function to generate sensible
312  request URI under Python 3.  This fixed a problem under Python 3 if you
313  were using non-absolute Location headers in responses.
314
3151.2b2
316------
317
318* Fix ``request.cookies.get('name', 'default')``.  Previously ``default`` was
319  ignored.
320
3211.2b1
322---------
323
324* Mutating the ``request.cookies`` property now reflects the mutations into
325  the ``HTTP_COOKIES`` environ header.
326
327* ``Response.etag = (tag, False)`` sets weak etag.
328
329* ``Range`` only parses single range now.
330
331* ``Range.satisfiable(..)`` is gone.
332
333* ``Accept.best_matches()`` is gone; use ``list(request.accept)`` or
334  ``request.accept.best_match(..)`` instead (applies to all Accept-*
335  headers) or similar with ``request.accept_language``.
336
337* ``Response.request`` and ``Response.environ`` attrs are undeprecated and no
338  longer raise exceptions when used.  These can also be passed to the
339  Response constructor.  This is to support codebases that pass them to the
340  constructor or assign them to a response instance.  However, some behavior
341  differences from 1.1 exist.  In particular, synchronization is no longer
342  done between environ and request attribute properties of Response; you may
343  pass either to the constructor (or both) or assign one or the other or
344  both, but they wont be managed specially and will remain the same over the
345  lifetime of the response just as you passed them.  Default values for both
346  ``request`` and ``environ`` on any given response are ``None`` now.
347
348* Undeprecated ``uscript_name`` and ``upath_info``.
349
350* For backwards compatibility purposes, switch ``req.script_name`` and
351  ``path_info`` back again to contain "raw" undecoded native strings rather
352  than text.  Use ``uscript_name`` and ``upath_info`` to get the text version
353  of SCRIPT_NAME and PATH_INFO.
354
355* Don't raise an exception if ``unicode_errors`` or ``decode_param_names`` is
356  passed to the Request constructor.  Instead, emit a warning.  For benefit
357  of Pylons 1.X, which passes both.
358
359* Don't raise an exception if HTTPException.exception is used; instead emit a
360  warning.  For benefit of Pylons 1.X, which uses it.
361
3621.2a2
363---------
364
365* ``req.script_name`` and ``path_info`` now contain text, not bytes.
366
367* Deprecated ``uscript_name`` and ``upath_info``.
368
369* ``charset`` argument to ``Request`` as well as the attribute can only
370  be set to UTF-8 or the value already present in the ``Content-Type`` header.
371
372* ``unicode_errors`` attribute of ``Request`` and related functionality is gone.
373
374* To process requests that come in an encoding different from UTF-8, the request
375  needs to be transcoded like this: ``req = req.decode('windows-1251')``
376
377* Added support for weak ETag matching in conditional responses.
378
379* Most of etag-related functionality was refactored.
380
381
3821.2a1
383---------
384
385* Python 3.2 compatibility.
386
387* No longer compatible with Python 2.5 (only 2.6, 2.7, and 3.2 are supported).
388
389* Switched VCS from Mercurial to Git
390
391* Moved development to `GitHub <https://github.com/Pylons/webob>`_
392
393* Added full history from PyCon 2011 sprint to the repository
394
395* Change ``LimitedLengthFile`` and ``FakeCGIBody`` to inherit from
396  ``io.RawIOBase`` and benefit from ``io.BufferedReader``.
397
398* Do not set ``resp.request`` in ``req.get_response(app)``
399
400* ``Response.request`` and ``.environ`` attrs are deprecated and raise exceptions
401  when used.
402
403* Deprecated request attributes ``str_GET``, ``str_POST``, ``str_cookies`` and
404  ``str_params`` now raise exceptions when touched.
405
406* Remove testing dependency on WebTest.
407
408* Remove UnicodeMultiDict class; the result of ``Request.GET`` and
409  ``Request.POST`` is now just a plain ``MultiDict``.
410
411* The ``decode_param_names`` Request constructor argument has been removed,
412  along with the ``Request.decode_param_names`` attribute.
413
414* The ``Request.as_string()`` method is now better known as
415  ``Request.as_bytes()``.
416
417* The ``Request.from_string()`` method is now better known as
418  ``Request.from_bytes()``.
419
420* A new method named ``Request.as_text()`` now exists.
421
422* A new method named ``Request.from_text()`` now exists.
423
424* The ``webob.dec.wsgify`` repr() is now much less informative, but a lot
425  easier to test and maintain.
426
427
4281.1.1
429---------
430
431* Fix disconnect detection being incorrect in some cases (`issue 21
432  <https://bitbucket.org/ianb/webob/issue/21>`_).
433
434* Fix exception when calling ``.accept.best_match(..)`` on a header containing
435  ``'*'`` (instead of ``'*/*'``).
436
437* Extract some of the ``Accept`` code into subclasses (``AcceptCharset``,
438  ``AcceptLanguage``).
439
440* Improve language matching so that the app can now offer a generic
441  language code and it will match any of the accepted dialects
442  (``'en' in AcceptLanguage('en-gb')``).
443
444* Normalize locale names when matching
445  (``'en_GB' in AcceptLanguage('en-gb')``).
446
447* Deprecate ``etag.weak_match(..)``.
448
449* Deprecate ``Response.request`` and ``Response.environ`` attrs.
450
451
4521.1
453---------
454
455* Remove deprecation warnings for ``unicode_body`` and ``ubody``.
456
457
4581.1rc1
459---------
460
461* Deprecate ``Response.ubody`` / ``.unicode_body`` in favor of new ``.text`` attribute
462  (the old names will be removed in 1.3 or even later).
463
464* Make ``Response.write`` much more efficient (`issue 18
465  <https://bitbucket.org/ianb/webob/issue/18>`_).
466
467* Make sure copying responses does not reset Content-Length or Content-MD5 of the
468  original (and that of future copies).
469
470* Change ``del res.body`` semantics so that it doesn't make the response invalid,
471  but only removes the response body.
472
473* Remove ``Response._body`` so the ``_app_iter`` is the only representation.
474
475
4761.1b2
477---------
478
479* Add detection for browser / user-agent disconnects. If the client disconnected
480  before sending the entire request body (POST / PUT), ``req.POST``, ``req.body``
481  and other related properties and methods will raise an exception.
482  Previously this caused the application get a truncated request with no indication that it
483  is incomplete.
484
485* Make ``Response.body_file`` settable. This is now valid:
486  ``Response(body_file=open('foo.bin'), content_type=...)``
487
488* Revert the restriction on req.body not being settable for GET and some
489  other requests. Such requests actually can have a body according to HTTP BIS
490  (see also `commit message <https://bitbucket.org/ianb/webob/changeset/b3ef34c57936>`_)
491
492* Add support for file upload testing via ``Request.blank(POST=..)``. Patch contributed by
493  Tim Perevezentsev. See also:
494  `ticket <https://bitbucket.org/ianb/webob/issue/15>`_,
495  `changeset <https://bitbucket.org/ianb/webob/changeset/4ba9ab0c3f99>`_.
496
497* Deprecate ``req.str_GET``, ``str_POST``, ``str_params`` and ``str_cookies`` (warning).
498
499
500* Deprecate ``req.decode_param_names`` (warning).
501
502* Change ``req.decode_param_names`` default to ``True``. This means that ``.POST``, ``.GET``,
503  ``.params`` and ``.cookies`` keys are now unicode. This is necessary for WebOb to behave
504  as close as possible on Python 2 and Python 3.
505
506
5071.1b1
508---------
509
510* We have acquired the webob.org domain, docs are now hosted at `docs.webob.org
511  <http://docs.webob.org/>`_
512
513* Make ``accept.quality(..)`` return best match quality, not first match quality.
514
515* Fix ``Range.satisfiable(..)`` edge cases.
516
517* Make sure ``WSGIHTTPException`` instances return the same headers for ``HEAD``
518  and ``GET`` requests.
519
520* Drop Python 2.4 support
521
522* Deprecate ``HTTPException.exception`` (warning on use).
523
524* Deprecate ``accept.first_match(..)`` (warning on use).
525  Use ``.best_match(..)`` instead.
526
527* Complete deprecation of ``req.[str_]{post|query}vars`` properties
528  (exception on use).
529
530* Remove ``FakeCGIBody.seek`` hack (no longer necessary).
531
532
5331.0.8
534------
535
536* Escape commas in cookie values (see also:
537  `stdlib Cookie bug <http://bugs.python.org/issue9824>`_)
538
539* Change cookie serialization to more closely match how cookies usually
540  are serialized (unquoted expires, semicolon separators even between morsels)
541
542* Fix some rare cases in cookie parsing
543
544* Enhance the req.is_body_readable to always guess GET, HEAD, DELETE and TRACE
545  as unreadable and PUT and POST as readable
546  (`issue 12 <https://bitbucket.org/ianb/webob/issue/12>`_)
547
548* Deny setting req.body or req.body_file to non-empty values for GET, HEAD and
549  other bodiless requests
550
551* Fix running nosetests with arguments on UNIX systems
552  (`issue 11 <https://bitbucket.org/ianb/webob/issue/11>`_)
553
554
5551.0.7
556------
557
558* Fix ``Accept`` header matching for items with zero-quality
559  (`issue 10 <https://bitbucket.org/ianb/webob/issue/10>`_)
560
561* Hide password values in ``MultiDict.__repr__``
562
5631.0.6
564------
565
566* Use ``environ['wsgi.input'].read()`` instead of ``.read(-1)`` because the former
567  is explicitly mentioned in PEP-3333 and CherryPy server does not support the latter.
568
569* Add new ``environ['webob.is_body_readable']`` flag which specifies if the
570  input stream is readable even if the ``CONTENT_LENGTH`` is not set.
571  WebOb now only ever reads the input stream if the content-length is known
572  or this flag is set.
573
574* The two changes above fix a hangup with CherryPy and wsgiref servers
575  (`issue 6 <https://bitbucket.org/ianb/webob/issue/6>`_)
576
577* ``req.body_file`` is now safer to read directly. For ``GET`` and other similar requests
578  it returns an empty ``StringIO`` or ``BytesIO`` object even if the server passed in
579  something else.
580
581* Setting ``req.body_file`` to a string now produces a PendingDeprecationWarning.
582  It will produce DeprecationWarning in 1.1 and raise an error in 1.2. Either
583  set ``req.body_file`` to a file-like object or set ``req.body`` to a string value.
584
585* Fix ``.pop()`` and ``.setdefault(..)`` methods of ``req/resp.cache_control``
586
587* Thanks to the participants of `Pyramid sprint at the PyCon US 2011
588  <https://bitbucket.org/ianb/webob/changeset/7b7dc3ec6159>`_ WebOb now has
589  100% test coverage.
590
5911.0.5
592------
593* Restore Python 2.4 compatibility.
594
5951.0.4
596------
597
598* The field names escaping bug semi-fixed in 1.0.3 and originally blamed on cgi module
599  was in fact a ``webob.request._encode_multipart`` bug (also in Google Chrome) and was
600  lurking in webob code for quite some time -- 1.0.2 just made it trigger more often.
601  Now it is fixed properly.
602
603* Make sure that req.url and related properties do not unnecessarily escape some chars
604  (``:@&+$``) in the URI path (`issue 5 <https://bitbucket.org/ianb/webob/issue/5>`_)
605
606* Revert some changes from 1.0.3 that have broken backwards compatibility for some apps.
607  Getting ``req.body_file`` does not make input stream seekable, but there's a new property
608  ``req.body_file_seekable`` that does.
609
610* ``Request.get_response`` and ``Request.call_application`` seek the input body to start
611  before calling the app (if possible).
612
613* Accessing ``req.body`` 'rewinds' the input stream back to pos 0 as well.
614
615* When accessing ``req.POST`` we now avoid making the body seekable as the input stream data
616  are preserved in ``FakeCGIBody`` anyway.
617
618* Add new method ``Request.from_string``.
619
620* Make sure ``Request.as_string()`` uses CRLF to separate headers.
621
622* Improve parity between ``Request.as_string()`` and ``.from_file``/``.from_string``
623  methods, so that the latter can parse output of the former and create a similar
624  request object which wasn't always the case previously.
625
6261.0.3
627------
628
629* Correct a caching issue introduced in WebOb 1.0.2 that was causing unnecessary reparsing
630  of POST requests.
631
632* Fix a bug regarding field names escaping for forms submitted as ``multipart/form-data``.
633  For more infromation see `the bug report and discussion
634  <https://bitbucket.org/ianb/webob/issue/2>`_ and 1.0.4 notes for further fix.
635
636* Add ``req.http_version`` attribute.
637
6381.0.2
639------
640
641* Primary maintainer is now `Sergey Schetinin <http://self.maluke.com/>`_.
642
643* Issue tracker moved from `Trac <http://bit.ly/webob-tickets>`_ to bitbucket's `issue
644  tracker <https://bitbucket.org/ianb/webob/issues>`_
645
646* WebOb 1.0.1 changed the behavior of ``MultiDict.update`` to be more in line with
647  other dict-like objects. We now also issue a warning when we detect that the
648  client code seems to expect the old, extending semantics.
649
650* Make ``Response.set_cookie(key, None)`` set the 'delete-cookie' (same as ``.delete_cookie(key)``)
651
652* Make ``req.upath_info`` and ``req.uscript_name`` settable
653
654* Add :meth:``Request.as_string()`` method
655
656* Add a ``req.is_body_seekable`` property
657
658* Support for the ``deflate`` method with ``resp.decode_content()``
659
660* To better conform to WSGI spec we no longer attempt to use seek on ``wsgi.input`` file
661  instead we assume it is not seekable unless ``env['webob.is_body_seekable']`` is set.
662  When making the body seekable we set that flag.
663
664* A call to ``req.make_body_seekable()`` now guarantees that the body is seekable, is at 0 position
665  and that a correct ``req.content_length`` is present.
666
667* ``req.body_file`` is always seekable. To access ``env['wsgi.input']`` without any processing,
668  use ``req.body_file_raw``. (Partially reverted in 1.0.4)
669
670* Fix responses to HEAD requests with Range.
671
672* Fix ``del resp.content_type``, ``del req.body``, ``del req.cache_control``
673
674* Fix ``resp.merge_cookies()`` when called with an argument that is not a Response instance.
675
676* Fix ``resp.content_body = None`` (was removing Cache-Control instead)
677
678* Fix ``req.body_file = f`` setting ``CONTENT_LENGTH`` to ``-1`` (now removes from environ)
679
680* Fix: make sure req.copy() leaves the original with seekable body
681
682* Fix handling of WSGI environs with missing ``SCRIPT_NAME``
683
684* A lot of tests were added by Mariano Mara and Danny Navarro.
685
686
687
6881.0.1
689-----
690
691* As WebOb requires Python 2.4 or later, drop some compatibility modules
692  and update the code to use the decorator syntax.
693
694* Implement optional on-the-fly response compression (``resp.encode_content(lazy=True)``)
695
696* Drop ``util.safezip`` module and make ``util`` a module instead of a subpackage.
697  Merge ``statusreasons`` into it.
698
699* Instead of using stdlib ``Cookie`` with monkeypatching, add a derived
700  but thoroughly rewritten, cleaner, safer and faster ``webob.cookies`` module.
701
702* Fix: ``Response.merge_cookies`` now copies the headers before modification instead of
703  doing it in-place.
704
705* Fix: setting request header attribute to ``None`` deletes that header.
706  (Bug only affected the 1.0 release).
707
708* Use ``io.BytesIO`` for the request body file on Python 2.7 and newer.
709
710* If a UnicodeMultiDict was used as the ``multi`` argument of another
711  UnicodeMultiDict, and a ``cgi.FieldStorage`` with a ``filename``
712  with high-order characters was present in the underlying
713  UnicodeMultiDict, a ``UnicodeEncodeError`` would be raised when any
714  helper method caused the ``_decode_value`` method to be called,
715  because the method would try to decode an already decoded string.
716
717* Fix tests to pass under Python 2.4.
718
719* Add descriptive docstrings to each exception in ``webob.exc``.
720
721* Change the behaviour of ``MultiDict.update`` to overwrite existing header
722  values instead of adding new headers. The extending semantics are now available
723  via the ``extend`` method.
724
725* Fix a bug in ``webob.exc.WSGIHTTPException.__init__``.  If a list of
726  ``headers`` was passed as a sequence which contained duplicate keys (for
727  example, multiple ``Set-Cookie`` headers), all but one of those headers
728  would be lost, because the list was effectively flattened into a dictionary
729  as the result of calling ``self.headers.update``.  Fixed via calling
730  ``self.headers.extend`` instead.
731
7321.0
733---
734
735* 1.0, yay!
736
737* Pull in werkzeug Cookie fix for malformed cookie bug.
738
739* Implement :meth:`Request.from_file` and
740  :meth:`Response.from_file` which are kind of the inversion of
741  ``str(req)`` and ``str(resp)``
742
743* Add optional ``pattern`` argument to :meth:`Request.path_info_pop` that requires
744  the ``path_info`` segment to match the passed regexp to get popped and returned.
745
746* Rewrite most of descriptor implementations for speed.
747
748* Reorder descriptor declarations to group them by their semantics.
749
750* Move code around so that there are fewer compat modules.
751
752* Change :meth:``HTTPError.__str__`` to better conform to PEP 352.
753
754* Make :attr:`Request.cache_control` a view on the headers.
755
756* Correct Accept-Language and Accept-Charset matching to fully conform to the HTTP spec.
757
758* Expose parts of :meth:`Request.blank` as :func:`environ_from_url`
759  and :func:`environ_add_POST`
760
761* Fix Authorization header parsing for some corner cases.
762
763* Fix an error generated if the user-agent sends a 'Content_Length' header
764  (note the underscore).
765
766* Kill :attr:`Request.default_charset`. Request charset defaults to UTF-8.
767  This ensures that all values in ``req.GET``, ``req.POST`` and ``req.params``
768  are always unicode.
769
770* Fix the ``headerlist`` and ``content_type`` constructor arguments priorities
771  for :class:`HTTPError` and subclasses.
772
773* Add support for weak etags to conditional Response objects.
774
775* Fix locale-dependence for some cookie dates strings.
776
777* Improve overall test coverage.
778
779* Rename class ``webob.datastruct.EnvironHeaders`` to ``webob.headers.EnvironHeaders``
780
781* Rename class ``webob.headerdict.HeaderDict`` to ``webob.headers.ResponseHeaders``
782
783* Rename class ``webob.updatedict.UpdateDict`` to ``webob.cachecontrol.UpdateDict``
784
7850.9.8
786-----
787
788* Fix issue with WSGIHTTPException inadvertently generating unicode body
789  and failing to encode it
790
791* WWW-Authenticate response header is accessible as
792  ``response.www_authenticate``
793
794* ``response.www_authenticate`` and ``request.authorization`` hold None
795  or tuple ``(auth_method, params)`` where ``params`` is a dictionary
796  (or a string when ``auth_method`` is not one of known auth schemes
797  and for Authenticate: Basic ...)
798
799* Don't share response headers when getting a response like ``resp =
800  req.get_response(some_app)``; this can avoid some funny errors with
801  modifying headers and reusing Response objects.
802
803* Add `overwrite` argument to :meth:`Response.set_cookie` that make the
804  new value overwrite the previously set. `False` by default.
805
806* Add `strict` argument to :meth:`Response.unset_cookie` that controls
807  if an exception should be raised in case there are no cookies to unset.
808  `True` by default.
809
810* Fix ``req.GET.copy()``
811
812* Make sure that 304 Not Modified responses generated by
813  :meth:`Response.conditional_response_app` exclude Content-{Length/Type}
814  headers
815
816* Fix ``Response.copy()`` not being an independent copy
817
818* When the requested range is not satisfiable, return a 416 error
819  (was returning entire body)
820
821* Truncate response for range requests that go beyond the end of body
822  (was treating as invalid).
823
8240.9.7.1
825-------
826
827* Fix an import problem with Pylons
828
8290.9.7
830-----
831
832* Moved repository from svn location to
833  http://bitbucket.org/ianb/webob/
834
835* Arguments to :meth:`Accept.best_match` must be specific types,
836  not wildcards. The server should know a list of specic types it can
837  offer and use ``best_match`` to select a specific one.
838
839* With ``req.accept.best_match([types])`` prefer the first type in the
840  list (previously it preferred later types).
841
842* Also, make sure that if the user-agent accepts multiple types and
843  there are multiple matches to the types that the application offers,
844  ``req.accept.best_match([..])`` returns the most specific match.
845  So if the server can satisfy either ``image/*`` or ``text/plain``
846  types, the latter will be picked independent from the order the accepted
847  or offered types are listed (given they have the same quality rating).
848
849* Fix Range, Content-Range and AppIter support all of which were broken
850  in many ways, incorrectly parsing ranges, reporting incorrect
851  content-ranges, failing to generate the correct body to satisfy the range
852  from ``app_iter`` etc.
853
854* Fix assumption that presense of a ``seek`` method means that the stream
855  is seekable.
856
857* Add ``ubody`` alias for ``Response.unicode_body``
858
859* Add Unicode versions of ``Request.script_name`` and ``path_info``:
860  ``uscript_name`` and ``upath_info``.
861
862* Split __init__.py into four modules: request, response, descriptors and
863  datetime_utils.
864
865* Fix ``Response.body`` access resetting Content-Length to zero
866  for HEAD responses.
867
868* Support passing Unicode bodies to :class:`WSGIHTTPException`
869  constructors.
870
871* Make ``bool(req.accept)`` return ``False`` for requests with missing
872  Accept header.
873
874* Add HTTP version to :meth:`Request.__str__` output.
875
876* Resolve deprecation warnings for parse_qsl on Python 2.6 and newer.
877
878* Fix :meth:`Response.md5_etag` setting Content-MD5 in incorrect
879  format.
880
881* Add ``Request.authorization`` property for Authorization header.
882
883* Make sure ETag value is always quoted (required by RFC)
884
885* Moved most ``Request`` behavior into a new class named
886  ``BaseRequest``.  The ``Request`` class is now a superclass for
887  ``BaseRequest`` and a simple mixin which manages
888  ``environ['webob.adhoc_attrs']`` when ``__setitem__``,
889  ``__delitem__`` and ``__getitem__`` are called.  This allows
890  framework developers who do not want the
891  ``environ['webob.adhoc_attrs']`` mutation behavior from
892  ``__setattr__``.  (chrism)
893
894* Added response attribute ``response.content_disposition`` for its
895  associated header.
896
897* Changed how ``charset`` is determined on :class:`webob.Request`
898  objects.  Now the ``charset`` parameter is read on the Content-Type
899  header, if it is present.  Otherwise a ``default_charset`` parameter
900  is read, or the ``charset`` argument to the Request constructor.
901  This is more similar to how :class:`webob.Response` handles the
902  charset.
903
904* Made the case of the Content-Type header consistent (note: this
905  might break some doctests).
906
907* Make ``req.GET`` settable, such that ``req.environ['QUERY_STRING']``
908  is updated.
909
910* Fix problem with ``req.POST`` causing a re-parse of the body when
911  you instantiate multiple ``Request`` objects over the same environ
912  (e.g., when using middleware that looks at ``req.POST``).
913
914* Recreate the request body properly when a ``POST`` includes file
915  uploads.
916
917* When ``req.POST`` is updated, the generated body will include the
918  new values.
919
920* Added a ``POST`` parameter to :meth:`webob.Request.blank`; when
921  given this will create a request body for the POST parameters (list
922  of two-tuples or dictionary-like object).  Note: this does not
923  handle unicode or file uploads.
924
925* Added method :meth:`webob.Response.merge_cookies`, which takes the
926  ``Set-Cookie`` headers from a Response, and merges them with another
927  response or WSGI application.  (This is useful for flash messages.)
928
929* Fix a problem with creating exceptions like
930  ``webob.exc.HTTPNotFound(body='<notfound/>',
931  content_type='application/xml')`` (i.e., non-HTML exceptions).
932
933* When a Location header is not absolute in a Response, it will be
934  made absolute when the Response is called as a WSGI application.
935  This makes the response less bound to a specific request.
936
937* Added :mod:`webob.dec`, a decorator for making WSGI applications
938  from functions with the signature ``resp = app(req)``.
939
9400.9.6.1
941-------
942
943* Fixed :meth:`Response.__init__`, which for some content types would
944  raise an exception.
945
946* The ``req.body`` property will not recreate a StringIO object
947  unnecessarily when rereading the body.
948
9490.9.6
950-----
951
952* Removed `environ_getter` from :class:`webob.Request`.  This
953  largely-unused option allowed a Request object to be instantiated
954  with a dynamic underlying environ.  Since it wasn't used much, and
955  might have been ill-advised from the beginning, and affected
956  performance, it has been removed (from Chris McDonough).
957
958* Speed ups for :meth:`webob.Response.__init__` and
959  :meth:`webob.Request.__init__`
960
961* Fix defaulting of ``CONTENT_TYPE`` instead of ``CONTENT_LENGTH`` to
962  0 in ``Request.str_POST``.
963
964* Added :meth:`webob.Response.copy`
965
9660.9.5
967-----
968
969* Fix ``Request.blank('/').copy()`` raising an exception.
970
971* Fix a potential memory leak with HEAD requests and 304 responses.
972
973* Make :func:`webob.html_escape` respect the ``.__html__()`` magic
974  method, which allows you to use HTML in
975  :class:`webob.exc.HTTPException` instances.
976
977* Handle unicode values for ``resp.location``.
978
979* Allow arbitrary keyword arguments to ``exc.HTTP*`` (the same
980  keywords you can send to :class:`webob.Response`).
981
982* Allow setting :meth:`webob.Response.cache_expires` (usually it is
983  called as a method).  This is primarily to allow
984  ``Response(cache_expires=True)``.
985
9860.9.4
987-----
988
989* Quiet Python 2.6 deprecation warnings.
990
991* Added an attribute ``unicode_errors`` to :class:`webob.Response` --
992  if set to something like ``unicode_errors='replace'`` it will decode
993  ``resp.body`` appropriately.  The default is ``strict`` (which was
994  the former un-overridable behavior).
995
9960.9.3
997-----
998
999* Make sure that if changing the body the Content-MD5 header is
1000  removed. (Otherwise a lot of middleware would accidentally
1001  corrupt responses).
1002
1003* Fixed ``Response.encode_content('identity')`` case (was a no-op even
1004  for encoded bodies).
1005
1006* Fixed :meth:`Request.remove_conditional_headers` that was removing
1007  If-Match header instead of If-None-Match.
1008
1009* Fixed ``resp.set_cookie(max_age=timedelta(...))``
1010
1011* ``request.POST`` now supports PUT requests with the appropriate
1012  Content-Type.
1013
10140.9.2
1015-----
1016
1017* Add more arguments to :meth:`Request.remove_conditional_headers`
1018  for more fine-grained control: `remove_encoding`, `remove_range`,
1019  `remove_match`, `remove_modified`. All of them are `True` by default.
1020
1021* Add an `set_content_md5` argument to :meth:`Response.md5_etag`
1022  that calculates and sets Content-MD5 reponse header from current
1023  body.
1024
1025* Change formatting of cookie expires, to use the more traditional
1026  format ``Wed, 5-May-2001 15:34:10 GMT`` (dashes instead of spaces).
1027  Browsers should deal with either format, but some other code expects
1028  dashes.
1029
1030* Added in ``sorted`` function for backward compatibility with Python
1031  2.3.
1032
1033* Allow keyword arguments to :class:`webob.Request`, which assign
1034  attributes (possibly overwriting values in the environment).
1035
1036* Added methods :meth:`webob.Request.make_body_seekable` and
1037  :meth:`webob.Request.copy_body`, which make it easier to share a
1038  request body among different consuming applications, doing something
1039  like `req.make_body_seekable(); req.body_file.seek(0)`
1040
10410.9.1
1042-----
1043
1044* ``request.params.copy()`` now returns a writable MultiDict (before
1045  it returned an unwritable object).
1046
1047* There were several things broken with ``UnicodeMultiDict`` when
1048  ``decode_param_names`` is turned on (when the dictionary keys are
1049  unicode).
1050
1051* You can pass keyword arguments to ``Request.blank()`` that will be
1052  used to construct ``Request`` (e.g., ``Request.blank('/',
1053  decode_param_names=True)``).
1054
1055* If you set headers like ``response.etag`` to a unicode value, they
1056  will be encoded as ISO-8859-1 (however, they will remain encoded,
1057  and ``response.etag`` will not be a unicode value).
1058
1059* When parsing, interpret times with no timezone as UTC (previously
1060  they would be interpreted as local time).
1061
1062* Set the Expires property on cookies when using
1063  ``response.set_cookie()``.  This is inherited from ``max_age``.
1064
1065* Support Unicode cookie values
1066
10670.9
1068---
1069
1070* Added ``req.urlarg``, which represents positional arguments in
1071  ``environ['wsgiorg.routing_args']``.
1072
1073* For Python 2.4, added attribute get/set proxies on exception objects
1074  from, for example, ``webob.exc.HTTPNotFound().exception``, so that
1075  they act more like normal response objects (despite not being
1076  new-style classes or ``webob.Response`` objects).  In Python 2.5 the
1077  exceptions are ``webob.Response`` objects.
1078
1079Backward Incompatible Changes
1080~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
1081
1082* The ``Response`` constructor has changed: it is now ``Response([body],
1083  [status], ...)`` (before it was ``Response([status], [body], ...)``).
1084  Body may be str or unicode.
1085
1086* The ``Response`` class defaults to ``text/html`` for the
1087  Content-Type, and ``utf8`` for the charset (charset is only set on
1088  ``text/*`` and ``application/*+xml`` responses).
1089
1090Bugfixes and Small Changes
1091~~~~~~~~~~~~~~~~~~~~~~~~~~
1092
1093* Use ``BaseCookie`` instead of ``SimpleCookie`` for parsing cookies.
1094
1095* Added ``resp.write(text)`` method, which is equivalent to
1096  ``resp.body += text`` or ``resp.unicode_body += text``, depending on
1097  the type of ``text``.
1098
1099* The ``decode_param_names`` argument (used like
1100  ``Request(decode_param_names=True)``) was being ignored.
1101
1102* Unicode decoding of file uploads and file upload filenames were
1103  causing errors when decoding non-file-upload fields (both fixes from
1104  Ryan Barrett).
1105
11060.8.5
1107-----
1108
1109* Added response methods ``resp.encode_content()`` and
1110  ``resp.decode_content()`` to gzip or ungzip content.
1111
1112* ``Response(status=404)`` now works (before you would have to use
1113  ``status="404 Not Found"``).
1114
1115* Bugfix (typo) with reusing POST body.
1116
1117* Added ``226 IM Used`` response status.
1118
1119* Backport of ``string.Template`` included for Python 2.3
1120  compatibility.
1121
11220.8.4
1123-----
1124
1125* ``__setattr__`` would keep ``Request`` subclasses from having
1126  properly settable environ proxies (like ``req.path_info``).
1127
11280.8.3
1129-----
1130
1131* ``request.POST`` was giving FieldStorage objects for *every*
1132  attribute, not just file uploads.  This is fixed now.
1133
1134
1135* Added request attributes ``req.server_name`` and ``req.server_port``
1136  for the environ keys ``SERVER_NAME`` and ``SERVER_PORT``.
1137
1138* Avoid exceptions in ``req.content_length``, even if
1139  ``environ['CONTENT_LENGTH']`` is somehow invalid.
1140
11410.8.2
1142-----
1143
1144* Python 2.3 compatibility: backport of ``reversed(seq)``
1145
1146* Made separate ``.exception`` attribute on ``webob.exc`` objects,
1147  since new-style classes can't be raised as exceptions.
1148
1149* Deprecate ``req.postvars`` and ``req.queryvars``, instead using the
1150  sole names ``req.GET`` and ``req.POST`` (also ``req.str_GET`` and
1151  ``req.str_POST``).  The old names give a warning; will give an error
1152  in next release, and be completely gone in the following release.
1153
1154* ``req.user_agent`` is now just a simple string (parsing the
1155  User-Agent header was just too volatile, and required too much
1156  knowledge about current browsers).  Similarly,
1157  ``req.referer_search_query()`` is gone.
1158
1159* Added parameters ``version`` and ``comment`` to
1160  ``Response.set_cookie()``, per William Dode's suggestion.
1161
1162* Was accidentally consuming file uploads, instead of putting the
1163  ``FieldStorage`` object directly in the parameters.
1164
11650.8.1
1166-----
1167
1168* Added ``res.set_cookie(..., httponly=True)`` to set the ``HttpOnly``
1169  attribute on the cookie, which keeps Javascript from reading the
1170  cookie.
1171
1172* Added some WebDAV-related responses to ``webob.exc``
1173
1174* Set default ``Last-Modified`` when using ``response.cache_expire()``
1175  (fixes issue with Opera)
1176
1177* Generally fix ``.cache_control``
1178
11790.8
1180---
1181
1182First release.  Nothing is new, or everything is new, depending on how
1183you think about it.
1184