Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Resolver spends too much time calculating "weights" to parents #10557

Closed
1 task done
Rizhiy opened this issue Oct 7, 2021 · 34 comments · Fixed by #10574
Closed
1 task done

Resolver spends too much time calculating "weights" to parents #10557

Rizhiy opened this issue Oct 7, 2021 · 34 comments · Fixed by #10574
Labels
C: dependency resolution About choosing which dependencies to install

Comments

@Rizhiy
Copy link

Rizhiy commented Oct 7, 2021

Description

When running something like pip install -c requirements.txt <package_name> sometimes pip starts checking unnecessary versions.

I know that version checking is unnecessary because requirements.txt contains all the packages with exact versions.

Everything works as expected with legacy resolver.

Expected behaviour

Since all of the versions are already specified, just get them.

pip version

21.2.4

Python version

3.8.8

OS

Ubuntu

How to Reproduce

Unfortunately, I can't provide a reproducible example since it only happens with a package on internal pip index.

The offending package does have the version specified in requirements.txt and a different version is installed when the command is run.

Output

It says something like:

INFO: pip is looking at multiple versions of kiwisolver to determine which version is compatible with other requirements. This could take a while.

But I already have kiwisolver==1.3.1 in my requirements.txt.

Code of Conduct

@Rizhiy Rizhiy added S: needs triage Issues/PRs that need to be triaged type: bug A confirmed bug or unintended behavior labels Oct 7, 2021
@Rizhiy
Copy link
Author

Rizhiy commented Oct 7, 2021

When I installed the offending package manually with the correct version, I got an error that it's version is incompatible with another specified package.

After resolving the conflict, the installation succeeds properly.

So I guess the problem is that there is a conflict in requirements.txt and pip tries to resolve it, but it is not possible.

Also, pip starts checking versions for packages which are not even part of the conflict which is bad.

@Rizhiy
Copy link
Author

Rizhiy commented Oct 7, 2021

I think I got the rough behaviour:

  • I'm installing package A, which has unrestricted dependency on package B
  • The latest version of package B has a restricted dependency on package C, which is in conflict with original requirements.txt
  • Pip detects the conflict and starts checking other versions of package B, which I believe causes it to also check different versions of B's dependencies even though all of them are already specified in original requirements.txt.
  • If there are a lot of dependencies trying to check all possible combinations will take a long time.

I will try to make a reproducible example later.

@DiddiLeija DiddiLeija added C: dependency resolution About choosing which dependencies to install state: needs reproducer Need to reproduce issue and removed S: needs triage Issues/PRs that need to be triaged labels Oct 7, 2021
@uranusjr
Copy link
Member

uranusjr commented Oct 8, 2021

There's no way to reproduce without your requirements.txt.

@uranusjr uranusjr added the S: awaiting response Waiting for a response/more information label Oct 8, 2021
@mauritsvanrees
Copy link
Sponsor Contributor

We have (probably) the same problem when installing Plone with pip. To reproduce (using an alpha version here) do the following. With an older pip (19.2.3) this works, or with latest pip and the legacy resolver, like here:

$ python3.9 -mvenv .
$ bin/pip install -U pip
...
Successfully installed pip-21.2.4
$ bin/pip install Products.CMFPlone -c https://dist.plone.org/release/pip-resolver-test/constraints.txt --use-deprecated legacy-resolver
$ time bin/pip install Products.CMFPlone --use-deprecated legacy-resolver
...lots of: Requirement already satisfied...
real	0m2.379s
user	0m2.208s
sys	0m0.163s

The first pip command needs to install a lot of packages, so it will take a while. The last command as you can see takes maybe two or three seconds.

Now retry with the standard resolver. Remember that the package is already installed, all dependencies were pinned in the constraints, I can start python and import Products.CMFPlone, so this should again take just a few seconds, right?

$ time bin/pip install Products.CMFPlone
...
real	4m5.401s
user	4m3.950s
sys	0m0.703s

Yes, that is four minutes, instead of a few seconds.
This is on Mac OS X 10.15.7.
In an earlier try, I stopped the process after about ten minutes, as I thought it was probably stuck in an eternal loop. Today for a completely different problem I raised the open file limit from 256 to 400 (ulimit -n 400) and that makes the command at least finish, so that is interesting.

I had a look with py-spy and it said:

Process 43996: /Users/maurits/tmp/piptestoctober/bin/python3.9 bin/pip install Products.CMFPlone
Python v3.9.7 (/Users/maurits/.pyenv/versions/3.9.7/bin/python3.9)

Thread 0x10F3F5DC0 (active+gil): "MainThread"
    visit (pip/_internal/resolution/resolvelib/resolver.py:243)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    visit (pip/_internal/resolution/resolvelib/resolver.py:245)
    get_topological_weights (pip/_internal/resolution/resolvelib/resolver.py:252)
    get_installation_order (pip/_internal/resolution/resolvelib/resolver.py:202)
    run (pip/_internal/commands/install.py:371)
    wrapper (pip/_internal/cli/req_command.py:203)
    _main (pip/_internal/cli/base_command.py:173)
    main (pip/_internal/cli/base_command.py:98)
    main (pip/_internal/cli/main.py:70)
    <module> (pip:8)

See also a thread on community.plone.org. One problem we found there, were cyclic dependencies, but we solved them all in the constraints used in my example above.

@mauritsvanrees
Copy link
Sponsor Contributor

For good measure, I thought I would make pip more verbose, but there does not seem to be anything interesting:

$ time bin/pip install Products.CMFPlone -vvvvvvvvvvvvvvv
Using pip 21.2.4 from /Users/maurits/tmp/piptestoctober/lib/python3.9/site-packages/pip (python 3.9)
Non-user install because user site-packages disabled
Created temporary directory: /private/var/folders/26/1plvhxbs6yx7g_82v2xdxc500000gn/T/pip-ephem-wheel-cache-4am_pg69
Created temporary directory: /private/var/folders/26/1plvhxbs6yx7g_82v2xdxc500000gn/T/pip-req-tracker-8mhy15lm
Initialized build tracking at /private/var/folders/26/1plvhxbs6yx7g_82v2xdxc500000gn/T/pip-req-tracker-8mhy15lm
Created build tracker: /private/var/folders/26/1plvhxbs6yx7g_82v2xdxc500000gn/T/pip-req-tracker-8mhy15lm
Entered build tracker: /private/var/folders/26/1plvhxbs6yx7g_82v2xdxc500000gn/T/pip-req-tracker-8mhy15lm
Created temporary directory: /private/var/folders/26/1plvhxbs6yx7g_82v2xdxc500000gn/T/pip-install-erlzkofm
Requirement already satisfied: Products.CMFPlone in ./lib/python3.9/site-packages (6.0.0a1.dev0)
...
Created temporary directory: /private/var/folders/26/1plvhxbs6yx7g_82v2xdxc500000gn/T/pip-unpack-292uz9ut
... after again almost 4 minutes:
Removed build tracker: '/private/var/folders/26/1plvhxbs6yx7g_82v2xdxc500000gn/T/pip-req-tracker-8mhy15lm'

I checked the directories a couple of times during the process, but there was nothing in them.

@uranusjr
Copy link
Member

uranusjr commented Oct 9, 2021

Closing since OP did not provide a reproduction, and the available reproduction has been fixed in #10239.

@uranusjr uranusjr closed this as completed Oct 9, 2021
@uranusjr uranusjr added resolution: duplicate Duplicate of an existing issue/PR and removed type: bug A confirmed bug or unintended behavior C: dependency resolution About choosing which dependencies to install S: awaiting response Waiting for a response/more information state: needs reproducer Need to reproduce issue labels Oct 9, 2021
@Rizhiy
Copy link
Author

Rizhiy commented Oct 9, 2021

@uranusjr Except it clearly hasn't, as indicated by example in @mauritsvanrees response?
This is either a new bug or you have a regression.

Here is the example:

pip install Products.CMFPlone -c https://dist.plone.org/release/pip-resolver-test/constraints.txt --use-deprecated legacy-resolver # Takes a long time for all dependencies
pip install Products.CMFPlone -c https://dist.plone.org/release/pip-resolver-test/constraints.txt --use-deprecated legacy-resolver # Takes 2 seconds
pip install Products.CMFPlone -c https://dist.plone.org/release/pip-resolver-test/constraints.txt # Hasn't finished after 2 minutes

Tested today with pip==21.2.4, which is after 21.2.2

P.S. Surely, closing the issue after 2 days just because I couldn't provide an example is ridiculous.

@uranusjr
Copy link
Member

uranusjr commented Oct 9, 2021

Likely I linked to an incorrect PR then. The bottom line is I couldn't reproduce on main.

@Rizhiy
Copy link
Author

Rizhiy commented Oct 9, 2021

I have checked that all the installed packages are specified in https://dist.plone.org/release/pip-resolver-test/constraints.txt (in fact it is overspecified by quite a bit).
Packages in constraints.txt are out of order, so you should sort it before comparing.

@Rizhiy
Copy link
Author

Rizhiy commented Oct 9, 2021

@uranusjr

Likely I linked to an incorrect PR then. The bottom line is I couldn't reproduce on main.

Just checked on main (21.3.dev0), still having problem:

git clone https://github.com/pypa/pip.git
pip install -e pip
python -m pip install Products.CMFPlone -c https://dist.plone.org/release/pip-resolver-test/constraints.txt --use-deprecated legacy-resolver # Takes a long time for all dependencies
python -m pip install Products.CMFPlone -c https://dist.plone.org/release/pip-resolver-test/constraints.txt --use-deprecated legacy-resolver # Takes 2 seconds
python -m pip install Products.CMFPlone -c https://dist.plone.org/release/pip-resolver-test/constraints.txt # Hasn't finished after 2 minutes

@Rizhiy
Copy link
Author

Rizhiy commented Oct 9, 2021

Also, if you run the installation command with -vv and Ctrl-C when it hangs, you get the stack trace which shows that resolver is doing too much work:

  File "/home/rizhiy/projects/pip/src/pip/_internal/cli/base_command.py", line 164, in exc_logging_wrapper
    status = run_func(*args)
  File "/home/rizhiy/projects/pip/src/pip/_internal/cli/req_command.py", line 204, in wrapper
    return func(self, options, args)
  File "/home/rizhiy/projects/pip/src/pip/_internal/commands/install.py", line 388, in run
    to_install = resolver.get_installation_order(requirement_set)
  File "/home/rizhiy/projects/pip/src/pip/_internal/resolution/resolvelib/resolver.py", line 181, in get_installation_order
    weights = get_topological_weights(
  File "/home/rizhiy/projects/pip/src/pip/_internal/resolution/resolvelib/resolver.py", line 231, in get_topological_weights
    visit(None)
  File "/home/rizhiy/projects/pip/src/pip/_internal/resolution/resolvelib/resolver.py", line 224, in visit
    visit(child)
  File "/home/rizhiy/projects/pip/src/pip/_internal/resolution/resolvelib/resolver.py", line 224, in visit
    visit(child)
  File "/home/rizhiy/projects/pip/src/pip/_internal/resolution/resolvelib/resolver.py", line 224, in visit
    visit(child)
  [Previous line repeated 13 more times]
  File "/home/rizhiy/projects/pip/src/pip/_internal/resolution/resolvelib/resolver.py", line 228, in visit
    weights[node] = max(last_known_parent_count, len(path))

@uranusjr
Copy link
Member

uranusjr commented Oct 9, 2021

If that's where the resolver hangs, your issue is not about constraints, since when the resolver reaches that point, it should have already finished version resolution, including constraints.

@uranusjr uranusjr reopened this Oct 9, 2021
@uranusjr uranusjr added state: needs reproducer Need to reproduce issue C: dependency resolution About choosing which dependencies to install and removed resolution: duplicate Duplicate of an existing issue/PR state: needs reproducer Need to reproduce issue labels Oct 9, 2021
@uranusjr uranusjr changed the title Constraints checks too many versions Resolver spends too much time calculating "weights" to parents Oct 9, 2021
@pradyunsg
Copy link
Member

Using #10481 and running:

$ pip install https://github.com/notatallshaw/pip/archive/refs/heads/prefer_failures.zip
$ python -m pip install Products.CMFPlone -c https://dist.plone.org/release/pip-resolver-test/constraints.txt --log /tmp/log.txt

The relevant log messages are:

2021-10-09T11:22:41,817 Using pip 21.3.dev0 from /Users/pradyunsg/Developer/resolvelib/.venv/lib/python3.9/site-packages/pip (python 3.9)
2021-10-09T11:24:36,613 Successfully built AccessControl ExtensionClass zope.i18nmessageid Acquisition pyScss z3c.autoinclude ZODB3 zope.container BTrees Chameleon lxml Persistence repoze.xmliter zope.hookable zope.proxy zope.security Zope2 python-gettext zope.globalrequest zodbpickle cffi future sgmllib3k z3c.formwidget.query zdaemon z3c.objpath

And that seems to tell me that the resolution is pretty quick with the fixes in #10481.

@pradyunsg
Copy link
Member

Note that this involved downloads as well. Running again with wheel instead, with all the downloads cached:

@uranusjr
Copy link
Member

uranusjr commented Oct 9, 2021

From the report, resolution time isn't the actual issue though, it's after the resolution where we sort packages for installation.

@pradyunsg
Copy link
Member

Indeed. Here's the graph we're trying to do that with:

2021-10-09T11:56:22,896 vertices: ['plone-namedfile[blobs]', 'zope-testbrowser', 'zope-container', 'plone-browserlayer', 'zope-hookable', 'zope-i18n[zcml]', 'plone-app-linkintegrity', 'z3c-autoinclude', 'zope-deprecation', 'plone-namedfile[scales]', 'plone-subrequest', 'plone-schemaeditor', 'plone-app-contentlisting', 'products-dcworkflow', 'products-pythonscripts', 'z3c-zcmlhook', 'zodbpickle', 'plone-session', 'zconfig', 'zope-componentvocabulary', 'plone-app-intid', 'products-btreefolder2', 'zope-schema', 'zope-cachedescriptors', 'zdaemon', 'products-pluggableauthservice', 'plone-portlet-collection', 'products-cmfdifftool', 'plone-app-event', 'plone-app-contenttypes', 'transaction', 'sgmllib3k', 'pillow', 'simplejson', 'zope-intid', '<Python from Requires-Python>', 'z3c-pt', 'zope-interface', None, 'zope-configuration', 'pytz', 'products-externalmethod', 'zope-browsermenu', 'setuptools', 'products-zopeversioncontrol', 'beautifulsoup4', 'authencoding', 'z3c-formwidget-query', 'plone-resourceeditor', 'zope-event', 'plone-app-registry', 'plone-scale', 'plone-app-customerize', 'products-standardcachemanagers', 'wsgiproxy2', 'zope-sendmail', 'products-pluginregistry', 'plone-scale[storage]', 'products-daterecurringindex', 'zope-component[zcml]', 'z3c-caching[zcml]', 'six', 'plone-folder', 'cssselect', 'zope-dottedname', 'record', 'plone-autoform', 'plone-app-portlets', 'plone-app-contentmenu', 'plone-app-workflow', 'zope-site', 'plone-z3cform', 'plone-protect', 'plone-app-uuid', 'plone-staticresources', 'plone-app-lockingbehavior', 'lxml[cssselect]', 'plone-intelligenttext', 'zope-contenttype', 'products-cmfdynamicviewfti', 'plone-app-contentrules', 'repoze-xmliter', 'zeo', 'restrictedpython', 'plone-portlets', 'zope-component', 'roman', 'waitress', 'plone-app-viewletmanager', 'plone-synchronize', 'cffi', 'zope-sequencesort', 'products-cmfcore', 'acquisition', 'products-genericsetup', 'plone-app-locales', 'plone-alterego', 'plone-registry', 'z3c-objpath', 'products-zcatalog', 'plone-app-dexterity', 'products-isurlinportal', 'products-portaltransforms', 'plone-app-relationfield', 'plone-behavior', 'soupsieve', 'plone-app-discussion', 'products-extendedpathindex', 'plone-app-users', 'docutils', 'mockup', 'plone-app-content', 'five-localsitemanager', 'zope-proxy', 'plone-portlet-static', 'zope-contentprovider', 'plone-supermodel', 'zope-browserpage', 'unidecode', 'plone-app-i18n', 'diazo', 'zope-tales', 'plone-app-versioningbehavior', 'products-mimetypesregistry', 'extensionclass', 'zope-i18nmessageid', 'zope-structuredtext', 'products-mailhost', 'python-dateutil', 'zope-security', 'pastedeploy', 'jsonschema', 'zope[wsgi]', 'plone-i18n', 'collective-monkeypatcher', 'zodb3', 'plone-app-textfield', 'zc-relation', 'zope-pagetemplate', 'zope-location', 'plone-formwidget-namedfile', 'products-cmfuid', 'zope-traversing', 'zope-deferredimport', 'zexceptions', 'zope-ramcache', 'products-siteerrorlog', 'products-cmfeditions', 'plone-app-multilingual', 'zodb', 'zope-app-locales', 'multipart', 'products-cmfplone', 'calmjs-parse', 'plone-app-theming', 'markdown', 'plone-memoize', 'plone-transformchain', 'z3c-relationfield', 'five-customerize', 'five-intid', 'plone-app-widgets', 'lxml', 'attrs', 'zope-publisher', 'plone-theme', 'zope-browserresource', 'accesscontrol', 'plone-caching', 'products-plonepas', 'plone-api', 'multimapping', 'documenttemplate', 'zope-testing', 'plone-resource', 'webtest', 'plone-namedfile', 'products-sessions', 'missing', 'chameleon', 'plone-app-layout', 'plone-app-vocabularies', 'plone-app-redirector', 'products-statusmessages', 'zope-viewlet', 'pyrsistent', 'plone-locking', 'plone-app-dexterity[relations]', 'plone-keyring', 'plone-stringinterp', 'python-gettext', 'zope2', 'piexif', 'plone-contentrules', 'zope-i18n', 'datetime', 'persistent', 'webob', 'pycparser', 'plone-dexterity', 'plonetheme-barceloneta', 'plone-batching', 'plone-event', 'zope-globalrequest', 'feedparser', 'zope-size', 'plone-app-querystring', 'decorator', 'z3c-form', 'btrees', 'zope-tal', 'zope-datetime', 'borg-localrole', 'zc-lockfile', 'zope-copy', 'plone-app-z3cform', 'zope-exceptions', 'plone-outputfilters', 'pyscss', 'plone-formwidget-recurrence', 'zope-browser', 'persistence', 'plone-formwidget-recurrence[z3cform]', 'paste', 'icalendar', 'zope-annotation', 'plone-indexer', 'zope-ptresource', 'zope-filerepresentation', 'plone-rfc822', 'plone-uuid', 'zope-keyreference', 'ply', 'future', 'zope-lifecycleevent', 'plone-schema', 'z3c-caching', 'zope-processlifetime', 'zope']
2021-10-09T11:56:22,897 edges: [(None, 'products-cmfplone'), ('products-cmfplone', 'zope-container'), ('products-cmfplone', 'plone-browserlayer'), ('products-cmfplone', 'plone-app-linkintegrity'), ('products-cmfplone', 'zope-deprecation'), ('products-cmfplone', 'plone-subrequest'), ('products-cmfplone', 'plone-app-contentlisting'), ('products-cmfplone', 'products-dcworkflow'), ('products-cmfplone', 'plone-session'), ('products-cmfplone', 'zope-cachedescriptors'), ('products-cmfplone', 'plone-portlet-collection'), ('products-cmfplone', 'products-pluggableauthservice'), ('products-cmfplone', 'products-cmfdifftool'), ('products-cmfplone', 'plone-app-contenttypes'), ('products-cmfplone', 'transaction'), ('products-cmfplone', 'pillow'), ('products-cmfplone', 'zope-interface'), ('products-cmfplone', 'setuptools'), ('products-cmfplone', 'zope-event'), ('products-cmfplone', 'plone-app-registry'), ('products-cmfplone', 'plone-app-customerize'), ('products-cmfplone', 'products-pluginregistry'), ('products-cmfplone', 'plone-folder'), ('products-cmfplone', 'zope-dottedname'), ('products-cmfplone', 'plone-app-portlets'), ('products-cmfplone', 'plone-app-contentmenu'), ('products-cmfplone', 'plone-app-workflow'), ('products-cmfplone', 'zope-site'), ('products-cmfplone', 'plone-protect'), ('products-cmfplone', 'plone-app-uuid'), ('products-cmfplone', 'plone-staticresources'), ('products-cmfplone', 'plone-intelligenttext'), ('products-cmfplone', 'products-cmfdynamicviewfti'), ('products-cmfplone', 'plone-app-contentrules'), ('products-cmfplone', 'plone-portlets'), ('products-cmfplone', 'zope-component'), ('products-cmfplone', 'plone-app-viewletmanager'), ('products-cmfplone', 'products-cmfcore'), ('products-cmfplone', 'acquisition'), ('products-cmfplone', 'products-genericsetup'), ('products-cmfplone', 'plone-app-locales'), ('products-cmfplone', 'plone-registry'), ('products-cmfplone', 'products-isurlinportal'), ('products-cmfplone', 'plone-app-dexterity'), ('products-cmfplone', 'products-portaltransforms'), ('products-cmfplone', 'plone-app-discussion'), ('products-cmfplone', 'products-extendedpathindex'), ('products-cmfplone', 'plone-app-users'), ('products-cmfplone', 'mockup'), ('products-cmfplone', 'plone-app-content'), ('products-cmfplone', 'five-localsitemanager'), ('products-cmfplone', 'plone-portlet-static'), ('products-cmfplone', 'plone-app-i18n'), ('products-cmfplone', 'zope-tales'), ('products-cmfplone', 'products-mimetypesregistry'), ('products-cmfplone', 'extensionclass'), ('products-cmfplone', 'zope-i18nmessageid'), ('products-cmfplone', 'zope-structuredtext'), ('products-cmfplone', 'zope[wsgi]'), ('products-cmfplone', 'plone-i18n'), ('products-cmfplone', 'zodb3'), ('products-cmfplone', 'zope-location'), ('products-cmfplone', 'zope-pagetemplate'), ('products-cmfplone', 'products-cmfuid'), ('products-cmfplone', 'zope-traversing'), ('products-cmfplone', 'zope-deferredimport'), ('products-cmfplone', 'products-siteerrorlog'), ('products-cmfplone', 'products-cmfeditions'), ('products-cmfplone', 'plone-app-multilingual'), ('products-cmfplone', 'zope-app-locales'), ('products-cmfplone', 'calmjs-parse'), ('products-cmfplone', 'plone-app-theming'), ('products-cmfplone', 'plone-memoize'), ('products-cmfplone', 'five-customerize'), ('products-cmfplone', 'zope-publisher'), ('products-cmfplone', 'plone-theme'), ('products-cmfplone', 'accesscontrol'), ('products-cmfplone', 'products-plonepas'), ('products-cmfplone', 'plone-api'), ('products-cmfplone', 'plone-app-vocabularies'), ('products-cmfplone', 'plone-app-redirector'), ('products-cmfplone', 'plone-app-layout'), ('products-cmfplone', 'products-statusmessages'), ('products-cmfplone', 'plone-locking'), ('products-cmfplone', 'plone-contentrules'), ('products-cmfplone', 'zope-i18n'), ('products-cmfplone', 'datetime'), ('products-cmfplone', 'plonetheme-barceloneta'), ('products-cmfplone', 'plone-batching'), ('products-cmfplone', 'zope-tal'), ('products-cmfplone', 'borg-localrole'), ('products-cmfplone', 'plone-outputfilters'), ('products-cmfplone', 'pyscss'), ('products-cmfplone', 'plone-indexer'), ('products-cmfplone', 'plone-schema'), ('products-cmfplone', 'z3c-autoinclude'), ('plone-app-event', 'plone-namedfile'), ('plone-app-event', 'plone-autoform'), ('plone-app-event', 'plone-app-portlets'), ('plone-app-event', 'zope-i18nmessageid'), ('plone-app-event', 'zope-container'), ('plone-app-event', 'plone-browserlayer'), ('plone-app-event', 'plone-app-vocabularies'), ('plone-app-event', 'plone-app-layout'), ('plone-app-event', 'products-statusmessages'), ('plone-app-event', 'plone-app-contentlisting'), ('plone-app-event', 'plone-z3cform'), ('plone-app-event', 'zope-schema'), ('plone-app-event', 'zope2'), ('plone-app-event', 'plone-app-textfield'), ('plone-app-event', 'zope-i18n'), ('plone-app-event', 'datetime'), ('plone-app-event', 'transaction'), ('plone-app-event', 'plone-portlets'), ('plone-app-event', 'plone-dexterity'), ('plone-app-event', 'zope-component'), ('plone-app-event', 'plone-event'), ('plone-app-event', 'zope-globalrequest'), ('plone-app-event', 'plone-app-querystring'), ('plone-app-event', 'zope-interface'), ('plone-app-event', 'z3c-form'), ('plone-app-event', 'plone-app-multilingual'), ('plone-app-event', 'products-cmfcore'), ('plone-app-event', 'acquisition'), ('plone-app-event', 'pytz'), ('plone-app-event', 'products-genericsetup'), ('plone-app-event', 'setuptools'), ('plone-app-event', 'products-cmfplone'), ('plone-app-event', 'plone-registry'), ('plone-app-event', 'products-zcatalog'), ('plone-app-event', 'plone-app-dexterity'), ('plone-app-event', 'plone-app-z3cform'), ('plone-app-event', 'plone-memoize'), ('plone-app-event', 'zope-event'), ('plone-app-event', 'plone-behavior'), ('plone-app-event', 'plone-app-registry'), ('plone-app-event', 'plone-formwidget-recurrence[z3cform]'), ('plone-app-event', 'icalendar'), ('plone-app-event', 'zope-annotation'), ('plone-app-event', 'plone-indexer'), ('plone-app-event', 'zope-publisher'), ('plone-app-event', 'plone-uuid'), ('plone-app-event', 'zope-contentprovider'), ('plone-app-event', 'products-daterecurringindex'), ('plone-app-event', 'plone-supermodel'), ('plone-app-event', 'six'), ('plone-app-event', 'zope-lifecycleevent'), ('plone-app-event', 'plone-folder'), ('plone-app-querystring', 'zope-dottedname'), ('plone-app-querystring', 'zope-i18nmessageid'), ('plone-app-querystring', 'plone-app-layout'), ('plone-app-querystring', 'python-dateutil'), ('plone-app-querystring', 'plone-app-contentlisting'), ('plone-app-querystring', 'zope-schema'), ('plone-app-querystring', 'zope-i18n'), ('plone-app-querystring', 'datetime'), ('plone-app-querystring', 'zope-component'), ('plone-app-querystring', 'plone-batching'), ('plone-app-querystring', 'zope-globalrequest'), ('plone-app-querystring', 'zope-interface'), ('plone-app-querystring', 'products-cmfcore'), ('plone-app-querystring', 'setuptools'), ('plone-app-querystring', 'products-cmfplone'), ('plone-app-querystring', 'plone-registry'), ('plone-app-querystring', 'plone-app-registry'), ('plone-app-querystring', 'zope-publisher'), ('plone-app-querystring', 'six'), ('plone-app-z3cform', 'zope-i18nmessageid'), ('plone-app-z3cform', 'zope-deprecation'), ('plone-app-z3cform', 'plone-z3cform'), ('plone-app-z3cform', 'plone-protect'), ('plone-app-z3cform', 'zope-schema'), ('plone-app-z3cform', 'zope2'), ('plone-app-z3cform', 'plone-app-textfield'), ('plone-app-z3cform', 'zope-i18n'), ('plone-app-z3cform', 'zope-component'), ('plone-app-z3cform', 'zope-traversing'), ('plone-app-z3cform', 'zope-globalrequest'), ('plone-app-z3cform', 'z3c-form'), ('plone-app-z3cform', 'zope-interface'), ('plone-app-z3cform', 'products-cmfcore'), ('plone-app-z3cform', 'acquisition'), ('plone-app-z3cform', 'setuptools'), ('plone-app-z3cform', 'products-cmfplone'), ('plone-app-z3cform', 'z3c-formwidget-query'), ('plone-app-z3cform', 'plone-app-widgets'), ('plone-app-z3cform', 'six'), ('plone-app-z3cform', 'zope-browserpage'), ('plone-app-widgets', 'products-cmfplone'), ('plone-app-widgets', 'six'), ('plone-app-widgets', 'setuptools'), ('plone-app-widgets', 'plone-app-vocabularies'), ('plone-formwidget-recurrence[z3cform]', 'z3c-form'), ('plone-formwidget-recurrence[z3cform]', 'zope-schema'), ('plone-formwidget-recurrence[z3cform]', 'setuptools'), ('plone-formwidget-recurrence[z3cform]', 'products-cmfplone'), ('plone-formwidget-recurrence[z3cform]', 'zope-i18nmessageid'), ('plone-formwidget-recurrence[z3cform]', 'zope-i18n'), ('plone-formwidget-recurrence[z3cform]', 'zope-component'), ('plone-formwidget-recurrence[z3cform]', 'zope-traversing'), ('plone-formwidget-recurrence[z3cform]', 'python-dateutil'), ('plone-formwidget-recurrence[z3cform]', 'plone-formwidget-recurrence'), ('plone-formwidget-recurrence[z3cform]', 'zope-interface'), ('plone-formwidget-recurrence[z3cform]', 'products-cmfcore'), ('plone-formwidget-recurrence', 'setuptools'), ('plone-formwidget-recurrence', 'products-cmfplone'), ('plone-formwidget-recurrence', 'zope-i18nmessageid'), ('plone-formwidget-recurrence', 'zope-i18n'), ('plone-formwidget-recurrence', 'zope-component'), ('plone-formwidget-recurrence', 'python-dateutil'), ('plone-formwidget-recurrence', 'zope-interface'), ('plone-formwidget-recurrence', 'products-cmfcore'), ('zope-dottedname', 'setuptools'), ('plone-app-layout', 'zope-dottedname'), ('plone-app-layout', 'plone-app-portlets'), ('plone-app-layout', 'zope-deprecation'), ('plone-app-layout', 'zope-viewlet'), ('plone-app-layout', 'zope-schema'), ('plone-app-layout', 'plone-i18n'), ('plone-app-layout', 'products-cmfdynamicviewfti'), ('plone-app-layout', 'zope2'), ('plone-app-layout', 'zope-i18n'), ('plone-app-layout', 'datetime'), ('plone-app-layout', 'plone-portlets'), ('plone-app-layout', 'zope-component'), ('plone-app-layout', 'plone-batching'), ('plone-app-layout', 'zope-deferredimport'), ('plone-app-layout', 'plone-app-viewletmanager'), ('plone-app-layout', 'zope-interface'), ('plone-app-layout', 'products-cmfeditions'), ('plone-app-layout', 'products-cmfcore'), ('plone-app-layout', 'acquisition'), ('plone-app-layout', 'setuptools'), ('plone-app-layout', 'plone-registry'), ('plone-app-layout', 'plone-memoize'), ('plone-app-layout', 'zope-publisher'), ('plone-app-layout', 'plone-app-content'), ('plone-app-layout', 'six'), ('products-cmfeditions', 'acquisition'), ('products-cmfeditions', 'zope-dottedname'), ('products-cmfeditions', 'products-genericsetup'), ('products-cmfeditions', 'zope2'), ('products-cmfeditions', 'setuptools'), ('products-cmfeditions', 'products-cmfdifftool'), ('products-cmfeditions', 'products-zopeversioncontrol'), ('products-cmfeditions', 'zope-i18nmessageid'), ('products-cmfeditions', 'transaction'), ('products-cmfeditions', 'datetime'), ('products-cmfeditions', 'zope-copy'), ('products-cmfeditions', 'products-cmfuid'), ('products-cmfeditions', 'six'), ('products-cmfeditions', 'zope-interface'), ('products-cmfeditions', 'products-cmfcore'), ('five-customerize', 'acquisition'), ('five-customerize', 'zope-dottedname'), ('five-customerize', 'zope-schema'), ('five-customerize', 'setuptools'), ('five-customerize', 'zope-pagetemplate'), ('five-customerize', 'plone-portlets'), ('five-customerize', 'zope-component'), ('five-customerize', 'zope-traversing'), ('five-customerize', 'zope-componentvocabulary'), ('five-customerize', 'zope-viewlet'), ('five-customerize', 'zope-lifecycleevent'), ('five-customerize', 'zope-interface'), ('five-customerize', 'zope'), ('plone-app-registry', 'zope-dottedname'), ('plone-app-registry', 'products-genericsetup'), ('plone-app-registry', 'zope2'), ('plone-app-registry', 'setuptools'), ('plone-app-registry', 'plone-autoform'), ('plone-app-registry', 'lxml'), ('plone-app-registry', 'plone-registry'), ('plone-app-registry', 'zope-i18nmessageid'), ('plone-app-registry', 'plone-app-z3cform'), ('plone-app-registry', 'zope-component'), ('plone-app-registry', 'products-statusmessages'), ('plone-app-registry', 'plone-supermodel'), ('plone-app-registry', 'zope-interface'), ('plone-app-registry', 'products-cmfcore'), ('plone-registry', 'zope-dottedname'), ('plone-registry', 'zope-schema'), ('plone-registry', 'setuptools'), ('plone-registry', 'zope-component'), ('plone-registry', 'zope-event'), ('plone-registry', 'zope-interface'), ('plone-app-workflow', 'zope-dottedname'), ('plone-app-workflow', 'zope-i18nmessageid'), ('plone-app-workflow', 'zope-site'), ('plone-app-workflow', 'products-statusmessages'), ('plone-app-workflow', 'products-dcworkflow'), ('plone-app-workflow', 'zope-schema'), ('plone-app-workflow', 'zope2'), ('plone-app-workflow', 'zope-i18n'), ('plone-app-workflow', 'datetime'), ('plone-app-workflow', 'transaction'), ('plone-app-workflow', 'zope-component'), ('plone-app-workflow', 'zope-interface'), ('plone-app-workflow', 'products-cmfcore'), ('plone-app-workflow', 'acquisition'), ('plone-app-workflow', 'products-genericsetup'), ('plone-app-workflow', 'setuptools'), ('plone-app-workflow', 'plone-memoize'), ('plone-app-workflow', 'six'), ('plone-app-workflow', 'zope-lifecycleevent'), ('plone-app-workflow', 'zope-testing'), ('z3c-autoinclude', 'zope-dottedname'), ('z3c-autoinclude', 'zope-schema'), ('z3c-autoinclude', 'setuptools'), ('z3c-autoinclude', 'zope-interface'), ('z3c-autoinclude', 'zope-configuration'), ('zope-container', 'zope-dottedname'), ('zope-container', 'zope-i18nmessageid'), ('zope-container', 'zope-security'), ('zope-container', 'zope-schema'), ('zope-container', 'zope-cachedescriptors'), ('zope-container', 'zope-location'), ('zope-container', 'persistent'), ('zope-container', 'zope-component'), ('zope-container', 'zope-traversing'), ('zope-container', '<Python from Requires-Python>'), ('zope-container', 'zope-size'), ('zope-container', 'zope-interface'), ('zope-container', 'btrees'), ('zope-container', 'setuptools'), ('zope-container', 'zope-event'), ('zope-container', 'zope-filerepresentation'), ('zope-container', 'zope-publisher'), ('zope-container', 'zope-proxy'), ('zope-container', 'six'), ('zope-container', 'zope-lifecycleevent'), ('plone-autoform', 'z3c-form'), ('plone-autoform', 'zope-dottedname'), ('plone-autoform', 'zope-schema'), ('plone-autoform', 'setuptools'), ('plone-autoform', 'plone-supermodel'), ('plone-autoform', 'six'), ('plone-autoform', 'zope-security'), ('plone-autoform', 'plone-z3cform'), ('plone-autoform', 'zope-interface'), ('plone-dexterity', 'zope-dottedname'), ('plone-dexterity', 'plone-autoform'), ('plone-dexterity', 'zope-container'), ('plone-dexterity', 'products-statusmessages'), ('plone-dexterity', 'zope-security'), ('plone-dexterity', 'plone-z3cform'), ('plone-dexterity', 'zope-schema'), ('plone-dexterity', 'products-cmfdynamicviewfti'), ('plone-dexterity', 'zope-location'), ('plone-dexterity', 'datetime'), ('plone-dexterity', 'zope-component'), ('plone-dexterity', 'zope-globalrequest'), ('plone-dexterity', 'zope-size'), ('plone-dexterity', 'plone-synchronize'), ('plone-dexterity', 'zope-interface'), ('plone-dexterity', 'products-cmfcore'), ('plone-dexterity', 'plone-alterego'), ('plone-dexterity', 'setuptools'), ('plone-dexterity', 'plone-memoize'), ('plone-dexterity', 'zope-browser'), ('plone-dexterity', 'plone-behavior'), ('plone-dexterity', 'zope-annotation'), ('plone-dexterity', 'zope-filerepresentation'), ('plone-dexterity', 'zope-publisher'), ('plone-dexterity', 'plone-rfc822'), ('plone-dexterity', 'plone-uuid'), ('plone-dexterity', 'plone-supermodel'), ('plone-dexterity', 'six'), ('plone-dexterity', 'zope-lifecycleevent'), ('plone-dexterity', 'plone-folder'), ('plone-dexterity', 'zope'), ('plone-supermodel', 'zope-dottedname'), ('plone-supermodel', 'zope-schema'), ('plone-supermodel', 'lxml'), ('plone-supermodel', 'setuptools'), ('plone-supermodel', 'zope-i18nmessageid'), ('plone-supermodel', 'zope-component'), ('plone-supermodel', 'zope-deferredimport'), ('plone-supermodel', 'six'), ('plone-supermodel', 'z3c-zcmlhook'), ('plone-supermodel', 'zope-interface'), ('products-zcatalog', 'zope-dottedname'), ('products-zcatalog', 'extensionclass'), ('products-zcatalog', 'record'), ('products-zcatalog', 'missing'), ('products-zcatalog', 'zope-schema'), ('products-zcatalog', 'datetime'), ('products-zcatalog', 'restrictedpython'), ('products-zcatalog', 'zope-globalrequest'), ('products-zcatalog', 'zope-deferredimport'), ('products-zcatalog', '<Python from Requires-Python>'), ('products-zcatalog', 'zexceptions'), ('products-zcatalog', 'zope-interface'), ('products-zcatalog', 'acquisition'), ('products-zcatalog', 'zodb'), ('products-zcatalog', 'btrees'), ('products-zcatalog', 'setuptools'), ('products-zcatalog', 'persistence'), ('products-zcatalog', 'accesscontrol'), ('products-zcatalog', 'six'), ('products-zcatalog', 'documenttemplate'), ('products-zcatalog', 'zope-testing'), ('products-zcatalog', 'zope'), ('plone-folder', 'products-btreefolder2'), ('plone-folder', 'zope2'), ('plone-folder', 'setuptools'), ('plone-folder', 'zope-container'), ('plone-folder', 'products-zcatalog'), ('plone-folder', 'zope-component'), ('plone-folder', 'plone-memoize'), ('plone-folder', 'six'), ('plone-folder', 'zope-interface'), ('plone-folder', 'products-cmfcore'), ('plone-folder', 'zope-annotation'), ('products-cmfdifftool', 'acquisition'), ('products-cmfdifftool', 'products-genericsetup'), ('products-cmfdifftool', 'zope2'), ('products-cmfdifftool', 'setuptools'), ('products-cmfdifftool', 'six'), ('products-cmfdifftool', 'zope-interface'), ('products-cmfdifftool', 'products-cmfcore'), ('zope-i18nmessageid', 'six'), ('zope-i18nmessageid', 'setuptools'), ('plone-app-contentmenu', 'acquisition'), ('plone-app-contentmenu', 'products-cmfdynamicviewfti'), ('plone-app-contentmenu', 'zope2'), ('plone-app-contentmenu', 'setuptools'), ('plone-app-contentmenu', 'zope-browsermenu'), ('plone-app-contentmenu', 'zope-publisher'), ('plone-app-contentmenu', 'plone-app-content'), ('plone-app-contentmenu', 'zope-i18nmessageid'), ('plone-app-contentmenu', 'zope-i18n'), ('plone-app-contentmenu', 'zope-contentprovider'), ('plone-app-contentmenu', 'zope-component'), ('plone-app-contentmenu', 'plone-memoize'), ('plone-app-contentmenu', 'plone-protect'), ('plone-app-contentmenu', 'zope-interface'), ('plone-app-contentmenu', 'products-cmfcore'), ('plone-app-contentmenu', 'plone-locking'), ('plone-app-content', 'zope-i18nmessageid'), ('plone-app-content', 'zope-container'), ('plone-app-content', 'plone-app-vocabularies'), ('plone-app-content', 'plone-protect'), ('plone-app-content', 'zope-schema'), ('plone-app-content', 'plone-i18n'), ('plone-app-content', 'products-cmfdynamicviewfti'), ('plone-app-content', 'zope-i18n'), ('plone-app-content', 'zope-component'), ('plone-app-content', 'plone-batching'), ('plone-app-content', 'simplejson'), ('plone-app-content', 'z3c-form'), ('plone-app-content', 'zope-interface'), ('plone-app-content', 'products-cmfcore'), ('plone-app-content', 'acquisition'), ('plone-app-content', 'setuptools'), ('plone-app-content', 'plone-memoize'), ('plone-app-content', 'zope-event'), ('plone-app-content', 'plone-app-widgets'), ('plone-app-content', 'zope-publisher'), ('plone-app-content', 'zope-lifecycleevent'), ('plone-app-content', 'zope'), ('plone-app-vocabularies', 'acquisition'), ('plone-app-vocabularies', 'zope-schema'), ('plone-app-vocabularies', 'zope2'), ('plone-app-vocabularies', 'setuptools'), ('plone-app-vocabularies', 'zope-i18n'), ('plone-app-vocabularies', 'zope-i18nmessageid'), ('plone-app-vocabularies', 'zope-component'), ('plone-app-vocabularies', 'zope-site'), ('plone-app-vocabularies', 'six'), ('plone-app-vocabularies', 'zope-browser'), ('plone-app-vocabularies', 'plone-app-querystring'), ('plone-app-vocabularies', 'pytz'), ('plone-app-vocabularies', 'zope-interface'), ('plone-app-vocabularies', 'products-cmfcore'), ('plone-i18n', 'zope-schema'), ('plone-i18n', 'zodb'), ('plone-i18n', 'setuptools'), ('plone-i18n', 'zope-publisher'), ('plone-i18n', 'zope-i18n'), ('plone-i18n', 'zope-i18nmessageid'), ('plone-i18n', 'accesscontrol'), ('plone-i18n', 'zope-component'), ('plone-i18n', 'zope-globalrequest'), ('plone-i18n', 'plone-supermodel'), ('plone-i18n', 'unidecode'), ('plone-i18n', 'zope-interface'), ('plone-i18n', 'zope'), ('plone-i18n', 'products-cmfcore'), ('zope-app-locales', 'zope-i18nmessageid'), ('zope-app-locales', 'zope-interface'), ('zope-app-locales', 'zope-cachedescriptors'), ('zope-app-locales', 'setuptools'), ('zope-traversing', 'setuptools'), ('zope-traversing', 'zope-publisher'), ('zope-traversing', 'zope-location'), ('zope-traversing', 'zope-i18n'), ('zope-traversing', 'zope-i18nmessageid'), ('zope-traversing', 'transaction'), ('zope-traversing', 'zope-proxy'), ('zope-traversing', 'zope-component'), ('zope-traversing', 'six'), ('zope-traversing', '<Python from Requires-Python>'), ('zope-traversing', 'zope-security'), ('zope-traversing', 'zope-interface'), ('zope[wsgi]', 'extensionclass'), ('zope[wsgi]', 'zope-testbrowser'), ('zope[wsgi]', 'zope-i18nmessageid'), ('zope[wsgi]', 'zope-container'), ('zope[wsgi]', 'chameleon'), ('zope[wsgi]', 'zope-i18n[zcml]'), ('zope[wsgi]', 'zope-site'), ('zope[wsgi]', 'zope-viewlet'), ('zope[wsgi]', 'zope-security'), ('zope[wsgi]', 'pastedeploy'), ('zope[wsgi]', 'zconfig'), ('zope[wsgi]', 'zope-contenttype'), ('zope[wsgi]', 'zope-schema'), ('zope[wsgi]', 'zope-location'), ('zope[wsgi]', 'zope-pagetemplate'), ('zope[wsgi]', 'datetime'), ('zope[wsgi]', 'transaction'), ('zope[wsgi]', 'restrictedpython'), ('zope[wsgi]', 'zope-component'), ('zope[wsgi]', 'zope-traversing'), ('zope[wsgi]', 'zope-globalrequest'), ('zope[wsgi]', 'zope-deferredimport'), ('zope[wsgi]', 'waitress'), ('zope[wsgi]', 'zope-size'), ('zope[wsgi]', 'zexceptions'), ('zope[wsgi]', 'z3c-pt'), ('zope[wsgi]', 'zope-interface'), ('zope[wsgi]', 'zope-sequencesort'), ('zope[wsgi]', 'zope-configuration'), ('zope[wsgi]', 'acquisition'), ('zope[wsgi]', 'zodb'), ('zope[wsgi]', 'btrees'), ('zope[wsgi]', 'zope-tal'), ('zope[wsgi]', 'setuptools'), ('zope[wsgi]', 'zope-browsermenu'), ('zope[wsgi]', 'zope-datetime'), ('zope[wsgi]', 'zope-exceptions'), ('zope[wsgi]', 'zope-event'), ('zope[wsgi]', 'zope-browser'), ('zope[wsgi]', 'persistence'), ('zope[wsgi]', 'paste'), ('zope[wsgi]', 'zope'), ('zope[wsgi]', 'zope-ptresource'), ('zope[wsgi]', 'zope-publisher'), ('zope[wsgi]', 'zope-proxy'), ('zope[wsgi]', 'zope-browserresource'), ('zope[wsgi]', 'accesscontrol'), ('zope[wsgi]', 'zope-contentprovider'), ('zope[wsgi]', 'multimapping'), ('zope[wsgi]', 'zope-lifecycleevent'), ('zope[wsgi]', 'zope-browserpage'), ('zope[wsgi]', 'documenttemplate'), ('zope[wsgi]', 'zope-testing'), ('zope[wsgi]', 'zope-processlifetime'), ('zope[wsgi]', 'zope-tales'), ('zope-pagetemplate', 'zope-tal'), ('zope-pagetemplate', 'setuptools'), ('zope-pagetemplate', 'zope-i18n'), ('zope-pagetemplate', 'zope-i18nmessageid'), ('zope-pagetemplate', 'zope-component'), ('zope-pagetemplate', 'zope-traversing'), ('zope-pagetemplate', 'six'), ('zope-pagetemplate', 'zope-interface'), ('zope-pagetemplate', 'zope-tales'), ('zope-i18n', 'zope-schema'), ('zope-i18n', 'setuptools'), ('zope-i18n', 'zope-i18nmessageid'), ('zope-i18n', 'zope-component'), ('zope-i18n', 'zope-deprecation'), ('zope-i18n', 'pytz'), ('zope-i18n', 'python-gettext'), ('zope-tal', 'zope-i18nmessageid'), ('zope-tal', 'zope-interface'), ('zope-tal', 'setuptools'), ('plone-app-contentrules', 'plone-autoform'), ('plone-app-contentrules', 'zope-i18nmessageid'), ('plone-app-contentrules', 'zope-container'), ('plone-app-contentrules', 'plone-app-vocabularies'), ('plone-app-contentrules', 'zope-site'), ('plone-app-contentrules', 'products-statusmessages'), ('plone-app-contentrules', 'plone-stringinterp'), ('plone-app-contentrules', 'zope-schema'), ('plone-app-contentrules', 'zope2'), ('plone-app-contentrules', 'zodb3'), ('plone-app-contentrules', 'plone-contentrules'), ('plone-app-contentrules', 'transaction'), ('plone-app-contentrules', 'zope-component'), ('plone-app-contentrules', 'zope-traversing'), ('plone-app-contentrules', 'zope-interface'), ('plone-app-contentrules', 'products-cmfcore'), ('plone-app-contentrules', 'acquisition'), ('plone-app-contentrules', 'products-genericsetup'), ('plone-app-contentrules', 'setuptools'), ('plone-app-contentrules', 'plone-app-z3cform'), ('plone-app-contentrules', 'plone-memoize'), ('plone-app-contentrules', 'zope-event'), ('plone-app-contentrules', 'zope-browser'), ('plone-app-contentrules', 'zope-annotation'), ('plone-app-contentrules', 'zope-publisher'), ('plone-app-contentrules', 'plone-uuid'), ('plone-app-contentrules', 'six'), ('plone-app-contentrules', 'zope-lifecycleevent'), ('plone-schema', 'z3c-form'), ('plone-schema', 'zope-schema'), ('plone-schema', 'setuptools'), ('plone-schema', 'zope-i18nmessageid'), ('plone-schema', 'plone-app-z3cform'), ('plone-schema', 'zope-component'), ('plone-schema', 'zope-interface'), ('plone-schema', 'jsonschema'), ('plone-app-portlets', 'plone-autoform'), ('plone-app-portlets', 'zope-i18nmessageid'), ('plone-app-portlets', 'zope-container'), ('plone-app-portlets', 'plone-app-vocabularies'), ('plone-app-portlets', 'zope-site'), ('plone-app-portlets', 'zope-schema'), ('plone-app-portlets', 'plone-i18n'), ('plone-app-portlets', 'products-cmfdynamicviewfti'), ('plone-app-portlets', 'products-pluggableauthservice'), ('plone-app-portlets', 'datetime'), ('plone-app-portlets', 'transaction'), ('plone-app-portlets', 'plone-portlets'), ('plone-app-portlets', 'zope-component'), ('plone-app-portlets', 'zope-traversing'), ('plone-app-portlets', 'feedparser'), ('plone-app-portlets', 'zope-interface'), ('plone-app-portlets', 'zope-configuration'), ('plone-app-portlets', 'products-cmfcore'), ('plone-app-portlets', 'acquisition'), ('plone-app-portlets', 'zodb'), ('plone-app-portlets', 'products-genericsetup'), ('plone-app-portlets', 'setuptools'), ('plone-app-portlets', 'plone-app-z3cform'), ('plone-app-portlets', 'plone-memoize'), ('plone-app-portlets', 'zope-event'), ('plone-app-portlets', 'zope-browser'), ('plone-app-portlets', 'five-customerize'), ('plone-app-portlets', 'zope-annotation'), ('plone-app-portlets', 'zope-publisher'), ('plone-app-portlets', 'zope-contentprovider'), ('plone-app-portlets', 'zope-lifecycleevent'), ('plone-app-portlets', 'plone-app-i18n'), ('plone-app-portlets', 'zope'), ('plone-contentrules', 'zope-schema'), ('plone-contentrules', 'zodb3'), ('plone-contentrules', 'setuptools'), ('plone-contentrules', 'zope-i18nmessageid'), ('plone-contentrules', 'zope-container'), ('plone-contentrules', 'zope-component'), ('plone-contentrules', 'zope-componentvocabulary'), ('plone-contentrules', 'six'), ('plone-contentrules', 'zope-lifecycleevent'), ('plone-contentrules', 'zope-testing'), ('plone-contentrules', 'zope-interface'), ('plone-contentrules', 'zope-configuration'), ('plone-contentrules', 'zope-annotation'), ('plone-locking', 'acquisition'), ('plone-locking', 'zope-schema'), ('plone-locking', 'zope2'), ('plone-locking', 'zodb3'), ('plone-locking', 'setuptools'), ('plone-locking', 'zope-i18nmessageid'), ('plone-locking', 'datetime'), ('plone-locking', 'zope-component'), ('plone-locking', 'zope-viewlet'), ('plone-locking', 'zope-interface'), ('plone-locking', 'products-cmfcore'), ('plone-locking', 'zope-annotation'), ('plone-portlet-static', 'zope-schema'), ('plone-portlet-static', 'plone-i18n'), ('plone-portlet-static', 'zope2'), ('plone-portlet-static', 'setuptools'), ('plone-portlet-static', 'plone-app-portlets'), ('plone-portlet-static', 'plone-app-textfield'), ('plone-portlet-static', 'zope-i18nmessageid'), ('plone-portlet-static', 'plone-portlets'), ('plone-portlet-static', 'zope-component'), ('plone-portlet-static', 'six'), ('plone-portlet-static', 'zope-interface'), ('z3c-form', 'zope-i18nmessageid'), ('z3c-form', 'zope-site'), ('z3c-form', 'zope-security'), ('z3c-form', 'zope-schema'), ('z3c-form', 'zope-location'), ('z3c-form', 'zope-pagetemplate'), ('z3c-form', 'zope-i18n'), ('z3c-form', 'zope-component'), ('z3c-form', 'zope-traversing'), ('z3c-form', 'zope-interface'), ('z3c-form', 'zope-configuration'), ('z3c-form', 'setuptools'), ('z3c-form', 'zope-event'), ('z3c-form', 'zope-browser'), ('z3c-form', 'zope-publisher'), ('z3c-form', 'zope-browserresource'), ('z3c-form', 'zope-contentprovider'), ('z3c-form', 'six'), ('z3c-form', 'zope-lifecycleevent'), ('z3c-form', 'zope-browserpage'), ('zope', 'extensionclass'), ('zope', 'zope-testbrowser'), ('zope', 'zope-i18nmessageid'), ('zope', 'zope-container'), ('zope', 'chameleon'), ('zope', 'zope-i18n[zcml]'), ('zope', 'zope-site'), ('zope', 'zope-viewlet'), ('zope', 'zope-security'), ('zope', 'pastedeploy'), ('zope', 'zconfig'), ('zope', 'zope-contenttype'), ('zope', 'zope-schema'), ('zope', 'zope-location'), ('zope', 'zope-pagetemplate'), ('zope', 'datetime'), ('zope', 'transaction'), ('zope', 'restrictedpython'), ('zope', 'zope-component'), ('zope', 'zope-traversing'), ('zope', 'zope-globalrequest'), ('zope', 'zope-deferredimport'), ('zope', '<Python from Requires-Python>'), ('zope', 'zope-size'), ('zope', 'waitress'), ('zope', 'zexceptions'), ('zope', 'z3c-pt'), ('zope', 'zope-interface'), ('zope', 'zope-sequencesort'), ('zope', 'zope-configuration'), ('zope', 'acquisition'), ('zope', 'zodb'), ('zope', 'btrees'), ('zope', 'zope-tal'), ('zope', 'setuptools'), ('zope', 'zope-browsermenu'), ('zope', 'zope-datetime'), ('zope', 'zope-exceptions'), ('zope', 'zope-event'), ('zope', 'zope-browser'), ('zope', 'persistence'), ('zope', 'zope-ptresource'), ('zope', 'zope-publisher'), ('zope', 'zope-proxy'), ('zope', 'zope-browserresource'), ('zope', 'accesscontrol'), ('zope', 'zope-contentprovider'), ('zope', 'multimapping'), ('zope', 'zope-lifecycleevent'), ('zope', 'zope-browserpage'), ('zope', 'documenttemplate'), ('zope', 'zope-testing'), ('zope', 'zope-processlifetime'), ('zope', 'zope-tales'), ('zope-security', 'zope-schema'), ('zope-security', 'setuptools'), ('zope-security', 'zope-location'), ('zope-security', 'zope-i18nmessageid'), ('zope-security', 'zope-proxy'), ('zope-security', 'zope-component'), ('zope-security', '<Python from Requires-Python>'), ('zope-security', 'zope-interface'), ('zope-browsermenu', 'zope-schema'), ('zope-browsermenu', 'setuptools'), ('zope-browsermenu', 'zope-publisher'), ('zope-browsermenu', 'zope-pagetemplate'), ('zope-browsermenu', 'zope-i18nmessageid'), ('zope-browsermenu', 'zope-component'), ('zope-browsermenu', 'zope-traversing'), ('zope-browsermenu', 'six'), ('zope-browsermenu', 'zope-browser'), ('zope-browsermenu', 'zope-security'), ('zope-browsermenu', 'zope-interface'), ('zope-browsermenu', 'zope-configuration'), ('zope-componentvocabulary', 'zope-schema'), ('zope-componentvocabulary', 'setuptools'), ('zope-componentvocabulary', 'zope-i18nmessageid'), ('zope-componentvocabulary', 'zope-component'), ('zope-componentvocabulary', 'six'), ('zope-componentvocabulary', 'zope-security'), ('zope-componentvocabulary', 'zope-interface'), ('zope-configuration', 'zope-i18nmessageid'), ('zope-configuration', 'zope-interface'), ('zope-configuration', 'setuptools'), ('zope-configuration', 'zope-schema'), ('zope-i18n[zcml]', 'zope-schema'), ('zope-i18n[zcml]', 'setuptools'), ('zope-i18n[zcml]', 'zope-i18n'), ('zope-i18n[zcml]', 'zope-i18nmessageid'), ('zope-i18n[zcml]', 'zope-component'), ('zope-i18n[zcml]', 'zope-component[zcml]'), ('zope-i18n[zcml]', 'zope-deprecation'), ('zope-i18n[zcml]', 'zope-security'), ('zope-i18n[zcml]', 'zope-configuration'), ('zope-i18n[zcml]', 'pytz'), ('zope-i18n[zcml]', 'python-gettext'), ('zope-size', 'zope-i18nmessageid'), ('zope-size', 'zope-interface'), ('zope-size', 'setuptools'), ('zope-viewlet', 'zope-schema'), ('zope-viewlet', 'setuptools'), ('zope-viewlet', 'zope-location'), ('zope-viewlet', 'zope-publisher'), ('zope-viewlet', 'zope-i18nmessageid'), ('zope-viewlet', 'zope-contentprovider'), ('zope-viewlet', 'zope-component'), ('zope-viewlet', 'zope-traversing'), ('zope-viewlet', 'zope-event'), ('zope-viewlet', 'zope-security'), ('zope-viewlet', 'zope-browserpage'), ('zope-viewlet', 'zope-interface'), ('zope-viewlet', 'zope-configuration'), ('zope-sendmail', 'zope-schema'), ('zope-sendmail', 'setuptools'), ('zope-sendmail', 'zope-i18nmessageid'), ('zope-sendmail', 'transaction'), ('zope-sendmail', 'zope-component'), ('zope-sendmail', '<Python from Requires-Python>'), ('zope-sendmail', 'zope-interface'), ('zope-sendmail', 'zope-configuration'), ('plone-caching', 'zope-schema'), ('plone-caching', 'zope2'), ('plone-caching', 'setuptools'), ('plone-caching', 'plone-registry'), ('plone-caching', 'zope-i18nmessageid'), ('plone-caching', 'zope-component'), ('plone-caching', 'plone-transformchain'), ('plone-caching', 'z3c-caching[zcml]'), ('plone-caching', 'zope-interface'), ('z3c-formwidget-query', 'z3c-form'), ('z3c-formwidget-query', 'zope-schema'), ('z3c-formwidget-query', 'setuptools'), ('z3c-formwidget-query', 'zope-i18nmessageid'), ('z3c-formwidget-query', 'zope-component'), ('z3c-formwidget-query', 'zope-interface'), ('zope-component[zcml]', 'setuptools'), ('zope-component[zcml]', 'zope-i18nmessageid'), ('zope-component[zcml]', 'zope-hookable'), ('zope-component[zcml]', 'zope-component'), ('zope-component[zcml]', 'zope-deprecation'), ('zope-component[zcml]', 'zope-deferredimport'), ('zope-component[zcml]', 'zope-event'), ('zope-component[zcml]', 'zope-interface'), ('zope-component[zcml]', 'zope-configuration'), ('zope-keyreference', 'zope-schema'), ('zope-keyreference', 'zodb'), ('zope-keyreference', 'setuptools'), ('zope-keyreference', 'zope-i18nmessageid'), ('zope-keyreference', 'zope-component'), ('zope-keyreference', 'zope-interface'), ('products-plonepas', 'plone-i18n'), ('products-plonepas', 'products-genericsetup'), ('products-plonepas', 'setuptools'), ('products-plonepas', 'products-pluggableauthservice'), ('products-plonepas', 'plone-registry'), ('products-plonepas', 'datetime'), ('products-plonepas', 'zope-component'), ('products-plonepas', 'zope-deprecation'), ('products-plonepas', 'plone-memoize'), ('products-plonepas', 'six'), ('products-plonepas', 'plone-protect'), ('products-plonepas', 'plone-session'), ('products-plonepas', 'zope'), ('products-plonepas', 'products-cmfcore'), ('plone-app-multilingual', 'plone-i18n'), ('plone-app-multilingual', 'six'), ('plone-app-multilingual', 'setuptools'), ('products-portaltransforms', 'acquisition'), ('products-portaltransforms', 'products-mimetypesregistry'), ('products-portaltransforms', 'zope2'), ('products-portaltransforms', 'zodb3'), ('products-portaltransforms', 'setuptools'), ('products-portaltransforms', 'zope-structuredtext'), ('products-portaltransforms', 'pillow'), ('products-portaltransforms', 'markdown'), ('products-portaltransforms', 'six'), ('products-portaltransforms', 'zope-interface'), ('products-portaltransforms', 'plone-intelligenttext'), ('products-portaltransforms', 'products-cmfcore'), ('plone-outputfilters', 'products-mimetypesregistry'), ('plone-outputfilters', 'products-genericsetup'), ('plone-outputfilters', 'lxml'), ('plone-outputfilters', 'setuptools'), ('plone-outputfilters', 'beautifulsoup4'), ('plone-outputfilters', 'products-portaltransforms'), ('plone-outputfilters', 'six'), ('plone-outputfilters', 'unidecode'), ('plone-outputfilters', 'products-cmfcore'), ('zope-tales', 'zope-interface'), ('zope-tales', 'six'), ('zope-tales', 'setuptools'), ('zope-tales', '<Python from Requires-Python>'), ('zope-contentprovider', 'zope-schema'), ('zope-contentprovider', 'setuptools'), ('zope-contentprovider', 'zope-location'), ('zope-contentprovider', 'zope-publisher'), ('zope-contentprovider', 'zope-component'), ('zope-contentprovider', 'zope-event'), ('zope-contentprovider', 'zope-interface'), ('zope-contentprovider', 'zope-tales'), ('borg-localrole', 'acquisition'), ('borg-localrole', 'products-genericsetup'), ('borg-localrole', 'zope2'), ('borg-localrole', 'setuptools'), ('borg-localrole', 'products-pluggableauthservice'), ('borg-localrole', 'zope-component'), ('borg-localrole', 'products-plonepas'), ('borg-localrole', 'zope-deferredimport'), ('borg-localrole', 'plone-memoize'), ('borg-localrole', 'six'), ('borg-localrole', 'zope-interface'), ('borg-localrole', 'products-cmfcore'), ('borg-localrole', 'zope-annotation'), ('plone-app-users', 'plone-namedfile'), ('plone-app-users', 'plone-autoform'), ('plone-app-users', 'plone-app-layout'), ('plone-app-users', 'products-statusmessages'), ('plone-app-users', 'plone-protect'), ('plone-app-users', 'zope-schema'), ('plone-app-users', 'zope2'), ('plone-app-users', 'plone-formwidget-namedfile'), ('plone-app-users', 'zope-component'), ('plone-app-users', 'z3c-form'), ('plone-app-users', 'zope-interface'), ('plone-app-users', 'products-cmfcore'), ('plone-app-users', 'acquisition'), ('plone-app-users', 'setuptools'), ('plone-app-users', 'zope-event'), ('plone-app-users', 'plone-uuid'), ('plone-app-users', 'accesscontrol'), ('plone-app-users', 'products-plonepas'), ('plone-app-users', 'six'), ('plone-app-users', 'plone-schema'), ('pyscss', 'six'), ('pillow', '<Python from Requires-Python>'), ('plone-theme', 'zope2'), ('plone-theme', 'setuptools'), ('plone-theme', 'zope-publisher'), ('plone-theme', 'zope-component'), ('plone-theme', 'zope-traversing'), ('plone-theme', 'zope-interface'), ('plone-theme', 'products-cmfcore'), ('zope-structuredtext', 'setuptools'), ('documenttemplate', 'acquisition'), ('documenttemplate', 'extensionclass'), ('documenttemplate', 'zope-structuredtext'), ('documenttemplate', 'restrictedpython'), ('documenttemplate', 'accesscontrol'), ('documenttemplate', 'roman'), ('documenttemplate', '<Python from Requires-Python>'), ('documenttemplate', 'zexceptions'), ('documenttemplate', 'zope-sequencesort'), ('zope-deprecation', 'setuptools'), ('plone-app-contenttypes', 'plone-namedfile[blobs]'), ('plone-app-contenttypes', 'setuptools'), ('plone-app-contenttypes', 'plone-app-event'), ('plone-app-contenttypes', 'plone-app-dexterity'), ('plone-app-contenttypes', 'plone-app-vocabularies'), ('plone-app-contenttypes', 'plone-app-contentmenu'), ('plone-app-contenttypes', 'plone-app-z3cform'), ('plone-app-contenttypes', 'plone-app-linkintegrity'), ('plone-app-contenttypes', 'plone-dexterity'), ('plone-app-contenttypes', 'zope-deprecation'), ('plone-app-contenttypes', 'six'), ('plone-app-contenttypes', 'plone-app-relationfield'), ('plone-app-contenttypes', 'plone-app-querystring'), ('plone-app-contenttypes', 'plone-behavior'), ('plone-app-contenttypes', 'plone-app-lockingbehavior'), ('plone-app-contenttypes', 'pytz'), ('plone-app-contenttypes', 'plone-app-versioningbehavior'), ('plone-app-dexterity', 'plone-autoform'), ('plone-app-dexterity', 'plone-app-layout'), ('plone-app-dexterity', 'plone-namedfile[scales]'), ('plone-app-dexterity', 'zope-deprecation'), ('plone-app-dexterity', 'plone-schemaeditor'), ('plone-app-dexterity', 'plone-z3cform'), ('plone-app-dexterity', 'plone-app-uuid'), ('plone-app-dexterity', 'zope-schema'), ('plone-app-dexterity', 'zope2'), ('plone-app-dexterity', 'plone-app-textfield'), ('plone-app-dexterity', 'plone-contentrules'), ('plone-app-dexterity', 'plone-portlets'), ('plone-app-dexterity', 'plone-formwidget-namedfile'), ('plone-app-dexterity', 'plone-dexterity'), ('plone-app-dexterity', 'zope-component'), ('plone-app-dexterity', 'z3c-form'), ('plone-app-dexterity', 'zope-interface'), ('plone-app-dexterity', 'products-cmfcore'), ('plone-app-dexterity', 'products-genericsetup'), ('plone-app-dexterity', 'setuptools'), ('plone-app-dexterity', 'plone-app-z3cform'), ('plone-app-dexterity', 'plone-behavior'), ('plone-app-dexterity', 'lxml'), ('plone-app-dexterity', 'zope-publisher'), ('plone-app-dexterity', 'plone-app-content'), ('plone-app-dexterity', 'plone-rfc822'), ('plone-app-dexterity', 'plone-supermodel'), ('plone-app-dexterity', 'six'), ('plone-app-dexterity', 'plone-schema'), ('plone-app-dexterity', 'zope-browserpage'), ('zope-component', 'setuptools'), ('zope-component', 'zope-hookable'), ('zope-component', 'zope-deprecation'), ('zope-component', 'zope-deferredimport'), ('zope-component', 'zope-event'), ('zope-component', 'zope-interface'), ('zope-site', 'setuptools'), ('zope-site', 'zope-location'), ('zope-site', 'zope-container'), ('zope-site', 'zope-component'), ('zope-site', 'zope-deprecation'), ('zope-site', 'zope-event'), ('zope-site', '<Python from Requires-Python>'), ('zope-site', 'zope-security'), ('zope-site', 'zope-lifecycleevent'), ('zope-site', 'zope-interface'), ('zope-site', 'zope-annotation'), ('plone-rfc822', 'zope-schema'), ('plone-rfc822', 'setuptools'), ('plone-rfc822', 'zope-component'), ('plone-rfc822', 'zope-deprecation'), ('plone-rfc822', 'python-dateutil'), ('plone-rfc822', 'zope-interface'), ('plone-app-dexterity[relations]', 'plone-autoform'), ('plone-app-dexterity[relations]', 'plone-app-layout'), ('plone-app-dexterity[relations]', 'plone-namedfile[scales]'), ('plone-app-dexterity[relations]', 'zope-deprecation'), ('plone-app-dexterity[relations]', 'plone-schemaeditor'), ('plone-app-dexterity[relations]', 'plone-z3cform'), ('plone-app-dexterity[relations]', 'plone-app-uuid'), ('plone-app-dexterity[relations]', 'plone-app-intid'), ('plone-app-dexterity[relations]', 'zope-schema'), ('plone-app-dexterity[relations]', 'zope2'), ('plone-app-dexterity[relations]', 'plone-app-textfield'), ('plone-app-dexterity[relations]', 'plone-contentrules'), ('plone-app-dexterity[relations]', 'plone-portlets'), ('plone-app-dexterity[relations]', 'plone-formwidget-namedfile'), ('plone-app-dexterity[relations]', 'plone-dexterity'), ('plone-app-dexterity[relations]', 'zope-component'), ('plone-app-dexterity[relations]', 'z3c-form'), ('plone-app-dexterity[relations]', 'zope-interface'), ('plone-app-dexterity[relations]', 'products-cmfcore'), ('plone-app-dexterity[relations]', 'products-genericsetup'), ('plone-app-dexterity[relations]', 'setuptools'), ('plone-app-dexterity[relations]', 'plone-app-dexterity'), ('plone-app-dexterity[relations]', 'plone-app-z3cform'), ('plone-app-dexterity[relations]', 'plone-app-relationfield'), ('plone-app-dexterity[relations]', 'z3c-relationfield'), ('plone-app-dexterity[relations]', 'plone-behavior'), ('plone-app-dexterity[relations]', 'lxml'), ('plone-app-dexterity[relations]', 'zope-publisher'), ('plone-app-dexterity[relations]', 'plone-app-content'), ('plone-app-dexterity[relations]', 'plone-rfc822'), ('plone-app-dexterity[relations]', 'plone-supermodel'), ('plone-app-dexterity[relations]', 'six'), ('plone-app-dexterity[relations]', 'plone-schema'), ('plone-app-dexterity[relations]', 'zope-browserpage'), ('plone-app-locales', 'setuptools'), ('plone-app-lockingbehavior', 'plone-app-locales'), ('plone-app-lockingbehavior', 'setuptools'), ('plone-app-lockingbehavior', 'plone-dexterity'), ('plone-app-lockingbehavior', 'plone-behavior'), ('plone-app-lockingbehavior', 'plone-locking'), ('transaction', 'zope-interface'), ('accesscontrol', 'extensionclass'), ('accesscontrol', 'zope-security'), ('accesscontrol', 'zope-schema'), ('accesscontrol', 'datetime'), ('accesscontrol', 'transaction'), ('accesscontrol', 'restrictedpython'), ('accesscontrol', 'zope-component'), ('accesscontrol', 'zope-deferredimport'), ('accesscontrol', '<Python from Requires-Python>'), ('accesscontrol', 'zexceptions'), ('accesscontrol', 'zope-interface'), ('accesscontrol', 'zope-configuration'), ('accesscontrol', 'acquisition'), ('accesscontrol', 'btrees'), ('accesscontrol', 'authencoding'), ('accesscontrol', 'persistence'), ('accesscontrol', 'zope-publisher'), ('accesscontrol', 'six'), ('accesscontrol', 'zope-testing'), ('products-siteerrorlog', 'acquisition'), ('products-siteerrorlog', 'setuptools'), ('products-siteerrorlog', 'transaction'), ('products-siteerrorlog', 'accesscontrol'), ('products-siteerrorlog', 'zope-component'), ('products-siteerrorlog', 'zope-event'), ('products-siteerrorlog', '<Python from Requires-Python>'), ('products-siteerrorlog', 'zexceptions'), ('products-siteerrorlog', 'zope-interface'), ('products-siteerrorlog', 'zope'), ('zodb3', 'zodb'), ('zodb3', 'btrees'), ('zodb3', 'zeo'), ('zodb3', 'transaction'), ('zodb3', 'persistent'), ('zeo', 'zdaemon'), ('zeo', 'zodb'), ('zeo', 'zc-lockfile'), ('zeo', 'transaction'), ('zeo', 'persistent'), ('zeo', 'six'), ('zeo', '<Python from Requires-Python>'), ('zeo', 'zconfig'), ('zeo', 'zope-interface'), ('zodb', 'btrees'), ('zodb', 'zc-lockfile'), ('zodb', 'transaction'), ('zodb', 'persistent'), ('zodb', 'six'), ('zodb', '<Python from Requires-Python>'), ('zodb', 'zconfig'), ('zodb', 'zodbpickle'), ('zodb', 'zope-interface'), ('products-sessions', 'acquisition'), ('products-sessions', 'zodb'), ('products-sessions', 'setuptools'), ('products-sessions', 'transaction'), ('products-sessions', 'persistent'), ('products-sessions', 'accesscontrol'), ('products-sessions', 'six'), ('products-sessions', '<Python from Requires-Python>'), ('products-sessions', 'persistence'), ('products-sessions', 'zope-interface'), ('products-sessions', 'zope'), ('products-standardcachemanagers', 'zope2'), ('products-standardcachemanagers', 'setuptools'), ('products-standardcachemanagers', 'transaction'), ('products-standardcachemanagers', 'accesscontrol'), ('products-standardcachemanagers', 'zope-component'), ('products-standardcachemanagers', 'six'), ('products-standardcachemanagers', '<Python from Requires-Python>'), ('products-zopeversioncontrol', 'acquisition'), ('products-zopeversioncontrol', 'zodb'), ('products-zopeversioncontrol', 'zope2'), ('products-zopeversioncontrol', 'setuptools'), ('products-zopeversioncontrol', 'datetime'), ('products-zopeversioncontrol', 'transaction'), ('products-zopeversioncontrol', 'six'), ('products-zopeversioncontrol', 'zope-interface'), ('acquisition', 'zope-interface'), ('acquisition', 'extensionclass'), ('acquisition', '<Python from Requires-Python>'), ('plone-app-viewletmanager', 'acquisition'), ('plone-app-viewletmanager', 'products-genericsetup'), ('plone-app-viewletmanager', 'zope2'), ('plone-app-viewletmanager', 'zodb3'), ('plone-app-viewletmanager', 'setuptools'), ('plone-app-viewletmanager', 'zope-contentprovider'), ('plone-app-viewletmanager', 'plone-app-vocabularies'), ('plone-app-viewletmanager', 'zope-component'), ('plone-app-viewletmanager', 'zope-site'), ('plone-app-viewletmanager', 'zope-viewlet'), ('plone-app-viewletmanager', 'zope-interface'), ('five-localsitemanager', 'acquisition'), ('five-localsitemanager', 'setuptools'), ('five-localsitemanager', 'zope-location'), ('five-localsitemanager', 'persistent'), ('five-localsitemanager', 'zope-component'), ('five-localsitemanager', 'zope-site'), ('five-localsitemanager', 'six'), ('five-localsitemanager', 'zope-event'), ('five-localsitemanager', 'zope-lifecycleevent'), ('five-localsitemanager', 'zope-testing'), ('five-localsitemanager', 'zope-interface'), ('five-localsitemanager', 'zope'), ('plone-app-customerize', 'acquisition'), ('plone-app-customerize', 'zope2'), ('plone-app-customerize', 'setuptools'), ('plone-app-customerize', 'zope-publisher'), ('plone-app-customerize', 'plone-portlets'), ('plone-app-customerize', 'plone-browserlayer'), ('plone-app-customerize', 'five-customerize'), ('plone-app-customerize', 'zope-component'), ('plone-app-customerize', 'zope-viewlet'), ('plone-app-customerize', 'zope-interface'), ('plone-app-customerize', 'products-cmfcore'), ('products-cmfdynamicviewfti', 'acquisition'), ('products-cmfdynamicviewfti', 'products-genericsetup'), ('products-cmfdynamicviewfti', 'extensionclass'), ('products-cmfdynamicviewfti', 'setuptools'), ('products-cmfdynamicviewfti', 'zope2'), ('products-cmfdynamicviewfti', 'zope-browsermenu'), ('products-cmfdynamicviewfti', 'zope-component'), ('products-cmfdynamicviewfti', 'six'), ('products-cmfdynamicviewfti', 'zope-interface'), ('products-cmfdynamicviewfti', 'products-cmfcore'), ('products-mailhost', 'acquisition'), ('products-mailhost', 'extensionclass'), ('products-mailhost', 'setuptools'), ('products-mailhost', 'datetime'), ('products-mailhost', 'zope-sendmail'), ('products-mailhost', 'accesscontrol'), ('products-mailhost', 'zope-deferredimport'), ('products-mailhost', 'six'), ('products-mailhost', '<Python from Requires-Python>'), ('products-mailhost', 'persistence'), ('products-mailhost', 'documenttemplate'), ('products-mailhost', 'zope-interface'), ('products-mailhost', 'zope'), ('plone-uuid', 'acquisition'), ('plone-uuid', 'setuptools'), ('plone-uuid', 'zope-publisher'), ('plone-uuid', 'zope-component'), ('plone-uuid', 'zope-lifecycleevent'), ('plone-uuid', 'zope-browserpage'), ('plone-uuid', 'zope-interface'), ('products-btreefolder2', 'acquisition'), ('products-btreefolder2', 'extensionclass'), ('products-btreefolder2', 'btrees'), ('products-btreefolder2', 'setuptools'), ('products-btreefolder2', 'zope2'), ('products-btreefolder2', 'zope-container'), ('products-btreefolder2', 'accesscontrol'), ('products-btreefolder2', 'six'), ('products-btreefolder2', 'zope-event'), ('products-btreefolder2', '<Python from Requires-Python>'), ('products-btreefolder2', 'persistence'), ('products-btreefolder2', 'zope-lifecycleevent'), ('products-btreefolder2', 'future'), ('products-externalmethod', 'acquisition'), ('products-externalmethod', 'zodb'), ('products-externalmethod', 'extensionclass'), ('products-externalmethod', 'setuptools'), ('products-externalmethod', 'accesscontrol'), ('products-externalmethod', '<Python from Requires-Python>'), ('products-externalmethod', 'persistence'), ('products-externalmethod', 'zope'), ('products-pythonscripts', 'acquisition'), ('products-pythonscripts', 'setuptools'), ('products-pythonscripts', 'datetime'), ('products-pythonscripts', 'restrictedpython'), ('products-pythonscripts', 'accesscontrol'), ('products-pythonscripts', '<Python from Requires-Python>'), ('products-pythonscripts', 'documenttemplate'), ('products-pythonscripts', 'zexceptions'), ('products-pythonscripts', 'zope'), ('five-intid', 'acquisition'), ('five-intid', 'setuptools'), ('five-intid', 'zope-location'), ('five-intid', 'five-localsitemanager'), ('five-intid', 'zope-keyreference'), ('five-intid', 'zope-component'), ('five-intid', 'zope-intid'), ('five-intid', 'zope-event'), ('five-intid', 'zope-lifecycleevent'), ('five-intid', 'zope-interface'), ('five-intid', 'zope'), ('datetime', 'zope-interface'), ('datetime', 'pytz'), ('zope-publisher', 'multipart'), ('zope-publisher', 'setuptools'), ('zope-publisher', 'zope-location'), ('zope-publisher', 'zope-i18n'), ('zope-publisher', 'zope-proxy'), ('zope-publisher', 'zope-exceptions'), ('zope-publisher', 'zope-component'), ('zope-publisher', 'six'), ('zope-publisher', 'zope-event'), ('zope-publisher', '<Python from Requires-Python>'), ('zope-publisher', 'zope-security'), ('zope-publisher', 'zope-browser'), ('zope-publisher', 'zope-interface'), ('zope-publisher', 'zope-configuration'), ('zope-publisher', 'zope-contenttype'), ('plone-portlets', 'zope-schema'), ('plone-portlets', 'zodb3'), ('plone-portlets', 'setuptools'), ('plone-portlets', 'zope-publisher'), ('plone-portlets', 'zope-container'), ('plone-portlets', 'zope-contentprovider'), ('plone-portlets', 'zope-component'), ('plone-portlets', 'zope-site'), ('plone-portlets', 'plone-memoize'), ('plone-portlets', 'zope-interface'), ('plone-portlets', 'zope-annotation'), ('plone-app-uuid', 'plone-indexer'), ('plone-app-uuid', 'setuptools'), ('plone-app-uuid', 'zope-publisher'), ('plone-app-uuid', 'plone-uuid'), ('plone-app-uuid', 'zope-interface'), ('plone-resourceeditor', 'zope-schema'), ('plone-resourceeditor', 'zope2'), ('plone-resourceeditor', 'setuptools'), ('plone-resourceeditor', 'zope-publisher'), ('plone-resourceeditor', 'zope-component'), ('plone-resourceeditor', 'six'), ('plone-resourceeditor', 'plone-staticresources'), ('plone-resourceeditor', 'zope-interface'), ('plone-schemaeditor', 'z3c-form'), ('plone-schemaeditor', 'zope-schema'), ('plone-schemaeditor', 'zope-cachedescriptors'), ('plone-schemaeditor', 'setuptools'), ('plone-schemaeditor', 'plone-autoform'), ('plone-schemaeditor', 'zope-publisher'), ('plone-schemaeditor', 'zope-container'), ('plone-schemaeditor', 'plone-app-z3cform'), ('plone-schemaeditor', 'zope-component'), ('plone-schemaeditor', 'zope-globalrequest'), ('plone-schemaeditor', 'six'), ('plone-schemaeditor', 'zope-lifecycleevent'), ('plone-schemaeditor', 'plone-z3cform'), ('plone-schemaeditor', 'zope-interface'), ('plone-schemaeditor', 'zope'), ('zexceptions', 'zope-interface'), ('zexceptions', 'setuptools'), ('zexceptions', 'zope-publisher'), ('zexceptions', 'zope-security'), ('zope-browserpage', 'zope-schema'), ('zope-browserpage', 'zope-tal'), ('zope-browserpage', 'setuptools'), ('zope-browserpage', 'zope-publisher'), ('zope-browserpage', 'zope-pagetemplate'), ('zope-browserpage', 'zope-component'), ('zope-browserpage', 'zope-traversing'), ('zope-browserpage', 'zope-security'), ('zope-browserpage', 'zope-interface'), ('zope-browserpage', 'zope-configuration'), ('zope-browserresource', 'zope-schema'), ('zope-browserresource', 'setuptools'), ('zope-browserresource', 'zope-location'), ('zope-browserresource', 'zope-publisher'), ('zope-browserresource', 'zope-i18n'), ('zope-browserresource', 'zope-component'), ('zope-browserresource', 'zope-traversing'), ('zope-browserresource', 'zope-interface'), ('zope-browserresource', 'zope-configuration'), ('zope-browserresource', 'zope-contenttype'), ('plone-resource', 'zope-schema'), ('plone-resource', 'zope2'), ('plone-resource', 'setuptools'), ('plone-resource', 'zope-filerepresentation'), ('plone-resource', 'zope-publisher'), ('plone-resource', 'zope-component'), ('plone-resource', 'zope-traversing'), ('plone-resource', 'plone-caching'), ('plone-resource', 'six'), ('plone-resource', 'python-dateutil'), ('plone-resource', 'z3c-caching'), ('plone-resource', 'zope-interface'), ('plone-resource', 'zope-configuration'), ('zope-globalrequest', 'zope-traversing'), ('zope-globalrequest', 'zope-interface'), ('zope-globalrequest', 'setuptools'), ('zope-globalrequest', 'zope-publisher'), ('zope-ptresource', 'setuptools'), ('zope-ptresource', 'zope-publisher'), ('zope-ptresource', 'zope-pagetemplate'), ('zope-ptresource', 'zope-browserresource'), ('zope-ptresource', 'zope-security'), ('zope-ptresource', 'zope-interface'), ('products-genericsetup', 'setuptools'), ('products-genericsetup', 'five-localsitemanager'), ('products-genericsetup', 'products-zcatalog'), ('products-genericsetup', 'six'), ('products-genericsetup', '<Python from Requires-Python>'), ('products-genericsetup', 'products-pythonscripts'), ('products-genericsetup', 'zope'), ('plone-browserlayer', 'products-genericsetup'), ('plone-browserlayer', 'zope2'), ('plone-browserlayer', 'setuptools'), ('plone-browserlayer', 'zope-component'), ('plone-browserlayer', 'zope-traversing'), ('plone-browserlayer', 'zope-interface'), ('plone-browserlayer', 'products-cmfcore'), ('products-cmfcore', 'products-standardcachemanagers'), ('products-cmfcore', 'products-genericsetup'), ('products-cmfcore', 'products-btreefolder2'), ('products-cmfcore', 'setuptools'), ('products-cmfcore', 'zope-datetime'), ('products-cmfcore', 'docutils'), ('products-cmfcore', 'five-localsitemanager'), ('products-cmfcore', 'products-mailhost'), ('products-cmfcore', 'products-zcatalog'), ('products-cmfcore', 'six'), ('products-cmfcore', '<Python from Requires-Python>'), ('products-cmfcore', 'products-pythonscripts'), ('products-cmfcore', 'zope-interface'), ('products-cmfcore', 'zope'), ('products-pluggableauthservice', 'products-standardcachemanagers'), ('products-pluggableauthservice', 'products-genericsetup'), ('products-pluggableauthservice', 'setuptools'), ('products-pluggableauthservice', 'products-sessions'), ('products-pluggableauthservice', 'products-pluginregistry'), ('products-pluggableauthservice', 'accesscontrol'), ('products-pluggableauthservice', 'six'), ('products-pluggableauthservice', '<Python from Requires-Python>'), ('products-pluggableauthservice', 'zope'), ('products-pluginregistry', 'products-genericsetup'), ('products-pluginregistry', 'setuptools'), ('products-pluginregistry', 'six'), ('products-pluginregistry', '<Python from Requires-Python>'), ('products-pluginregistry', 'zope'), ('plone-staticresources', 'products-genericsetup'), ('plone-staticresources', 'setuptools'), ('plone-staticresources', 'plone-resource'), ('products-dcworkflow', 'products-genericsetup'), ('products-dcworkflow', 'setuptools'), ('products-dcworkflow', 'six'), ('products-dcworkflow', '<Python from Requires-Python>'), ('products-dcworkflow', 'products-pythonscripts'), ('products-dcworkflow', 'zope'), ('products-dcworkflow', 'products-cmfcore'), ('products-dcworkflow', 'products-externalmethod'), ('plone-app-theming', 'docutils'), ('plone-app-theming', 'repoze-xmliter'), ('plone-app-theming', 'lxml'), ('plone-app-theming', 'setuptools'), ('plone-app-theming', 'zope-traversing'), ('plone-app-theming', 'roman'), ('plone-app-theming', 'plone-subrequest'), ('plone-app-theming', 'six'), ('plone-app-theming', 'plone-transformchain'), ('plone-app-theming', 'plone-resourceeditor'), ('plone-app-theming', 'python-dateutil'), ('plone-app-theming', 'plone-app-registry'), ('plone-app-theming', 'plone-staticresources'), ('plone-app-theming', 'diazo'), ('plone-portlet-collection', 'setuptools'), ('plone-portlet-collection', 'plone-app-portlets'), ('plone-portlet-collection', 'plone-portlets'), ('plone-portlet-collection', 'plone-app-vocabularies'), ('plone-portlet-collection', 'plone-memoize'), ('plone-app-relationfield', 'z3c-form'), ('plone-app-relationfield', 'zope-schema'), ('plone-app-relationfield', 'plone-app-intid'), ('plone-app-relationfield', 'setuptools'), ('plone-app-relationfield', 'plone-autoform'), ('plone-app-relationfield', 'plone-rfc822'), ('plone-app-relationfield', 'z3c-formwidget-query'), ('plone-app-relationfield', 'plone-app-vocabularies'), ('plone-app-relationfield', 'plone-app-z3cform'), ('plone-app-relationfield', 'zope-component'), ('plone-app-relationfield', 'zope-intid'), ('plone-app-relationfield', 'plone-supermodel'), ('plone-app-relationfield', 'plone-schemaeditor'), ('plone-app-relationfield', 'z3c-relationfield'), ('plone-app-relationfield', 'zope-interface'), ('plone-app-relationfield', 'five-intid'), ('plone-app-relationfield', 'products-cmfcore'), ('plone-api', 'setuptools'), ('plone-api', 'plone-uuid'), ('plone-api', 'plone-app-linkintegrity'), ('plone-api', 'products-statusmessages'), ('plone-api', 'zope-globalrequest'), ('plone-api', 'plone-app-uuid'), ('plone-api', 'decorator'), ('plone-app-discussion', 'plone-indexer'), ('plone-app-discussion', 'z3c-form'), ('plone-app-discussion', 'zodb3'), ('plone-app-discussion', 'setuptools'), ('plone-app-discussion', 'plone-registry'), ('plone-app-discussion', 'zope-container'), ('plone-app-discussion', 'plone-app-layout'), ('plone-app-discussion', 'plone-app-z3cform'), ('plone-app-discussion', 'zope-component'), ('plone-app-discussion', 'zope-site'), ('plone-app-discussion', 'six'), ('plone-app-discussion', 'zope-event'), ('plone-app-discussion', 'zope-lifecycleevent'), ('plone-app-discussion', 'plone-z3cform'), ('plone-app-discussion', 'plone-app-registry'), ('plone-app-discussion', 'plone-app-uuid'), ('plone-app-discussion', 'zope-interface'), ('plone-app-discussion', 'zope-annotation'), ('plone-app-redirector', 'plone-memoize'), ('plone-app-redirector', 'six'), ('plone-app-redirector', 'setuptools'), ('products-mimetypesregistry', 'zope2'), ('products-mimetypesregistry', 'setuptools'), ('products-mimetypesregistry', 'zope-contenttype'), ('products-mimetypesregistry', 'accesscontrol'), ('products-mimetypesregistry', 'zope-deferredimport'), ('products-mimetypesregistry', 'six'), ('products-mimetypesregistry', 'zope-interface'), ('products-mimetypesregistry', 'products-cmfcore'), ('plone-app-versioningbehavior', 'plone-namedfile[blobs]'), ('plone-app-versioningbehavior', 'plone-autoform'), ('plone-app-versioningbehavior', 'setuptools'), ('plone-app-versioningbehavior', 'plone-rfc822'), ('plone-app-versioningbehavior', 'zope-container'), ('plone-app-versioningbehavior', 'plone-dexterity'), ('plone-app-versioningbehavior', 'plone-behavior'), ('plone-app-versioningbehavior', 'plone-app-dexterity[relations]'), ('plone-app-versioningbehavior', 'products-cmfeditions'), ('zope-deferredimport', 'zope-proxy'), ('zope-deferredimport', 'setuptools'), ('plone-protect', 'repoze-xmliter'), ('plone-protect', 'zope2'), ('plone-protect', 'setuptools'), ('plone-protect', 'collective-monkeypatcher'), ('plone-protect', 'zope-component'), ('plone-protect', 'plone-transformchain'), ('plone-protect', 'six'), ('plone-protect', 'zope-interface'), ('plone-protect', 'lxml[cssselect]'), ('plone-protect', 'plone-keyring'), ('plone-indexer', 'setuptools'), ('plone-indexer', 'products-zcatalog'), ('plone-indexer', 'zope-component'), ('plone-indexer', 'zope-interface'), ('plone-indexer', 'products-cmfcore'), ('plone-memoize', 'setuptools'), ('plone-memoize', 'zope-component'), ('plone-memoize', 'six'), ('plone-memoize', 'zope-ramcache'), ('plone-memoize', 'zope-interface'), ('plone-memoize', 'zope-annotation'), ('plone-session', 'zope2'), ('plone-session', 'setuptools'), ('plone-session', 'products-pluggableauthservice'), ('plone-session', 'zope-component'), ('plone-session', 'six'), ('plone-session', 'plone-protect'), ('plone-session', 'zope-interface'), ('plone-session', 'plone-keyring'), ('plone-behavior', 'zope-schema'), ('plone-behavior', 'setuptools'), ('plone-behavior', 'zope-component'), ('plone-behavior', 'zope-interface'), ('plone-behavior', 'zope-configuration'), ('plone-behavior', 'zope-annotation'), ('plone-namedfile[blobs]', 'plone-namedfile'), ('plone-namedfile[blobs]', 'setuptools'), ('plone-namedfile[blobs]', 'piexif'), ('plone-namedfile[blobs]', 'plone-rfc822'), ('plone-namedfile[blobs]', 'zope-copy'), ('plone-namedfile[blobs]', 'plone-scale[storage]'), ('plone-namedfile[blobs]', 'zope-component'), ('plone-namedfile[blobs]', 'zope-traversing'), ('plone-namedfile[blobs]', 'plone-supermodel'), ('plone-namedfile[blobs]', 'six'), ('plone-namedfile[blobs]', 'plone-schemaeditor'), ('plone-namedfile[blobs]', 'zope-security'), ('plone-namedfile[blobs]', 'zope-browserpage'), ('plone-namedfile[scales]', 'plone-namedfile'), ('plone-namedfile[scales]', 'setuptools'), ('plone-namedfile[scales]', 'piexif'), ('plone-namedfile[scales]', 'plone-rfc822'), ('plone-namedfile[scales]', 'zope-copy'), ('plone-namedfile[scales]', 'plone-scale[storage]'), ('plone-namedfile[scales]', 'zope-component'), ('plone-namedfile[scales]', 'zope-traversing'), ('plone-namedfile[scales]', 'plone-supermodel'), ('plone-namedfile[scales]', 'six'), ('plone-namedfile[scales]', 'plone-schemaeditor'), ('plone-namedfile[scales]', 'zope-security'), ('plone-namedfile[scales]', 'zope-browserpage'), ('plone-z3cform', 'setuptools'), ('plone-z3cform', 'zope-i18n'), ('plone-z3cform', 'zope-component'), ('plone-z3cform', 'plone-batching'), ('plone-z3cform', 'six'), ('plone-z3cform', 'zope-browserpage'), ('plone-z3cform', 'z3c-form'), ('plone-z3cform', 'zope'), ('plone-app-textfield', 'zope-schema'), ('plone-app-textfield', 'setuptools'), ('plone-app-textfield', 'zodb3'), ('plone-app-textfield', 'zope-component'), ('plone-app-textfield', 'six'), ('plone-app-textfield', 'zope-interface'), ('plone-namedfile', 'setuptools'), ('plone-namedfile', 'piexif'), ('plone-namedfile', 'plone-rfc822'), ('plone-namedfile', 'zope-copy'), ('plone-namedfile', 'plone-scale[storage]'), ('plone-namedfile', 'zope-component'), ('plone-namedfile', 'zope-traversing'), ('plone-namedfile', 'plone-supermodel'), ('plone-namedfile', 'six'), ('plone-namedfile', 'plone-schemaeditor'), ('plone-namedfile', 'zope-security'), ('plone-namedfile', 'zope-browserpage'), ('plone-transformchain', 'zope-schema'), ('plone-transformchain', 'zope2'), ('plone-transformchain', 'setuptools'), ('plone-transformchain', 'zope-component'), ('plone-transformchain', 'six'), ('plone-transformchain', 'zope-interface'), ('z3c-pt', 'setuptools'), ('z3c-pt', 'zope-i18n'), ('z3c-pt', 'zope-contentprovider'), ('z3c-pt', 'chameleon'), ('z3c-pt', 'zope-component'), ('z3c-pt', 'zope-traversing'), ('z3c-pt', 'six'), ('z3c-pt', '<Python from Requires-Python>'), ('z3c-pt', 'zope-interface'), ('zope-annotation', 'setuptools'), ('zope-annotation', 'zope-location'), ('zope-annotation', 'zope-proxy'), ('zope-annotation', 'zope-component'), ('zope-annotation', 'zope-interface'), ('plone-event', 'setuptools'), ('plone-event', 'zope-component'), ('plone-event', 'python-dateutil'), ('plone-event', 'zope-interface'), ('plone-event', 'pytz'), ('plone-scale[storage]', 'setuptools'), ('plone-scale[storage]', 'zope-component'), ('plone-scale[storage]', 'six'), ('plone-scale[storage]', 'plone-scale'), ('plone-scale[storage]', 'persistence'), ('plone-scale[storage]', 'zope-interface'), ('plone-scale[storage]', 'zope-configuration'), ('plone-scale[storage]', 'zope-annotation'), ('plone-alterego', 'zope-interface'), ('plone-alterego', 'setuptools'), ('plone-alterego', 'zope-component'), ('z3c-caching', 'setuptools'), ('z3c-caching', 'zope-component'), ('z3c-caching', 'zope-event'), ('z3c-caching', 'zope-lifecycleevent'), ('z3c-caching', 'zope-browser'), ('z3c-caching', 'zope-interface'), ('z3c-zcmlhook', 'zope-schema'), ('z3c-zcmlhook', 'setuptools'), ('z3c-zcmlhook', 'zope-component'), ('z3c-zcmlhook', 'zope-interface'), ('z3c-zcmlhook', 'zope-configuration'), ('zope-intid', 'btrees'), ('zope-intid', 'setuptools'), ('zope-intid', 'zope-location'), ('zope-intid', 'persistent'), ('zope-intid', 'zope-keyreference'), ('zope-intid', 'zope-component'), ('zope-intid', 'zope-event'), ('zope-intid', 'zope-lifecycleevent'), ('zope-intid', 'zope-security'), ('zope-intid', 'zope-interface'), ('z3c-caching[zcml]', 'setuptools'), ('z3c-caching[zcml]', 'zope-component'), ('z3c-caching[zcml]', 'zope-event'), ('z3c-caching[zcml]', 'zope-lifecycleevent'), ('z3c-caching[zcml]', 'zope-browser'), ('z3c-caching[zcml]', 'z3c-caching'), ('z3c-caching[zcml]', 'zope-interface'), ('z3c-caching[zcml]', 'zope-configuration'), ('plone-keyring', 'zodb3'), ('plone-keyring', 'setuptools'), ('plone-keyring', 'zope-location'), ('plone-keyring', 'zope-container'), ('plone-keyring', 'zope-interface'), ('zc-relation', 'zodb3'), ('zc-relation', 'setuptools'), ('zc-relation', 'six'), ('zc-relation', 'zope-testing'), ('zc-relation', 'zope-interface'), ('zope-interface', 'setuptools'), ('zope-interface', '<Python from Requires-Python>'), ('zope-location', 'zope-schema'), ('zope-location', 'zope-interface'), ('zope-location', 'setuptools'), ('zope-location', 'zope-proxy'), ('products-statusmessages', 'setuptools'), ('products-statusmessages', 'zope-i18n'), ('products-statusmessages', 'six'), ('products-statusmessages', 'zope-interface'), ('products-statusmessages', 'zope-annotation'), ('btrees', 'persistent'), ('btrees', 'zope-interface'), ('persistent', 'zope-interface'), ('persistent', 'cffi'), ('zope-filerepresentation', 'zope-schema'), ('zope-filerepresentation', 'zope-interface'), ('zope-filerepresentation', 'setuptools'), ('zope-filerepresentation', '<Python from Requires-Python>'), ('zope-lifecycleevent', 'zope-interface'), ('zope-lifecycleevent', 'zope-event'), ('zope-lifecycleevent', 'setuptools'), ('zope-proxy', 'zope-interface'), ('zope-proxy', 'setuptools'), ('zope-schema', 'zope-interface'), ('zope-schema', 'zope-event'), ('zope-schema', '<Python from Requires-Python>'), ('zope-schema', 'setuptools'), ('zope-browser', 'zope-interface'), ('zope-browser', 'setuptools'), ('zope-copy', 'zope-interface'), ('zope-copy', 'setuptools'), ('zope-exceptions', 'zope-interface'), ('zope-exceptions', 'setuptools'), ('zope-processlifetime', 'zope-interface'), ('zope-processlifetime', 'setuptools'), ('zope-ramcache', 'persistent'), ('zope-ramcache', 'zope-interface'), ('zope-ramcache', 'setuptools'), ('zope-ramcache', 'zope-location'), ('zope-testbrowser', 'zope-schema'), ('zope-testbrowser', 'zope-cachedescriptors'), ('zope-testbrowser', 'setuptools'), ('zope-testbrowser', 'wsgiproxy2'), ('zope-testbrowser', 'beautifulsoup4'), ('zope-testbrowser', 'six'), ('zope-testbrowser', 'soupsieve'), ('zope-testbrowser', 'zope-interface'), ('zope-testbrowser', 'webtest'), ('zope-testbrowser', 'pytz'), ('products-daterecurringindex', 'zodb'), ('products-daterecurringindex', 'btrees'), ('products-daterecurringindex', 'zope-schema'), ('products-daterecurringindex', 'setuptools'), ('products-daterecurringindex', 'products-zcatalog'), ('products-daterecurringindex', 'plone-event'), ('products-daterecurringindex', 'zope-interface'), ('z3c-objpath', 'zope-interface'), ('z3c-objpath', 'setuptools'), ('plone-app-linkintegrity', 'plone-app-intid'), ('plone-app-linkintegrity', 'plone-app-relationfield'), ('plone-app-linkintegrity', 'six'), ('plone-app-linkintegrity', 'setuptools'), ('products-extendedpathindex', 'six'), ('products-extendedpathindex', 'setuptools'), ('products-extendedpathindex', 'zope'), ('products-extendedpathindex', 'products-zcatalog'), ('zope-cachedescriptors', 'setuptools'), ('plone-stringinterp', 'zope-i18n'), ('plone-stringinterp', 'plone-memoize'), ('plone-stringinterp', 'setuptools'), ('plone-stringinterp', 'products-cmfcore'), ('plone-app-i18n', 'setuptools'), ('plonetheme-barceloneta', 'plone-batching'), ('plonetheme-barceloneta', 'setuptools'), ('plonetheme-barceloneta', 'plone-app-theming'), ('products-isurlinportal', 'setuptools'), ('plone-app-contentlisting', 'setuptools'), ('plone-batching', 'zope2'), ('plone-batching', 'setuptools'), ('plone-intelligenttext', 'setuptools'), ('zope-event', 'setuptools'), ('products-cmfuid', 'products-zcatalog'), ('products-cmfuid', 'setuptools'), ('products-cmfuid', 'zope'), ('products-cmfuid', 'products-cmfcore'), ('calmjs-parse', 'ply'), ('calmjs-parse', 'setuptools'), ('plone-subrequest', 'zope-globalrequest'), ('plone-subrequest', 'six'), ('plone-subrequest', 'setuptools'), ('persistence', 'persistent'), ('persistence', 'extensionclass'), ('persistence', 'six'), ('multimapping', 'extensionclass'), ('missing', 'extensionclass'), ('record', 'extensionclass'), ('setuptools', '<Python from Requires-Python>'), ('plone-formwidget-namedfile', 'plone-namedfile'), ('plone-formwidget-namedfile', 'z3c-form'), ('plone-formwidget-namedfile', 'setuptools'), ('plone-formwidget-namedfile', 'plone-z3cform'), ('repoze-xmliter', 'lxml'), ('repoze-xmliter', 'setuptools'), ('repoze-xmliter', 'future'), ('zope-contenttype', 'setuptools'), ('zope-hookable', 'setuptools'), ('zope-hookable', '<Python from Requires-Python>'), ('collective-monkeypatcher', 'six'), ('collective-monkeypatcher', 'setuptools'), ('jsonschema', 'six'), ('jsonschema', 'setuptools'), ('jsonschema', 'attrs'), ('jsonschema', 'pyrsistent'), ('paste', 'six'), ('paste', 'setuptools'), ('pastedeploy', 'setuptools'), ('plone-app-intid', 'setuptools'), ('plone-app-intid', 'zope-intid'), ('plone-app-intid', 'zope-lifecycleevent'), ('plone-app-intid', 'five-intid'), ('plone-app-intid', 'products-cmfcore'), ('zope-datetime', 'six'), ('zope-datetime', 'setuptools'), ('zope-sequencesort', 'setuptools'), ('zope-testing', 'setuptools'), ('z3c-relationfield', 'zope-intid'), ('z3c-relationfield', 'z3c-objpath'), ('z3c-relationfield', 'setuptools'), ('z3c-relationfield', 'zc-relation'), ('zodbpickle', 'setuptools'), ('plone-synchronize', 'setuptools'), ('zc-lockfile', 'setuptools'), ('zdaemon', 'zconfig'), ('zdaemon', 'setuptools'), ('plone-scale', 'six'), ('plone-scale', 'setuptools'), ('restrictedpython', '<Python from Requires-Python>'), ('authencoding', 'six'), ('authencoding', '<Python from Requires-Python>'), ('six', '<Python from Requires-Python>'), ('diazo', 'cssselect'), ('diazo', 'six'), ('diazo', 'future'), ('diazo', 'lxml'), ('python-dateutil', 'six'), ('python-dateutil', '<Python from Requires-Python>'), ('webtest', 'beautifulsoup4'), ('webtest', 'six'), ('webtest', 'webob'), ('webtest', 'waitress'), ('wsgiproxy2', 'six'), ('wsgiproxy2', 'webob'), ('chameleon', '<Python from Requires-Python>'), ('docutils', '<Python from Requires-Python>'), ('lxml', '<Python from Requires-Python>'), ('markdown', '<Python from Requires-Python>'), ('unidecode', '<Python from Requires-Python>'), ('decorator', '<Python from Requires-Python>'), ('feedparser', '<Python from Requires-Python>'), ('feedparser', 'sgmllib3k'), ('roman', '<Python from Requires-Python>'), ('simplejson', '<Python from Requires-Python>'), ('waitress', '<Python from Requires-Python>'), ('attrs', '<Python from Requires-Python>'), ('cssselect', '<Python from Requires-Python>'), ('pyrsistent', '<Python from Requires-Python>'), ('soupsieve', '<Python from Requires-Python>'), ('future', '<Python from Requires-Python>'), ('icalendar', 'python-dateutil'), ('icalendar', '<Python from Requires-Python>'), ('icalendar', 'pytz'), ('piexif', '<Python from Requires-Python>'), ('webob', '<Python from Requires-Python>'), ('pycparser', '<Python from Requires-Python>'), ('zope2', 'zope'), ('lxml[cssselect]', 'lxml'), ('lxml[cssselect]', 'cssselect'), ('beautifulsoup4', 'soupsieve'), ('cffi', 'pycparser')]

@Rizhiy
Copy link
Author

Rizhiy commented Oct 9, 2021

I think I have made a reproducible example: https://github.com/Rizhiy/pip-conflicts

While making it, I realised that the problem is, most likely, that pip conflict resolution is just very slow/stupid and not that it is incorrect.

@notatallshaw
Copy link
Member

While making it I realised that the problem is that pip conflict resolution it just very slow/stupid and not incorrect.

As someone who had that gut feeling many months ago and have been trying to come up with better approaches ever since I can tell you it's not an easy problem to solve.

Finding a solution on a dependency graph is basically a brute force problem if you don't make any assumptions about said dependency graph. Hopefully though #10481 will fix the time it takes your requirements to resolve. Otherwise I have some more ideas on how to improve resolution time further.

@pradyunsg
Copy link
Member

It's not the dependency resolution that is slow here -- I've demonstrated that above. As @uranusjr noted, the problem in this case is the logic that's computing the "order to install packages" (get_installation_order -> get_topological_weights). That logic is being ridiculously slow, likely due to the very edge-heavy/dense dependency graph that this situation has; and possibly due to a state management bug in that logic.

@notatallshaw
Copy link
Member

It's not the dependency resolution that is slow here -- I've demonstrated that above. As @uranusjr noted, the problem in this case is the logic that's computing the "order to install packages" (get_installation_order -> get_topological_weights). That logic is being ridiculously slow, likely due to the very edge-heavy/dense dependency graph that this situation has; and possibly due to a state management bug in that logic.

I see, I thought OP had changed their mind on what the issue was, thanks for the correction.

@Rizhiy
Copy link
Author

Rizhiy commented Oct 9, 2021

@pradyunsg Did you look at the example I provided? The behaviour seems different from the @mauritsvanrees case.

Even if resolver is not at fault here, there seems to be erroneous logging since I'm getting messages like:

INFO: This is taking longer than usual. You might need to provide the dependency resolver with stricter constraints to reduce runtime. If you want to abort this run, you can press Ctrl + C to do so. To improve how pip performs, tell us what happened here: https://pip.pypa.io/surveys/backtracking
INFO: pip is looking at multiple versions of srsly to determine which version is compatible with other requirements. This could take a while.
INFO: pip is looking at multiple versions of idna to determine which version is compatible with other requirements. This could take a while.

P.S. I checked behaviour using #10481 and the problem is still there.

@pradyunsg
Copy link
Member

pradyunsg commented Oct 9, 2021

No, I haven't played with your example repository yet. There's two separate things in this issue, as far as I'm concerned:

Based on a quick look, it looks like your example repository demonstrates the first issue, where the resolver is going to try too hard to get a solution; especially if one doesn't exist. That's already got a bunch of other issues to track it -- #9517 is one that is handy right now.

$ python -m pip install Products.CMFPlone -c https://dist.plone.org/release/pip-resolver-test/constraints.txt --log /tmp/log.txt

For this example, #10481 solves the stupid backtracking issue; although the computation of what order to install packages in still takes a long time; likely due to the dense nature of the dependency graph.

P.S. I checked behaviour using #1048 and the problem is still there.

I'm guessing this is a typo?

@Rizhiy
Copy link
Author

Rizhiy commented Oct 10, 2021

Yes, I meant #10481, fixed original.

@mauritsvanrees
Copy link
Sponsor Contributor

I added a bit of debugging code in the pip main branch to see how often nodes are visited in the "get installation order" logic, especially setuptools which is a dependency of most packages:

$ git diff
diff --git a/src/pip/_internal/resolution/resolvelib/resolver.py b/src/pip/_internal/resolution/resolvelib/resolver.py
index 12f967020..90fe1aa7d 100644
--- a/src/pip/_internal/resolution/resolvelib/resolver.py
+++ b/src/pip/_internal/resolution/resolvelib/resolver.py
@@ -212,6 +212,7 @@ def get_topological_weights(
     """
     path: Set[Optional[str]] = set()
     weights: Dict[Optional[str], int] = {}
+    visited: Dict[Optional[str], int] = {}
 
     def visit(node: Optional[str]) -> None:
         if node in path:
@@ -219,6 +220,11 @@ def get_topological_weights(
             return
 
         # Time to visit the children!
+        if node in visited:
+            visited[node] += 1
+        else:
+            visited[node] = 1
+        visited["dummy"] += 1
         path.add(node)
         for child in graph.iter_children(node):
             visit(child)
@@ -228,7 +234,13 @@ def get_topological_weights(
         weights[node] = max(last_known_parent_count, len(path))
 
     # `None` is guaranteed to be the root node by resolvelib.
+    # breakpoint()
+    print(f"Expected node count: {expected_node_count}")
+    visited["dummy"] = 0
     visit(None)
+    print(f"Weight setuptools: {weights['setuptools']}.")
+    print(f"Visited setuptools {visited['setuptools']} times.")
+    print(f"Visited any node: {visited['dummy']} times.")
 
     # Sanity checks
     assert weights[None] == 0

I tried this with Zope, which is a sub part of Plone, so it is installed already if you followed my example from above:

$ bin/python -m pip install Zope -c https://dist.plone.org/release/pip-resolver-test/constraints.txt
...
Expected node count: 80
Weight setuptools: 12.
Visited setuptools 4486 times.
Visited any node: 9545 times.

So for 80 packages, the setuptools node is visited about 4500 times, and the visit function is called almost 10,000 times. This goes fast, the part that calculated the weights takes about a second.

Then try Products.CMFPlone, with lots more packages:

$ bin/python -m pip install Products.CMFPlone -c https://dist.plone.org/release/pip-resolver-test/constraints.txt
...
Expected node count: 238
Weight setuptools: 30.
Visited setuptools 150681071 times.
Visited any node: 321043495 times.

So the setuptools node is visited 150 million times, and the visit function is called over 300 million times. It takes a few minutes.

As suspected, it does not scale very well. :-)

Maybe iterating over graph.iter_edges helps, but I don't yet see how.

@pradyunsg
Copy link
Member

pradyunsg commented Oct 11, 2021

Yup yup. This was written for correctness, rather than speed, so that looks about right to me.

It's basically exploring all paths on the graph, and remembering the length of the longest one.

It makes sense to me that this would be horrendous for a dense graph like that. :)

@mauritsvanrees
Copy link
Sponsor Contributor

This much simpler version of get_topological_weights works for me, but I suppose it is too simplistic:

weights: Dict[Optional[str], int] = {}
for key in graph:
    weights[key] = len(graph._backwards[key]) - len(graph._forwards[key])
assert len(weights) == expected_node_count
return weights

In my case, setuptools gets a lot of points, just like zope.interface which is a very central package in the Zope/Plone universe. Products.CMFPlone has a large negative value, because it depends on lots of packages, without other packages depending on it.

Hypothetically, if ten packages depend on zope.interface, and zope.interface is the only one that depends on setuptools, then this simple method gives zope.interface 10-1=9 points, so it gets installed before setuptools which has only one point. And I can imagine this was actually the initial implementation, and then smarter people than me made it more correct.

So:

  • I hope someone has a brain wave to make this function not only correct, but also fast. I'll think about, but don't count on it.
  • Meanwhile, please keep the legacy resolver available.
  • One small thing that would be a big improvement, is to not actually call this code unless needed. Currently, get_installation_order gets the topological weights and then uses this to sort the requirement set. But in my case, the requirement set is empty: I have initially installed it with the legacy resolver, which does not have this problem. And then when I use the new standard resolver, it should see that all requirements have already been installed, so there is no need to sort anything.

@Rizhiy
Copy link
Author

Rizhiy commented Oct 11, 2021

I guess I'm missing something here. Why does installation order matter at all? Unless a package has install_requires specified, can't you just install them in any order?

@uranusjr
Copy link
Member

A lot of packages out there depend on installation ordering to work correctly, e.g. some namespace packages overwrite files already installed by another package, and produce incorrect end results if we swap the order.

@Rizhiy
Copy link
Author

Rizhiy commented Oct 11, 2021

Somehow I have a feeling that while it might be a lot in absolute terms, it is a very small as a percentage of all packages.
I think this problem should be solved by forcing such packages to specify install_requires or something similar and then running graph resolution only on that sub-graph.

@Rizhiy
Copy link
Author

Rizhiy commented Oct 11, 2021

In the meantime, another question: why is setuptools in @mauritsvanrees example visited so many times?
Can't you check each package once, construct a dependency DAG and then optimise weights on that?

@uranusjr
Copy link
Member

First of all, the dependency graph is not guaranteed to be acyclic 🙂 The resolver indeed constructed a graph, so feel free to contribute an implementation that reduces node visits if you have algorithmics insights on this .

@Rizhiy Rizhiy closed this as completed Oct 11, 2021
@Rizhiy Rizhiy reopened this Oct 11, 2021
@pradyunsg
Copy link
Member

The discussion in #8127 is relevant, in case someone wants to tackle this. There's existing tests for this method's logic here:

def test_new_resolver_topological_weights(

If this were guarenteed to be an DAG, then we wouldn't be having this conversation. :)


I suppose it is too simplistic

Yea, we're not measuring in-degree vs out-degree here. This implementation will fail all the tests for what get_topological_weights is supposed to do. :)

From #8127:

We want the length for the longest path to any node from root, ignoring any paths containing cycles.

@mauritsvanrees
Copy link
Sponsor Contributor

Okay, I have a solution that works for me, and passes the test_resolver tests, except for one but I think the slightly different outcome is actually okay. I'll do a PR (my first on pip).

@mauritsvanrees
Copy link
Sponsor Contributor

Done: #10574
But I guess this may need to be done in resolvelib first.

pradyunsg pushed a commit that referenced this issue Nov 20, 2021
Fixes #10557 where the resolver spends too much time calculating the weights.

Also, do not let `get_installation_order` calculate these weights at all when there is nothing left to install.

Co-authored-by: Tzu-ping Chung <[email protected]>
@github-actions github-actions bot locked as resolved and limited conversation to collaborators Dec 21, 2021
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
C: dependency resolution About choosing which dependencies to install
Projects
None yet
Development

Successfully merging a pull request may close this issue.

6 participants