[Python-Dev] Should urlencode() sort the query parameters (if they come from a dict)?

MRAB python at mrabarnett.plus.com
Sat Aug 18 20:47:57 CEST 2012


On 18/08/2012 18:34, Guido van Rossum wrote:
> On Sat, Aug 18, 2012 at 6:28 AM, Christian Heimes <lists at cheimes.de> wrote:
>> Am 17.08.2012 21:27, schrieb Guido van Rossum:
>>> I wonder if it wouldn't make sense to change urlencode() to generate
>>> URLs that don't depend on the hash order, for all versions of Python
>>> that support PYTHONHASHSEED? It seems a one-line fix:
>>>>>> query = query.items()
>>>>>> with this:
>>>>>> query = sorted(query.items())
>>>>>> This would not prevent breakage of unit tests, but it would make a
>>> much simpler fix possible: simply sort the parameters in the URL.
>>>> I vote -0. The issue can also be addressed with a small and simple
>> helper function that wraps urlparse and compares the query parameter. Or
>> you cann urlencode() with `sorted(qs.items)` instead of `qs` in the
>> application.
>> Hm. That's actually a good point.
>>> The order of query string parameter is actually important for some
>> applications, for example Zope, colander+deform and other form
>> frameworks use the parameter order to group parameters.
>>>> Therefore I propose that the query string is only sorted when the query
>> is exactly a dict and not some subclass or class that has an items() method.
>>>> if type(query) is dict:
>> query = sorted(query.items())
>> else:
>> query = query.items()
>> That's already in the bug I filed. :-) I also added that the sort may
> fail if the keys mix e.g. bytes and str (or int and str, for that
> matter).
>One possible way around that is to add the class names, perhaps only if
sorting raises an exception:
def make_key(pair):
 return type(pair[0]).__name__, type(pair[1]).__name__, pair
if type(query) is dict:
 try:
 query = sorted(query.items())
 except TypeError:
 query = sorted(query.items(), key=make_key)
else:
 query = query.items()


More information about the Python-Dev mailing list

AltStyle によって変換されたページ (->オリジナル) /