Undoc Assumption that Container Keys Cannot Be Non-String Immutables

Bug #98332 reported by Jeff Rush
2
Affects Status Importance Assigned to Milestone
Zope 3
Fix Released
Critical
Unassigned

Bug Description

The traversal code makes an undocumented assumption that keys() are strings or something that list(path) can be called on. But containers that have non-string but immutable values as keys raise the exception:

  path = list(path)
  TypeError: iteration over non-sequence

from within zope/app/traversing/adapters.py

In my case, my keys are small integers, which (correctly) fail to test as strings, and then raise the above exception when the code in adapters.py tries to coerce an integer to a list(). My workaround is to change my keys() to stringified ints. This issue should be reviewed as to whether this restriction is intentional/desirable and either removed or documented. There shouldn't be an unclear unassumption of the return type of IContainer.keys().

To duplicate the problem, just toss together a minimal IContainer, have keys() return unique integers, and traverse it, in my case, using @@singleBranchTree.xml from within the Rotterdam skin. But it fails for any traversal.

Tags: core issue
Revision history for this message
Philipp von Weitershausen (philikon) wrote :

The assumption is that container names are unicodes. Because of Python's (stupid) feature that strings can be compared to unicodes and are considered equal sometimes (e.g. 'hi' == u'hi'), ASCII strings are also acceptable.

If this is undocumented (I couldn't find any documetnation in IWriteContainer), then this indeed needs to be documented. Feel free to round up a patch, Jeff. :)

By the way, the traversing API is also documented by interfaces. Perhaps it should be made clear that names are always expected to be unicodes for traversal as well.

Revision history for this message
Stephan Richter (srichter) wrote :

Changes: submitter email, edited transcript, importance (medium => critical), revised version_info, new comment

I have fallen into this trap before as well. This really deserves a few lines of writing in the interfaces.

Revision history for this message
Philipp von Weitershausen (philikon) wrote :

Status: Pending => Resolved

IWriteContainer says:

    def __setitem__(name, object):
        """Add the given `object` to the container under the given name.

        Raises a ``TypeError`` if the key is not a unicode or ascii string.
        Raises a ``ValueError`` if key is empty.

So, it's pretty clear that names must be Unicode objects or ASCII strings. I have no idea how new this docstring is, but at least it's there now.

In addition to that I went through the traversal interfaces in zope.publisher and zope.traversing and added notes wherever applicable that traversed names must be ASCII or unicode strings as well. Checked in in r69595/r69596.

To post a comment you must log in.
This report contains Public information  
Everyone can see this information.

Other bug subscribers

Remote bug watches

Bug watches keep track of this bug in other bug trackers.