[Checkins] SVN: groktoolkit/branches/jw-documentation-rearangement/doc start moving Grok documentation to the groktoolkit
Jan-Wijbrand Kolman
janwijbrand at gmail.com
Wed Jan 12 11:38:04 EST 2011
Log message for revision 119545:
start moving Grok documentation to the groktoolkit
Changed:
A groktoolkit/branches/jw-documentation-rearangement/doc/
A groktoolkit/branches/jw-documentation-rearangement/doc/ACKS.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/Makefile
A groktoolkit/branches/jw-documentation-rearangement/doc/README.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/_build/
A groktoolkit/branches/jw-documentation-rearangement/doc/_build/Makefile
A groktoolkit/branches/jw-documentation-rearangement/doc/_build/make.bat
A groktoolkit/branches/jw-documentation-rearangement/doc/_static/
A groktoolkit/branches/jw-documentation-rearangement/doc/_static/default.css
A groktoolkit/branches/jw-documentation-rearangement/doc/_static/grok.css
A groktoolkit/branches/jw-documentation-rearangement/doc/_static/grok_club.gif
A groktoolkit/branches/jw-documentation-rearangement/doc/_static/logo.gif
A groktoolkit/branches/jw-documentation-rearangement/doc/_static/logo.png
A groktoolkit/branches/jw-documentation-rearangement/doc/_static/top_bg.jpg
A groktoolkit/branches/jw-documentation-rearangement/doc/_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/bugs.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/changes.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/conf.py
A groktoolkit/branches/jw-documentation-rearangement/doc/contents.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/copyright.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/design/
A groktoolkit/branches/jw-documentation-rearangement/doc/design/adapters.py
A groktoolkit/branches/jw-documentation-rearangement/doc/design/annotations.py
A groktoolkit/branches/jw-documentation-rearangement/doc/design/container.py
A groktoolkit/branches/jw-documentation-rearangement/doc/design/grok_beginner.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/design/grok_dev.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/design/menu.py
A groktoolkit/branches/jw-documentation-rearangement/doc/design/model.py
A groktoolkit/branches/jw-documentation-rearangement/doc/design/permission.py
A groktoolkit/branches/jw-documentation-rearangement/doc/design/skin-minimal.py
A groktoolkit/branches/jw-documentation-rearangement/doc/design/skin.py
A groktoolkit/branches/jw-documentation-rearangement/doc/design/subscriber.py
A groktoolkit/branches/jw-documentation-rearangement/doc/design/traversal.py
A groktoolkit/branches/jw-documentation-rearangement/doc/design/utility.py
A groktoolkit/branches/jw-documentation-rearangement/doc/design/views.py
A groktoolkit/branches/jw-documentation-rearangement/doc/developing_grok.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/docindex.template
A groktoolkit/branches/jw-documentation-rearangement/doc/glossary.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/grok_overview.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app_templates/anotherindex.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app_templates/sampleindex.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app_templates/bye.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/ftesting.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/static/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/static/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/tests.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app_templates/entryindex.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app_templates/sampleindex.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app_templates/bye.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/ftesting.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/static/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/static/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/tests.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app_templates/edit.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app_templates/edit.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/static/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/static/style.css
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app_templates/edit.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app_templates/edit.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app_templates/edit.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app_templates/edit.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/bootstrap.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/buildout.cfg
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/README.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/debug.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/deploy.ini.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/site.zcml.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/zope.conf.in
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/extends-cache/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/setup.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/__init__.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/app.py
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/app_templates/
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/app_templates/index.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/configure.zcml
A groktoolkit/branches/jw-documentation-rearangement/doc/index.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/layout.html
A groktoolkit/branches/jw-documentation-rearangement/doc/license.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/make.bat
A groktoolkit/branches/jw-documentation-rearangement/doc/naming_conventions.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/reference/
A groktoolkit/branches/jw-documentation-rearangement/doc/reference/components.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/reference/conf.py
A groktoolkit/branches/jw-documentation-rearangement/doc/reference/decorators.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/reference/directives.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/reference/events.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/reference/exceptions.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/reference/functions.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/reference/index.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/reference/testing.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/reference/utils.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/resources/
A groktoolkit/branches/jw-documentation-rearangement/doc/resources/evencaveman.jpg
A groktoolkit/branches/jw-documentation-rearangement/doc/resources/grok-standing.jpg
A groktoolkit/branches/jw-documentation-rearangement/doc/style.tex
A groktoolkit/branches/jw-documentation-rearangement/doc/template.pt
A groktoolkit/branches/jw-documentation-rearangement/doc/tutorial.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/tutorial_outline.txt
A groktoolkit/branches/jw-documentation-rearangement/doc/upgrade.rst
A groktoolkit/branches/jw-documentation-rearangement/doc/upgrade.txt
A groktoolkit/branches/jw-documentation-rearangement/documentation.cfg
-=-
Added: groktoolkit/branches/jw-documentation-rearangement/doc/ACKS.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/ACKS.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/ACKS.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,23 @@
+Contributors to the Grok Documentation
+======================================
+
+This section lists people who have contributed in some way to the Grok
+documentation. It is probably not complete -- if you feel that you or
+anyone else should be on this list, please let us know (send email to
+grok-dev at zope.org), and we'll be glad to correct the problem.
+
+.. acks::
+
+ * Darryl Cousins
+ * Kushal Das
+ * Martijn Faassen
+ * Uli Fouquet
+ * Jim Fulton
+ * Jan-Wijbrand Kolman
+ * Luis de la Parra
+ * Luciano Ramalho
+ * Lennart Regebro
+ * Brandon Craig Rhodes
+ * Kevin Teague
+ * Sebastian Ware
+ * Philipp von Weitershausen
Added: groktoolkit/branches/jw-documentation-rearangement/doc/Makefile
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/Makefile (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/Makefile 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,130 @@
+# Makefile for Sphinx documentation
+#
+
+# You can set these variables from the command line.
+SPHINXOPTS =
+SPHINXBUILD = sphinx-build
+PAPER =
+BUILDDIR = _build
+
+# Internal variables.
+PAPEROPT_a4 = -D latex_paper_size=a4
+PAPEROPT_letter = -D latex_paper_size=letter
+ALLSPHINXOPTS = -d $(BUILDDIR)/doctrees $(PAPEROPT_$(PAPER)) $(SPHINXOPTS) .
+
+.PHONY: help clean html dirhtml singlehtml pickle json htmlhelp qthelp devhelp epub latex latexpdf text man changes linkcheck doctest
+
+help:
+ @echo "Please use \`make <target>' where <target> is one of"
+ @echo " html to make standalone HTML files"
+ @echo " dirhtml to make HTML files named index.html in directories"
+ @echo " singlehtml to make a single large HTML file"
+ @echo " pickle to make pickle files"
+ @echo " json to make JSON files"
+ @echo " htmlhelp to make HTML files and a HTML help project"
+ @echo " qthelp to make HTML files and a qthelp project"
+ @echo " devhelp to make HTML files and a Devhelp project"
+ @echo " epub to make an epub"
+ @echo " latex to make LaTeX files, you can set PAPER=a4 or PAPER=letter"
+ @echo " latexpdf to make LaTeX files and run them through pdflatex"
+ @echo " text to make text files"
+ @echo " man to make manual pages"
+ @echo " changes to make an overview of all changed/added/deprecated items"
+ @echo " linkcheck to check all external links for integrity"
+ @echo " doctest to run all doctests embedded in the documentation (if enabled)"
+
+clean:
+ -rm -rf $(BUILDDIR)/*
+
+html:
+ $(SPHINXBUILD) -b html $(ALLSPHINXOPTS) $(BUILDDIR)/html
+ @echo
+ @echo "Build finished. The HTML pages are in $(BUILDDIR)/html."
+
+dirhtml:
+ $(SPHINXBUILD) -b dirhtml $(ALLSPHINXOPTS) $(BUILDDIR)/dirhtml
+ @echo
+ @echo "Build finished. The HTML pages are in $(BUILDDIR)/dirhtml."
+
+singlehtml:
+ $(SPHINXBUILD) -b singlehtml $(ALLSPHINXOPTS) $(BUILDDIR)/singlehtml
+ @echo
+ @echo "Build finished. The HTML page is in $(BUILDDIR)/singlehtml."
+
+pickle:
+ $(SPHINXBUILD) -b pickle $(ALLSPHINXOPTS) $(BUILDDIR)/pickle
+ @echo
+ @echo "Build finished; now you can process the pickle files."
+
+json:
+ $(SPHINXBUILD) -b json $(ALLSPHINXOPTS) $(BUILDDIR)/json
+ @echo
+ @echo "Build finished; now you can process the JSON files."
+
+htmlhelp:
+ $(SPHINXBUILD) -b htmlhelp $(ALLSPHINXOPTS) $(BUILDDIR)/htmlhelp
+ @echo
+ @echo "Build finished; now you can run HTML Help Workshop with the" \
+ ".hhp project file in $(BUILDDIR)/htmlhelp."
+
+qthelp:
+ $(SPHINXBUILD) -b qthelp $(ALLSPHINXOPTS) $(BUILDDIR)/qthelp
+ @echo
+ @echo "Build finished; now you can run "qcollectiongenerator" with the" \
+ ".qhcp project file in $(BUILDDIR)/qthelp, like this:"
+ @echo "# qcollectiongenerator $(BUILDDIR)/qthelp/Grok.qhcp"
+ @echo "To view the help file:"
+ @echo "# assistant -collectionFile $(BUILDDIR)/qthelp/Grok.qhc"
+
+devhelp:
+ $(SPHINXBUILD) -b devhelp $(ALLSPHINXOPTS) $(BUILDDIR)/devhelp
+ @echo
+ @echo "Build finished."
+ @echo "To view the help file:"
+ @echo "# mkdir -p $$HOME/.local/share/devhelp/Grok"
+ @echo "# ln -s $(BUILDDIR)/devhelp $$HOME/.local/share/devhelp/Grok"
+ @echo "# devhelp"
+
+epub:
+ $(SPHINXBUILD) -b epub $(ALLSPHINXOPTS) $(BUILDDIR)/epub
+ @echo
+ @echo "Build finished. The epub file is in $(BUILDDIR)/epub."
+
+latex:
+ $(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex
+ @echo
+ @echo "Build finished; the LaTeX files are in $(BUILDDIR)/latex."
+ @echo "Run \`make' in that directory to run these through (pdf)latex" \
+ "(use \`make latexpdf' here to do that automatically)."
+
+latexpdf:
+ $(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex
+ @echo "Running LaTeX files through pdflatex..."
+ make -C $(BUILDDIR)/latex all-pdf
+ @echo "pdflatex finished; the PDF files are in $(BUILDDIR)/latex."
+
+text:
+ $(SPHINXBUILD) -b text $(ALLSPHINXOPTS) $(BUILDDIR)/text
+ @echo
+ @echo "Build finished. The text files are in $(BUILDDIR)/text."
+
+man:
+ $(SPHINXBUILD) -b man $(ALLSPHINXOPTS) $(BUILDDIR)/man
+ @echo
+ @echo "Build finished. The manual pages are in $(BUILDDIR)/man."
+
+changes:
+ $(SPHINXBUILD) -b changes $(ALLSPHINXOPTS) $(BUILDDIR)/changes
+ @echo
+ @echo "The overview file is in $(BUILDDIR)/changes."
+
+linkcheck:
+ $(SPHINXBUILD) -b linkcheck $(ALLSPHINXOPTS) $(BUILDDIR)/linkcheck
+ @echo
+ @echo "Link check complete; look for any errors in the above output " \
+ "or in $(BUILDDIR)/linkcheck/output.txt."
+
+doctest:
+ $(SPHINXBUILD) -b doctest $(ALLSPHINXOPTS) $(BUILDDIR)/doctest
+ @echo "Testing of doctests in the sources finished, look at the " \
+ "results in $(BUILDDIR)/doctest/output.txt."
Added: groktoolkit/branches/jw-documentation-rearangement/doc/README.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/README.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/README.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,95 @@
+*********************
+About these documents
+*********************
+
+These documents are generated from `reStructuredText
+<http://docutils.sf.net/rst.html>`_ sources by `Sphinx
+<http://sphinx.pocoo.org>`_, an excellent document processor
+specifically written for the Python documentation by Georg Brandl and
+contributors.
+
+Development of this documentation and its toolchain takes place on the
+grok-dev at zope.org mailing list. We're always looking for volunteers
+wanting to help with the docs, so feel free to send a mail there!
+
+Many thanks go to:
+
+* the `docutils <http://docutils.sf.net/>`_ project for creating
+ reStructuredText and the docutils suite;
+* Georg Brandl for his `Sphinx` package.
+
+See :ref:`reporting-bugs` for information how to report bugs in Grok
+itself.
+
+.. including the ACKS file here so that it can be maintained separately
+.. include:: ACKS.txt
+
+It is only with the input and contributions of the Grok community
+that Grok has so much documentation -- Thank You!
+
+
+The Grok documentation toolchain
+================================
+
+Grok now makes use of the ``Sphinx`` package, which was written by
+Georg Brandl and volunteers, to generate the official Python
+documentation. Sphinx is able to generate HTML as well as LaTeX and
+other formats.
+
+
+How can I generate nice HTML/LaTeX/PDF documentation for Grok?
+--------------------------------------------------------------
+
+If you have run ``bin/buildout``, than you're nearly finished. This
+will generate some scripts in the ``bin/`` directory. Just run::
+
+ $ bin/grokdocs2html
+
+to generate the HTML documentation. The docs will be placed in
+
+ docs/build/html/
+
+For LaTeX/PDF docs you must have LaTeX and ``pdflatex`` installed. Then, to generate PDF docs, run::
+
+ $ bin/grokdocs2pdf
+
+which will first generate .tex files and appropriate Makefiles in
+``docs/build/latex`` and afterwards run ``pdflatex`` to generate PDFs.
+
+If everything works smoothly three documents will be generated:
+
+1) The Tutorial (``tutorial.pdf``)
+
+2) The Reference (``reference.pdf``)
+
+3) The whole documentation (``grokdocs.pdf``)
+
+which can be found in ``docs/build/latex``.
+
+Any warnings during the document processing can be ignored for the
+time being.
+
+The ``grokdocs2...`` scripts generated in ``bin/`` unfortunately yet
+do not accept much options. In fact they accept no options at all. But
+you can use the also generated script ``bin/sphinx-build`` to finetune
+parameters or, after running ``grokdocs2...`` change to the ``build/``
+directory and run for instance::
+
+ $ make html SPHINXOPTS="-E -a"
+
+to regenerate all docs in HTML format.
+
+
+How to tweak the layout/settings of the documentation toolchain
+---------------------------------------------------------------
+
+Beside passing options to Spinx (see above), the general settings of
+documentation generated by ``sphinx`` are settable in a file
+``conf.py`` which must be in the source root directory of your
+docs. Have a look at ``docs/conf.py`` for deeper insights.
+
+The structure of the HTML entry page is defined in
+``build/docindex.template``, which is a template for the Jinja
+templating engine used by Sphinx.
+
+The layout details are defined in ``docs/_static/grok.css``.
Added: groktoolkit/branches/jw-documentation-rearangement/doc/_build/Makefile
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/_build/Makefile (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/_build/Makefile 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,130 @@
+# Makefile for Sphinx documentation
+#
+
+# You can set these variables from the command line.
+SPHINXOPTS =
+SPHINXBUILD = /home/jw/projects/grokdocumentation/groktoolkit/bin/grokpy /home/jw/projects/grokdocumentation/groktoolkit/bin/sphinx-build
+PAPER =
+BUILDDIR = /home/jw/projects/grokdocumentation/groktoolkit/doc/_build
+
+# Internal variables.
+PAPEROPT_a4 = -D latex_paper_size=a4
+PAPEROPT_letter = -D latex_paper_size=letter
+ALLSPHINXOPTS = -d $(BUILDDIR)/doctrees $(PAPEROPT_$(PAPER)) $(SPHINXOPTS) /home/jw/projects/grokdocumentation/groktoolkit/doc
+
+.PHONY: help clean html dirhtml singlehtml pickle json htmlhelp qthelp devhelp epub latex latexpdf text man changes linkcheck doctest
+
+help:
+ @echo "Please use \`make <target>' where <target> is one of"
+ @echo " html to make standalone HTML files"
+ @echo " dirhtml to make HTML files named index.html in directories"
+ @echo " singlehtml to make a single large HTML file"
+ @echo " pickle to make pickle files"
+ @echo " json to make JSON files"
+ @echo " htmlhelp to make HTML files and a HTML help project"
+ @echo " qthelp to make HTML files and a qthelp project"
+ @echo " devhelp to make HTML files and a Devhelp project"
+ @echo " epub to make an epub"
+ @echo " latex to make LaTeX files, you can set PAPER=a4 or PAPER=letter"
+ @echo " latexpdf to make LaTeX files and run them through pdflatex"
+ @echo " text to make text files"
+ @echo " man to make manual pages"
+ @echo " changes to make an overview of all changed/added/deprecated items"
+ @echo " linkcheck to check all external links for integrity"
+ @echo " doctest to run all doctests embedded in the documentation (if enabled)"
+
+clean:
+ -rm -rf $(BUILDDIR)/*
+
+html:
+ $(SPHINXBUILD) -b html $(ALLSPHINXOPTS) $(BUILDDIR)/html
+ @echo
+ @echo "Build finished. The HTML pages are in $(BUILDDIR)/html."
+
+dirhtml:
+ $(SPHINXBUILD) -b dirhtml $(ALLSPHINXOPTS) $(BUILDDIR)/dirhtml
+ @echo
+ @echo "Build finished. The HTML pages are in $(BUILDDIR)/dirhtml."
+
+singlehtml:
+ $(SPHINXBUILD) -b singlehtml $(ALLSPHINXOPTS) $(BUILDDIR)/singlehtml
+ @echo
+ @echo "Build finished. The HTML page is in $(BUILDDIR)/singlehtml."
+
+pickle:
+ $(SPHINXBUILD) -b pickle $(ALLSPHINXOPTS) $(BUILDDIR)/pickle
+ @echo
+ @echo "Build finished; now you can process the pickle files."
+
+json:
+ $(SPHINXBUILD) -b json $(ALLSPHINXOPTS) $(BUILDDIR)/json
+ @echo
+ @echo "Build finished; now you can process the JSON files."
+
+htmlhelp:
+ $(SPHINXBUILD) -b htmlhelp $(ALLSPHINXOPTS) $(BUILDDIR)/htmlhelp
+ @echo
+ @echo "Build finished; now you can run HTML Help Workshop with the" \
+ ".hhp project file in $(BUILDDIR)/htmlhelp."
+
+qthelp:
+ $(SPHINXBUILD) -b qthelp $(ALLSPHINXOPTS) $(BUILDDIR)/qthelp
+ @echo
+ @echo "Build finished; now you can run "qcollectiongenerator" with the" \
+ ".qhcp project file in $(BUILDDIR)/qthelp, like this:"
+ @echo "# qcollectiongenerator $(BUILDDIR)/qthelp/docs.qhcp"
+ @echo "To view the help file:"
+ @echo "# assistant -collectionFile $(BUILDDIR)/qthelp/docs.qhc"
+
+devhelp:
+ $(SPHINXBUILD) -b devhelp $(ALLSPHINXOPTS) $(BUILDDIR)/devhelp
+ @echo
+ @echo "Build finished."
+ @echo "To view the help file:"
+ @echo "# mkdir -p $$HOME/.local/share/devhelp/docs"
+ @echo "# ln -s $(BUILDDIR)/devhelp $$HOME/.local/share/devhelp/docs"
+ @echo "# devhelp"
+
+epub:
+ $(SPHINXBUILD) -b epub $(ALLSPHINXOPTS) $(BUILDDIR)/epub
+ @echo
+ @echo "Build finished. The epub file is in $(BUILDDIR)/epub."
+
+latex:
+ $(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex
+ @echo
+ @echo "Build finished; the LaTeX files are in $(BUILDDIR)/latex."
+ @echo "Run \`make' in that directory to run these through (pdf)latex" \
+ "(use \`make latexpdf' here to do that automatically)."
+
+latexpdf:
+ $(SPHINXBUILD) -b latex $(ALLSPHINXOPTS) $(BUILDDIR)/latex
+ @echo "Running LaTeX files through pdflatex..."
+ make -C $(BUILDDIR)/latex all-pdf
+ @echo "pdflatex finished; the PDF files are in $(BUILDDIR)/latex."
+
+text:
+ $(SPHINXBUILD) -b text $(ALLSPHINXOPTS) $(BUILDDIR)/text
+ @echo
+ @echo "Build finished. The text files are in $(BUILDDIR)/text."
+
+man:
+ $(SPHINXBUILD) -b man $(ALLSPHINXOPTS) $(BUILDDIR)/man
+ @echo
+ @echo "Build finished. The manual pages are in $(BUILDDIR)/man."
+
+changes:
+ $(SPHINXBUILD) -b changes $(ALLSPHINXOPTS) $(BUILDDIR)/changes
+ @echo
+ @echo "The overview file is in $(BUILDDIR)/changes."
+
+linkcheck:
+ $(SPHINXBUILD) -b linkcheck $(ALLSPHINXOPTS) $(BUILDDIR)/linkcheck
+ @echo
+ @echo "Link check complete; look for any errors in the above output " \
+ "or in $(BUILDDIR)/linkcheck/output.txt."
+
+doctest:
+ $(SPHINXBUILD) -b doctest $(ALLSPHINXOPTS) $(BUILDDIR)/doctest
+ @echo "Testing of doctests in the sources finished, look at the " \
+ "results in $(BUILDDIR)/doctest/output.txt."
Added: groktoolkit/branches/jw-documentation-rearangement/doc/_build/make.bat
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/_build/make.bat (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/_build/make.bat 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,170 @@
+ at ECHO OFF
+
+REM Command file for Sphinx documentation
+
+if "%SPHINXBUILD%" == "" (
+ set SPHINXBUILD=sphinx-build
+)
+set BUILDDIR=/home/jw/projects/grokdocumentation/groktoolkit/doc/_build
+set ALLSPHINXOPTS=-d %BUILDDIR%/doctrees %SPHINXOPTS% /home/jw/projects/grokdocumentation/groktoolkit/doc
+if NOT "%PAPER%" == "" (
+ set ALLSPHINXOPTS=-D latex_paper_size=%PAPER% %ALLSPHINXOPTS%
+)
+
+if "%1" == "" goto help
+
+if "%1" == "help" (
+ :help
+ echo.Please use `make ^<target^>` where ^<target^> is one of
+ echo. html to make standalone HTML files
+ echo. dirhtml to make HTML files named index.html in directories
+ echo. singlehtml to make a single large HTML file
+ echo. pickle to make pickle files
+ echo. json to make JSON files
+ echo. htmlhelp to make HTML files and a HTML help project
+ echo. qthelp to make HTML files and a qthelp project
+ echo. devhelp to make HTML files and a Devhelp project
+ echo. epub to make an epub
+ echo. latex to make LaTeX files, you can set PAPER=a4 or PAPER=letter
+ echo. text to make text files
+ echo. man to make manual pages
+ echo. changes to make an overview over all changed/added/deprecated items
+ echo. linkcheck to check all external links for integrity
+ echo. doctest to run all doctests embedded in the documentation if enabled
+ goto end
+)
+
+if "%1" == "clean" (
+ for /d %%i in (%BUILDDIR%\*) do rmdir /q /s %%i
+ del /q /s %BUILDDIR%\*
+ goto end
+)
+
+if "%1" == "html" (
+ %SPHINXBUILD% -b html %ALLSPHINXOPTS% %BUILDDIR%/html
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished. The HTML pages are in %BUILDDIR%/html.
+ goto end
+)
+
+if "%1" == "dirhtml" (
+ %SPHINXBUILD% -b dirhtml %ALLSPHINXOPTS% %BUILDDIR%/dirhtml
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished. The HTML pages are in %BUILDDIR%/dirhtml.
+ goto end
+)
+
+if "%1" == "singlehtml" (
+ %SPHINXBUILD% -b singlehtml %ALLSPHINXOPTS% %BUILDDIR%/singlehtml
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished. The HTML pages are in %BUILDDIR%/singlehtml.
+ goto end
+)
+
+if "%1" == "pickle" (
+ %SPHINXBUILD% -b pickle %ALLSPHINXOPTS% %BUILDDIR%/pickle
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished; now you can process the pickle files.
+ goto end
+)
+
+if "%1" == "json" (
+ %SPHINXBUILD% -b json %ALLSPHINXOPTS% %BUILDDIR%/json
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished; now you can process the JSON files.
+ goto end
+)
+
+if "%1" == "htmlhelp" (
+ %SPHINXBUILD% -b htmlhelp %ALLSPHINXOPTS% %BUILDDIR%/htmlhelp
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished; now you can run HTML Help Workshop with the ^
+.hhp project file in %BUILDDIR%/htmlhelp.
+ goto end
+)
+
+if "%1" == "qthelp" (
+ %SPHINXBUILD% -b qthelp %ALLSPHINXOPTS% %BUILDDIR%/qthelp
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished; now you can run "qcollectiongenerator" with the ^
+.qhcp project file in %BUILDDIR%/qthelp, like this:
+ echo.^> qcollectiongenerator %BUILDDIR%\qthelp\docs.qhcp
+ echo.To view the help file:
+ echo.^> assistant -collectionFile %BUILDDIR%\qthelp\docs.ghc
+ goto end
+)
+
+if "%1" == "devhelp" (
+ %SPHINXBUILD% -b devhelp %ALLSPHINXOPTS% %BUILDDIR%/devhelp
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished.
+ goto end
+)
+
+if "%1" == "epub" (
+ %SPHINXBUILD% -b epub %ALLSPHINXOPTS% %BUILDDIR%/epub
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished. The epub file is in %BUILDDIR%/epub.
+ goto end
+)
+
+if "%1" == "latex" (
+ %SPHINXBUILD% -b latex %ALLSPHINXOPTS% %BUILDDIR%/latex
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished; the LaTeX files are in %BUILDDIR%/latex.
+ goto end
+)
+
+if "%1" == "text" (
+ %SPHINXBUILD% -b text %ALLSPHINXOPTS% %BUILDDIR%/text
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished. The text files are in %BUILDDIR%/text.
+ goto end
+)
+
+if "%1" == "man" (
+ %SPHINXBUILD% -b man %ALLSPHINXOPTS% %BUILDDIR%/man
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished. The manual pages are in %BUILDDIR%/man.
+ goto end
+)
+
+if "%1" == "changes" (
+ %SPHINXBUILD% -b changes %ALLSPHINXOPTS% %BUILDDIR%/changes
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.The overview file is in %BUILDDIR%/changes.
+ goto end
+)
+
+if "%1" == "linkcheck" (
+ %SPHINXBUILD% -b linkcheck %ALLSPHINXOPTS% %BUILDDIR%/linkcheck
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Link check complete; look for any errors in the above output ^
+or in %BUILDDIR%/linkcheck/output.txt.
+ goto end
+)
+
+if "%1" == "doctest" (
+ %SPHINXBUILD% -b doctest %ALLSPHINXOPTS% %BUILDDIR%/doctest
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Testing of doctests in the sources finished, look at the ^
+results in %BUILDDIR%/doctest/output.txt.
+ goto end
+)
+
+:end
Added: groktoolkit/branches/jw-documentation-rearangement/doc/_static/default.css
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/_static/default.css (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/_static/default.css 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,796 @@
+/**
+ * Sphinx Doc Design
+ */
+
+body {
+ font-family: sans-serif;
+ font-size: 100%;
+ background-color: #ff303d;
+ color: #000;
+ margin: 0;
+ padding: 0;
+}
+
+/* :::: LAYOUT :::: */
+
+div.document {
+ background-color: #1c4e63;
+}
+
+div.documentwrapper {
+ float: left;
+ width: 100%;
+}
+
+div.bodywrapper {
+ margin: 0 0 0 230px;
+}
+
+div.body {
+ background-color: white;
+ padding: 0 20px 30px 20px;
+}
+
+div.sidebarwrapper {
+ padding: 10px 5px 0 10px;
+}
+
+div.sidebar {
+ float: left;
+ width: 230px;
+ margin-left: -100%;
+ font-size: 90%;
+}
+
+div.clearer {
+ clear: both;
+}
+
+div.footer {
+ color: #fff;
+ width: 100%;
+ padding: 9px 0 9px 0;
+ text-align: center;
+ font-size: 75%;
+}
+
+div.footer a {
+ color: #fff;
+ text-decoration: underline;
+}
+
+div.related {
+ background-color: #133f52;
+ color: #fff;
+ width: 100%;
+ height: 30px;
+ line-height: 30px;
+ font-size: 90%;
+}
+
+div.related h3 {
+ display: none;
+}
+
+div.related ul {
+ margin: 0;
+ padding: 0 0 0 10px;
+ list-style: none;
+}
+
+div.related li {
+ display: inline;
+}
+
+div.related li.right {
+ float: right;
+ margin-right: 5px;
+}
+
+div.related a {
+ color: white;
+}
+
+/* ::: TOC :::: */
+div.sidebar h3 {
+ font-family: 'Trebuchet MS', sans-serif;
+ color: white;
+ font-size: 1.4em;
+ font-weight: normal;
+ margin: 0;
+ padding: 0;
+}
+
+div.sidebar h4 {
+ font-family: 'Trebuchet MS', sans-serif;
+ color: white;
+ font-size: 1.3em;
+ font-weight: normal;
+ margin: 5px 0 0 0;
+ padding: 0;
+}
+
+div.sidebar p {
+ color: white;
+}
+
+div.sidebar p.topless {
+ margin: 5px 10px 10px 10px;
+}
+
+div.sidebar ul {
+ margin: 10px;
+ padding: 0;
+ list-style: none;
+ color: white;
+}
+
+div.sidebar ul ul,
+div.sidebar ul.want-points {
+ margin-left: 20px;
+ list-style: square;
+}
+
+div.sidebar ul ul {
+ margin-top: 0;
+ margin-bottom: 0;
+}
+
+div.sidebar a {
+ color: #98dbcc;
+}
+
+div.sidebar form {
+ margin-top: 10px;
+}
+
+div.sidebar input {
+ border: 1px solid #98dbcc;
+ font-family: sans-serif;
+ font-size: 1em;
+}
+
+/* :::: MODULE CLOUD :::: */
+div.modulecloud {
+ margin: -5px 10px 5px 10px;
+ padding: 10px;
+ line-height: 160%;
+ border: 1px solid #cbe7e5;
+ background-color: #f2fbfd;
+}
+
+div.modulecloud a {
+ padding: 0 5px 0 5px;
+}
+
+/* :::: SEARCH :::: */
+ul.search {
+ margin: 10px 0 0 20px;
+ padding: 0;
+}
+
+ul.search li {
+ padding: 5px 0 5px 20px;
+ background-image: url(file.png);
+ background-repeat: no-repeat;
+ background-position: 0 7px;
+}
+
+ul.search li a {
+ font-weight: bold;
+}
+
+ul.search li div.context {
+ color: #888;
+ margin: 2px 0 0 30px;
+ text-align: left;
+}
+
+ul.keywordmatches li.goodmatch a {
+ font-weight: bold;
+}
+
+/* :::: COMMON FORM STYLES :::: */
+
+div.actions {
+ padding: 5px 10px 5px 10px;
+ border-top: 1px solid #cbe7e5;
+ border-bottom: 1px solid #cbe7e5;
+ background-color: #e0f6f4;
+}
+
+form dl {
+ color: #333;
+}
+
+form dt {
+ clear: both;
+ float: left;
+ min-width: 110px;
+ margin-right: 10px;
+ padding-top: 2px;
+}
+
+input#homepage {
+ display: none;
+}
+
+div.error {
+ margin: 5px 20px 0 0;
+ padding: 5px;
+ border: 1px solid #d00;
+ font-weight: bold;
+}
+
+/* :::: INLINE COMMENTS :::: */
+
+div.inlinecomments {
+ position: absolute;
+ right: 20px;
+}
+
+div.inlinecomments a.bubble {
+ display: block;
+ float: right;
+ background-image: url(style/comment.png);
+ background-repeat: no-repeat;
+ width: 25px;
+ height: 25px;
+ text-align: center;
+ padding-top: 3px;
+ font-size: 0.9em;
+ line-height: 14px;
+ font-weight: bold;
+ color: black;
+}
+
+div.inlinecomments a.bubble span {
+ display: none;
+}
+
+div.inlinecomments a.emptybubble {
+ background-image: url(style/nocomment.png);
+}
+
+div.inlinecomments a.bubble:hover {
+ background-image: url(style/hovercomment.png);
+ text-decoration: none;
+ color: #3ca0a4;
+}
+
+div.inlinecomments div.comments {
+ float: right;
+ margin: 25px 5px 0 0;
+ max-width: 50em;
+ min-width: 30em;
+ border: 1px solid #2eabb0;
+ background-color: #f2fbfd;
+ z-index: 150;
+}
+
+div#comments {
+ border: 1px solid #2eabb0;
+ margin-top: 20px;
+}
+
+div#comments div.nocomments {
+ padding: 10px;
+ font-weight: bold;
+}
+
+div.inlinecomments div.comments h3,
+div#comments h3 {
+ margin: 0;
+ padding: 0;
+ background-color: #2eabb0;
+ color: white;
+ border: none;
+ padding: 3px;
+}
+
+div.inlinecomments div.comments div.actions {
+ padding: 4px;
+ margin: 0;
+ border-top: none;
+}
+
+div#comments div.comment {
+ margin: 10px;
+ border: 1px solid #2eabb0;
+}
+
+div.inlinecomments div.comment h4,
+div.commentwindow div.comment h4,
+div#comments div.comment h4 {
+ margin: 10px 0 0 0;
+ background-color: #2eabb0;
+ color: white;
+ border: none;
+ padding: 1px 4px 1px 4px;
+}
+
+div#comments div.comment h4 {
+ margin: 0;
+}
+
+div#comments div.comment h4 a {
+ color: #d5f4f4;
+}
+
+div.inlinecomments div.comment div.text,
+div.commentwindow div.comment div.text,
+div#comments div.comment div.text {
+ margin: -5px 0 -5px 0;
+ padding: 0 10px 0 10px;
+}
+
+div.inlinecomments div.comment div.meta,
+div.commentwindow div.comment div.meta,
+div#comments div.comment div.meta {
+ text-align: right;
+ padding: 2px 10px 2px 0;
+ font-size: 95%;
+ color: #538893;
+ border-top: 1px solid #cbe7e5;
+ background-color: #e0f6f4;
+}
+
+div.commentwindow {
+ position: absolute;
+ width: 500px;
+ border: 1px solid #cbe7e5;
+ background-color: #f2fbfd;
+ display: none;
+ z-index: 130;
+}
+
+div.commentwindow h3 {
+ margin: 0;
+ background-color: #2eabb0;
+ color: white;
+ border: none;
+ padding: 5px;
+ font-size: 1.5em;
+ cursor: pointer;
+}
+
+div.commentwindow div.actions {
+ margin: 10px -10px 0 -10px;
+ padding: 4px 10px 4px 10px;
+ color: #538893;
+}
+
+div.commentwindow div.actions input {
+ border: 1px solid #2eabb0;
+ background-color: white;
+ color: #135355;
+ cursor: pointer;
+}
+
+div.commentwindow div.form {
+ padding: 0 10px 0 10px;
+}
+
+div.commentwindow div.form input,
+div.commentwindow div.form textarea {
+ border: 1px solid #3c9ea2;
+ background-color: white;
+ color: black;
+}
+
+div.commentwindow div.error {
+ margin: 10px 5px 10px 5px;
+ background-color: #fbe5dc;
+ display: none;
+}
+
+div.commentwindow div.form textarea {
+ width: 99%;
+}
+
+div.commentwindow div.preview {
+ margin: 10px 0 10px 0;
+ background-color: #70d0d4;
+ padding: 0 1px 1px 25px;
+}
+
+div.commentwindow div.preview h4 {
+ margin: 0 0 -5px -20px;
+ padding: 4px 0 0 4px;
+ color: white;
+ font-size: 1.3em;
+}
+
+div.commentwindow div.preview div.comment {
+ background-color: #f2fbfd;
+}
+
+div.commentwindow div.preview div.comment h4 {
+ margin: 10px 0 0 0!important;
+ padding: 1px 4px 1px 4px!important;
+ font-size: 1.2em;
+}
+
+/* :::: SUGGEST CHANGES :::: */
+div#suggest-changes-box input, div#suggest-changes-box textarea {
+ border: 1px solid #ccc;
+ background-color: white;
+ color: black;
+}
+
+div#suggest-changes-box textarea {
+ width: 99%;
+ height: 400px;
+}
+
+
+/* :::: PREVIEW :::: */
+div.preview {
+ background-image: url(style/preview.png);
+ padding: 0 20px 20px 20px;
+ margin-bottom: 30px;
+}
+
+
+/* :::: INDEX PAGE :::: */
+
+table.contentstable {
+ width: 90%;
+}
+
+table.contentstable p.biglink {
+ line-height: 150%;
+}
+
+a.biglink {
+ font-size: 1.3em;
+}
+
+span.linkdescr {
+ font-style: italic;
+ padding-top: 5px;
+ font-size: 90%;
+}
+
+/* :::: INDEX STYLES :::: */
+
+table.indextable td {
+ text-align: left;
+ vertical-align: top;
+}
+
+table.indextable dl, table.indextable dd {
+ margin-top: 0;
+ margin-bottom: 0;
+}
+
+table.indextable tr.pcap {
+ height: 10px;
+}
+
+table.indextable tr.cap {
+ margin-top: 10px;
+ background-color: #f2f2f2;
+}
+
+img.toggler {
+ margin-right: 3px;
+ margin-top: 3px;
+ cursor: pointer;
+}
+
+form.pfform {
+ margin: 10px 0 20px 0;
+}
+
+/* :::: GLOBAL STYLES :::: */
+
+.docwarning {
+ background-color: #ffe4e4;
+ padding: 10px;
+ margin: 0 -20px 0 -20px;
+ border-bottom: 1px solid #f66;
+}
+
+p.subhead {
+ font-weight: bold;
+ margin-top: 20px;
+}
+
+a {
+ color: #355f7c;
+ text-decoration: none;
+}
+
+a:hover {
+ text-decoration: underline;
+}
+
+div.body h1,
+div.body h2,
+div.body h3,
+div.body h4,
+div.body h5,
+div.body h6 {
+ font-family: 'Trebuchet MS', sans-serif;
+ background-color: #f2f2f2;
+ font-weight: normal;
+ color: #20435c;
+ border-bottom: 1px solid #ccc;
+ margin: 20px -20px 10px -20px;
+ padding: 3px 0 3px 10px;
+}
+
+div.body h1 { margin-top: 0; font-size: 200%; }
+div.body h2 { font-size: 160%; }
+div.body h3 { font-size: 140%; }
+div.body h4 { font-size: 120%; }
+div.body h5 { font-size: 110%; }
+div.body h6 { font-size: 100%; }
+
+a.headerlink {
+ color: #c60f0f;
+ font-size: 0.8em;
+ padding: 0 4px 0 4px;
+ text-decoration: none;
+ visibility: hidden;
+}
+
+h1:hover > a.headerlink,
+h2:hover > a.headerlink,
+h3:hover > a.headerlink,
+h4:hover > a.headerlink,
+h5:hover > a.headerlink,
+h6:hover > a.headerlink,
+dt:hover > a.headerlink {
+ visibility: visible;
+}
+
+a.headerlink:hover {
+ background-color: #c60f0f;
+ color: white;
+}
+
+div.body p, div.body dd, div.body li {
+ text-align: justify;
+ line-height: 130%;
+}
+
+div.body td {
+ text-align: left;
+}
+
+ul.fakelist {
+ list-style: none;
+ margin: 10px 0 10px 20px;
+ padding: 0;
+}
+
+/* "Footnotes" heading */
+p.rubric {
+ margin-top: 30px;
+ font-weight: bold;
+}
+
+/* "Topics" */
+
+div.topic {
+ background-color: #eee;
+ border: 1px solid #ccc;
+ padding: 0 7px 0 7px;
+ margin: 10px 0 10px 0;
+}
+
+p.topic-title {
+ font-size: 1.1em;
+ font-weight: bold;
+ margin-top: 10px;
+}
+
+/* Admonitions */
+
+div.admonition {
+ margin-top: 10px;
+ margin-bottom: 10px;
+ padding: 7px;
+}
+
+div.admonition dt {
+ font-weight: bold;
+}
+
+div.admonition dl {
+ margin-bottom: 0;
+}
+
+div.admonition p {
+ display: inline;
+}
+
+div.seealso {
+ background-color: #ffc;
+ border: 1px solid #ff6;
+}
+
+div.warning {
+ background-color: #ffe4e4;
+ border: 1px solid #f66;
+}
+
+div.note {
+ background-color: #eee;
+ border: 1px solid #ccc;
+}
+
+p.admonition-title {
+ margin: 0px 10px 5px 0px;
+ font-weight: bold;
+ display: inline;
+}
+
+p.admonition-title:after {
+ content: ":";
+}
+
+div.body p.centered {
+ text-align: center;
+ margin-top: 25px;
+}
+
+table.docutils {
+ border: 0;
+}
+
+table.docutils td, table.docutils th {
+ padding: 1px 8px 1px 0;
+ border-top: 0;
+ border-left: 0;
+ border-right: 0;
+ border-bottom: 1px solid #aaa;
+}
+
+table.field-list td, table.field-list th {
+ border: 0 !important;
+}
+
+table.footnote td, table.footnote th {
+ border: 0 !important;
+}
+
+dl {
+ margin-bottom: 15px;
+ clear: both;
+}
+
+dd p {
+ margin-top: 0px;
+}
+
+dd ul, dd table {
+ margin-bottom: 10px;
+}
+
+dd {
+ margin-top: 3px;
+ margin-bottom: 10px;
+ margin-left: 30px;
+}
+
+.refcount {
+ color: #060;
+}
+
+dt:target,
+.highlight {
+ background-color: #fbe54e;
+}
+
+dl.glossary dt {
+ font-weight: bold;
+ font-size: 1.1em;
+}
+
+th {
+ text-align: left;
+ padding-right: 5px;
+}
+
+pre {
+ padding: 5px;
+ background-color: #efc;
+ color: #333;
+ border: 1px solid #ac9;
+ border-left: none;
+ border-right: none;
+}
+
+tt {
+ background-color: #ecf0f3;
+ padding: 0 1px 0 1px;
+ font-size: 0.95em;
+}
+
+tt.descname {
+ background-color: transparent;
+ font-weight: bold;
+ font-size: 1.2em;
+}
+
+tt.descclassname {
+ background-color: transparent;
+}
+
+tt.xref, a tt {
+ background-color: transparent;
+ font-weight: bold;
+}
+
+.footnote:target { background-color: #ffa }
+
+h1 tt, h2 tt, h3 tt, h4 tt, h5 tt, h6 tt {
+ background-color: transparent;
+}
+
+.optional {
+ font-size: 1.3em;
+}
+
+.versionmodified {
+ font-style: italic;
+}
+
+form.comment {
+ margin: 0;
+ padding: 10px 30px 10px 30px;
+ background-color: #eee;
+}
+
+form.comment h3 {
+ background-color: #326591;
+ color: white;
+ margin: -10px -30px 10px -30px;
+ padding: 5px;
+ font-size: 1.4em;
+}
+
+form.comment input,
+form.comment textarea {
+ border: 1px solid #ccc;
+ padding: 2px;
+ font-family: sans-serif;
+ font-size: 100%;
+}
+
+form.comment input[type="text"] {
+ width: 240px;
+}
+
+form.comment textarea {
+ width: 100%;
+ height: 200px;
+ margin-bottom: 10px;
+}
+
+.system-message {
+ background-color: #fda;
+ padding: 5px;
+ border: 3px solid red;
+}
+
+/* :::: PRINT :::: */
+ at media print {
+ div.document,
+ div.documentwrapper,
+ div.bodywrapper {
+ margin: 0;
+ width : 100%;
+ }
+
+ div.sidebar,
+ div.related,
+ div.footer,
+ div#comments div.new-comment-box,
+ #top-link {
+ display: none;
+ }
+}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/_static/grok.css
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/_static/grok.css (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/_static/grok.css 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,940 @@
+/*
+ * Grok Official Documentation CSS
+ *
+ * (clean me up! improve me! make me look nicer!)
+ *
+ */
+
+body {
+ font-family: sans-serif;
+ font-size: 100%;
+ background-color: #11303d;
+ background-color: #dddddd;
+ background: #cfcccc url("top_bg.jpg") repeat-x;
+ color: #000;
+ margin: 0;
+ padding: 0;
+}
+
+td {
+ vertical-align: top;
+}
+
+/* :::: LAYOUT :::: */
+
+div.document {
+ background-color: #dddddd;
+}
+
+div.documentwrapper {
+ float: left;
+ width: 100%;
+}
+
+div.bodywrapper {
+ margin: 0 0 0 250px;
+}
+
+div.body {
+ background-color: white;
+ padding: 1.5em;
+ border-left: 1px solid #999;
+
+}
+
+div.clearer {
+ clear: both;
+}
+
+div.footer {
+ color: #740;
+ width: 100%;
+ padding: 9px 0 9px 0;
+ text-align: center;
+ font-size: 75%;
+}
+
+div.footer a {
+ color: #740;
+ text-decoration: underline;
+}
+
+div.header {
+ background: #999999 url("top_bg.jpg") repeat-x;
+ padding: 0.5em 1em 0 1em;
+}
+
+div.header a{
+ color: #520;
+ padding: 0.5em;
+ text-decoration: none;
+}
+
+div.globalnav {
+ color: #740;
+ border-bottom: 1px solid #aaa;
+ width: 100%;
+ font-size: small;
+}
+
+div.globalnav h3 {
+ display: none;
+}
+
+#globalnavwrapper {
+ padding: 2px;
+ margin: 0.5em 0 0 0;
+}
+
+div.globalnav ul {
+ margin: 0 0 0 0;
+ padding: 0;
+ list-style: none;
+}
+
+div.globalnav li {
+ display: inline;
+ padding: 2px 0.5em;
+ margin: 0 1px;
+ background-color: #eee;
+ border: 1px solid #999;
+}
+
+div.globalnav a {
+ color: #436976;
+ text-decoration: none;
+}
+
+div.globalnav li:hover {
+ background-color: white;
+}
+
+/* ::: Table of Contents :::: */
+
+.document > div.sidebarwrapper {
+ padding: 10px 5px 0 10px;
+}
+
+.sphinxsidebar {
+ float: left;
+ width: 250px;
+ margin-left: -100%;
+ font-size: small;
+ color: #333333;
+ padding: 8px;
+}
+
+.sphinxsidebar a {
+ color: #436976;
+}
+
+.sphinxsidebar h3 {
+ font-family: 'Trebuchet MS', sans-serif;
+ font-size: 1.4em;
+ font-weight: normal;
+ margin: 0;
+ padding: 0;
+}
+
+.sphinxsidebar h4 {
+ font-family: 'Trebuchet MS', sans-serif;
+ font-size: 1.3em;
+ font-weight: normal;
+ margin: 5px 0 0 0;
+ padding: 0;
+}
+
+.sphinxsidebar p.topless {
+ margin: 5px 10px 10px 10px;
+}
+
+.sphinxsidebar ul {
+ margin: 10px;
+ padding: 0;
+ list-style: none;
+ color: #c90;
+}
+
+.sphinxsidebar ul ul,
+.sphinxsidebar ul.want-points {
+ margin-left: 20px;
+ list-style: square;
+ color: #436976;
+}
+
+.sphinxsidebar ul ul {
+ margin-top: 0;
+ margin-bottom: 0;
+}
+
+.sphinxsidebar ul li {
+ margin: 0.25em 0 0.5em 0;
+}
+
+.sphinxsidebar form {
+ margin-top: 10px;
+}
+
+.sphinxsidebar input {
+ border: 1px solid #555555;
+ font-family: sans-serif;
+ font-size: 1em;
+}
+
+/* Grok Tutorial style sidebar */
+.section div.sidebar {
+ margin: 1em 2em;
+ padding: 0.5em 2em 1em 100px;
+ background-color: #fafaf8;
+ border: 1px solid #aaa;
+ border-top-width: 6px;
+ background-image: url(grok_club.gif);
+ background-repeat: no-repeat;
+}
+
+.section .sidebar-title {
+ font-weight: bold;
+ font-size: 110%;
+}
+
+/* :::: MODULE CLOUD :::: */
+div.modulecloud {
+ margin: -5px 10px 5px 10px;
+ padding: 10px;
+ line-height: 160%;
+ border: 1px solid #cbe7e5;
+ background-color: #f2fbfd;
+}
+
+div.modulecloud a {
+ padding: 0 5px 0 5px;
+}
+
+/* :::: SEARCH :::: */
+ul.search {
+ margin: 10px 0 0 20px;
+ padding: 0;
+}
+
+ul.search li {
+ padding: 5px 0 5px 20px;
+ background-image: url(file.png);
+ background-repeat: no-repeat;
+ background-position: 0 7px;
+}
+
+ul.search li a {
+ font-weight: bold;
+}
+
+ul.search li div.context {
+ color: #888;
+ margin: 2px 0 0 30px;
+ text-align: left;
+}
+
+ul.keywordmatches li.goodmatch a {
+ font-weight: bold;
+}
+
+/* :::: COMMON FORM STYLES :::: */
+
+div.actions {
+ padding: 5px 10px 5px 10px;
+ border-top: 1px solid #cbe7e5;
+ border-bottom: 1px solid #cbe7e5;
+ background-color: #e0f6f4;
+}
+
+form dl {
+ color: #333;
+}
+
+form dt {
+ clear: both;
+ float: left;
+ min-width: 110px;
+ margin-right: 10px;
+ padding-top: 2px;
+}
+
+input#homepage {
+ display: none;
+}
+
+div.error {
+ margin: 5px 20px 0 0;
+ padding: 5px;
+ border: 1px solid #d00;
+ font-weight: bold;
+}
+
+/* :::: INLINE COMMENTS :::: */
+
+div.inlinecomments {
+ position: absolute;
+ right: 20px;
+}
+
+div.inlinecomments a.bubble {
+ display: block;
+ float: right;
+ background-image: url(style/comment.png);
+ background-repeat: no-repeat;
+ width: 25px;
+ height: 25px;
+ text-align: center;
+ padding-top: 3px;
+ font-size: 0.9em;
+ line-height: 14px;
+ font-weight: bold;
+ color: black;
+}
+
+div.inlinecomments a.bubble span {
+ display: none;
+}
+
+div.inlinecomments a.emptybubble {
+ background-image: url(style/nocomment.png);
+}
+
+div.inlinecomments a.bubble:hover {
+ background-image: url(style/hovercomment.png);
+ text-decoration: none;
+ color: #3ca0a4;
+}
+
+div.inlinecomments div.comments {
+ float: right;
+ margin: 25px 5px 0 0;
+ max-width: 50em;
+ min-width: 30em;
+ border: 1px solid #2eabb0;
+ background-color: #f2fbfd;
+ z-index: 150;
+}
+
+div#comments {
+ border: 1px solid #2eabb0;
+ margin-top: 20px;
+}
+
+div#comments div.nocomments {
+ padding: 10px;
+ font-weight: bold;
+}
+
+div.inlinecomments div.comments h3,
+div#comments h3 {
+ margin: 0;
+ padding: 0;
+ background-color: #2eabb0;
+ color: white;
+ border: none;
+ padding: 3px;
+}
+
+div.inlinecomments div.comments div.actions {
+ padding: 4px;
+ margin: 0;
+ border-top: none;
+}
+
+div#comments div.comment {
+ margin: 10px;
+ border: 1px solid #2eabb0;
+}
+
+div.inlinecomments div.comment h4,
+div.commentwindow div.comment h4,
+div#comments div.comment h4 {
+ margin: 10px 0 0 0;
+ background-color: #2eabb0;
+ color: white;
+ border: none;
+ padding: 1px 4px 1px 4px;
+}
+
+div#comments div.comment h4 {
+ margin: 0;
+}
+
+div#comments div.comment h4 a {
+ color: #d5f4f4;
+}
+
+div.inlinecomments div.comment div.text,
+div.commentwindow div.comment div.text,
+div#comments div.comment div.text {
+ margin: -5px 0 -5px 0;
+ padding: 0 10px 0 10px;
+}
+
+div.inlinecomments div.comment div.meta,
+div.commentwindow div.comment div.meta,
+div#comments div.comment div.meta {
+ text-align: right;
+ padding: 2px 10px 2px 0;
+ font-size: 95%;
+ color: #538893;
+ border-top: 1px solid #cbe7e5;
+ background-color: #e0f6f4;
+}
+
+div.commentwindow {
+ position: absolute;
+ width: 500px;
+ border: 1px solid #cbe7e5;
+ background-color: #f2fbfd;
+ display: none;
+ z-index: 130;
+}
+
+div.commentwindow h3 {
+ margin: 0;
+ background-color: #2eabb0;
+ color: white;
+ border: none;
+ padding: 5px;
+ font-size: 1.5em;
+ cursor: pointer;
+}
+
+div.commentwindow div.actions {
+ margin: 10px -10px 0 -10px;
+ padding: 4px 10px 4px 10px;
+ color: #538893;
+}
+
+div.commentwindow div.actions input {
+ border: 1px solid #2eabb0;
+ background-color: white;
+ color: #135355;
+ cursor: pointer;
+}
+
+div.commentwindow div.form {
+ padding: 0 10px 0 10px;
+}
+
+div.commentwindow div.form input,
+div.commentwindow div.form textarea {
+ border: 1px solid #3c9ea2;
+ background-color: white;
+ color: black;
+}
+
+div.commentwindow div.error {
+ margin: 10px 5px 10px 5px;
+ background-color: #fbe5dc;
+ display: none;
+}
+
+div.commentwindow div.form textarea {
+ width: 99%;
+}
+
+div.commentwindow div.preview {
+ margin: 10px 0 10px 0;
+ background-color: #70d0d4;
+ padding: 0 1px 1px 25px;
+}
+
+div.commentwindow div.preview h4 {
+ margin: 0 0 -5px -20px;
+ padding: 4px 0 0 4px;
+ color: white;
+ font-size: 1.3em;
+}
+
+div.commentwindow div.preview div.comment {
+ background-color: #f2fbfd;
+}
+
+div.commentwindow div.preview div.comment h4 {
+ margin: 10px 0 0 0!important;
+ padding: 1px 4px 1px 4px!important;
+ font-size: 1.2em;
+}
+
+/* :::: SUGGEST CHANGES :::: */
+div#suggest-changes-box input, div#suggest-changes-box textarea {
+ border: 1px solid #dddddd;
+ background-color: white;
+ color: black;
+}
+
+div#suggest-changes-box textarea {
+ width: 99%;
+ height: 400px;
+}
+
+
+/* :::: PREVIEW :::: */
+div.preview {
+ background-image: url(style/preview.png);
+ padding: 0 20px 20px 20px;
+ margin-bottom: 30px;
+}
+
+
+/* :::: INDEX PAGE :::: */
+
+table.contentstable {
+ width: 90%;
+ margin-top: -1em;
+ margin-left: 2em;
+}
+
+table.contentstable p.biglink {
+ line-height: 150%;
+}
+
+a.biglink {
+ font-size: 1.3em;
+}
+
+span.linkdescr {
+ color: #555;
+ padding-top: 0.25em;
+ font-size: 90%;
+}
+
+/* :::: INDEX STYLES :::: */
+
+table.indextable td {
+ text-align: left;
+ vertical-align: top;
+}
+
+table.indextable dl, table.indextable dd {
+ margin-top: 0;
+ margin-bottom: 0;
+}
+
+table.indextable tr.pcap {
+ height: 10px;
+}
+
+table.indextable tr.cap {
+ margin-top: 10px;
+ background-color: #f2f2f2;
+}
+
+img.toggler {
+ margin-right: 3px;
+ margin-top: 3px;
+ cursor: pointer;
+}
+
+form.pfform {
+ margin: 10px 0 20px 0;
+}
+
+/* :::: GLOBAL STYLES :::: */
+
+.docwarning {
+ background-color: #ffe4e4;
+ padding: 10px;
+ margin: 0 -20px 0 -20px;
+ border-bottom: 1px solid #f66;
+}
+
+p.subhead {
+ font-weight: bold;
+ margin-top: 20px;
+}
+
+a {
+ color: #355f7c;
+ color: #a70;
+ text-decoration: none;
+}
+
+a:hover {
+ text-decoration: underline;
+}
+
+div.body h1,
+div.body h2,
+div.body h3,
+div.body h4,
+div.body h5,
+div.body h6 {
+ font-family: 'Trebuchet MS', sans-serif;
+ font-weight: normal;
+ color: #c90;
+ border-bottom: 1px solid #ddd;
+ margin: 1em 0 0.5em 0;
+ padding: 3px 1em 3px 0.25em;
+}
+
+div.body h1 { margin-top: 0; background-color: #f2f2f2; font-size: 200%; }
+div.body h2 { font-size: 160%; background-color: #f2f2f2; }
+div.body h3 { font-size: 140%; border-bottom-width: 0; padding-left: 0; }
+div.body h4 { font-size: 120%; border-bottom-width: 0; padding-left: 0; }
+div.body h5 { font-size: 110%; border-bottom-width: 0; padding-left: 0; }
+div.body h6 { font-size: 100%; border-bottom-width: 0; padding-left: 0; }
+
+a.headerlink {
+ color: #dddddd;
+ font-size: 0.8em;
+ padding: 0 4px 0 4px;
+ text-decoration: none;
+ visibility: hidden;
+}
+
+h1:hover > a.headerlink,
+h2:hover > a.headerlink,
+h3:hover > a.headerlink,
+h4:hover > a.headerlink,
+h5:hover > a.headerlink,
+h6:hover > a.headerlink,
+dt:hover > a.headerlink {
+ visibility: visible;
+}
+
+a.headerlink:hover {
+ color: #555555;
+}
+
+div.body p, div.body dd, div.body li {
+ line-height: 150%;
+}
+
+div.body td {
+ text-align: left;
+}
+
+ul.fakelist {
+ list-style: none;
+ margin: 10px 0 10px 20px;
+ padding: 0;
+}
+
+/* "Footnotes" heading */
+p.rubric {
+ margin-top: 30px;
+ font-weight: bold;
+}
+
+/* "Topics" */
+
+div.topic {
+ background-color: #eeeeee;
+ border: 1px solid #dddddd;
+ padding: 0 7px 0 7px;
+ margin: 10px 0 10px 0;
+}
+
+p.topic-title {
+ font-size: 1.1em;
+ font-weight: bold;
+ margin-top: 10px;
+}
+
+.topic ul {
+ margin: 0 0 0.5em 1.5em;
+ padding: 0;
+}
+
+.section blockquote {
+ margin: 0em;
+ padding: 0.5em;
+}
+
+.simple li {
+ list-style-type: circle;
+}
+
+/* Admonitions */
+
+div.admonition {
+ margin: 0.5em 0;
+ padding: 0.5em;
+}
+
+div.admonition dt {
+ font-weight: bold;
+}
+
+div.admonition dl {
+ margin-bottom: 0;
+}
+
+div.admonition p {
+ display: inline;
+}
+
+div.seealso {
+ padding: 0;
+ background-color: #ffc;
+ border: 1px solid #ff6;
+}
+
+div.seealso .first {
+ background-color: #ffa;
+ padding: 0.25em 0.5em;
+ display: block;
+ float: left;
+ margin: 0 0.5em 0 0;
+}
+
+div.seealso .last {
+ padding: 0.25em 0;
+ display: block;
+ margin: 0;
+}
+
+div.warning {
+ background-color: #ffe4e4;
+ border: 1px solid #f66;
+}
+
+div.note {
+ background-color: #eeeeee;
+ border: 1px solid #dddddd;
+}
+
+
+/* only applies to the class name */
+dl.class {
+ color: #555555;
+ background: #fafaf8;
+ padding: 0 1em 1em 1em;
+ border: 1px solid #eed;
+}
+
+dl.class dt {
+ margin: 0;
+ padding: 0;
+}
+
+dl.class > dt {
+ padding: 0.5em;
+ margin: 0 -1em;
+ background-color: #eed;
+}
+
+dl.class dd {
+ color: black;
+ font-size: 100%;
+ padding: 0;
+ margin: 0.5em 1em 0.5em 1em;
+}
+
+dl.class > dd {
+ margin: 0.5em 0 0 0;
+ padding: 0;
+}
+
+/* only applies to functions */
+dl.function {
+ color: #555555;
+ background: #fafaf8;
+ padding: 0 1em 1em 1em;
+ border: 1px solid #eed;
+}
+
+dl.function dt {
+ margin: 0;
+ padding: 0;
+}
+
+dl.function > dt {
+ padding: 0.5em;
+ margin: 0 -1em;
+ background-color: #eed;
+}
+
+dl.function dd {
+ color: black;
+ font-size: 100%;
+ padding: 0;
+ margin: 0.5em 1em 0.5em 1em;
+}
+
+dl.function > dd {
+ margin: 0.5em 0 0 0;
+ padding: 0;
+}
+
+p.admonition-title {
+ margin: 0 0.5em 0.5em 0;
+ display: inline;
+}
+
+p.admonition-title:after {
+ content: ":";
+}
+
+div.body p.centered {
+ text-align: center;
+ margin-top: 25px;
+}
+
+table.docutils {
+ border: 0;
+}
+
+table.docutils td, table.docutils th {
+ padding: 1px 8px 1px 0;
+ border: 0;
+}
+
+table.field-list td, table.field-list th {
+ border: 0 !important;
+}
+
+table.footnote td, table.footnote th {
+ border: 0 !important;
+}
+
+dl {
+ margin-bottom: 15px;
+ clear: both;
+}
+
+dd p {
+ margin-top: 0px;
+}
+
+dd ul, dd table {
+ margin-bottom: 10px;
+}
+
+dd {
+ margin-top: 3px;
+ margin-bottom: 10px;
+ margin-left: 30px;
+}
+
+.refcount {
+ color: #060;
+}
+
+dt:target,
+.highlight {
+ background-color: #fbe54e;
+}
+
+dl.glossary dt {
+ font-weight: bold;
+ font-size: 1.1em;
+}
+
+th {
+ text-align: left;
+ padding-right: 5px;
+}
+
+pre {
+ padding: 1em;
+ background-color: #fafafa;
+ color: #333333;
+ border: 2px dotted #eee;
+ border-left: none;
+ border-right: none;
+ font-size: medium;
+ line-height: 150%;
+}
+
+tt {
+ background-color: #ecf0f3;
+ padding: 0;
+}
+
+tt.descname {
+ background-color: transparent;
+ font-weight: bold;
+ font-size: 1.2em;
+}
+
+tt.descclassname {
+ background-color: transparent;
+ font-weight: bold;
+ font-size: 1.2em;
+ /* a little hand kerning for grok.Whatever typography */
+ margin-right: -1px;
+}
+
+tt.xref, a tt {
+ background-color: transparent;
+ font-weight: bold;
+}
+
+.footnote:target { background-color: #ffa }
+
+h1 tt, h2 tt, h3 tt, h4 tt, h5 tt, h6 tt {
+ background-color: transparent;
+}
+
+.optional {
+ font-size: 1.3em;
+}
+
+.versionmodified {
+ font-style: italic;
+}
+
+form.comment {
+ margin: 0;
+ padding: 10px 30px 10px 30px;
+ background-color: #eee;
+}
+
+form.comment h3 {
+ background-color: #326591;
+ color: white;
+ margin: -10px -30px 10px -30px;
+ padding: 5px;
+ font-size: 1.4em;
+}
+
+form.comment input,
+form.comment textarea {
+ border: 1px solid #dddddd;
+ padding: 2px;
+ font-family: sans-serif;
+ font-size: 100%;
+}
+
+form.comment input[type="text"] {
+ width: 240px;
+}
+
+form.comment textarea {
+ width: 100%;
+ height: 200px;
+ margin-bottom: 10px;
+}
+
+.system-message {
+ background-color: #fda;
+ padding: 5px;
+ border: 3px solid red;
+}
+
+img.logo {
+ border-width: 0;
+ margin-bottom: 1em;
+}
+
+/* :::: PRINT :::: */
+ at media print {
+ div.document,
+ div.documentwrapper,
+ div.bodywrapper {
+ margin: 0;
+ width : 100%;
+ }
+
+ div.sidebar,
+ div.globalnav,
+ div.footer,
+ div#comments div.new-comment-box,
+ #top-link {
+ display: none;
+ }
+}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/_static/grok_club.gif
===================================================================
(Binary files differ)
Property changes on: groktoolkit/branches/jw-documentation-rearangement/doc/_static/grok_club.gif
___________________________________________________________________
Added: svn:mime-type
+ application/octet-stream
Added: groktoolkit/branches/jw-documentation-rearangement/doc/_static/logo.gif
===================================================================
(Binary files differ)
Property changes on: groktoolkit/branches/jw-documentation-rearangement/doc/_static/logo.gif
___________________________________________________________________
Added: svn:mime-type
+ application/octet-stream
Added: groktoolkit/branches/jw-documentation-rearangement/doc/_static/logo.png
===================================================================
(Binary files differ)
Property changes on: groktoolkit/branches/jw-documentation-rearangement/doc/_static/logo.png
___________________________________________________________________
Added: svn:mime-type
+ application/octet-stream
Added: groktoolkit/branches/jw-documentation-rearangement/doc/_static/top_bg.jpg
===================================================================
(Binary files differ)
Property changes on: groktoolkit/branches/jw-documentation-rearangement/doc/_static/top_bg.jpg
___________________________________________________________________
Added: svn:mime-type
+ application/octet-stream
Added: groktoolkit/branches/jw-documentation-rearangement/doc/bugs.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/bugs.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/bugs.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,64 @@
+.. _reporting-bugs:
+
+**********************
+Reporting Bugs in Grok
+**********************
+
+Grok aims to become a mature framework and tries to earn reputation
+for stability. In order to maintain this reputation, the developers
+would like to know of any deficiencies you find in Grok.
+
+If you find errors in the documentation, you can correct it yourself
+on the Grok website http://grok.zope.org/ . You only need to register
+with the website for that, which is necessary to block spammers. On
+some pages you then can use the "Add a comment" feature of the
+relevant page.
+
+All other bug reports should be submitted via the Grok Bug Tracker
+(https://bugs.launchpad.net/grok/). The bug tracker offers a Web form
+which allows pertinent information to be entered and submitted to the
+developers.
+
+The first step in filing a report is to determine whether the problem
+has already been reported. The advantage in doing so, aside from
+saving the developers time, is that you learn what has been done to
+fix it; it may be that the problem has already been fixed for the next
+release, or additional information is needed (in which case you are
+welcome to provide it if you can!). To do this, search the bug
+database using the search box on the top of the page or by clicking on
+"List all open bugs".
+
+If the problem you're reporting is not already in the bug tracker, go
+back to the Grok Bug Tracker and click the red "Report a bug" box on
+the right. If you don't already have a launchpad account, you will be
+asked to complete the registration by giving an e-mail address and
+following the steps mailed to you. Complete the registration process.
+Otherwise, if you're not logged in, enter your credentials and select
+"Log In". It is not possible to submit a bug report anonymously.
+
+Being now logged in, you can submit a bug. You will be asked a number
+of questions.
+
+For the "Summary" field, enter a *very* short description of the
+problem; less than ten words is good. In the "Further Information"
+field, describe your problem as accurate as possible. A good
+description will enables the developers to reproduce your
+problem. Name also the version of grok/grokproject you used.
+
+Each bug report will be assigned to a developer who will determine
+what needs to be done to correct the problem. You will receive an
+update each time action is taken on the bug.
+
+.. seealso::
+
+ `How to Report Bugs Effectively
+ <http://www.chiark.greenend.org.uk/~sgtatham/bugs.html>`_ Article
+ which goes into some detail about how to create a useful bug
+ report. This describes what kind of information is useful and why
+ it is useful.
+
+ `Bug Writing Guidelines
+ <http://www.mozilla.org/quality/bug-writing-guidelines.html>`_
+ Information about writing a good bug report. Some of this is
+ specific to the Mozilla project, but describes general good
+ practices.
Added: groktoolkit/branches/jw-documentation-rearangement/doc/changes.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/changes.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/changes.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+.. include:: ../CHANGES.txt
Added: groktoolkit/branches/jw-documentation-rearangement/doc/conf.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/conf.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/conf.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,144 @@
+# -*- coding: utf-8 -*-
+#
+# Grok Reference documentation build configuration file, created by
+# sphinx-quickstart.py on Wed Feb 20 02:11:17 2008.
+#
+# This file is execfile()d with the current directory set to its containing dir.
+#
+# The contents of this file are pickled, so don't put values in the namespace
+# that aren't pickleable (module imports are okay, they're removed automatically).
+#
+# All configuration values have a default value; values that are commented out
+# show the default value as assigned to them.
+
+import sys
+import pkg_resources
+
+from os import path, curdir
+
+# If your extensions are in another directory, add it here.
+#sys.path.append('some/directory')
+
+# General configuration
+# ---------------------
+
+# Add any Sphinx extension module names here, as strings. They can be extensions
+# coming with Sphinx (named 'sphinx.ext.*') or your custom ones.
+extensions = ['sphinx.ext.autodoc',
+ 'sphinx.ext.doctest',
+ 'sphinx.ext.intersphinx',
+ # 'sphinx.ext.viewcode', # This is currently broken?
+ ]
+
+# Order autodoc generated docs in source code order.
+autodoc_member_order = 'bysource'
+
+# Add any paths that contain templates here, relative to this directory.
+templates_path = ['.']
+
+# The suffix of source filenames.
+source_suffix = '.rst'
+
+# The master toctree document.
+master_doc = 'index'
+
+# General substitutions.
+project = 'Official Grok'
+copyright = '2006-2010, The Zope Foundation'
+
+# The default replacements for |version| and |release|, also used in various
+# other places throughout the built documents.
+#
+# The short X.Y version.
+version = pkg_resources.get_distribution('grok').version
+# The full version, including alpha/beta/rc tags.
+release = version
+if release.endswith('dev'):
+ release = '%s (unreleased)' % release
+
+# There are two options for replacing |today|: either, you set today to some
+# non-false value, then it is used:
+#today = ''
+# Else, today_fmt is used as the format for a strftime call.
+today_fmt = '%B %d, %Y'
+
+# List of documents that shouldn't be included in the build.
+unused_docs = ['build']
+
+# If true, '()' will be appended to :func: etc. cross-reference text.
+#add_function_parentheses = True
+
+# If true, the current module name will be prepended to all description
+# unit titles (such as .. function::).
+#add_module_names = True
+
+
+# Options for HTML output
+# -----------------------
+
+# If not '', a 'Last updated on:' timestamp is inserted at every page bottom,
+# using the given strftime format.
+html_last_updated_fmt = '%b %d, %Y'
+
+# If true, SmartyPants will be used to convert quotes and dashes to
+# typographically correct entities.
+html_use_smartypants = True
+
+# Custom sidebar templates, maps page names to filenames relative to this file.
+#html_sidebars = {}
+
+# Additional templates that should be rendered to pages, maps page names to
+# filenames relative to this file.
+html_additional_pages = {'index':'docindex.template'}
+
+# If true, the reST sources are included in the HTML build as _sources/<name>.
+#html_copy_source = True
+
+# Output file base name for HTML help builder.
+htmlhelp_basename = 'Grokdoc'
+
+# The name of the Pygments (syntax highlighting) style to use.
+pygments_style = 'sphinx'
+
+# The style sheet to use for HTML and HTML Help pages. A file of that name
+# must exist either in Sphinx' static/ path, or in one of the custom paths
+# given in html_static_path.
+html_style = 'grok.css'
+
+# Add any paths that contain custom static files (such as style sheets) here,
+# relative to this directory. They are copied after the builtin static files,
+# so a file named "default.css" will overwrite the builtin "default.css".
+html_static_path = [path.join(path.abspath(curdir), '_static')]
+
+
+# Options for LaTeX output
+# ------------------------
+
+# The paper size ('letter' or 'a4').
+#latex_paper_size = 'letter'
+
+# The font size ('10pt', '11pt' or '12pt').
+#latex_font_size = '10pt'
+latex_font_size = '11pt'
+
+# Grouping the document tree into LaTeX files. List of tuples
+# (source start file, target name, title, author, document class [howto/manual]).
+#latex_documents = []
+latex_documents = [
+ ('contents', 'grokdocs.tex', 'Grok Documentation', 'The Grok Team',
+ 'manual'),
+ ('tutorial', 'tutorial.tex', 'Grok Tutorial', 'The Grok Team',
+ 'manual'),
+ (path.join('reference', 'index'), 'reference.tex', 'Grok Reference',
+ 'The Grok Team', 'manual'),
+ ]
+
+# Additional stuff for the LaTeX preamble.
+#latex_preamble = '
+latex_preamble = '''
+\usepackage{epsfig}
+
+'''
+
+# Documents to append as an appendix to all manuals.
+#latex_appendices = []
Added: groktoolkit/branches/jw-documentation-rearangement/doc/contents.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/contents.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/contents.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,20 @@
+===========================
+Grok Documentation Contents
+===========================
+
+.. toctree::
+ :maxdepth: 2
+
+ changes.rst
+ upgrade.rst
+ tutorial.rst
+ grok_overview.rst
+ reference/index.rst
+ naming_conventions.rst
+ developing_grok.rst
+
+ bugs.rst
+ license.rst
+ README.rst
+ copyright.rst
+ glossary.rst
Added: groktoolkit/branches/jw-documentation-rearangement/doc/copyright.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/copyright.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/copyright.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,11 @@
+*********
+Copyright
+*********
+
+Grok and this documentation is:
+
+Copyright © 2006-2009 Zope Community and Contributors. All rights reserved.
+
+----------
+
+See: :ref:`license` for complete license and permissions information.
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/adapters.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/adapters.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/adapters.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+import grok
+from zope.publisher.interfaces.browser import IBrowserRequest, IBrowserView
+from zope.contentprovider.interfaces import IContentProvider
+from calc import Calculator
+
+class SingleAdapter(grok.Adapter):
+ grok.context(Calculator)
+ grok.adapts(Calculator) # generally allowed, but not in this case, because there's already grok.context
+ grok.implements(ISomething) # if this is not specified, app breaks
+ grok.provides(ISomething) # if adapter implements more than one interface
+ grok.name('') # this is actually the default
+
+ def something(self):
+ """self.context is automatically provided"""
+ return self.context.foo
+
+class CalculatorContentProvider(grok.MultiAdapter)
+ grok.adapts(Calculator, IBrowserRequest, IBrowserView)
+ grok.implements(IContentProvider)
+
+ def __init__(self, context, request, view):
+ self.context = context
+ self.request = request
+ self.view = view
+
+ # ...
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/annotations.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/annotations.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/annotations.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,28 @@
+import grok
+from zope import interface
+from BTrees.OOBTree import OOTreeSet
+
+class Article(grok.Model):
+ pass
+
+class IComments(interface.Interface):
+
+ def addComment(text):
+ pass
+
+ def getComments():
+ pass
+
+class Comments(grok.Annotation):
+ grok.context(Article) # this is actually the default
+ grok.implements(IComments)
+ grok.name('annotations.Comments') # this is actually the default
+
+ def __init__(self):
+ self.comments = OOTreeSet()
+
+ def addComment(self, text):
+ self.comments.insert(text)
+
+ def getComments(self):
+ return list(self.comments)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/container.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/container.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/container.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+import grok
+
+class Contact(grok.Model):
+ pass
+
+class AddressBook(grok.App, grok.Container):
+ pass
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/grok_beginner.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/grok_beginner.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/grok_beginner.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,412 @@
+==========================
+Grok: Making Zope 3 Easier
+==========================
+
+**NOTE:** This document was written *before* grok was implemented. It
+has been part of the design phase during which it served well to
+discuss and preserve grok's goals. The actual implementation of grok
+differs from the concrete code examples given here. This is NOT a
+grok tutorial nor should it be seen as any part of grok's current
+documentation!
+
+
+Publishing web pages
+====================
+
+You want to publish a web site that is in a directory. This includes
+any pictures and javascript and CSS you may have in that directory::
+
+ import grok
+
+ class Website(grok.View):
+ grok.files('mydirectory')
+
+XXX use htdocs here, familiar to some people
+
+Once you do this, you can browse into these from the Zope 3 root site.
+Files and assets in any subdirectories will also be published. (XXX
+how?)
+
+Dynamic pages
+=============
+
+Often you want your web pages not to be static but *dynamic*. A web
+page is dynamic when, before the web page is served to your user for
+display in a browser, you want to generate part or all of the
+information of the web page automatically.
+
+Zope reads your HTML files as Zope Page Templates (ZPT), meaning you
+can use TAL (Template Attribute Language) to script your
+templates. TAL is added to HTML as attributes, meaning your HTML still
+looks very familiar. For an example of very simple TAL, consider this
+HTML snippet::
+
+ <p tal:content="python:1 + 1">Result here</p>
+
+This will generate the following::
+
+ <p>2</p>
+
+This means that the result of the Python expression `1 + 1` is
+dynamically inserted as the content of this `p` tag, replacing what
+was already there.
+
+You can add TAL to any of your HTML pages to make them dynamic.
+
+For more about TAL see XXX (TAL tutorial in here?)
+
+Using Python
+============
+
+Just TAL by itself, even when you use `python:` to embed snippets of
+Python, is limited. The idea of good application design is to use TAL
+just for fairly simple templating purposes, and to do anything a bit
+more complicated in Python code. Using TAL with Python code is easy:
+you just add methods to your view class and use them from your
+template.
+
+Here we add a method that formats the current date and time::
+
+ from zope import grok
+ from datetime import datetime
+
+ class Website(grok.View):
+ grok.files('mydirectory')
+
+ def currentDatetime(self):
+ return datetime.now().strftime('%Y-%m-%d %H:%M')
+
+We can then use this with TAL to display the current date and time::
+
+ <p tal:content="view/currentDatetime">Datetime goes here</p>
+
+All the methods you add to the class of your site are automatically
+available on the special `view` name from within your
+templates. `view` is one of the few names that are available in views
+by default.
+
+Note that we have used TAL's built-in `path` language here; this can
+be used for simple method calls instead of spelling it out explicitly.
+For the same effect, you can also use it using Python directly::
+
+ <p tal:content="python:view.currentDatetime()">Datetime goes here</p>
+
+This can be useful when you want to pass parameters to your methods.
+
+Generating HTML from Python
+===========================
+
+Sometimes you want to generate complicated HTML in Python and then
+include it in an existing web page. For reasons of security against
+cross-site scripting attacks, TAL will automatically escape any HTML
+into `>` and `<`. With the `structure` directive, you can tell
+TAL explicitly to not escape HTML this way, so it is passed literally
+into the template::
+
+ from zope import grok
+
+ class Website(grok.View):
+ grok.files('mydirectory')
+
+ def someHTML(self):
+ return '<strong>%s</strong>' % (1 + 1)
+
+And then with TAL in one of your templates::
+
+ <p tal:content="structure view/someHTML">Result goes here</p>
+
+Generating the whole page from Python
+=====================================
+
+If for some reason you do not want to use a HTML template but just
+want to generate HTML directly from Python, this is also possible::
+
+ class Foo(grok.View):
+ @grok.page('serverload.html')
+ def serverLoad(self):
+ return '<html>..</html>'
+
+XXX a word on unicode
+
+Simple forms
+============
+
+Typical web applications have forms. Let's make a web form and use
+it. First we'll add the following form to one of our templates::
+
+ <form action="hello.html" method="post">
+ <p>
+ Please type your name: <input type="text" name="name" value="" /><br/>
+ <input type="submit" value="Submit" />
+ </p>
+ </form>
+
+As you can see, this form submits to the template named
+`hello.html`. Create such a template in your site and put the
+following TAL in there::
+
+ <html><body>
+ <p>Hello, <strong tal:content="request/form/name">name</strong></p>
+ </body></html>
+
+Now when you go to the form and submit it with the name `John`, you
+should see a web page that says:
+
+ Hello **John**
+
+Simple forms with Python
+========================
+
+Let's make a simple calculator to demonstrate how we combine this with
+Python::
+
+ <form action="sum.html" method="post">
+ <p>
+ First value: <input type="text" name="first" value="" /><br />
+ Second value: <input type="text" name="second" value="" /><br />
+ <input type="submit" value="Get the sum" />
+ </p>
+ </form>
+
+And create the following template `sum.html`::
+
+ <html><body>
+ <p>The sum is: <strong tal:content="data/sum">the sum goes here</strong></p>
+ </body></html>
+
+We've referred to a method `sum` here that does not exist yet, so let's
+implement it. It takes the raw values in the request and adds them to
+together, returning the sum::
+
+ from zope import grok
+
+ from ... import TemplateFile
+
+ class Website(grok.View):
+ grok.files('mydirectory')
+
+ @grok.page('sum.html')
+ def sum(self):
+ # before
+ self.sendEmail()
+ # call template (pull calculateSum2)
+ result = self.renderTemplate('sum.html', sum=self.calculateSum())
+ # post processing
+ result = result.replace('foo', 'bar')
+ return result
+
+
+ def sum(self):
+ self.before()
+ result = self.render('sum.html', **self.push())
+ result = self.after(result)
+ return result
+
+ def before(self):
+ pass
+
+class Website(grok.View):
+ grok.files('mydirectory')
+
+ class sum(object):
+ """corresponds to sum.html"""
+
+ @grok.before()
+ def sendEmail(self):
+ ...
+
+ @grok.after()
+ def barify(self, result):
+ return result.replace('foo', 'bar')
+
+ def calculateSum(self):
+ return ...
+
+ def sum2(self):
+ return ...
+
+ class fancysum(sum):
+ """corresponds to fancysum.html"""
+
+ def calculateSum(self):
+ ...
+
+
+ @grok.data('sum.html', 'sum')
+ def sum(self):
+ # get hold of the form, from the request object that
+ # we can get from self
+ form = self.request.form
+ # now get first and second from the form; if no value found
+ # assume it's 0
+ first = form.get('first', 0)
+ second = form.get('second', 0)
+ # convert the input which was text to the numbers
+ # note that we don't handle any errors yet in case someone fills in
+ # something that's not a number
+ first = int(first)
+ second = int(second)
+ # now add the numbers and return this result
+ return first + second
+
+ @grok.page('sum.html')
+ def sum(self):
+ return "<html>...</html>"
+
+
+Form side effects
+=================
+
+Often you don't just want to see a result page when a user submits a
+form, but you want the let the system do some work just before we show
+the result. An example of this is to send an email. Another common
+example is to store the data that's in the form in a database
+somewhere.
+
+This can be easily accomplished using the `@grok.before` decorator,
+which allows us to execute some Python code just before the template
+is rendered::
+
+ class Website(grok.View):
+ grok.templates('mydirectory')
+
+ @grok.before('email_sent.html')
+ def email(self):
+ ... send the email XXX ...
+
+
+Storing data
+============
+
+Instead of emailing the data, what if we wanted to record what the
+user entered instead? Zope offers a number of options for storing
+data, such as making a connection to relational databases (XXX which
+we'll handle later?), but Zope also ships with a powerful database of
+its own: the Zope Object Database (ZODB).
+
+The ZODB is a database of Python objects. You can store any Python object
+in it, and there are just a few things you need to be aware of initially:
+
+* You should subclass your own data classes from persistent.Persistent
+ so it's easy to store them in the ZODB.
+
+* To make sure the ZODB knows you changed a mutable attribute in the
+ instance, set the special `_p_changed` attribute on that instance to
+ `True`. This is only necessary if that attribute is not `Persistent`
+ itself. It's not necessary when you assign to an attribute directly
+ using `=`.
+
+This may sound complicated but it's not. Don't worry for now - most
+things work as normal in Python, and the rules just described are not
+difficult.
+
+So how do we get a space in the database to store our data in?
+`zope.grok` supports a special area where you can store your data.
+
+To get to the database in Python code, call `grok.database()`. This
+gives us access to a dictionary-like object, in which we can store our
+own sub objects::
+
+ from zope import grok
+ from persistent import Persistent
+
+ class NamesStorage(Persistent):
+ def __init__(self):
+ self.names = []
+
+ def addName(self, name):
+ self.names.append(name)
+ self._p_changed = True
+
+ class Website(grok.View):
+ grok.templates('mydirectory')
+
+ def getNamesStorage(self):
+ """Get the names storage, or create it if it's not there yet.
+ """
+ db = grok.database()
+ storage = db.get('myapp.names_storage')
+ if storage is None:
+ db['myapp.names_storage'] = NamesStorage()
+ return storage
+
+ def storeName(self):
+ """
+ Retrieve the name from request and store it in
+ the names section.
+ """
+ storage = self.getNamesStorage()
+ storage.addName(self.request['name'])
+
+XXX should following be separate section?
+
+Note that storing names in a list is not very efficient if the list of
+names grows to a larger size, as the object database will need to load
+the whole list of names into memory each time it is changed. We can
+avoid this using BTrees. XXX BTree explanation
+
+XXX showing the names in a web page
+
+Self-posting forms
+==================
+
+It's a good design for many forms to be *self-posting*, that is, the
+result of a form submission shows the original form again. This way,
+mistakes by the user can be easily shown in the context of the form,
+and the user can correct them. When the form submission does succeed,
+the user is commonly redirected to another page.
+
+Let's first make a form that posts to itself, we'll call it just
+`form.html`::
+
+ <html><body>
+ <form action="." method="post">
+ <input type="text" name="number" value="" />
+ </form>
+ </body></html>
+
+We expect the user to enter an integer number, and we also want it the
+number to be required. Only if those conditions are true
+....
+
+XXX can't use . perhaps, need to do absolute trick and explain it: request/URL
+
+n. .. self posting form ..
+
+Powerful forms using formlib
+============================
+
+class Foo(grok.View):
+
+ class Form(grok.Form):
+ grok.name('entry.html')
+ # would really be step 7 to control the template
+ # that renders the form. (this template needs to be
+ # moved)
+ template = grok.Template('entry.html')
+
+ form_fields = grok.Fields(
+ name=schema.TextLine(title='Name'),
+ )
+
+ @grok.action('Submit')
+ def handle_submit(self, action, data):
+ .. send email ..
+ self.message = "The mail has successfully been sent."
+
+
+
+class MeetingView(grok.view):
+
+ grok.context(IMeeting, id=getfromrequestpath)
+
+n. You want to associate your application to a specific site
+
+n. You want to create a site content object
+
+n. You want to create a content object and associate views to that.
+
+n. You want to index content objects to search them.
+
+
+Some basic explanation of what's going on with unicode in Zope 3.
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/grok_dev.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/grok_dev.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/grok_dev.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,394 @@
+==========================
+Grok: Making Zope 3 Easier
+==========================
+
+**NOTE:** This document was written *before* grok was implemented. It
+has been part of the design phase during which it served well to
+discuss and preserve grok's goals. The actual implementation of grok
+differs from the concrete code examples given here. This is NOT a
+grok tutorial nor should it be seen as any part of grok's current
+documentation!
+
+Introduction
+============
+
+The Grok project tries to it easier to develop Zope 3
+applications. Zope 3 is typically configured using ZCML, the Zope
+Configuration Markup Language. ZCML is non-Python and very explicit.
+
+ZCML was in part inspired by the difficulties surrounding
+configuration in Zope 2. Zope 2 is heavy on implicit configuration
+("no docstring means no public access", "a permission used is a
+permission defined"). In addition, lots of the configuration happens
+in Python code, such as in the `__init__.py` of a product. These
+techniques can lead to problems: hard to understand configuration code
+interweaved with non-configuration code. Such code tends to be
+difficult to maintain, extend, and evolve.
+
+ZCML aims to separate configuration strongly from software to avoid
+these problems. The ZCML model in combination with the notion of
+explicit interfaces offers a strong model for evolving software over a
+longer period of time.
+
+ZCML has drawbacks however. Zope 3's setup for modularity, components
+and evolution results in more entities for a programmer to worry
+about: explicit interfaces, a multiplication of files and modules, a
+large list of places to import from, a series of ZCML directives to
+remember. Even though individual entities may be easier to understand,
+the combination of such can make the whole more difficult to
+understand, and there is just a lot to learn overall.
+
+This is especially off-putting to developers who are trying to start
+learning Zope 3. Even experienced programmers can be frustrated by so
+much need to state obvious things explicitly - the multiplication of
+entities in Zope 3 hurts agility of development. Finally, ZCML can be
+intimidating to a Python programmer merely by being non-Python, and
+XML in particular. While the latter is at least in part a superficial
+concern, it is one that stops people from trying Zope 3.
+
+Grok aims to reduce the visibility of ZCML to the Zope 3
+programmer. Grok also aims to reduce the entities a programmer needs
+to worry about: ideally a Zope 3 application should be able to fit
+completely inside a single module. Grok does not aim to do away with
+ZCML altogether: explicit configuration is valuable. Grok merely aims
+to keep the advanced concepts out of the programmer's face when not
+needed.
+
+How does Grok aim accomplish these goals? We will try to follow the
+guidelines that work for Ruby on Rails:
+
+* DRY: Don't Repeat Yourself
+
+* Convention over configuration
+
+Grok is specified as autogenerated ZCML. This is for convenience of
+specification: Grok does not need to be implemented this way but could
+be calling underlying component architecture APIs directly where
+needed. In fact, one of the aims of Grok is to produce more readable
+errors that guide programmers into the right direction to solve their
+problem.
+
+Grok does not aim to make the programmer do correct security - an
+application written with Grok without the programmer taking any
+particular actions will be entirely public by default. Convenience of
+development trumps security here. The idea of Grok is that the
+programmer should have the easiest time possible to get an application
+running first, and then can gradually tighten the application in
+various ways, including security, later on.
+
+Views
+-----
+
+To declare a browser view, a new class-level declaration `views` is
+added, with as argument the class or interface the view is being
+declared for::
+
+ from zope import grok
+
+ class FooView(grok.View):
+ grok.views(Foo)
+
+As you can see, Grok views are inherited from `grok.View`.
+
+This is equivalent to the following ZCML::
+
+ <browser:page
+ name="FooView"
+ for="Foo"
+ class="FooView"
+ permission="zope.Public"
+ />
+
+Note that the name is deduced entirely from the name of the view
+class. Where this is not desired, the view name can be controlled
+using the `name` declaration on the view:
+
+ from zope import grok
+
+ class FooView(grok.View):
+ grok.name("info.html")
+ grok.views(Foo)
+
+ @grok.page('info.info')
+ ...
+
+which translates to::
+
+ <browser:page
+ name="info.html"
+ for="Foo"
+ class="FooView"
+ permission="zope.Public"
+ />
+
+It's also possible to set the skin the view is in using ``skin``
+declaration::
+
+ from zope import grok
+ from myskin import IMySkin
+
+ class FooView(grok.View):
+ grok.skin(IMySkin)
+
+XXX can we somehow stop the concept of interface from being introduced
+here? Class-based skins?
+
+Views that do not specify *any* declarations but inherit from
+grok.View are also automatically registered, for everything (`*`)::
+
+ from zope import grok
+
+ class MyView(grok.View):
+ def getData(self):
+ return fadfkjdlkfjd
+ __call__ = template('foo.pt')
+
+is equivalent to the following ZCML::
+
+ <browser:page
+ name="MyView"
+ for="*"
+ class="MyView"
+ permission="zope.Public"
+ />
+
+View Security
+-------------
+
+The default permission on views generated by Grok is `zope.Public`. At
+first glance, this seems to be going back to the bad old insecure days
+of Zope 2. Zope 3 has a different security model though: content
+objects can declare their own security. Since Grok declares content
+objects entirely public by default as well however, that is not a very
+strong argument.
+
+The more important argument for this "wide-open" default is that
+dealing with security issues early on in application development tends
+to be very painful and distracting for most application developers,
+breaking their flow. The temptation is therefore large to just give
+any permissions that will permit the developer to continue. Security
+issues are typically ignored until a later stage of development. We
+recognize this pattern of development, and we can't really enforce
+developers doing security right anyway, so Grok doesn't aim to try.
+
+Of course it is possible to override the default, using a class
+declaration on the view called `permission`::
+
+ from zope import grok
+
+ class MyView:
+ grok.views(SomeContent)
+ grok.permission('zope.ManageContent')
+
+Non-existing permissions are not created automatically - new
+permissions have to be declared explicitly, using ZCML.
+
+Finally, Grok also offers a "security testing" mode, where the default
+permission of all views in a package is specified by the
+developer. This can be used at a later stage during development to
+flush out any security problems.
+
+XXX explain spelling for that
+
+Class security
+--------------
+
+Attributes, both reading and writing on content are protected with the
+`zope.Public` permission by default. The aim of Grok is to get out of
+the programmers hair.
+
+How does Grok determine that something is a content class and thus
+should have its attributes made public?
+
+Grok determines something is a content class if:
+
+* it has views that directly view it
+
+* it is a subclass of a class that has views
+
+* it has an interface that has views registered for it
+
+For the purposes of security, views registered for `*` do *not* count
+as views registered for a class or interface.
+
+To restrict the permission of a content class explicitly, the same
+`permission` class declaration can be used as the one defined for
+views. This declaration sets the default access permission for *all*
+attributes of the class::
+
+ from zope import grok
+
+ class FooContent:
+ grok.permission('zope.ManageContent')
+
+It is often desirable to make an exception for some attributes, however::
+
+ from zope ipmort grok
+
+ class FooContent:
+ grok.permission('myapp.View')
+
+ @@grok.protected('myapp.Edit')
+ def protectedMethod(self):
+ pass
+
+ @@grok.private()
+ def privateMethod(self):
+ pass
+
+ def _alsoPrivate():
+ pass
+
+As soon as specific declarations are used to restrict the access to
+various methods, the default view permission of `zope.Public` does not
+apply anymore for that class.
+
+Importing
+---------
+
+As you've seen from the examples, every import in a simple Grok
+application will be from the `zope.grok` package. This means that the
+developer does not need to remember a complicated set of imports from
+a wide-ranging set of packages just to build a simple package.
+
+This is the opposite of the current trend in Zope 3 development:
+imports from `zope.app.zapi`, intended to be an easy location to get
+important stuff are replaced with the imports from the real location.
+
+`zope.app.zapi` as an approach to simplify things failed for a number
+of reasons: it not very coherent, so hard to predict what ended up
+there, and it was incomplete: to build a real Zope 3 application you
+always needed to import from places beyond `zope.app.zapi`. In
+contrast, `zope.grok` aims to provide a relatively small number of
+names to use, and that should be *all* needed to produce a simple
+`zope.grok`-based application.
+
+Of course as a grok-based application grows developers will find
+themselves importing from other package. This should be a voyage of
+gradual discovery for the developer. There should be no need to go the
+whole way right away.
+
+XXX possible exceptions: zope.schema, zope.formlib
+
+Schema-classes
+--------------
+
+It is possible to define the schema of a class directly::
+
+ from zope import grok
+
+ class MyContent(grok.Content):
+ class data:
+ foo = TextLine(u'Foo')
+
+Fields defined are automatically created as attributes on instances
+using the defaults specified by the fields (the default default if no
+default is specified).
+
+XXX schema really should accept pure ascii strings in all cases
+ instead of unicode strings, and not *require* a u'' in front of
+ strings and give an obscure error. If you need non-ascii, *then*
+ you worry about unicode. Yet another thing less to explain to
+ beginners however.
+
+XXX we cannot use the name `schema` for the schema inner class as that
+ would conflict with `from zope import schema`...
+
+By default the schema is readable and writeable by all.
+
+The schema read and write permissions for schema fields can be set
+using special class declarations::
+
+ from zope import grok
+
+ class MyContent(grok.Content):
+ class data:
+ read_permission('myapp.View')
+ write_permission('myapp.Edit')
+
+ foo = TextLine(u'Foo')
+
+XXX want to handle the usecase of a class with multiple related
+ schemas that have an inheritance relationship to each other?
+
+No interfaces necessary
+-----------------------
+
+A Grok application can be written without a single interface in
+sight. No interfaces means less entities for the developer to care
+about, and the goal of grok is to avoid having to worry about
+interfaces when building an application. Interfaces can always be
+added later during the evolution of an application.
+
+XXX exception for skins at present..
+
+As an application grows a developer can start introducing interfaces:
+grok does not *stop* the use of interfaces.
+
+Adapters
+--------
+
+XXX is this something to be treated by grok or is this an "advanced
+topic" outside the purview of grok? It should be easy to recognize
+adapters that use `adapts()` and automatically register them.
+
+Forms
+-----
+
+Let's see how `zope.formlib` fits in with grok::
+
+ from zope import schema
+ from zope import grok
+
+ class MyContent(grok.Content):
+ class data:
+ name = schema.TextLine("Name")
+ age = schema.Int("Age")
+
+ class MyContentView(grok.EditForm):
+ grok.name('edit.html')
+ grok.views(MyContent)
+
+ # XXX can it be automatically deduced where the fields come from
+ # at this point?
+ form_fields = grok.Fields()
+
+ grok.action('Ok')
+ def handle_input(self, action, data):
+ pass
+
+XXX should be really be covering up formlib.form? ``grok.Fields()``
+ seems to imply we might have to.
+
+Templates
+---------
+
+This sets up a template to use::
+
+ from zope import grok
+
+ class MyView(grok.View):
+ grok.template('mytemplate.pt')
+
+XXX Sensible default behavior:
+
+ * use template for __call__ if no __call__ defined
+
+ * template/update pattern?
+
+Menus
+-----
+
+XXX How to make things show up in menus? When we create a new content
+object we at least want an easy way to create it, though not
+necessarily through the ZMI. Menu class declaration?
+
+TDB
+---
+
+* Easy way to generate add views
+
+* easy local utility registration?
+
+* bread - easy creation of tables, catalog-based search
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/menu.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/menu.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/menu.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,192 @@
+"""megrok.menu
+
+A simple but extensible menu system for Zope 3.
+
+What is a menu?
+
+ For web applications there are two competing design patterns that can be
+ handled under the term 'menu': classic GUI menus and web site navigation.
+
+ The essential difference in those two is the 'status' or 'context' of the
+ menu. In classic GUI applications, a menu is (more or less) stateless,
+ independent of the view to the application that is currently being used.
+
+ In classic web sites, the navigation gives a navigatable overview of the
+ site's hierarchy using an 'active' flag to indicate the user's position in
+ the site.
+
+ In web applications those two concepts start to mix.
+
+ The basic implementation of the menu system takes care of the classic
+ listing of options a user has in a specific context.
+
+ An extension mechanism is used to provide status-annotation to menu items
+ to show where a user currently is.
+
+Design goals:
+
+ - Simple, central, menu definition without ZCML
+
+ - Allow submenus.
+
+ - Make status determination pluggable to allow for application-specific
+ complex scenarios without tainting the menu system.
+
+Menu rendering process:
+
+ - create set of choices (apply filters in context, permissions, condition)
+
+ - apply (status) annotations
+
+Determining whether an item is active:
+
+ a) Model based
+
+ - find out which object belongs to the menu item
+
+ - Is this object the same as the context of the menu?
+
+ b) View based
+
+ - find out which view belongs to the menu item
+
+ - Is it the currently published view?
+
+ Generalisation:
+
+Zope/Grok stuff:
+
+ - Menus are utilities
+
+Questions:
+
+ - How to integrate with skin layers?
+
+ - Aren't menus just browser views? (context, request)
+
+ - Two variations: allow menu items to render their HTML, or not?
+
+ Allow HTML:
+
+ - provides ability to implement various menu item types
+
+ - codes in presentation
+
+ Don't allow HTML:
+
+ - more flexible to customize?
+
+ -> use views on menu items!
+"""
+
+import grok
+from megrok import menu
+
+class AddressBook(grok.Model):
+ pass
+
+class Contact(grok.Model):
+ pass
+
+class EditContact(grok.EditForm):
+ grok.context(Contact)
+ grok.annotation("title", _(u"Edit XY"))
+
+
+layout = grok.PageTemplate("""\
+<html>
+<body>
+
+ <!-- Most simple: Render the whole menu -->
+ <div tal:replace="structure menu/main/@@links"/>
+
+ <!-- Variation 1: Render whole menu as drop down list -->
+ <div tal:replace="structure menu/main/@@dropdown"/>
+
+ <!-- Variation 2: Render menu manually, get each item as link
+ <ul>
+ <li tal:repeat="item menu/main">
+ <a tal:replace="structure item/@@link">
+ </li>
+ </ul>
+
+ <!-- Variation 3: Render menu and items manually
+ <ul tal:repeat="item menu/main"><a tal:attributes="href item/action" tal:content="item/title"></ul>
+ </ul>
+
+ <!-- Variation 4: Render option elements automatically -->
+ <select>
+ <option tal:repeat="item menu:main" tal:replace="item/@@option">
+ </select>
+
+ <!-- Bind the menu to a different object explicitly -->
+ <div tal:replace="structure python:menu['main'].bind(object1, request)"/>
+ '
+ <!-- Alternative: use a grok variable in the templates: -->
+ <div tal:replace="structure grok/menu/main/context:asdf/"/>
+
+
+
+ <grok:menu
+</body>
+</html>""")
+
+class IMenuItem(Interface):
+
+ action
+ title
+ submenu
+
+
+main = menu.Menu(
+ menu.View(EditContact), # Link to a view. Necessary information: context, name
+ # Link to a generic action/URL
+ menu.Action(_("External action"), "string:http://${context/"),
+ menu.SubMenu(
+ menu.Item(
+
+
+############ Implementation sketches
+
+class ViewMenuItem(object):
+
+ def __init__(self, view):
+ # View must be a view
+
+
+class Action(object):
+
+ def __init__(self, title, target):
+ self.title = title
+ self.target = target # TALES expression
+
+ def
+
+
+class BaseMenuItem(object):
+
+ def __init__(self, condition):
+ self.condition = condition
+
+ def checkCondition(context, request):
+ # - does this item apply in the given context?
+ # - does the user have the necessary permissions
+ # - does the user supplied condition evalute to true?
+
+
+class Menu(object):
+
+ def __init__(self, menu_items):
+ # XXX assert: All items must be menu items
+ self.menu_items = menu_items
+
+ def __call__(self, context, request):
+ relevant_items = []
+
+ for item in self.menu_items:
+ if not item.checkCondition(context, request):
+ continue
+
+ relevant_item.append(item)
+
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/model.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/model.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/model.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,56 @@
+"""
+Schema-driven development with grok
+"""
+import grok
+
+grok.directory('contact')
+
+class Contact(grok.SchemaModel):
+ """
+ This works now:
+
+ >>> c = Contact(name=u'Martijn', city=u'Rotterdam')
+ >>> c.name
+ u'Martijn'
+
+ Also w/o kw:
+
+ >>> c = Contact(u'Martijn', u'Rotterdam')
+ >>> c.name
+ u'Martijn'
+
+ """
+ class fields:
+ name = schema.TextLine()
+ city = schema.TextLine()
+
+
+class Edit(grok.EditForm):
+ pass
+ # this will automatically render an edit form, and use an
+ # 'edit.html' template if available
+
+class Index(grok.DisplayForm):
+ pass
+ # this will automatically render an display form, and use an
+ # 'index.html' template if available
+
+class Add(grok.AddForm):
+ grok.context(Contact) # this is actually the default
+ grok.container(IContainer) # this is actually the default
+
+class FancyEdit(grok.EditForm):
+ """ use cases:
+
+ * (actions with permissions)
+
+ *
+
+ """
+
+ @grok.action("Save")
+ def save(self, **data):
+ """
+ this overrides any actions defined on the base class
+ """
+ self.applyChanges(data)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/permission.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/permission.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/permission.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+import grok
+
+grok.definepermission('grok.Complex') # define permission first
+
+class Complex(grok.Model):
+ # this sets the default for all methods
+ grok.require('zope.Public') # this is actually the default
+
+ # this sets the default for reading all attributes that are not methods
+ grok.readable('zope.Public') # this is actually the default
+
+ # this sets the default for writing all attributes that are not methods
+ grok.writable('zope.Public') # this is actually the default
+
+ # this overrides the above
+ grok.readable('grok.Complex', 'attr1') # override default
+ grok.readable('zope.ManageServices', 'attr2') # override default
+ grok.writable('zope.ManageContent', 'attr1', 'attr2') # override default
+
+ def __init__(self):
+ self.attr1 = 1
+ self.attr2 = 2
+
+ @grok.require('some.permission')
+ def doSomethingVerySecret(self):
+ pass
+
+ @grok.require('zope.Public') # this is actually the default
+ def imPublic(self):
+ pass
+
+class SubClass(Complex):
+ # it's all inherited
+
+ grok.readable('zope.Public', 'attr1')
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/skin-minimal.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/skin-minimal.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/skin-minimal.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,18 @@
+import grok
+from zope import interface
+
+
+grok.definelayer('my')
+grok.defineskin('my') # Picks up the layer 'my' if it exists
+
+grok.layer('my') # If there is only a single layer defined
+ # in a module, it will be the default
+
+
+class Painting(grok.View):
+ pass
+
+
+fireplace = grok.PageTemplate("""\
+<html><body></body></html>
+""")
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/skin.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/skin.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/skin.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,25 @@
+import grok
+from zope import interface
+
+
+grok.definelayer('my')
+grok.definelayer('admin')
+
+grok.layer('my')
+
+grok.defineskin('my', ['my']) # this is the default
+grok.defineskin('my') # does the same as the line above
+grok.defineskin('admin', ['admin', 'my'])
+
+
+class Painting(grok.View):
+ pass
+
+
+fireplace = grok.PageTemplate("""\
+<html><body></body></html>
+""")
+
+
+class AdminPainting(grok.View):
+ grok.layer('adminlayer')
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/subscriber.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/subscriber.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/subscriber.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,11 @@
+from zope.lifecycleevent.interfaces import IObjectModifiedEvent
+from calc import Calculator
+import grok
+
+ at grok.subscriber(Calculator, IObjectModifiedEvent)
+def calculatorChanged(calc, event):
+ pass
+
+
+# perhaps alias zope.event.notify to grok.notify???
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/traversal.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/traversal.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/traversal.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,50 @@
+import grok
+
+class Appointment(grok.Model):
+ pass
+
+class Day(grok.Model):
+
+ def getAppointment(self, number):
+ if number in self.appointments:
+ return Appointment(number)
+ return None # try to look up views then
+
+ def traverse(self, name):
+ return self.getAppointment(int(number))
+
+class Calendar(grok.Model):
+ def getYear(self, year):
+ return Year(year)
+
+ def traverse(self, name):
+ return self.getYear(int(number))
+
+# interpretation of traverse:
+
+# * do the traverse traversal first
+
+# * if this raises an error, propagate exception, do not swallow it (test)
+
+# * if this returns None, fall back on "normal" traversal for the
+ object (i.e. container traversal)
+
+"""
+http://.../calendar/2006/10/13/1/
+ ^^^^^^^^ ^^^^ ^^ ^^ ^
+ Cal. Year ... A.
+"""
+
+#XXX routes (http://routes.groovie.org/) for advanced cases
+
+
+# instead of traverser on the model, you can also write a separate
+# traverser component:
+
+class CalendarTraverser(grok.Traverser):
+ grok.context(Calendar) # this is actually the default
+ grok.register(site=CalendarApp) #...
+
+ def traverse(self, name):
+ now look up stuff on self.context with 'name'...
+ return that
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/utility.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/utility.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/utility.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,31 @@
+import grok
+
+class Calculator(grok.GlobalUtility):
+ grok.implements(ICalculator) # if this is not specified, it breaks
+ grok.name('') # this is actually the default
+ grok.provides(ICalculator) # this is actually the default
+
+grok.global_utility(factory, provides=IFace, name=u'')
+
+class Calculator(grok.LocalUtility):
+ grok.utility_provides(ICalculator)
+
+class Anything(grok.Model):
+ pass
+
+class NonPersistent(object):
+ pass
+
+class SpecialAnything(Anything):
+ pass
+
+class Foo(grok.Model, grok.Site):
+ grok.local_utility(Anything, hide=False, name_in_container='foo',
+ persistent=None)
+ grok.local_adapter()
+ grok.local_view()
+
+class Foo2(Foo):
+ grok.local_utility(SpecialAnything)
+
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/design/views.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/design/views.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/design/views.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,85 @@
+import grok
+
+grok.templatedir('calc_templates') # this is actually the default (from module name, calc.py)
+
+class Calculator(grok.Model):
+ pass
+
+class Sum(grok.View):
+ """Simple view for a model"""
+ grok.context(Calculator) # this is actually the default (from module)
+ grok.template('sum') # this is actually the default (from class name)
+ grok.name('sum') # this is actually the default (from class name)
+ grok.require('zope.Public') # this is actually the default
+
+ def calculateSum(self):
+ """you can pull this in the template through view/calculateSum"""
+
+ def update(self):
+ """executed before the template is rendered"""
+ self.sum = self.calculateSum()
+ self.sendEmail()
+
+ def sendEmail(self):
+ """send an email here"""
+
+class PDFSum(grok.View):
+
+ def update(self):
+ pass
+
+ def render(self):
+ return pdfdata
+
+sum = grok.PageTemplate("""\
+<p tal:content="view/calculateSum">...</p>
+<p tal:content="view/precalculatedSum">...</p>
+""")
+
+
+from zope import schema
+
+class Index(grok.Form):
+ """a form
+
+ this is the default view for the Calculator model (because it's
+ called Index)
+ """
+
+ class fields:
+ operand = schema.Int(title=u'Operand')
+ operator = schema.Choice(...)
+ operand2 = schema.Int(...)
+
+ @grok.action('Calculate')
+ def calculate(self, operand, operator, operand2):
+ """it's possible to receive any number of form fields in any
+ order, or just use **kw to receive them all in a dict"""
+ self.result = operator(operand, operand2)
+
+ # this will raise a helpful error message at startup time (encoded
+ # strings)
+ @grok.action('Bääää')
+ def whatever(self, **data):
+ pass
+
+index = grok.PageTemplate("""\
+<form tal:attributes="action request/URL">
+<p tal:condition="exists:view/result">
+ The result is: <span tal:replace="view/result" />
+</p>
+
+XXX render fields
+XXX render actions
+</form>
+""")
+
+class CalculatorXMLRPC(grok.XMLRPC):
+
+ @grok.require('zope.Public') # this is actually the default
+ def sum(self, operand, operator, operand2):
+ return ...
+
+ @grok.require('something.else')
+ def whatever(self):
+ return ...
Added: groktoolkit/branches/jw-documentation-rearangement/doc/developing_grok.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/developing_grok.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/developing_grok.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,123 @@
+===============
+Developing Grok
+===============
+
+.. contents::
+
+Making Grok (Toolkit) releases
+------------------------------
+
+Manual steps
+~~~~~~~~~~~~
+
+Grok Toolkit's release procedure (and that of the comprising package like grok
+and the ``grokcore.*`` family of libraries) follows ZTK's `official release
+guidelines`_.
+
+.. _`official release guidelines`: http://docs.zope.org/zopetoolkit/process/releasing-software.html
+
+Automated steps
+~~~~~~~~~~~~~~~
+
+Even if it can be useful to follow these release steps by hand, most of it is
+automated in the `zest.releaser`_ package that is included in Grok Toolkit's
+``buildout.cfg``. Using this tool will prevent making mistakes caused by the
+rather repetitive nature of the release process.
+
+.. _`zest.releaser`: http://pypi.python.org/pypi/zest.releaser
+
+Part of the `official release guidelines`_ is reviewing the changelog recorded
+in ``CHANGES.txt``. This is an important step that cannot be automated.
+
+In other words, before starting a release make sure that:
+
+ 1) All tests pass
+ 2) All local changes are committed
+ 3) The changelogs in the Grok packages are up to date.
+
+The `zest.releaser` package provides a command line utility to help reviewing
+the changelog. It will display a diff between the most recently created
+release tag and the current maintenance branch of trunk::
+
+ $ ./bin/lasttagdiff
+
+After having reviewed the changelog (and making sure any changes are commited!)
+the actual release can be made::
+
+ $ ./bin/fullrelease
+
+Grok Tookit contains a post-release step triggered by zest.releaser that will
+upload a ``versions.cfg`` file to::
+
+ grok.zope.org:/var/www/html/grok/releaseinfo/[VERSION]/versions.cfg
+
+Manual post release steps
+~~~~~~~~~~~~~~~~~~~~~~~~~
+
+After having released Grok, the following steps should be taken:
+
+1. Grokproject generates a ``buildout.cfg`` with an ``extends`` directive
+ pointing to the most recent release versions file. It determines the URL
+ to this versions file by reading http://grok.zope.org/releaseinfo/current.
+ This file needs to be updated to point to the uploaded ``*.cfg`` file for
+ the official "final" releases.
+
+2. Add a document with the release announcement in the `releases folder`_
+ Name it after the release version number. Summarize what is in
+ ``CHANGES.txt``. Make sure you move it to become the first item of the
+ releases folder. You can move it up by using the contents view of the
+ folder. The last column in that table presents a handle by which you can
+ drag up the document in the folder.
+
+ .. _`releases folder`: http://grok.zope.org/project/releases/
+
+3. Official Documentation: Create a build of the docs from the tagged
+ release and copy it to the server. Detailed steps are documented in the
+ `Updating the Official Grok Documentation (OGD)`_ page.
+
+4. Create a news item in the `blog folder`_ announcing the news. The text
+ can be based on the release notes written at point 7.
+
+ .. _`blog folder`: http://grok.zope.org/blog/
+
+5. Make both the new release notes, the new news item, as well as the
+ updated upgrade notes public.
+
+6. Update the sidebar in the site. You can edit it here::
+
+ http://grok.zope.org/portal_skins/custom/portlet_download/manage_main
+
+7. Community Documentation: Update the Plone Help Center used for Grok
+ Community Documentation so that the new Version is available. Important: you
+ can select multiple "current" versions for community documentation, any
+ documentation for a release which is not "current" gets a big nasty
+ "outdated" header at the top of it. We only want to do this for
+ documentation which is truly outdated and no longer best practice. Do this
+ here: http://grok.zope.org/documentation/edit
+
+8. Send out an email to at least zope-announce at zope.org as well as grok-
+ dev at zope.org announcing the new release. The text can be based on the
+ release notes written at step 2.
+
+9. Update the Grok Wikipedia article with the information about the latest
+ release: http://en.wikipedia.org/wiki/Grok_(web_framework)
+
+.. _`Updating the Official Grok Documentation (OGD)`: http://grok.zope.org/project/meta/updating-the-official-grok-documentation-ogd
+
+Binary eggs on Windows
+----------------------
+
+Grok aims to work on Windows as well. This is not a problem for the most part,
+but takes special attention when updating the list of dependencies. The follow
+eggs need a compiler on Unixy platforms, and a binary egg on Windows::
+
+ zope.i18nmessageid
+ zope.interface
+ zope.security
+ zope.container
+ ZODB3
+ zope.hookable
+ zope.proxy
+
+Please make sure a Windows version of the egg is available when you update a
+dependency!
Added: groktoolkit/branches/jw-documentation-rearangement/doc/docindex.template
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/docindex.template (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/docindex.template 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,87 @@
+{% extends "layout.html" %}
+{% set title = 'Overview' %}
+{% block body %}
+
+ <h1>{{ docstitle }}</h1>
+ <p>
+ This is official documentation for Grok {{ release }}.
+ {% if last_updated %}Last modifed on {{ last_updated }}.{% endif %}
+ </p>
+
+ <p><strong>Sections</strong></p>
+ <table class="contentstable" align="center"><tr>
+ <td width="50%">
+ <p class="biglink"><a class="biglink" href="{{ pathto("tutorial") }}"
+ >Grok Tutorial</a><br>
+ <span class="linkdescr">Get started with Grok.</span></p>
+
+ <p class="biglink"><a class="biglink" href="{{ pathto("reference/index") }}">The Grok Reference</a><br>
+ <span class="linkdescr">Describes syntax and package elements.</span></p>
+
+ <p class="biglink"><a class="biglink" href="{{ pathto("grok_overview") }}"
+ >Grok Developer Notes</a><br>
+ <span class="linkdescr">Overview of what's in Grok and how to use it.</span></p>
+
+ <p class="biglink"><a class="biglink" href="{{ pathto("naming_conventions") }}">Naming Conventions</a><br>
+ <span class="linkdescr">How to name your stuff correctly.</span></p>
+
+ </td><td width="50%">
+ <p class="biglink"><a class="biglink" href="{{ pathto("changes") }}"
+ >What's new in Grok?</a><br>
+ <span class="linkdescr">Changes made in each Grok release.</span></p>
+
+ <p class="biglink"><a class="biglink" href="{{ pathto("upgrade") }}"
+ >Upgrading notes</a><br>
+ <span class="linkdescr">How to upgrade your project to a new version of the Grok Toolkit.</span></p>
+
+ <p class="biglink"><a class="biglink" href="{{ pathto("developing_grok") }}">Developing Grok</a><br>
+ <span class="linkdescr">Notes for developers <strong>of</strong> Grok.</span></p>
+
+ </td></tr>
+ </table>
+
+ <p><strong>Indices and tables</strong></p>
+ <table class="contentstable" align="center"><tr>
+ <td width="50%">
+ <p class="biglink"><a class="biglink" href="{{ pathto("contents") }}">Table of Contents</a><br>
+ <span class="linkdescr">Lists all sections and subsections.</span></p>
+<!--
+ <p class="biglink"><a class="biglink" href="{{ pathto("search") }}">Search page</a><br>
+ <span class="linkdescr">search this documentation</span></p>
+-->
+ </td><td width="50%">
+ <p class="biglink"><a class="biglink" href="{{ pathto("genindex") }}">Index</a><br>
+ <span class="linkdescr">All functions, classes, terms.</span></p>
+ </td></tr>
+ </table>
+
+ <p><strong>Further information</strong></p>
+ <table class="contentstable" align="center"><tr>
+ <td width="50%">
+
+ <p class="biglink"><a class="biglink" href="{{ pathto("bugs") }}"
+ >Reporting bugs</a><br>
+
+ <p class="biglink"><a class="biglink" href="{{ pathto("README") }}"
+ >About the documentation</a><br>
+
+ </td><td width="50%">
+
+ <p class="biglink"><a class="biglink" href="{{ pathto("license") }}"
+ >License</a><br>
+
+ <p class="biglink"><a class="biglink" href="{{ pathto("copyright") }}"
+ >Copyright</a><br>
+
+ </td></tr>
+ </table>
+
+ <p>
+ The <b>Official Grok Documentation</b> documents the core features of the
+ Grok framework. For further reading, the
+ <a href="http://grok.zope.org/documentation/">Community Grok Documentation</a>
+ contains deeper information on working with Grok, as well as using
+ additional packages with Grok that are not part of the core framework.
+ </p>
+
+{% endblock %}
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/glossary.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/glossary.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/glossary.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,99 @@
+=================
+Grok Glossary
+=================
+
+* **adapter** -
+ An Adapter takes an object providing an existing interface and extends it to
+ provide a new interface.
+
+* **(Grok) application** -
+ Applications are top-level objects. They are typically used to hold global
+ configuration and behaviour for an application instance, as well as holding
+ data objects such as grok.Container and grok.Model object instances.
+
+* **buildout** -
+ ...
+
+* **buildout egg** -
+ ...
+
+* **(Grok) container** -
+ Objects in a container are manipulated using the same syntax as you would with
+ a standard Python Dictionary object. The container implements the
+ zope.app.container.interfaces.IContainer interface using a BTree, providing
+ reasonable performance for large collections of objects.
+
+* **(Grok) directive** -
+ The grok module defines a set of directives that allow you to configure and
+ register your components.
+
+* **directory resource** -
+ ...
+
+* **egg** -
+ ...
+
+* **global utility** -
+ A global utility is an object which provides an interface, and can be
+ looked-up by that interface and optionally the component name. The attributes
+ provided by a global utility are not persistent.
+
+* **grokproject** -
+ A command line tool for creating a Grok project using buildout.
+
+* **layer** -
+ A layer for the view.
+
+* **local utility** -
+ A local utility is an object which provides an interface, and can be looked-up
+ by that interface and optionally the component name. The attributes provided
+ by a local utility are transparently stored in the database (ZODB). This means
+ that configuration changes to a local utility lasts between server restarts.
+
+* **martian** -
+ ...
+
+* **megrok** -
+ ...
+
+* **(Grok) model** -
+ Model objects provide persistence and containment. Model in Grok refers to an
+ applications data model - that is data which is persistently saved to disk, by
+ default in the Zope Object Dataabse (ZODB).
+
+* **Python Cheeseshop** -
+ ...
+
+* **(Grok) site** -
+ Contains a Site Manager. Site Managers act as containers for registerable
+ components.
+
+* **skin** -
+ A named layer.
+
+* **(Grok) view** -
+ Views handle interactions between the user and the model.
+
+* **viewlet** -
+ Viewlets are a flexible way to compound HTML snippets.
+
+* **viewlet manager** -
+ A ViewletManager is a component that provides access to a set of content
+ providers (Viewlets).
+
+* **zc.buildout** -
+ see buildout
+
+* **zc.resourcelibrary** -
+ ...
+
+* **ZCML** -
+ Zope Configuration Markup Language
+
+* **ZODB** -
+ Zope Object Database
+
+* **ZPT** -
+ Zope Page Template
+
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/grok_overview.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/grok_overview.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/grok_overview.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,1374 @@
+Grok Developer's Notes
+======================
+
+This document is a developer's overview of Grok. It is not intended to
+be a beginner's tutorial. It's also not a reference. It gives a
+succinct an overview of *what's there* in Grok, with a brief idea on
+how to use it, so you can try it out and learn more about it. This
+includes rules, common APIs and patterns.
+
+Models
+------
+
+A Grok-based application is composed out of one or more *models*. We
+also call these *content objects*, or just *objects*. The objects are
+just Python objects, instantiated from a class. Models can be stored
+in the object database (ZODB), created by an object relational mapper,
+or created on the fly by your code.
+
+Grok comes with two kinds of models: ``grok.Model`` and
+``grok.Container``. ``grok.Model`` is the most basic one and doesn't
+really do much for you. You can subclass from ``grok.Model``, like
+this::
+
+ class Document(grok.Model):
+ pass
+
+The main thing subclassing from ``grok.Model`` does is make it
+possible (but not required) to store instances in the ZODB.
+
+You can also subclass from ``grok.Container``, like this::
+
+ class Folder(grok.Container):
+ pass
+
+A container is like a model, but also acts much like a Python
+dictionary. The main difference with Python dictionaries is that its
+methods, like ``keys`` and ``items``, are iterator-like. They also do
+more, like send events, but we can forget about that for now.
+
+In order to be able to install an application, you need to mix in
+``grok.Application`` into a class::
+
+ class Application(grok.Application, grok.Container):
+ pass
+
+Instances of this class can now be installable in the Grok web UI.
+
+Let's make a structure with some folders and documents::
+
+ app = Application()
+ app['a'] = a = Container()
+ a['b'] = Document()
+ a['c'] = Container()
+ a['c']['d'] = Document()
+
+Grok publishes these objects to the web: this is called object
+publishing. What this means in essence is that objects can be
+addressed with URLs. When you access a URL of a Grok application with
+your web browser, Grok uses this URL to find an object.
+
+An example: if ``app`` were installed under
+``http://localhost:8080/app``, the following URLs will exist in your
+application::
+
+ http://localhost:8080/app
+ http://localhost:8080/app/a
+ http://localhost:8080/app/a/b
+ http://localhost:8080/app/a/c
+ http://localhost:8080/app/a/c/d
+
+``__parent__`` and ``__name__``
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Models in Grok are automatically supplied with a ``__parent__`` and a
+``__name__`` attribute.
+
+* ``__parent__`` points to object this object is in. If the object is in
+ a container, this is the container.
+
+* ``__name__`` is the name this object has in a URL (and in its
+ container, if it is in a container).
+
+These attributes are used for navigation through content space, and
+Grok also uses them to construct URLs automatically (see below). The
+``__parent__`` and ``__name__`` attributes are automatically added to
+an object when it is placed in a container, or when it is being
+traversed through using ``traverse``.
+
+Custom traversing
+~~~~~~~~~~~~~~~~~
+
+Grok resolves URLs to objects by *traversing* through the containers
+and models in question. What if you want to customize the way this
+traversal works? Perhaps you want to traverse through objects you
+create yourself, or objects created by an object relational
+mapper. Grok offers a handy way to do so: the ``traverse`` method on
+models.
+
+A math example: imagine you want to create an application that
+represents integer numbers, and you want to traverse to each
+individual number, like this::
+
+ http://localhost:8080/integers/0
+ http://localhost:8080/integers/1
+ http://localhost:8080/integers/2
+ http://localhost:8080/integers/3
+ ...
+
+and so on. How would we implement this? We cannot create a container
+and fill it with all integers possible, as there are an infinite
+number of them. Okay, so we are in a math example, so let's be exact:
+this is true if we ignore memory limitations and URL length
+limitations. Storing all possible integers in a container is just not
+*practical*.
+
+We use the ``traverse`` method::
+
+ class ParticularInteger(grok.Model):
+ def __init__(self, number):
+ self.number = number
+
+ class Integers(grok.Application, grok.Model):
+ def traverse(self, name):
+ try:
+ value = int(name)
+ except ValueError:
+ return None # not an integer
+ return ParticularInteger(value)
+
+Now all URLs for numbers are available. What's more, other URLs like
+this are not::
+
+ http://localhost:8080/integers/foo
+
+The ``traverse`` method works by trying to convert the path element
+that comes in as ``name`` to an integer. If it fails, we return
+``None``, telling Grok that the ``traverse()`` method didn't find the
+object asked for. Grok then falls back on default behavior, which in
+this case would mean a ``404 Not Found`` error.
+
+Traversable attributes
+~~~~~~~~~~~~~~~~~~~~~~
+
+In some cases, you want to traverse to attributes or methods of your
+``grok.Model``. This can be done easily using the ``grok.traversable``
+directive::
+
+ class Mammoth(grok.Model):
+ grok.traversable('trunk')
+
+ trunk = Trunk()
+
+ class MammothView(grok.View):
+ grok.context(Mammoth)
+
+ def render(self):
+ return "I'm a mammoth!"
+
+Now, if traversing to http://localhost/mammoth/trunk , a Trunk()
+object will be exposed at that URL.
+
+Views
+-----
+
+Now that we have models and can build structures of them, we will need
+to look at ways to actually present them to the user: views. So what
+is a view? A view is a class that represents a model in some way. It
+creates a user interface of some sort (typically HTML) for a model. A
+single model can have more than one view. It looks like this::
+
+ class Index(grok.View):
+ grok.context(Application)
+
+ def render(self):
+ return "This is the application"
+
+The ``grok.context`` bit in the class is an example of using a *Grok
+directive*. If you use ``grok.context`` on a view class, it connects
+the view to the class we give it. So in this case, ``Index`` is a view
+for ``Application``. Note that if there is only a single model in the
+module and you want your view to be associated with it, you can leave
+out ``grok.context`` and the view will be associated with that model
+by default. Many directives have such default behavior, allowing you
+to leave them out of your code if you organize your code in a certain
+way.
+
+The default view for a model is called ``index``. You can specify
+``index`` at the end of the URL, like this::
+
+ http://localhost:8080/app/index
+
+What happens when you go to this URL is that Grok instantiates the
+``Index`` class, creating a ``Index`` instance. View instances have
+a number of attributes by default:
+
+ * ``context``, the model instance that the view is presenting.
+
+ * ``request``, the current web request.
+
+ * ``response``, an object representing the response sent to the
+ user. Used less often.
+
+``index`` views are special, as it's also fine not to add ``index`` at
+the end, because the name ``index`` is the default::
+
+ http://localhost:8080/app
+
+You can also create views with different names::
+
+ class Edit(grok.View):
+ grok.context(Application)
+
+ def render(self):
+ return "This is the edit screen for the application"
+
+Now you can go to this URL::
+
+ http://localhost:8080/app/edit
+
+The name of the view is the name of the view class, lowercased. This
+is the default behavior: you can override this using the ``grok.name``
+directive::
+
+ class SomeImpossiblyLongClassName(grok.View):
+ grok.context(Application)
+ grok.name('edit')
+
+ def render(self):
+ return "This is the edit screen for the application"
+
+Templates
+~~~~~~~~~
+
+In the previous examples, we used the ``render`` method to determine
+what you actually see on a web page. For most views we don't want to
+do that: we want to use a template to prepare presentation. Using a
+template with a view is easy. First create a directory
+``<name>_templates``, where ``<name>`` is the the module that contains
+the views. So, if you are developing in a module ``app.py``, you need
+to create a subdirectory ``app_templates`` for templates in the same
+directory as the ``app.py`` module.
+
+You can then add templates to that directory with the same name as the
+view class name (lowercase), with the ``.pt`` extension
+appended. These templates follow the Zope Page Template (ZPT) rules,
+though Grok can also be extended to support other template languages.
+
+You could for instance have this view::
+
+ class Index(grok.View):
+ grok.context(Application)
+
+and a file ``index.pt`` in the module's templates directory containing
+template code.
+
+These are the defaults. If for some reason you want the name of the
+template directory not to be based on the name of module, you can
+manually set the name of the template directory used by a module by
+using the ``grok.templatedir`` directive in the module. If you want
+the name of the template not to be based on the name of the class, you
+use the ``grok.template`` directive in the view class.
+
+The template can access attributes and methods on the view through the
+special ``view`` name available in the template. The template can
+access attributes and methods on the model through the special
+``context`` name available in the template. The template has the
+following special names available::
+
+* ``view`` - the view that this template is associated with
+
+* ``context`` - the model that is being viewed
+
+* ``request`` - the current request object
+
+* ``static`` - to make URLs to static content made available by this module
+
+and any names you also make available using the ``namespace`` method.
+
+static content
+~~~~~~~~~~~~~~
+
+A typical web page references one or more CSS files, javascript files
+and images: static content that is part of the layout.
+
+To make available static content to your template create a directory
+in your package called ``static``. Put ``.css`` files, ``.js`` files,
+image and whatever else is needed in there.
+
+You can now refer to these static files in your template using the
+special name ``static``, like this (ZPT example)::
+
+ <img tal:attributes="src static/my_image.png" />
+
+This will automatically create a URL to the place where Grok published
+that image.
+
+You can create subdirectories in ``static`` and refer to them as you'd
+expect::
+
+ <image tal:attributes="src static/images/some_image.gif" />
+
+``update``
+~~~~~~~~~~
+
+You can define an ``update`` method in a view to prepare a view just
+before it is accessed. You can use this to process information in the
+request (URL parameters or form variables) or in the context, and set
+attributes on the view that can be used in the template::
+
+ def update(self):
+ self.total = int(self.request.form['a']) + int(self.request.form['b'])
+
+The template now has access to ``view.total``.
+
+You can define parameters in the update view. These will be
+automatically bound to parameters (or form values) in the request::
+
+ def update(self, a, b):
+ self.total = int(a) + int(b)
+
+``namespace``
+~~~~~~~~~~~~~
+
+If you just want a variable to become available in the top-level of
+your template (much like ``view`` and ``model``), you can also define
+the ``namespace`` method on the view::
+
+ def namespace(self):
+ return {'foo': "Some value"}
+
+You can now refer to ``foo`` in your template and have available to
+this value.
+
+the ``url`` method
+~~~~~~~~~~~~~~~~~~
+
+Views have a special method called ``url()`` that can be used to
+create URLs to objects. The ``url`` method takes zero, one or two
+arguments and an additional optional keyword argument 'data' that
+is converted into a CGI query string appended to the URL::
+
+* self.url() - URL to this view.
+
+* self.url(object) - URL to the provided object.
+
+* self.url(u"name") - URL to the context object, with ``/name`` appended,
+ to point to a view or subobject of the context.
+
+* self.url(object, u"name") - URL to the provided object, with
+ ``/name`` appended, to point to a view or subobject
+ of the provided object.
+
+* self.url(object, u"name", data={'name':'Peter', 'age':28})
+ - URL to the provided object, with ``/name`` appended
+ with '?name=Peter&age=28' at the end.
+
+* self.url(data={'name':u'Andr\xe9', 'age:int':28}) - URL to the provided
+ object with '?name=Andre%C3%A9'&age%3Aint=28'.
+
+From the view, this is accessed through ``self.url()``. From the
+template, this method can be accessed using ``view.url()``.
+
+the ``application_url`` method
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+When using views it is sometimes desirable to be able to construct a
+URL to the application object. ``application_url`` is a quick way to
+do it. It takes a single optional argument, name, which is the name
+of a view of the application.
+
+the ``redirect`` method
+~~~~~~~~~~~~~~~~~~~~~~~
+
+The ``redirect`` method on views can be used to redirect the browser
+to another URL. Example::
+
+ def render(self):
+ self.redirect(self.url(self.context.__parent__))
+ # return empty body as we are going to redirect anyway
+ return ''
+
+``__parent__`` and ``__name__`` on views
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Like models, views also get supplied with a ``__parent__`` and
+``__name__`` object when they are instantiated for a particular model.
+
+``__parent__`` points to the model being viewed (and is the same as
+``context``, which should normally be used).
+
+``__name__`` is the name of the view in the URL.
+
+The ``@@`` thing
+~~~~~~~~~~~~~~~~
+
+Supposing you have a view called ``edit``, whenever you write this::
+
+ http://localhost:8080/app/edit
+
+you can also write this::
+
+ http://localhost:8080/app/@@edit
+
+Why the ugly ``@@`` syntax? Imagine that ``app`` is a container, and
+that your user interface lets the user add objects to it with a name
+of their own choosing. The user could decide to add an object called
+``index``. In that case Grok wouldn't know whether the
+``http://localhost:8080/app/index`` index is to get to a view or a
+subobject. ``@@`` tells the system to look up a view definitely. If
+``@@`` is not provided, subobjects take precedence over views in case
+of name collision.
+
+Request
+-------
+
+Some useful things to know about the request object (accessible as an
+attribute on the view):
+
+Information on the ``request`` object can be accessed using mapping
+access (``request[`foo`]``). You can access request form variables and
+cookies and headers (including `environment variables`_).
+
+.. _`environment variables`: http://hoohoo.ncsa.uiuc.edu/cgi/env.html
+
+To access form variables in particular use: ``request.form['foo']``.
+
+To access cookies in particular use: ``request.cookies['foo']``.
+
+To access headers (and environment variables) in particular use:
+``request.headers['foo']``. You can also use ``request.getHeader()``,
+with the header name as the argument, and an optional second default
+argument.
+
+Instead of the mapping access, the ``get`` methods work as well, as on
+normal Python dictionaries.
+
+More can be found in the ``IHTTPRequest`` interface documentation
+in ``zope.publisher.interfaces.http``.
+
+Response
+--------
+
+Some useful things to know about the response object (accessible as
+an attribute on the view):
+
+``setStatus(name, reason)`` sets the HTTP status code. The argument
+may either be an integer representing the status code (such as ``200``
+or ``400``), or a string (``OK``, ``NotFound``). The optional second
+argument can be be used to pass the human-readable representation
+(``Not Found``).
+
+``setHeader(name, value)`` can be used to set HTTP response headers. The first
+argument is the header name, the second the value.
+
+``addHeader(name, value)`` can be used to add a HTTP header, while
+retaining any previously set headers with the same name.
+
+``setCookie(name, value, **kw)`` can be used to set a cookie. The first
+argument is the cookie name, the second the value. Optional keyword
+arguments can be used to set up further cookie properties (such as
+``max_age`` and ``expires``).
+
+``expireCookie(name, **kw)`` can be used to immediately expire a
+cookie.
+
+More can be found in the ``IHTTPResponse`` interface documentation
+in ``zope.publisher.interfaces.http``.
+
+Adapters
+--------
+
+An adapter is much like a view, but is aimed towards developers, not
+end users. It presents an interface to an object, but an interface for
+developers, not an user interface for end-users.
+
+The section on adapters will of necessity be rather abstract. Feel
+free to skip it until you want to know what is going on up with
+interfaces and adapters - it is an important foundation to Grok, but one
+you do not know much about when you get started.
+
+An adapter can be used to add new methods to an object without
+changing the object. To demonstrate the principle, we will construct
+adapters entirely by hand first. At the end we will show how Groks
+helps in constructing adapters and using them.
+
+Imagine we are developing a content management system and we want to
+get information about the size (in, say, bytes, approximately) of
+content objects stored in our CMS, for instance in order to display it
+in our UI or to calculate the total size of all objects in a
+container. The simplest approach would be to add a ``size()`` method
+to all our content objects::
+
+ class Document(grok.Model):
+ def __init__(self, text):
+ self.text = text
+
+ def size(self):
+ return len(self.text.encode('UTF-8'))
+
+ class Image(grok.Model):
+ def __init__(self, data):
+ self.data = data
+
+ def size(self):
+ return len(self.data)
+
+ class Container(grok.Container):
+ def size(self):
+ total = 0
+ for obj in self.values():
+ total += obj.size()
+ return total
+
+For simple cases this is fine, but for larger applications this can
+become a problem. Our ``Document`` model needs a ``size`` method, and
+does our ``Image`` model, and our ``Container``, and our ``News Item``
+model, and so on. Given the requirements of a typical CMS, content
+objects would soon end up with a very large number of methods, for all
+sorts of functionality, from getting the size of objects to offering a
+commenting facility. It would be nicer to separate things out and keep
+the underlying models clean.
+
+To do this, we can use the adaptation pattern. As said, we will do it
+by hand at first. An adapter is an object that adds an API to another
+object (typically stored as the ``context`` attribute of the
+adapter)::
+
+ class DocumentSized(object):
+ def __init__(self, context):
+ self.context = context
+
+ def size(self):
+ return len(self.context.text.encode('UTF-8'))
+
+We would use it like this::
+
+ DocumentSized(document).size()
+
+We could extend this same adapter to work for different kinds of
+content objects, but that isn't very extensible when new adapters need
+to be made::
+
+ class Sized(object):
+ def __init__(self, context):
+ self.context = context
+
+ def size(self):
+ if isinstance(self.context, Document):
+ return len(self.context.text.encode('UTF-8'))
+ elif isinstance(self.context, Image):
+ return len(self.context.data)
+ elif isintance(self.context, Container):
+ total = 0
+ for obj in self.context.values():
+ total += Sized(obj).size()
+ return total
+
+Instead, we can create a smart ``sized`` factory that does this
+switch-on-type behavior instead, keeping our adapters clean::
+
+ class DocumentSized(object):
+ def __init__(self, context):
+ self.context = context
+
+ def size(self):
+ return len(self.context.text.encode('UTF-8'))
+
+ class ImageSized(object):
+ def __init__(self, context):
+ self.context = context
+
+ def size(self):
+ return len(self.context.data)
+
+ class ContainerSized(object):
+ def __init__(self, context):
+ self.context = context
+
+ def size(self):
+ total = 0
+ for obj in self.context.values():
+ total += sized(obj).size()
+ return total
+
+ def sized(context):
+ if isinstance(context, Document):
+ return DocumentedSized(context)
+ elif isinstance(context, Image):
+ return ImageSized(context)
+ elif isinstance(context, Container):
+ return ContainerSized(context)
+
+We can now call ``sized`` for a content object and get an object back
+that implements the "sized API"::
+
+ s = sized(my_content_object)
+ print s.size()
+
+It's good to spell out the APIs of your application explicitly, as
+documentation so that other developers can work with them and also
+implement them for their own content objects. Grok lets you do this
+using an *interface* specification, using the ``zope.interface``
+package::
+
+ from zope.interface import Interface
+
+ class ISized(Interface):
+ def size():
+ "Return the size of the object"
+
+We can now make this ``ISized`` interface into the adapter factory
+(like ``sized`` above), without actually having to implement it
+directly. Let's do that now by subclassing from ``grok.Adapter`` and
+using a few grok directives::
+
+ class DocumentSized(grok.Adapter):
+ grok.context(Document)
+ grok.provides(ISized)
+
+ def size(self):
+ return len(self.context.text.encode('UTF-8'))
+
+ class ImageSized(grok.Adapter):
+ grok.context(Image)
+ grok.provides(ISized)
+
+ def size(self):
+ return len(self.context.data)
+
+ class ContainerSized(grok.Adapter):
+ grok.context(Container)
+ grok.provides(ISized)
+
+ def size(self):
+ total = 0
+ for obj in self.context.values():
+ total += ISized(obj).size()
+ return total
+
+We can now use ``ISized`` like we used ``sized`` above::
+
+ s = ISized(my_content_object)
+ print s.size()
+
+When new content objects were to be created for this CMS, ``ISized``
+adapters can be registered for them anywhere. Using this pattern,
+existing objects implemented by someone else can be made to conform
+with the ``ISized`` API without having to modify them.
+
+``grok.context`` works as for views. It is useful to point it to any
+class however, not just that of models. ``grok.provides`` has to be
+pointed to an interface (the interface that the adapter *adapts to*).
+
+Interfaces
+~~~~~~~~~~
+
+Classes can also be made to *implement* an interface. This means that
+instances of that class *provide* that interface::
+
+ from zope.interface import Interface, Attribute
+
+ class IAnimal(Interface):
+ name = Attribute("The name of the animal")
+
+ def makeSound():
+ "The sound the animal makes."
+
+ class Cow(object):
+ grok.implements(IAnimal)
+
+ def __init__(self, name):
+ self.name = name
+
+ def makeSound(self):
+ return "Mooo"
+
+We can ask the interface machinery whether an object provides an interface::
+
+ >>> cow = Cow()
+ >>> IAnimal.providedBy(cow)
+ True
+
+If you use an interface to adapt an object, and this object already
+provides the interface, you get back the object itself::
+
+ >>> IAnimal(cow) is cow
+ True
+
+``grok.context`` can always point to an interface instead of a class
+directly. This indirection can be useful to make a view or adapter
+work for a whole set of classes that all implement the same interface.
+
+``ComponentLookupError``
+~~~~~~~~~~~~~~~~~~~~~~~~
+
+What if an adapter cannot be found for a particular object? Perhaps no
+adapter has been registered for a particular object or a particular
+interface. The system will raise a ``ComponentLookupError``::
+
+ >>> ISized(cow)
+ Traceback (most recent call last):
+ ...
+ ComponentLookupError
+
+If you want to catch this exception, you can import it from
+``zope.component.interfaces``::
+
+ from zope.component.interfaces import ComponentLookupError
+
+Named adapters
+~~~~~~~~~~~~~~
+
+It is possible to give an adapter a name, making it a *named
+adapter*. This way it is possible to have more than one adapter
+registered for a single object that all provide the same interface,
+each with a different name. This feature is rarely used directly,
+but internally it is used for views, as we will see later. The
+``grok.name()`` directive can be used to give an adapter a name::
+
+ class Adapter(object):
+ grok.name('somename')
+ grok.context(SomeClass)
+ grok.provides(ISomeInterface)
+
+Actually all adapters are named: by default the name of an adapter is
+the empty string.
+
+You cannot call the interface directly to get a named adapter for an
+object. Instead, you need to use the APIs provided by the
+``zope.component`` package, in particular ``getAdapter``::
+
+ from zope import component
+
+ my_adapter = component.getAdapter(some_object, ISomeInterface,
+ name='somename')
+
+``getAdapter`` can also be used to look up unnamed adapters, as an
+alternative to using the interface directly::
+
+ myadapter = component.getAdapter(some_object, ISomeInterface)
+
+Functions as adapters
+~~~~~~~~~~~~~~~~~~~~~
+
+Sometimes an adapter doesn't need to be a full-fledged class;
+registering the factory function itself is enough. We can do this with
+the ``@grok.adapter`` and ``@grok.implementer`` decorators. This way
+we can write simple adapters that don't need to return a full-fledged
+custom class instance but for instance some built-in Python object
+like a string::
+
+ @grok.adapter(SomeClass)
+ @grok.implementer(ISomeInterface)
+ def some_interface_for_some_class(some_instance):
+ return str(some_instance)
+
+You can now do the following::
+
+ some_instance = SomeClass()
+ s = ISomeInterface(some_instance)
+ print s
+
+``ISomeInterface`` now behaves much like ``str`` for ``SomeClass``.
+
+Multi adapters
+~~~~~~~~~~~~~~
+
+Another feature of adapters is that you can adapt multiple objects at
+once using a *multi adapter*. Again this feature is rarely used in
+practice, except internally to implement views and events.
+
+You can construct a multi adapter by subclassing from
+``grok.MultiAdapter``::
+
+ class MyMultiAdapter(grok.MultiAdapter):
+ grok.adapts(SomeClass, AnotherClass)
+ grok.provides(ISomeInterface)
+
+ def __init__(some_instance, another_instance):
+ self.some_interface = some_instance
+ self.another_instance = another_instance
+
+The multi-adapter receives as many arguments as what it was registered
+for using ``grok.adapts``.
+
+A multi adapter also cannot be looked up directly by calling the
+interface. Instead, we need to use the ``zope.component`` package
+again::
+
+ from zope import component
+
+ my_multi_adapter = component.getMultiAdapter((some_object, another_object),
+ ISomeInterface)
+
+``getMultiAdapter`` receives as the first argument a tuple with the
+combination of objects to adapt.
+
+It can also optionally be named using ``grok.name`` and then looked up
+using a name argument::
+
+ my_named_multi_adapter = component.getMultiAdapter(
+ (some_object, another_object), ISomeInterface, name="foo")
+
+Views as adapters
+~~~~~~~~~~~~~~~~~
+
+A view in Grok is in fact a named multi adapter, providing the base
+interface (``Interface``). This means that a view in Grok can be
+looked up in code by the following call::
+
+ from zope.interface import Interface
+
+ view = component.getMultiAdapter((object, request), Interface, name="index")
+
+Since the default for the second argument is in fact ``Interface``, this
+call can be shorted to this::
+
+ view = component.getMultiAdapter((object, request), name="index")
+
+Being able to do this in code is sometimes useful. It is also what
+Grok does internally when it looks up a view.
+
+Events
+------
+
+Grok lets you write handlers for *events*. Using event handlers you
+can hook into code that you do not control. Events allow decoupling: a
+framework can send events without worrying who is interested in it,
+and similarly you can send events to work with existing bits of
+framework that expects them. You can also define new types of events
+if you are designing a framework yourself.
+
+You write an event handler by writing a function that *subscribes* to
+the event, and marking it with a python decorator::
+
+ @grok.subscribe(Document, grok.IObjectAddedEvent)
+ def handle(obj, event):
+ print "Object %s was added." % obj
+
+Whenever an instance of a model of class ``Document`` (or subclasses)
+is added to a container, this code will be run. You can then take some
+action. Any ``grok.Container`` subclass will take care of sending
+these events automatically. You can have as many subscribers for a
+particular event as you like. The order in which they are run is not
+guaranteed by the system, so cannot be relied on.
+
+The event handler takes two arguments: the object for which the event
+was fired, and the event instance. The event instance has attributes,
+depending on the type of event.
+
+Events defined by Grok
+~~~~~~~~~~~~~~~~~~~~~~
+
+Here we describe the standard events defined by Grok. Described are
+the interfaces which you would use in a subscriber, and how you can
+send this event yourself. Other events may be defined by libraries or
+by you.
+
+``IObjectMovedEvent``
++++++++++++++++++++++
+
+Will be fired whenever an object is moved from container to container,
+renamed, added or removed.
+
+The event object has these attributes:
+
+* ``object`` - the object being moved
+
+* ``oldParent`` - the parent (container) from which the object was moved
+ or removed, or ``None`` if this object is newly added.
+
+* ``oldName`` - the previous name of the object in its container,
+ before renaming if renaming took place, or ``None`` if
+ this object is newly added.
+
+* ``newParent`` - the parent (container) to this object was moved or
+ added. ``None`` if this object was removed.
+
+* ``newName`` - the name the object has in the new container, or ``None``
+ if this object was removed.
+
+Containers take care of sending this event, but should you want to
+send it yourself, use::
+
+ grok.notify(grok.ObjectMovedEvent(obj, oldParent, oldName, newParent, newName))
+
+``IObjectAddedEvent``
++++++++++++++++++++++
+
+Fired when an object is added to a container. Specialization of
+``IObjectMovedEvent``, and shares the attributes as described.
+
+Containers take care of sending this event, but should you want to send it
+yourself, use::
+
+ grok.notify(grok.ObjectAddedEvent(obj))
+
+or::
+
+ grok.notify(grok.ObjectAddedEvent(obj, newParent, newName))
+
+``IObjectRemovedEvent``
++++++++++++++++++++++++
+
+Fired when an object is removed from a container (and not re-added
+elsewhere). Specialization of ``IObjectMovedEvent``, and shares the
+attributes as described.
+
+Containers take care of sending this event, but should you want to send it
+yourself, use::
+
+ grok.notify(grok.ObjectRemovedEvent(obj)
+
+or::
+
+ grok.notify(grok.ObjectRemovedEvent(obj, oldparent, oldName))
+
+``IObjectModifiedEvent``
+++++++++++++++++++++++++
+
+Fired when an object is modified by the system, such as when a form is
+saved. If you modify the object in code, the system won't know about
+this, and you will have to remember to send it yourself.
+
+This event has a single attribute, ``object``, which is the object
+that was modified.
+
+To send this event yourself, use::
+
+ grok.notify(grok.ObjectModifiedEvent(obj))
+
+``IContainerModifiedEvent``
++++++++++++++++++++++++++++
+
+A specialization of ``IObjectModifiedEvent`` that fires when the
+container was modified by adding something to it or removing from it.
+
+Containers take care of sending this event, but if you want to send it
+yourself, use::
+
+ grok.notify(grok.ContainerModifiedEvent(obj))
+
+``IObjectCreatedEvent``
++++++++++++++++++++++++
+
+Fired when an object is created. When you create your own objects the
+system won't know about this, and you will have to remember to send it
+yourself if you care about listing to ``IObjectCreatedEvent``. This is
+fairly rare - usually you're better of looking at
+``IObjectAddedEvent`` if you can.
+
+This event has a single attribute, ``object``, which is the object
+that was created.
+
+To send this event yourself::
+
+ grok.notify(grok.ObjectCreatedEvent(obj))
+
+``IObjectCopiedEvent``
+++++++++++++++++++++++
+
+Fired when an object was copied. It is a specialization of
+``IObjectCreatedEvent`` that is fired by the system if you use the
+``zope.copypastemove`` functionality.
+
+Besides the ``object`` attribute it shares with
+``IObjectCreattedEvent``, it has also has the ``original`` attribute,
+which was the object that iwas copied from.
+
+To send this event yourself::
+
+ grok.notify(grok.ObjectCopiedEvent(copy, original))
+
+``IBeforeTraverseEvent``
++++++++++++++++++++++++++
+
+Fired when the publisher is about to traverse into your object. This
+is useful to specify on your application object if you for instance
+want to set the default skin for your application.
+
+Creating and sending your own events
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+If you are going to send an object that pertains to a particular object,
+subclass ``zope.component.interfaces.ObjectEvent``::
+
+ from zope.component.interfaces import ObjectEvent
+
+ class MyEvent(ObjectEvent):
+ pass
+
+You can then send it like this::
+
+ grok.notify(MyEvent(some_obj))
+
+And listen for it like this::
+
+ @grok.subscribe(SomeClass, MyEvent)
+ def handle_my_event(obj, event):
+ pass
+
+This subclassing from ``ObjectEvent`` is not required; if your event
+isn't about an object, you can choose to design your event class
+entirely yourself. See ``zope.sendmail`` for the construction of mail sending
+events for an example.
+
+Interfaces for events
+~~~~~~~~~~~~~~~~~~~~~
+
+For documentation purposes it can be a good idea to to define an
+interface for your event. You can then also allow for multiple
+implementations of the same event interface. When you have an
+interface for your event, you can then listen for the interface in the
+subscribers as well::
+
+ from zope.interface import Interface
+
+ class IMyEvent(zope.component.interfaces.IObjectEvent):
+ "My special event"
+
+ class MyEvent(zope.component.interfaces.ObjectEvent):
+ grok.implements(IMyEvent)
+
+ @grok.subscribe(SomeClass, IMyEvent):
+ def handle_my_event(obj, event):
+ pass
+
+More about interfaces
+---------------------
+
+We have seen small examples of interfaces before, but here we will go
+a bit more into them, and why they are useful.
+
+An *interface* is a description of the API of a class (or more rarely,
+module or object). Interfaces are useful because:
+
+* They are API documentation.
+
+* They can describe how a framework expects you to implement classes
+ that fit into it.
+
+* The system can inspect the interfaces a particular object provides,
+ and treat them as an abstract form of classes for registration
+ purposes.
+
+Interfaces make it possible to use a generic framework's pluggability
+points with confidence: you can clearly see what you are supposed to
+implement to plug into it. You can define very generic frameworks
+yourself by defining them in terms of interfaces.
+
+Some interface features
+~~~~~~~~~~~~~~~~~~~~~~~
+
+A summary of interface features we've seen:
+
+* To create an interface, subclass from ``zope.interface.Interface``.
+
+* To state that implementors of the interface must have a method, supply
+ the method with arguments. Don't use ``self`` as the first
+ arguments, as this is an implementation detail not important to the
+ interface. Instead, describe the methods as they look to the caller.
+
+* To state that implementors of the interface must have an attribute, use::
+
+ some_attribute = zope.interface.Attribute("Description of attribute")
+
+* To state a class *implements* an interface, use ``grok.implements``.
+
+* Instances of a class are said to *provide* the interface that the
+ class *implements*.
+
+* You can check whether an instance provides a certain interface by using
+ ``some_interface.providedBy``::
+
+ IObjectEvent.providedBy(NonSubclassEvent(some_obj))
+
+Interfaces and events
+~~~~~~~~~~~~~~~~~~~~~
+
+Let's study interfaces some more in connection with
+``IObjectModifiedEvent``. The ``IObjectModifiedEvent`` interface looks
+like this::
+
+ class IObjectModifiedEvent(zope.component.interfaces.IObjectEvent):
+ """An object has been modified"""
+
+This refers us to the ``IObjectEvent`` interface, which looks like
+this::
+
+ from zope import interface
+
+ class IObjectEvent(interface.Interface):
+ """An event related to an object.
+ """
+
+ object = interface.Attribute("The subject of the event.")
+
+We therefore know that if we implement ``IObjectModifiedEvent``, we
+must supply a single attribute, ``object``.
+
+The following event handler for instances of ``SomeClass`` subscribes
+to *any* event that provides ``IModifiedObjectEvent``::
+
+ @grok.subscribe(SomeClass, IObjectModifiedEvent):
+ def handle_event(obj, event):
+ "Called when there is an IObjectModifiedEvent for SomeClass instances."
+
+This handler will be called not only for subclasses of the
+``grok.ObjectModifiedEvent`` class, but also for other, otherwise
+unrelated classes that implement ``IObjectEvent``, such as this one::
+
+ class NonSubclassObjectEvent(object):
+ grok.implements(IObjectEvent)
+
+ def __init__(self, object):
+ self.object = object
+
+So far we have only used interfaces for the second argument of the
+event handler registration, but the principle also works for the first
+argument. For example, to handle ``IObjectModifiedEvent`` events for
+all kinds of containers, you can subscribe to
+``zope.container.interfaces.IContainer`` objects::
+
+ @grok.subscribe(IContainer, IObjectModifiedEvent):
+ def handle_event(obj, event):
+ "Called whenever any container is modified"
+
+``zope.container.interfaces.IContainer`` defines the abstract
+container API that all containers must provide, no matter how they are
+implemented internally.
+
+Interfaces and adapters
+~~~~~~~~~~~~~~~~~~~~~~~
+
+The same principle also works for adapters and ``grok.context``. You
+can use ``grok.context`` with interfaces as well as with concrete
+classes. To write an adapter that works for any kind of container, you
+can write::
+
+ from zope.container.interfaces import IContainer
+
+ class SortedKeysAdapter(grok.Adapter):
+ grok.context(IContainer)
+ grok.provides(ISortedKeys)
+
+ def sortedKeys(self):
+ return sorted(self.context.keys())
+
+Interfaces and views
+~~~~~~~~~~~~~~~~~~~~
+
+The same principle can also be used with ``grok.context`` in other
+places, such as in views. This view is registered for all containers::
+
+ from zope.container.interfaces import IContainer
+
+ class Keys(grok.View):
+ grok.context(IContainer)
+
+ def render(self):
+ return ', '.join(ISortedKeysAdapter(self.context).sortedKeys())
+
+The view ``keys`` exists for all containers, no matter how they are
+implement, where they are implemented or who implemented them, as long
+as they provide ``IContainer``.
+
+Using the fact ``Interface`` is the base of all interfaces, you can
+even register a view for *all* objects. This can be useful to register
+ZPT macros, which will then be available on all contexts::
+
+ class Layout(grok.View):
+ grok.context(Interface)
+
+with a template ``layout.pt`` associated to it.
+
+You can then use these macros in any page template anywhere by
+referring to them like this::
+
+ <html metal:use-macro="context/@@layout/macros/page">
+
+Forms
+-----
+
+Grok can autogenerate web forms from descriptions called *schema*. A
+schema is a special kind of interface. We already saw ``Attribute``,
+which can be used to specify that something that provides that
+interface should have that attribute. The ``zope.schema`` package adds
+a lot more specific field descriptions. Here is an example of a
+schema::
+
+ from zope.interface import Interface
+ from zope import schema
+
+ class ISpecies(Interface):
+ name = schema.TextLine(u"Animal species name")
+ scientific_name = schema.TextLine(u"Scientific name")
+ legs = schema.Int(u"Number of legs")
+
+Let's also look at a simple implementation of this interface::
+
+ class Species(grok.Model):
+ grok.implements(ISpecies)
+
+Note how we aren't even creating an ``__init__`` to set the
+attributes; we could, but we'll see below that Grok's ``applyData``
+can take care of this automatically.
+
+The ``ISpecies`` schema can be turned into a form. Grok does this by
+looking up a *widget* for each schema field to display it. A widget is
+very much like a view. Let's look at a form for this schema::
+
+ class Species(grok.Form):
+ form_fields = grok.Fields(ISpecies)
+
+ @grok.action(u"Save form")
+ def handle_save(self, **data):
+ print data['name']
+ print data['scientific_name']
+ print data['legs']
+
+What is going on here? Firstly we use a special base class called
+``grok.Form``. A form is a special kind of ``grok.View``, and
+associates the same way (using ``grok.context``). A form expects two
+things:
+
+* a ``form_fields`` attribute. Above we see the most common way to construct
+ this attribute, using ``grok.Fields`` on the interface.
+
+* one or more actions. Actions are specified by using the
+ ``@grok.action`` decorator. An action gets the fields filled in the
+ form as keyword parameters, so ``**data`` in this case. We could
+ also have specified the arguments we expected specifically.
+
+Form widgets translate the raw HTML form input to Python objects, such
+as (unicode) strings, integers and datetime objects, as specified by
+schema fields. The schema fields can then be used to validate this
+input further. Forms are self-submitting, and in case of a validation
+error the form can render them in-line next to the fields.
+
+We'll look at a lot of form features next.
+
+``grok.AddForm``
+~~~~~~~~~~~~~~~~
+
+An add form is used to create a new object. Most forms are views of
+the object that they are representing, but an add form is typically
+associated a view of the container in which new objects are to be
+added. Let's look at an example::
+
+ class SpeciesContainer(grok.Container):
+ pass
+
+ class Add(grok.AddForm):
+ grok.context(SpeciesContainer)
+
+ form_fields = grok.Fields(ISpecies)
+
+ @grok.action(u"Add species")
+ def add_species(self, **data):
+ # create a species instance
+ species = Species()
+ # assign the right attributes to fulfill ISpecies schema with
+ # the form data
+ self.applyData(species, **data)
+ # stores the instance into the SpeciesContainer
+ name = data['name']
+ self.context[name] = species
+ # redirect to the newly created object
+ self.redirect(self.url(species))
+ # we don't want to display anything, as we redirect
+ return ''
+
+The user can now go to ``myspeciescontainer/add`` to add a species,
+where ``myspeciescontainer`` is any instance of ``SpeciesContainer``.
+
+``grok.EditForm``
+~~~~~~~~~~~~~~~~~
+
+Now that we can create species objects, let's create a form so you can
+easily edit them. This *is* a view of the ``Species`` model::
+
+ class Edit(grok.EditForm):
+ grok.context(Species)
+
+ form_fields = grok.Fields(ISpecies)
+
+ @grok.action(u"Edit species")
+ def edit_species(self, **data):
+ self.applyData(self.context, **data)
+
+Forms are self-submitting, so this will show the edit form again. If
+you want to display another page, you can redirect the browser as we
+showed for the add form previously.
+
+The user can now go to ``myspecies/edit`` to edit the species.
+
+``grok.DisplayForm``
+~~~~~~~~~~~~~~~~~~~~
+
+Sometimes you just want to display an object, and not actually edit
+it. If the object is schema-based, an easy way to do this is to use
+display forms. Let's look at an example::
+
+ class Display(grok.DisplayForm):
+ grok.context(Species)
+
+ form_fields = grok.Fields(ISpecies)
+
+The user can now go to ``myspecies/display`` to look at the species.
+
+Associating a template for a form
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+By default, Grok supplies some templates for forms. They work, but
+they are not very pretty and don't fit into your application's
+layout. You can instead use your own form rendering logic in a
+template you associate with the form just like you associate templates
+with views. You can also abstract form rendering logic you keep
+reusing into a ZPT macro. Below is an example of form rendering logic
+to help you get started. The example doesn't have any consideration
+for layouting to make the logic clear. As a result, the form will be
+very ugly if you use this - you will want to use CSS or table HTML to
+layout things::
+
+ <!-- render the form tag -->
+ <form action="." tal:attributes="action request/URL" method="post"
+ class="edit-form" enctype="multipart/form-data">
+ <!-- render any validation errors on top -->
+ <ul class="errors" tal:condition="view/errors">
+ <li tal:repeat="error view/error_views">
+ <span tal:replace="structure error">Error Type</span>
+ </li>
+ </ul>
+
+ <!-- render the widgets -->
+ <tal:block repeat="widget view/widgets">
+ <label tal:attributes="for widget/name">
+ <!-- a * when the widget is required -->
+ <span class="required" tal:condition="widget/required">*</span>
+ <!-- the title of the field -->
+ <span i18n:translate="" tal:content="widget/label">label</span>
+ </label>
+
+ <!-- render the HTML widget -->
+ <div class="widget" tal:content="structure widget">
+ <input type="text" />
+ </div>
+
+ <!-- render any field specific validation error from a previous
+ form submit next to the field -->
+ <div class="error" tal:condition="widget/error">
+ <span tal:replace="structure widget/error">error</span>
+ </div>
+ </tal:block>
+
+ <!-- render all the action submit buttons -->
+ <span class="actionButtons" tal:condition="view/availableActions">
+ <input tal:repeat="action view/actions"
+ tal:replace="structure action/render" />
+ </span>
+ </form>
+
+The template for a display form a lot simpler::
+
+ <tal:block repeat="widget view/widgets">
+ <tal:block content="widget/label" />
+ <input tal:replace="structure widget" />
+ </tal:block>
+
+ <!-- render all the action submit buttons -->
+ <span class="actionButtons" tal:condition="view/availableActions">
+ <input tal:repeat="action view/actions"
+ tal:replace="structure action/render" />
+ </span>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,15 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Another(grok.Application, grok.Model):
+ pass
+
+class SampleIndex(grok.View):
+ grok.context(Sample)
+ grok.name('index')
+
+class AnotherIndex(grok.View):
+ grok.context(Another)
+ grok.name('index')
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app_templates/anotherindex.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app_templates/anotherindex.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app_templates/anotherindex.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p>Another index</p>
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app_templates/sampleindex.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app_templates/sampleindex.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/app_templates/sampleindex.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p>Sample index</p>
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_model/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,11 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ pass
+
+class Bye(grok.View):
+ pass
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app_templates/bye.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app_templates/bye.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app_templates/bye.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p>Bye world!</p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p>Hello world!</p>
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_second_view/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ def information(self):
+ return "This is important information!"
+
+class Index(grok.View):
+ pass
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p tal:content="python:context.information()">replaced</p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,9 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ def information(self):
+ return "This is important information!"
+
+class Index(grok.View):
+ def reversed_information(self):
+ return ''.join(reversed(self.context.information()))
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,10 @@
+<html>
+<body>
+<p>The information:
+ <span tal:content="python:context.information()">info</span>
+</p>
+<p>The information, reversed:
+ <span tal:replace="python:view.reversed_information()">info</span>
+</p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/a_view_for_a_model2/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+# this directory is a package
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,7 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ pass # see app_templates/index.pt
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,32 @@
+Do a functional doctest test on the app.
+========================================
+
+:Test-Layer: functional
+
+Let's first create an instance of Sample at the top level:
+
+ >>> from sample.app import Sample
+ >>> root = getRootFolder()
+ >>> root['app'] = Sample()
+
+
+Run tests in the testbrowser
+----------------------------
+
+The zope.testbrowser.browser module exposes a Browser class that
+simulates a web browser similar to Mozilla Firefox or IE. We use that
+to test how our application behaves in a browser. For more
+information, see http://pypi.python.org/pypi/zope.testbrowser.
+
+Create a browser and visit the instance you just created:
+
+ >>> from zope.testbrowser.testing import Browser
+ >>> browser = Browser()
+ >>> browser.open('http://localhost/app')
+
+Check some basic information about the page you visit:
+
+ >>> browser.url
+ 'http://localhost/app'
+ >>> browser.headers.get('Status').upper()
+ '200 OK'
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,11 @@
+<html>
+<head>
+</head>
+<body>
+ <h1>Congratulations!</h1>
+
+ <p>Your Grok application is up and running.
+ Edit <code>sample/app_templates/index.pt</code> to change
+ this page.</p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/ftesting.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/ftesting.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/ftesting.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,34 @@
+<configure
+ xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample"
+ package="sample"
+ >
+
+ <include package="sample" />
+
+ <!-- Typical functional testing security setup -->
+ <securityPolicy
+ component="zope.securitypolicy.zopepolicy.ZopeSecurityPolicy"
+ />
+
+ <unauthenticatedPrincipal
+ id="zope.anybody"
+ title="Unauthenticated User"
+ />
+ <grant
+ permission="zope.View"
+ principal="zope.anybody"
+ />
+
+ <principal
+ id="zope.mgr"
+ title="Manager"
+ login="mgr"
+ password="mgrpw"
+ />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager" principal="zope.mgr" />
+
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/static/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/static/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/static/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,2 @@
+Put static files here, like javascript and css. They will be
+available as static/<filename> in views.
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/tests.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/tests.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/an_empty_grok_project/src/sample/tests.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,10 @@
+import os.path
+import z3c.testsetup
+from zope.app.wsgi.testlayer import BrowserLayer
+
+import sample
+
+browser_layer = BrowserLayer(sample)
+
+test_suite = z3c.testsetup.register_all_tests(
+ 'sample', globs={'getRootFolder': browser_layer.getRootFolder})
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ def render(self):
+ return "ME GROK NO TEMPLATE"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/completely_python_driven_views/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,21 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Entry(grok.Model):
+ def __init__(self, text):
+ self.text = text
+
+class SampleIndex(grok.View):
+ grok.context(Sample)
+ grok.name('index')
+
+ def update(self, name=None, text=None):
+ if name is None or text is None:
+ return
+ self.context[name] = Entry(text)
+
+class EntryIndex(grok.View):
+ grok.context(Entry)
+ grok.name('index')
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app_templates/entryindex.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app_templates/entryindex.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app_templates/entryindex.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+<html>
+<head>
+</head>
+<body>
+ <h2>Entry <span tal:replace="python:context.__name__"></span></h2>
+ <p tal:content="python:context.text"></p>
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app_templates/sampleindex.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app_templates/sampleindex.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/app_templates/sampleindex.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,21 @@
+<html>
+<head>
+</head>
+<body>
+ <h2>Existing entries</h2>
+ <ul>
+ <li tal:repeat="key python:context.keys()">
+ <a tal:attributes="href python:view.url(key)"
+ tal:content="python:key"></a>
+ </li>
+ </ul>
+
+ <h2>Add a new entry</h2>
+ <form tal:attributes="action python:view.url()" method="POST">
+ Name: <input type="text" name="name" value="" /><br />
+ Text: <input type="text" name="text" value="" /><br />
+ <input type="submit" value="Add entry" />
+ </form>
+
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/containers/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,9 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ def update(self):
+ self.alpha = 2 ** 8
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p tal:content="python:view.alpha">result</p>
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/doing_some_calculation_before_viewing_a_page/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,12 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ grok.context(Sample)
+
+class Bye(grok.View):
+ grok.context(Sample)
+
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app_templates/bye.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app_templates/bye.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app_templates/bye.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p>Bye world!</p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p>Hello world!</p>
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/explicitly_associating_a_view_with_a_model/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,9 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ def some_html(self):
+ return "<b>ME GROK BOLD</b>"
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p tal:content="structure python:view.some_html()"></p>
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/generating_html_from_python/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ pass
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p tal:content="python: 1 + 1">this is replaced</p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/making_our_page_dynamic/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,7 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ pass
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,32 @@
+Do a functional doctest test on the app.
+========================================
+
+:Test-Layer: functional
+
+Let's first create an instance of Sample at the top level:
+
+ >>> from sample.app import Sample
+ >>> root = getRootFolder()
+ >>> root['app'] = Sample()
+
+
+Run tests in the testbrowser
+----------------------------
+
+The zope.testbrowser.browser module exposes a Browser class that
+simulates a web browser similar to Mozilla Firefox or IE. We use that
+to test how our application behaves in a browser. For more
+information, see http://pypi.python.org/pypi/zope.testbrowser.
+
+Create a browser and visit the instance you just created:
+
+ >>> from zope.testbrowser.testing import Browser
+ >>> browser = Browser()
+ >>> browser.open('http://localhost/app')
+
+Check some basic information about the page you visit:
+
+ >>> browser.url
+ 'http://localhost/app'
+ >>> browser.headers.get('Status').upper()
+ '200 OK'
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p>Hello world!</p>
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/ftesting.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/ftesting.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/ftesting.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,34 @@
+<configure
+ xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample"
+ package="sample"
+ >
+
+ <include package="sample" />
+
+ <!-- Typical functional testing security setup -->
+ <securityPolicy
+ component="zope.securitypolicy.zopepolicy.ZopeSecurityPolicy"
+ />
+
+ <unauthenticatedPrincipal
+ id="zope.anybody"
+ title="Unauthenticated User"
+ />
+ <grant
+ permission="zope.View"
+ principal="zope.anybody"
+ />
+
+ <principal
+ id="zope.mgr"
+ title="Manager"
+ login="mgr"
+ password="mgrpw"
+ />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager" principal="zope.mgr" />
+
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/static/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/static/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/static/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,2 @@
+Put static files here, like javascript and css. They will be
+available as static/<filename> in views.
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/tests.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/tests.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/publishing_a_simple_web_page/src/sample/tests.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,10 @@
+import os.path
+import z3c.testsetup
+from zope.app.wsgi.testlayer import BrowserLayer
+
+import sample
+
+browser_layer = BrowserLayer(sample)
+
+test_suite = z3c.testsetup.register_all_tests(
+ 'sample', globs={'getRootFolder': browser_layer.getRootFolder})
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ def update(self, value1, value2):
+ self.sum = int(value1) + int(value2)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p tal:content="python:view.sum">sum</p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ def update(self, value1=0, value2=0):
+ self.sum = int(value1) + int(value2)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p tal:content="python:view.sum">sum</p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/reading_url_parameters2/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,14 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ text = 'default text'
+
+class Index(grok.View):
+ pass
+
+class Edit(grok.View):
+ def update(self, text=None):
+ if text is None:
+ return
+ self.context.text = text
+ self.redirect(self.url('index'))
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app_templates/edit.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app_templates/edit.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app_templates/edit.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+<html>
+<body>
+<form tal:attributes="action view/url" method="POST">
+Text to store: <input type="text" name="text" value="" /><br />
+<input type="submit" value="Store" />
+</form>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<html>
+<body>
+<p>The text: <span tal:replace="python:context.text">text</span></p>
+<p><a tal:attributes="href python:view.url('edit')">Edit this page</a></p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/redirection/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,10 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ def render(self):
+ self.response.setHeader('Content-Type',
+ 'text/xml; charset=UTF-8')
+ return "<doc>Some XML</doc>"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/setting_the_content_type/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,14 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ text = 'default text'
+
+class Index(grok.View):
+ pass
+
+class Edit(grok.View):
+ def update(self, text=None):
+ if text is None:
+ return
+ self.context.text = text
+ self.redirect(self.url('index'))
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app_templates/edit.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app_templates/edit.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app_templates/edit.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+<html>
+<body>
+<form tal:attributes="action view/url" method="POST">
+Text to store: <input type="text" name="text" tal:attributes="value python:context.text" value="" /><br />
+<input type="submit" value="Store" />
+</form>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<html>
+<body>
+<p>The text: <span tal:replace="python:context.text">text</span></p>
+<p><a tal:attributes="href python:view.url('edit')">Edit this page</a></p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/showing_the_value_in_the_form/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ def update(self, value1=0, value2=0):
+ self.sum = int(value1) + int(value2)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,10 @@
+<html>
+<body>
+<form tal:attributes="action python:view.url()" method="GET">
+ Value 1: <input type="text" name="value1" value="" /><br />
+ Value 2: <input type="text" name="value2" value="" /><br />
+ <input type="submit" value="Sum!" />
+</form>
+<p>The sum is: <span tal:replace="python:view.sum">sum</span></p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,14 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ def update(self, value1=None, value2=None):
+ try:
+ value1 = int(value1)
+ value2 = int(value2)
+ except (TypeError, ValueError):
+ self.sum = "No sum"
+ return
+ self.sum = value1 + value2
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,10 @@
+<html>
+<body>
+<form tal:attributes="action python:view.url()" method="GET">
+ Value 1: <input type="text" name="value1" value="" /><br />
+ Value 2: <input type="text" name="value2" value="" /><br />
+ <input type="submit" value="Sum!" />
+</form>
+<p>The sum is: <span tal:replace="python:view.sum">sum</span></p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/simple_forms2/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,7 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ pass
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,9 @@
+<html>
+<head>
+<link rel="stylesheet" type="text/css"
+ tal:attributes="href static/style.css" />
+</head>
+<body>
+<p>Hello world!</p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/static/style.css
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/static/style.css (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/static_resources_for_our_web_page/src/sample/static/style.css 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,3 @@
+body {
+ background-color: #FF0000;
+}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,13 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ text = 'default text'
+
+class Index(grok.View):
+ pass
+
+class Edit(grok.View):
+ def update(self, text=None):
+ if text is None:
+ return
+ self.context.text = text
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app_templates/edit.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app_templates/edit.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app_templates/edit.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+<html>
+<body>
+<form tal:attributes="action view/url" method="POST">
+Text to store: <input type="text" name="text" value="" /><br />
+<input type="submit" value="Store" />
+</form>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p>The text: <span tal:replace="python:context.text">text</span></p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/storing_data/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+# this directory is a package
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,7 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ pass # see app_templates/index.pt
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,11 @@
+<html>
+<head>
+</head>
+<body>
+ <h1>Congratulations!</h1>
+
+ <p>Your Grok application is up and running.
+ Edit <code>sample/app_templates/index.pt</code> to change
+ this page.</p>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/template/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,17 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ def __init__(self):
+ super(Sample, self).__init__()
+ self.list = []
+
+class Index(grok.View):
+ pass
+
+class Edit(grok.View):
+ def update(self, text=None):
+ if text is None:
+ return
+ # this code has a BUG!
+ self.context.list.append(text)
+ self.redirect(self.url('index'))
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app_templates/edit.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app_templates/edit.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app_templates/edit.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+<html>
+<body>
+<form tal:attributes="action view/url" method="POST">
+Text to store: <input type="text" name="text" value="" /><br />
+<input type="submit" value="Store" />
+</form>
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,9 @@
+<html>
+<body>
+We store the following texts:
+<ul>
+ <li tal:repeat="text python:context.list" tal:content="text"></li>
+</ul>
+<a tal:attributes="href python:view.url('edit')">Add a text</a>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,17 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ def __init__(self):
+ super(Sample, self).__init__()
+ self.list = []
+
+class Index(grok.View):
+ pass
+
+class Edit(grok.View):
+ def update(self, text=None):
+ if text is None:
+ return
+ self.context.list.append(text)
+ self.context._p_changed = True
+ self.redirect(self.url('index'))
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app_templates/edit.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app_templates/edit.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app_templates/edit.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+<html>
+<body>
+<form tal:attributes="action view/url" method="POST">
+Text to store: <input type="text" name="text" value="" /><br />
+<input type="submit" value="Store" />
+</form>
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,9 @@
+<html>
+<body>
+We store the following texts:
+<ul>
+ <li tal:repeat="text python:context.list" tal:content="text"></li>
+</ul>
+<a tal:attributes="href python:view.url('edit')">Add a text</a>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence2/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,20 @@
+import grok
+
+class Sample(grok.Application, grok.Container):
+ def __init__(self):
+ super(Sample, self).__init__()
+ self.list = []
+
+ def addText(self, text):
+ self.list.append(text)
+ self._p_changed = True
+
+class Index(grok.View):
+ pass
+
+class Edit(grok.View):
+ def update(self, text=None):
+ if text is None:
+ return
+ self.context.addText(text)
+ self.redirect(self.url('index'))
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app_templates/edit.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app_templates/edit.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app_templates/edit.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,8 @@
+<html>
+<body>
+<form tal:attributes="action view/url" method="POST">
+Text to store: <input type="text" name="text" value="" /><br />
+<input type="submit" value="Store" />
+</form>
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,9 @@
+<html>
+<body>
+We store the following texts:
+<ul>
+ <li tal:repeat="text python:context.list" tal:content="text"></li>
+</ul>
+<a tal:attributes="href python:view.url('edit')">Add a text</a>
+</body>
+</html>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/the_rules_of_persistence3/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/bootstrap.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/bootstrap.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/bootstrap.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,260 @@
+##############################################################################
+#
+# Copyright (c) 2006 Zope Foundation and Contributors.
+# All Rights Reserved.
+#
+# This software is subject to the provisions of the Zope Public License,
+# Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
+# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
+# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
+# FOR A PARTICULAR PURPOSE.
+#
+##############################################################################
+"""Bootstrap a buildout-based project
+
+Simply run this script in a directory containing a buildout.cfg.
+The script accepts buildout command-line options, so you can
+use the -c option to specify an alternate configuration file.
+"""
+
+import os, shutil, sys, tempfile, textwrap, urllib, urllib2, subprocess
+from optparse import OptionParser
+
+if sys.platform == 'win32':
+ def quote(c):
+ if ' ' in c:
+ return '"%s"' % c # work around spawn lamosity on windows
+ else:
+ return c
+else:
+ quote = str
+
+# See zc.buildout.easy_install._has_broken_dash_S for motivation and comments.
+stdout, stderr = subprocess.Popen(
+ [sys.executable, '-Sc',
+ 'try:\n'
+ ' import ConfigParser\n'
+ 'except ImportError:\n'
+ ' print 1\n'
+ 'else:\n'
+ ' print 0\n'],
+ stdout=subprocess.PIPE, stderr=subprocess.PIPE).communicate()
+has_broken_dash_S = bool(int(stdout.strip()))
+
+# In order to be more robust in the face of system Pythons, we want to
+# run without site-packages loaded. This is somewhat tricky, in
+# particular because Python 2.6's distutils imports site, so starting
+# with the -S flag is not sufficient. However, we'll start with that:
+if not has_broken_dash_S and 'site' in sys.modules:
+ # We will restart with python -S.
+ args = sys.argv[:]
+ args[0:0] = [sys.executable, '-S']
+ args = map(quote, args)
+ os.execv(sys.executable, args)
+# Now we are running with -S. We'll get the clean sys.path, import site
+# because distutils will do it later, and then reset the path and clean
+# out any namespace packages from site-packages that might have been
+# loaded by .pth files.
+clean_path = sys.path[:]
+import site
+sys.path[:] = clean_path
+for k, v in sys.modules.items():
+ if k in ('setuptools', 'pkg_resources') or (
+ hasattr(v, '__path__') and
+ len(v.__path__)==1 and
+ not os.path.exists(os.path.join(v.__path__[0],'__init__.py'))):
+ # This is a namespace package. Remove it.
+ sys.modules.pop(k)
+
+is_jython = sys.platform.startswith('java')
+
+setuptools_source = 'http://peak.telecommunity.com/dist/ez_setup.py'
+distribute_source = 'http://python-distribute.org/distribute_setup.py'
+
+# parsing arguments
+def normalize_to_url(option, opt_str, value, parser):
+ if value:
+ if '://' not in value: # It doesn't smell like a URL.
+ value = 'file://%s' % (
+ urllib.pathname2url(
+ os.path.abspath(os.path.expanduser(value))),)
+ if opt_str == '--download-base' and not value.endswith('/'):
+ # Download base needs a trailing slash to make the world happy.
+ value += '/'
+ else:
+ value = None
+ name = opt_str[2:].replace('-', '_')
+ setattr(parser.values, name, value)
+
+usage = '''\
+[DESIRED PYTHON FOR BUILDOUT] bootstrap.py [options]
+
+Bootstraps a buildout-based project.
+
+Simply run this script in a directory containing a buildout.cfg, using the
+Python that you want bin/buildout to use.
+
+Note that by using --setup-source and --download-base to point to
+local resources, you can keep this script from going over the network.
+'''
+
+parser = OptionParser(usage=usage)
+parser.add_option("-v", "--version", dest="version",
+ help="use a specific zc.buildout version")
+parser.add_option("-d", "--distribute",
+ action="store_true", dest="use_distribute", default=False,
+ help="Use Distribute rather than Setuptools.")
+parser.add_option("--setup-source", action="callback", dest="setup_source",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or file location for the setup file. "
+ "If you use Setuptools, this will default to " +
+ setuptools_source + "; if you use Distribute, this "
+ "will default to " + distribute_source +"."))
+parser.add_option("--download-base", action="callback", dest="download_base",
+ callback=normalize_to_url, nargs=1, type="string",
+ help=("Specify a URL or directory for downloading "
+ "zc.buildout and either Setuptools or Distribute. "
+ "Defaults to PyPI."))
+parser.add_option("--eggs",
+ help=("Specify a directory for storing eggs. Defaults to "
+ "a temporary directory that is deleted when the "
+ "bootstrap script completes."))
+parser.add_option("-t", "--accept-buildout-test-releases",
+ dest='accept_buildout_test_releases',
+ action="store_true", default=False,
+ help=("Normally, if you do not specify a --version, the "
+ "bootstrap script and buildout gets the newest "
+ "*final* versions of zc.buildout and its recipes and "
+ "extensions for you. If you use this flag, "
+ "bootstrap and buildout will get the newest releases "
+ "even if they are alphas or betas."))
+parser.add_option("-c", None, action="store", dest="config_file",
+ help=("Specify the path to the buildout configuration "
+ "file to be used."))
+
+options, args = parser.parse_args()
+
+# if -c was provided, we push it back into args for buildout's main function
+if options.config_file is not None:
+ args += ['-c', options.config_file]
+
+if options.eggs:
+ eggs_dir = os.path.abspath(os.path.expanduser(options.eggs))
+else:
+ eggs_dir = tempfile.mkdtemp()
+
+if options.setup_source is None:
+ if options.use_distribute:
+ options.setup_source = distribute_source
+ else:
+ options.setup_source = setuptools_source
+
+if options.accept_buildout_test_releases:
+ args.append('buildout:accept-buildout-test-releases=true')
+args.append('bootstrap')
+
+try:
+ import pkg_resources
+ import setuptools # A flag. Sometimes pkg_resources is installed alone.
+ if not hasattr(pkg_resources, '_distribute'):
+ raise ImportError
+except ImportError:
+ ez_code = urllib2.urlopen(
+ options.setup_source).read().replace('\r\n', '\n')
+ ez = {}
+ exec ez_code in ez
+ setup_args = dict(to_dir=eggs_dir, download_delay=0)
+ if options.download_base:
+ setup_args['download_base'] = options.download_base
+ if options.use_distribute:
+ setup_args['no_fake'] = True
+ ez['use_setuptools'](**setup_args)
+ if 'pkg_resources' in sys.modules:
+ reload(sys.modules['pkg_resources'])
+ import pkg_resources
+ # This does not (always?) update the default working set. We will
+ # do it.
+ for path in sys.path:
+ if path not in pkg_resources.working_set.entries:
+ pkg_resources.working_set.add_entry(path)
+
+cmd = [quote(sys.executable),
+ '-c',
+ quote('from setuptools.command.easy_install import main; main()'),
+ '-mqNxd',
+ quote(eggs_dir)]
+
+if not has_broken_dash_S:
+ cmd.insert(1, '-S')
+
+find_links = options.download_base
+if not find_links:
+ find_links = os.environ.get('bootstrap-testing-find-links')
+if find_links:
+ cmd.extend(['-f', quote(find_links)])
+
+if options.use_distribute:
+ setup_requirement = 'distribute'
+else:
+ setup_requirement = 'setuptools'
+ws = pkg_resources.working_set
+setup_requirement_path = ws.find(
+ pkg_resources.Requirement.parse(setup_requirement)).location
+env = dict(
+ os.environ,
+ PYTHONPATH=setup_requirement_path)
+
+requirement = 'zc.buildout'
+version = options.version
+if version is None and not options.accept_buildout_test_releases:
+ # Figure out the most recent final version of zc.buildout.
+ import setuptools.package_index
+ _final_parts = '*final-', '*final'
+ def _final_version(parsed_version):
+ for part in parsed_version:
+ if (part[:1] == '*') and (part not in _final_parts):
+ return False
+ return True
+ index = setuptools.package_index.PackageIndex(
+ search_path=[setup_requirement_path])
+ if find_links:
+ index.add_find_links((find_links,))
+ req = pkg_resources.Requirement.parse(requirement)
+ if index.obtain(req) is not None:
+ best = []
+ bestv = None
+ for dist in index[req.project_name]:
+ distv = dist.parsed_version
+ if _final_version(distv):
+ if bestv is None or distv > bestv:
+ best = [dist]
+ bestv = distv
+ elif distv == bestv:
+ best.append(dist)
+ if best:
+ best.sort()
+ version = best[-1].version
+if version:
+ requirement = '=='.join((requirement, version))
+cmd.append(requirement)
+
+if is_jython:
+ import subprocess
+ exitcode = subprocess.Popen(cmd, env=env).wait()
+else: # Windows prefers this, apparently; otherwise we would prefer subprocess
+ exitcode = os.spawnle(*([os.P_WAIT, sys.executable] + cmd + [env]))
+if exitcode != 0:
+ sys.stdout.flush()
+ sys.stderr.flush()
+ print ("An error occurred when trying to install zc.buildout. "
+ "Look above this message for any errors that "
+ "were output by easy_install.")
+ sys.exit(exitcode)
+
+ws.add_entry(eggs_dir)
+ws.require(requirement)
+import zc.buildout.buildout
+zc.buildout.buildout.main(args)
+if not options.eggs: # clean up temporary egg directory
+ shutil.rmtree(eggs_dir)
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/buildout.cfg
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/buildout.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/buildout.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,96 @@
+[buildout]
+extends = http://svn.zope.org/repos/main/groktoolkit/branches/1.2/grok.cfg
+extends-cache = extends-cache
+find-links =
+include-site-packages = false
+develop = .
+parts =
+ app
+ debug_ini
+ deploy_ini
+ i18n
+ mkdirs
+ site_zcml
+ test
+ zope_conf
+ zpasswd
+ interactive_debugger
+newest = false
+versions = versions
+extensions = buildout.dumppickedversions
+
+[app]
+recipe = z3c.recipe.scripts
+eggs = Sample
+ z3c.evalexception>=2.0
+ Paste
+ PasteScript
+ PasteDeploy
+interpreter = python-console
+
+[deploy_ini]
+recipe = collective.recipe.template
+input = etc/deploy.ini.in
+output = ${buildout:parts-directory}/etc/deploy.ini
+host = 127.0.0.1
+port = 8080
+
+[debug_ini]
+recipe = collective.recipe.template
+input = etc/debug.ini.in
+output = ${buildout:parts-directory}/etc/debug.ini
+host = 127.0.0.1
+port = 8080
+
+# this section named so that the i18n scripts are called bin/i18n...
+[i18n]
+recipe = z3c.recipe.i18n:i18n
+packages = sample
+eggs = sample
+domain = sample
+output = src/sample/locales
+zcml =
+
+[mkdirs]
+recipe = z3c.recipe.mkdir
+paths =
+ ${zope_conf:filestorage}
+ ${zope_conf:logfiles}
+ ${zope_conf:blobstorage}
+
+[site_zcml]
+recipe = collective.recipe.template
+input = etc/site.zcml.in
+output = ${buildout:parts-directory}/etc/site.zcml
+
+[test]
+recipe = zc.recipe.testrunner
+eggs = Sample
+defaults = ['-v']
+
+[zope_conf]
+recipe = collective.recipe.template
+input = etc/zope.conf.in
+output = ${buildout:parts-directory}/etc/zope.conf
+filestorage = ${buildout:directory}/var/filestorage
+blobstorage = ${buildout:directory}/var/blobstorage
+logfiles = ${buildout:directory}/var/log
+extra =
+# 'extra' is copied verbatim. Use it for product config sections and so.
+
+# This section is named so that the zpasswd utility is
+# called `zpasswd`
+[zpasswd]
+recipe = z3c.recipe.scripts
+eggs =
+ Sample
+ zope.password
+entry-points =
+ zpasswd=zope.password.zpasswd:main
+
+[interactive_debugger]
+recipe = z3c.recipe.scripts
+eggs = Sample
+entry-points =
+ interactive_debugger=grokcore.startup.startup:interactive_debug_prompt
+arguments = zope_conf="${zope_conf:output}"
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/README.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/README.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/README.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,26 @@
+In this directory you can find templates which are used by
+``zc.buildout`` to create the configuration files in the parts/etc/ subdir
+of your project.
+
+If you modify files in this directory, you have to run::
+
+ $ bin/buildout
+
+afterwards to rebuild the configuration files in parts/etc/.
+
+In the templates you can use placesholders recognized by zc.buildout
+to name local paths, etc. A zc.buildout placeholder looks like this::
+
+ ${buildout:directory}
+
+which gives you the path of the project directory and will be
+substituted with the real path when you run buildout the next
+time. The set of available placeholders depends on your
+buildout.cfg.
+
+You can also modify files in parts/etc directly, but those changes
+will be overwritten after running bin/buildout the next time.
+
+To run your project you can do::
+
+ $ bin/paster serve parts/etc/deploy.ini
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/debug.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/debug.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/debug.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,67 @@
+# debug.ini
+#
+# Debugging configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[filter-app:main]
+# Change the last part from 'ajax' to 'pdb' for a post-mortem debugger
+# on the console:
+use = egg:z3c.evalexception#ajax
+next = zope
+
+[app:zope]
+use = egg:Sample#debug
+filter-with = translogger
+exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/deploy.ini.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/deploy.ini.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/deploy.ini.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,60 @@
+# deploy.ini
+#
+# Deployment configuration for use with paster/WSGI
+#
+
+[loggers]
+keys = root, wsgi
+
+[handlers]
+keys = console, accesslog
+
+[formatters]
+keys = generic, accesslog
+
+[logger_root]
+level = INFO
+handlers = console
+
+[logger_wsgi]
+level = INFO
+handlers = accesslog
+qualname = wsgi
+propagate = 0
+
+[handler_console]
+class = StreamHandler
+args = (sys.stderr,)
+level = NOTSET
+formatter = generic
+
+[handler_accesslog]
+class = FileHandler
+args = (os.path.join(r'${buildout:directory}', 'parts', 'log', 'access.log'),
+ 'a')
+level = INFO
+formatter = accesslog
+
+[formatter_generic]
+format = %(asctime)s %(levelname)s [%(name)s] %(message)s
+
+[formatter_accesslog]
+format = %(message)s
+
+[filter:translogger]
+use = egg:Paste#translogger
+setup_console_handler = False
+logger_name = wsgi
+
+[app:main]
+use = egg:Sample
+filter-with = translogger
+
+[server:main]
+use = egg:Paste#http
+host = 127.0.0.1
+port = 8080
+
+[DEFAULT]
+# set the name of the zope.conf file
+zope_conf = %(here)s/zope.conf
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/site.zcml.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/site.zcml.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/site.zcml.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ i18n_domain="sample">
+
+ <include package="sample" />
+
+ <configure i18n_domain="sample">
+
+ <unauthenticatedPrincipal id="zope.anybody"
+ title="Unauthenticated User" />
+ <unauthenticatedGroup id="zope.Anybody"
+ title="Unauthenticated Users" />
+ <authenticatedGroup id="zope.Authenticated"
+ title="Authenticated Users" />
+ <everybodyGroup id="zope.Everybody"
+ title="All Users" />
+ <principal id="zope.manager"
+ title="Manager"
+ login="grok"
+ password_manager="SHA1"
+ password="8977f073739bd029629243732eb682db005a7541f7509622"
+ />
+
+ <!-- Replace the following directive if you do not want
+ public access -->
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+ <grant permission="zope.app.dublincore.view"
+ principal="zope.Anybody" />
+
+ <role id="zope.Manager" title="Site Manager" />
+ <role id="zope.Member" title="Site Member" />
+ <grantAll role="zope.Manager" />
+ <grant role="zope.Manager"
+ principal="zope.manager" />
+ </configure>
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/zope.conf.in
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/zope.conf.in (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/etc/zope.conf.in 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,40 @@
+# Identify the component configuration used to define the site:
+site-definition ${site_zcml:output}
+
+<zodb>
+ # Standard blob storage
+ <blobstorage>
+ blob-dir ${zope_conf:blobstorage}
+ <filestorage>
+ path ${zope_conf:filestorage}/Data.fs
+ </filestorage>
+ </blobstorage>
+
+# Uncomment this if you want a blob-less standard file storage instead:
+# <filestorage>
+# path ${zope_conf:filestorage}
+# </filestorage>
+
+# Uncomment this if you want to connect to a ZEO server instead:
+# <zeoclient>
+# server localhost:8100
+# storage 1
+# # ZEO client cache, in bytes
+# cache-size 20MB
+# # Uncomment to have a persistent disk cache
+# #client zeo1
+# </zeoclient>
+
+</zodb>
+
+<eventlog>
+# logfiles are setup in the debug.ini and deploy.ini files.
+</eventlog>
+
+# Comment this line to disable developer mode. This should be done in
+# production
+devmode on
+
+# Extra configuration lines can be added to zope_conf's extra option. Put for
+# instance productconf sections in here.
+${zope_conf:extra}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/setup.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/setup.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/setup.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,36 @@
+from setuptools import setup, find_packages
+
+version = '0.0'
+
+setup(name='Sample',
+ version=version,
+ description="",
+ long_description="""\
+""",
+ # Get strings from http://www.python.org/pypi?%3Aaction=list_classifiers
+ classifiers=[],
+ keywords="",
+ author="",
+ author_email="",
+ url="",
+ license="",
+ package_dir={'': 'src'},
+ packages=find_packages('src'),
+ include_package_data=True,
+ zip_safe=False,
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ 'grokcore.startup',
+ # Add extra requirements here
+ ],
+ entry_points = """
+ [console_scripts]
+ sample-debug = grokcore.startup:interactive_debug_prompt
+ sample-ctl = grokcore.startup:zdaemon_controller
+ [paste.app_factory]
+ main = grokcore.startup:application_factory
+ debug = grokcore.startup:debug_application_factory
+ """,
+ )
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/__init__.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/__init__.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/__init__.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+#
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/app.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/app.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/app.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,10 @@
+import grok
+from datetime import datetime
+
+class Sample(grok.Application, grok.Container):
+ pass
+
+class Index(grok.View):
+ def current_datetime(self):
+ now = datetime.now()
+ return now.strftime('%Y-%m-%d %H:%M')
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/app_templates/index.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/app_templates/index.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/app_templates/index.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,5 @@
+<html>
+<body>
+<p tal:content="python:view.current_datetime()">Hello world!</p>
+</body>
+</html>
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/configure.zcml
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/configure.zcml (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/groktut/using_view_methods/src/sample/configure.zcml 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,6 @@
+<configure xmlns="http://namespaces.zope.org/zope"
+ xmlns:grok="http://namespaces.zope.org/grok">
+ <include package="grok" />
+ <includeDependencies package="." />
+ <grok:grok package="." />
+</configure>
Added: groktoolkit/branches/jw-documentation-rearangement/doc/index.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/index.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/index.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,7 @@
+Official Grok Documentation Overview
+************************************
+
+.. toctree::
+ :hidden:
+
+ contents.rst
Added: groktoolkit/branches/jw-documentation-rearangement/doc/layout.html
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/layout.html (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/layout.html 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,35 @@
+{% extends "!layout.html" %}
+
+{%- set reldelim1 = reldelim1 is not defined and ' »' or reldelim1 %}
+{%- set reldelim2 = reldelim2 is not defined and ' |' or reldelim2 %}
+
+{%- macro relbar_grok() %}
+ <div class="header">
+ {%- block rootrellink %}
+ <a href="{{ pathto('index') }}">Official Grok Documentation</a> version {{ release }}
+ {%- endblock %}
+ <div class="globalnav">
+ <h3>Navigation</h3>
+ <div id="globalnavwrapper">
+ <ul>
+ <li><a href="{{ pathto("tutorial") }}">Tutorial</a></li>
+ <li><a href="{{ pathto("grok_overview") }}">Developer's Notes</a></li>
+ <li><a href="{{ pathto("reference/index")}}">Reference</a></li>
+ <li><a rel="index" title="Global index" href="{{pathto('genindex') }}">Index</a></li>
+ <li><a href="http://grok.zope.org/documentation/">Grok Community Documentation</a></li>
+ {%- block relbaritems %}{% endblock %}
+ </ul>
+ </div>
+ </div>
+ </div>
+{%- endmacro %}
+
+{%- block sidebarlogo %}
+ <a href="{{ pathto('index') }}">
+ <img src="{{ pathto('_static/logo.png', 1) }}"
+ alt="Grok Logo"
+ class="logo"
+ /></a>
+{% endblock %}
+{%- block relbar1 %}{{ relbar_grok() }}{% endblock %}
+{%- block relbar2 %}<!-- no footer relbar -->{% endblock %}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/license.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/license.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/license.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,62 @@
+.. _license:
+
+***********
+The License
+***********
+
+Zope Public License (ZPL) Version 2.1
+-------------------------------------
+
+A copyright notice accompanies this license document that
+identifies the copyright holders.
+
+This license has been certified as open source. It has also
+been designated as GPL compatible by the Free Software
+Foundation (FSF).
+
+Redistribution and use in source and binary forms, with or
+without modification, are permitted provided that the
+following conditions are met:
+
+1. Redistributions in source code must retain the
+ accompanying copyright notice, this list of conditions,
+ and the following disclaimer.
+
+2. Redistributions in binary form must reproduce the accompanying
+ copyright notice, this list of conditions, and the
+ following disclaimer in the documentation and/or other
+ materials provided with the distribution.
+
+3. Names of the copyright holders must not be used to
+ endorse or promote products derived from this software
+ without prior written permission from the copyright
+ holders.
+
+4. The right to distribute this software or to use it for
+ any purpose does not give you the right to use
+ Servicemarks (sm) or Trademarks (tm) of the copyright
+ holders. Use of them is covered by separate agreement
+ with the copyright holders.
+
+5. If any files are modified, you must cause the modified
+ files to carry prominent notices stating that you changed
+ the files and the date of any change.
+
+Disclaimer
+
+ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS ''AS IS''
+ AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT
+ NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
+ AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN
+ NO EVENT SHALL THE COPYRIGHT HOLDERS BE
+ LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
+ OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
+ DAMAGE.
+
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/make.bat
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/make.bat (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/make.bat 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,170 @@
+ at ECHO OFF
+
+REM Command file for Sphinx documentation
+
+if "%SPHINXBUILD%" == "" (
+ set SPHINXBUILD=sphinx-build
+)
+set BUILDDIR=_build
+set ALLSPHINXOPTS=-d %BUILDDIR%/doctrees %SPHINXOPTS% .
+if NOT "%PAPER%" == "" (
+ set ALLSPHINXOPTS=-D latex_paper_size=%PAPER% %ALLSPHINXOPTS%
+)
+
+if "%1" == "" goto help
+
+if "%1" == "help" (
+ :help
+ echo.Please use `make ^<target^>` where ^<target^> is one of
+ echo. html to make standalone HTML files
+ echo. dirhtml to make HTML files named index.html in directories
+ echo. singlehtml to make a single large HTML file
+ echo. pickle to make pickle files
+ echo. json to make JSON files
+ echo. htmlhelp to make HTML files and a HTML help project
+ echo. qthelp to make HTML files and a qthelp project
+ echo. devhelp to make HTML files and a Devhelp project
+ echo. epub to make an epub
+ echo. latex to make LaTeX files, you can set PAPER=a4 or PAPER=letter
+ echo. text to make text files
+ echo. man to make manual pages
+ echo. changes to make an overview over all changed/added/deprecated items
+ echo. linkcheck to check all external links for integrity
+ echo. doctest to run all doctests embedded in the documentation if enabled
+ goto end
+)
+
+if "%1" == "clean" (
+ for /d %%i in (%BUILDDIR%\*) do rmdir /q /s %%i
+ del /q /s %BUILDDIR%\*
+ goto end
+)
+
+if "%1" == "html" (
+ %SPHINXBUILD% -b html %ALLSPHINXOPTS% %BUILDDIR%/html
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished. The HTML pages are in %BUILDDIR%/html.
+ goto end
+)
+
+if "%1" == "dirhtml" (
+ %SPHINXBUILD% -b dirhtml %ALLSPHINXOPTS% %BUILDDIR%/dirhtml
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished. The HTML pages are in %BUILDDIR%/dirhtml.
+ goto end
+)
+
+if "%1" == "singlehtml" (
+ %SPHINXBUILD% -b singlehtml %ALLSPHINXOPTS% %BUILDDIR%/singlehtml
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished. The HTML pages are in %BUILDDIR%/singlehtml.
+ goto end
+)
+
+if "%1" == "pickle" (
+ %SPHINXBUILD% -b pickle %ALLSPHINXOPTS% %BUILDDIR%/pickle
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished; now you can process the pickle files.
+ goto end
+)
+
+if "%1" == "json" (
+ %SPHINXBUILD% -b json %ALLSPHINXOPTS% %BUILDDIR%/json
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished; now you can process the JSON files.
+ goto end
+)
+
+if "%1" == "htmlhelp" (
+ %SPHINXBUILD% -b htmlhelp %ALLSPHINXOPTS% %BUILDDIR%/htmlhelp
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished; now you can run HTML Help Workshop with the ^
+.hhp project file in %BUILDDIR%/htmlhelp.
+ goto end
+)
+
+if "%1" == "qthelp" (
+ %SPHINXBUILD% -b qthelp %ALLSPHINXOPTS% %BUILDDIR%/qthelp
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished; now you can run "qcollectiongenerator" with the ^
+.qhcp project file in %BUILDDIR%/qthelp, like this:
+ echo.^> qcollectiongenerator %BUILDDIR%\qthelp\Grok.qhcp
+ echo.To view the help file:
+ echo.^> assistant -collectionFile %BUILDDIR%\qthelp\Grok.ghc
+ goto end
+)
+
+if "%1" == "devhelp" (
+ %SPHINXBUILD% -b devhelp %ALLSPHINXOPTS% %BUILDDIR%/devhelp
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished.
+ goto end
+)
+
+if "%1" == "epub" (
+ %SPHINXBUILD% -b epub %ALLSPHINXOPTS% %BUILDDIR%/epub
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished. The epub file is in %BUILDDIR%/epub.
+ goto end
+)
+
+if "%1" == "latex" (
+ %SPHINXBUILD% -b latex %ALLSPHINXOPTS% %BUILDDIR%/latex
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished; the LaTeX files are in %BUILDDIR%/latex.
+ goto end
+)
+
+if "%1" == "text" (
+ %SPHINXBUILD% -b text %ALLSPHINXOPTS% %BUILDDIR%/text
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished. The text files are in %BUILDDIR%/text.
+ goto end
+)
+
+if "%1" == "man" (
+ %SPHINXBUILD% -b man %ALLSPHINXOPTS% %BUILDDIR%/man
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Build finished. The manual pages are in %BUILDDIR%/man.
+ goto end
+)
+
+if "%1" == "changes" (
+ %SPHINXBUILD% -b changes %ALLSPHINXOPTS% %BUILDDIR%/changes
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.The overview file is in %BUILDDIR%/changes.
+ goto end
+)
+
+if "%1" == "linkcheck" (
+ %SPHINXBUILD% -b linkcheck %ALLSPHINXOPTS% %BUILDDIR%/linkcheck
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Link check complete; look for any errors in the above output ^
+or in %BUILDDIR%/linkcheck/output.txt.
+ goto end
+)
+
+if "%1" == "doctest" (
+ %SPHINXBUILD% -b doctest %ALLSPHINXOPTS% %BUILDDIR%/doctest
+ if errorlevel 1 exit /b 1
+ echo.
+ echo.Testing of doctests in the sources finished, look at the ^
+results in %BUILDDIR%/doctest/output.txt.
+ goto end
+)
+
+:end
Added: groktoolkit/branches/jw-documentation-rearangement/doc/naming_conventions.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/naming_conventions.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/naming_conventions.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,33 @@
+Grok naming conventions
+-----------------------
+
+Zope 3 used to follow PEP 8, but then PEP 8 changed so that
+methodNames() is deprecated in favor of method_names().
+
+Grok aims to be mostly consistent with Zope 3, but does make some
+changes in the direction of PEP 8.
+
+modulenames - module and package names are all lower case, no
+underscores
+
+ClassNames - CamelCase (Zope 3 + PEP 8)
+
+methodNames - camelCase: follow Zope 3 conventions. We work a lot with Zope 3
+ classes and sometimes subclass.
+
+attribute_names - Zope 3 + PEP 8
+
+class_annotations - we break with Zope 3 tradition
+ (grok.local_utility() versus implementsOnly()).
+ This makes class annotations stand out a bit
+ more and is more consistent with the use of
+ class-level attribute names for customization
+ as well (as in formlib).
+
+top_level_functions - Zope 3 uses camel case (getUtility()). Grok
+ uses underscores for top-level functions that
+ define class annotations. Grok internally has also
+ been using underscores for functions defined
+ internally. So far we have avoided exposing them
+ to the outside world. If you need to expose
+ one of these, bring it up on the grok-dev mailing list.
Added: groktoolkit/branches/jw-documentation-rearangement/doc/reference/components.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/reference/components.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/reference/components.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,1687 @@
+
+**********
+Components
+**********
+
+.. Here we documented the component base classes. For the directive
+ possible for each component we document only the specifics within
+ its context. We then refer to the directives documented in the
+ directives.rst file.
+
+The :mod:`grok` module defines a set of base classes for creating new
+components of different types, that provide basic Zope 3 functionality in a
+convenient way. Grok applications are built by subclassing these components.
+
+Components in Grok and Zope 3 are any plain Python object, that declare they
+provide one or more Interface(s). The inclusion of these Grok base
+classes in your own class inheritance automatically handles the
+component registration with the Zope Component Architecture. This process of
+introspecting your Grok code during initialization and wiring together
+components based on common conventions that you follow in the structure
+of your source code is called "grokking".
+
+Core components
+~~~~~~~~~~~~~~~
+
+
+
+:class:`grok.Application`
+=========================
+
+Applications are top-level objects. They are typically used to hold global
+configuration and behaviour for an application instance, as well as holding
+data objects such as :class:`grok.Container` and :class:`grok.Model` object
+instances.
+
+.. autoclass:: grok.Application
+ :members:
+
+
+:class:`grok.Model`
+===================
+
+Model objects provide persistence and containment. Model in Grok refers to
+an applications data model - that is data which is persistently saved to
+disk, by default in the Zope Object Database (ZODB).
+
+.. autoclass:: grok.Model
+ :members:
+
+ .. attribute:: __parent__
+
+ The parent in the location hierarchy.
+
+ If you recursively follow the :attr:`__parent__` attribute, you
+ will always reach a reference to a top-level grok.Application
+ object instance.
+
+ .. attribute:: __name__
+
+ The name within the parent.
+
+ Traverse the parent with this name to get the object.
+
+ Name in Grok means "human-readable identifier" as the
+ :attr:`__name__` attribute is used to reference the object
+ within an URL.
+
+
+:class:`grok.Container`
+=======================
+
+Objects in a container are manipulated using the same syntax as you would
+with a standard Python Dictionary object. The container implements the
+zope.container.interfaces.IContainer interface using a BTree, providing
+reasonable performance for large collections of objects.
+
+.. autoclass:: grok.Container
+
+ .. attribute:: __parent__
+
+ The parent in the location hierarchy.
+
+ If you recursively follow the :attr:`__parent__` attribute, you
+ will always reach a reference to a top-level grok.Application
+ object instance.
+
+ .. attribute:: __name__
+
+ The name within the parent.
+
+ Traverse the parent with this name to get the object.
+
+ Name in Grok means "human-readable identifier" as the
+ :attr:`__name__` attribute is used to reference the object
+ within an URL.
+
+ .. method:: items(key=None)
+
+ Return an iterator over the key-value pairs in the container.
+
+ If ``None`` is passed as `key`, this method behaves as if no argument
+ were passed.
+
+ If `key` is in the container, the first item provided by the iterator
+ will correspond to that key. Otherwise, the first item will be for
+ the key that would come next if `key` were in the container.
+
+ .. method:: keys(key=None)
+
+ Return an iterator over the keys in the container.
+
+ If ``None`` is passed as `key`, this method behaves as if no argument
+ were passed.
+
+ If `key` is in the container, the first key provided by the iterator
+ will be that key. Otherwise, the first key will be the one that would
+ come next if `key` were in the container.
+
+ .. method:: values(key=None)
+
+ Return an iterator over the values in the container.
+
+ If ``None`` is passed as `key`, this method behaves as if no argument
+ were passed.
+
+ If `key` is in the container, the first value provided by the iterator
+ will correspond to that key. Otherwise, the first value will be for
+ the key that would come next if `key` were in the container.
+
+
+ .. method:: __getitem__(key)
+
+ Get a value for a key
+
+ A KeyError is raised if there is no value for the key.
+
+ .. method:: get(key, default=None)
+
+ Get a value for a key
+
+ The default is returned if there is no value for the key.
+
+ .. method:: __contains__(key)
+
+ Tell if a key exists in the mapping.
+
+
+ .. method:: __iter__()
+
+ Return an iterator for the keys of the mapping object.
+
+ .. method:: values()
+
+ Return the values of the mapping object.
+
+ .. method:: items()
+
+ Return the items of the mapping object.
+
+ .. method:: __len__()
+
+ Return the number of items.
+
+ .. method:: has_key(key)
+
+ Tell if a key exists in the mapping.
+
+ .. method:: __setitem__(name, object)
+
+ Add the given `object` to the container under the given name.
+
+ Raises a ``TypeError`` if the key is not a unicode or ascii string.
+ Raises a ``ValueError`` if key is empty.
+
+ The container might choose to add a different object than the
+ one passed to this method.
+
+ If the object doesn't implement `IContained`, then one of two
+ things must be done:
+
+ 1. If the object implements `ILocation`, then the `IContained`
+ interface must be declared for the object.
+
+ 2. Otherwise, a `ContainedProxy` is created for the object and
+ stored.
+
+ The object's `__parent__` and `__name__` attributes are set to the
+ container and the given name.
+
+ If the old parent was ``None``, then an `IObjectAddedEvent` is
+ generated, otherwise, an `IObjectMovedEvent` is generated. An
+ `IContainerModifiedEvent` is generated for the container.
+
+ If the object replaces another object, then the old object is
+ deleted before the new object is added, unless the container
+ vetos the replacement by raising an exception.
+
+ If the object's `__parent__` and `__name__` were already set to
+ the container and the name, then no events are generated and
+ no hooks. This allows advanced clients to take over event
+ generation.
+
+ .. method:: __delitem__(name)
+
+ Delete the named object from the container.
+
+ Raises a ``KeyError`` if the object is not found.
+
+ If the deleted object's `__parent__` and `__name__` match the
+ container and given name, then an `IObjectRemovedEvent` is
+ generated and the attributes are set to ``None``. If the object
+ can be adapted to `IObjectMovedEvent`, then the adapter's
+ `moveNotify` method is called with the event.
+
+ Unless the object's `__parent__` and `__name__` attributes were
+ initially ``None``, generate an `IContainerModifiedEvent` for the
+ container.
+
+ If the object's `__parent__` and `__name__` were already set to
+ ``None``, then no events are generated. This allows advanced
+ clients to take over event generation.
+
+
+**Example 1: Perform Create, Read, Update and Delete (CRUD) on a container**
+
+.. code-block:: python
+
+ # define a container and a model and then create them
+ class BoneBag(grok.Container): pass
+ class Bone(grok.Model): pass
+ bag = BoneBag()
+ skull = Bone()
+
+ # ... your classes are then "grokked" by Grok ...
+
+ # store an object in a container
+ bag['bone1'] = skull
+
+ # test for containment
+ bag.has_key('bone1')
+
+ # retrieve an object from a container
+ first_bone = bag['bone1']
+
+ # iterate through objects in a container with .values()
+ # you can also use .keys() and .items()
+ for bone in bag.values():
+ bone.marks = 'teeth'
+
+ # delete objects using the del keyword
+ del bag['bone1']
+
+
+:class:`grok.OrderedContainer`
+==============================
+
+OrderedContainers act just like Containers, but also support the ability
+to maintain order on the items within the container. This implementation
+maintains a persistent list of keys on a private attribute, so it's
+important to note that OrderedContainers will have poorer performance than
+a normal Container.
+
+.. autoclass:: grok.OrderedContainer
+ :members:
+
+
+Indexes
+~~~~~~~
+
+:class:`grok.Indexes`
+=====================
+
+:class:`Indexes` are local utilities for holding a set of indexes
+alongside a :class:`grok.Site` or :class:`grok.Application`. An index
+is a data structure that provides a way of quickly finding certain
+types of objects, i.e. it provides catalog functionality for
+attributes/contents of stored objects.
+
+.. autodata:: grok.Indexes
+
+ **Directives:**
+
+ :func:`grok.context(context_obj_or_interface)`
+ Required. Identifies the type of objects that should be
+ catalogued. The ``context`` type can also be set module-wide.
+
+ .. seealso::
+
+ :func:`grok.context`
+
+ :func:`grok.site(application_type_or_interface)`
+ Required. Identifies the type of site or application in which
+ objects should be catalogued.
+
+ .. seealso::
+
+ :func:`grok.site`
+
+
+Grok Index Definitions
+======================
+
+.. automodule:: grok.index
+ :members:
+ :inherited-members:
+ :undoc-members:
+
+**Example 1: Index the Mammoths in a Herd**
+
+Imagine you have a herd of mammoths, and you wish to quickly find a
+mammoth based on their last name. First we will create a simple Grok
+application that defines a Herd and some Mammoths:
+
+.. code-block:: python
+
+ import grok
+ import grok.index
+ import zope.interface
+ import zope.schema
+
+ class Herd(grok.Container, grok.Application):
+ pass
+
+ class IMammoth(zope.interface.Interface):
+ full_name = zope.schema.TextLine(title=u'Full Name')
+
+ class MammothIndexes(grok.Indexes):
+ grok.site(Herd)
+ grok.context(IMammoth)
+
+ full_name = grok.index.Text()
+
+ class Mammoth(grok.Model):
+ grok.implements(IMammoth)
+
+ def __init__(self, full_name):
+ self.full_name = full_name
+
+We can now create a Herd application, add some Mammoths to the Herd, and
+query for those Mammoths by their last name.
+
+Imagine ``root`` is our ZODB root as provided for instance by a
+debugger::
+
+ >>> herd = Herd()
+ >>> root['herd'] = herd # <-- the indexes are created here
+
+We manually set the 'site' to search. This happens automatically when
+we do for instance regular browser requests::
+
+ >>> from zope.site.hooks import setSite
+ >>> setSite(herd)
+
+Populate the herd::
+
+ >>> herd['one'] = Mammoth('Manfred Mammoth')
+ >>> herd['two'] = Mammoth('Joe Mammoth')
+ >>> herd['three'] = Mammoth('Marty the Wooly')
+
+Search the herd::
+
+ >>> import zope.component
+ >>> from zope.catalog.interfaces import ICatalog
+ >>> catalog = zope.component.getUtility(ICatalog)
+ >>> mammoths = catalog.searchResults(full_name='Mammoth')
+
+``mammoths`` would be a list containing ``'Manfred Mammoth'`` and
+``'Joe Mammoth'`` but not ``'Marty the Wooly'``
+
+
+Adapters
+~~~~~~~~
+
+.. currentmodule:: grok
+
+:class:`grok.Adapter`
+=====================
+
+An Adapter takes an object providing an existing interface and extends
+it to provide a new interface.
+
+The object providing the existing interface is passed to the Adapter
+in the constructor, and is stored in an attribute named 'context.
+The source code for the `grok.Adapter` base class is simply:
+
+.. code-block:: python
+
+ class Adapter(object):
+ def __init__(self, context):
+ self.context = context
+
+.. autoclass:: grok.Adapter
+ :members:
+
+ .. The Adapter class itself does not provide docstrings.
+
+ Base class to define an adapter. Adapters are automatically
+ registered when a module is "grokked".
+
+ .. attribute:: context
+
+ The adapted object.
+
+ **Directives:**
+
+ :data:`grok.context(context_obj_or_interface)`
+ Maybe required. Identifies the type of objects or interface for
+ the adaptation.
+
+ .. seealso::
+
+ :func:`grok.context`
+
+ :data:`grok.implements(\*interfaces)`
+ Required. Identifies the interface(s) the adapter implements.
+
+ .. seealso::
+
+ :func:`grok.implements`
+
+ :data:`grok.name(name)`
+ Optional. Identifies the name used for the adapter
+ registration. If ommitted, no name will be used.
+
+ When a name is used for the adapter registration, the adapter
+ can only be retrieved by explicitely using its name.
+
+ .. seealso::
+
+ :func:`grok.name`
+
+ :func:`grok.provides(name)`
+ Maybe required.
+
+ .. seealso::
+
+ :func:`grok.provides`
+
+
+**Example 1: Simple adaptation example**
+
+.. code-block:: python
+
+ import grok
+ from zope import interface
+
+ class Cave(grok.Model):
+ "Cave is the class being adapted (the adaptee)"
+
+ def __init__(self, size=100):
+ self.size = size
+
+ class IHome(interface.Interface):
+ "IHome is the interface we want to add to a Cave"
+
+ def renovate():
+ "Enlarge Cave"
+
+ class CaveHome(grok.Adapter):
+ "Turns a Cave into a Home"
+ grok.context(Cave)
+ grok.implements(IHome) # the new interface provided by the adapter
+
+ def renovate(self):
+ # the adaptee is an attribute named 'context'
+ # and is passed in to the constructor
+ self.context.size += 10
+
+ # Adapation (component look-up) is invoked by passing the adaptee
+ # to the interface as a constructor and returns the component adapted to
+ home = IHome(cave)
+ home.renovate()
+
+ # Multiple adapters can exist that adapt and provide the same interfaces.
+ # They can be distinguished by name.
+
+ import zope.component
+
+ class LargeCaveHome(grok.Adapater):
+ "Turns a Cave in a large Home"
+ grok.context(Cave)
+ grok.implements(IHome)
+ grok.name('largehome')
+
+ def renovate(self):
+ self.context.size += 200
+
+ largehome = zope.component.getAdapter(cave, IHome, name='largehome')
+ largehome.renovate()
+
+:class:`grok.MultiAdapter`
+==========================
+
+A MultiAdapter takes multiple objects providing existing interface(s)
+and extends them to provide a new interface.
+
+The :class:`grok.MultiAdapter` base class does not provide a default
+constructor implementation, it's up to the individual multi-adapters
+to determine how to handle the objects being adapted.
+
+.. autoclass:: grok.MultiAdapter
+ :members:
+
+ Base class to define a Multi Adapter.
+
+ **Directives:**
+
+ :data:`grok.adapts(\*objects_or_interfaces)`
+ Required. Identifies the combination of types of objects or interfaces
+ for the adaptation.
+
+ :data:`grok.implements(\*interfaces)`
+ Required. Identifies the interfaces(s) the adapter implements.
+
+ :data:`grok.name(name)`
+ Optional. Identifies the name used for the adapter registration. If
+ ommitted, no name will be used.
+
+ When a name is used for the adapter registration, the adapter
+ can only be retrieved by explicitely using its name.
+
+ :data:`grok.provides(name)`
+ Only required if the adapter implements more than one
+ interface. :func:`grok.provides` is required to disambiguate
+ for which interface the adapter will be registered for.
+
+**Example: A home is made from a cave and a fireplace.**
+
+.. code-block:: python
+
+ import grok
+ import zope.component
+ import zope.interface
+
+ class Fireplace(grok.Model): pass
+ class Cave(grok.Model): pass
+ class IHome(zope.interface.Interface): pass
+
+ class Home(grok.MultiAdapter):
+ grok.adapts(Cave, Fireplace)
+ grok.implements(IHome)
+
+ def __init__(self, cave, fireplace):
+ self.cave = cave
+ self.fireplace = fireplace
+
+ home = zope.component.getMultiAdapter((cave, fireplace), IHome)
+
+**Example: A Grok View is a MultiAdapter**
+
+In Grok, MultiAdapters are most commonly encountered in the form of
+Views. A View is a MultiAdapter which adapts the `request` and the
+`context` to provide the `IGrokView` interface. You can lookup a
+View component using the `getMultiAdapter` function.
+
+.. code-block:: python
+
+ class FireplaceView(grok.View):
+ grok.context(Fireplace)
+ grok.name('fire-view')
+
+ class AlternateFireplaceView(grok.View):
+ grok.context(Fireplace)
+
+ def render(self):
+ fireplaceview = zope.component.getMultiAdapter(
+ (self.context, self.request), IGrokView, name='fire-view'
+ )
+ return fireplaceview.render()
+
+
+:class:`grok.Annotation`
+========================
+
+Annotation components are persistent writeable adapters.
+
+.. autoclass:: grok.Annotation
+ :members:
+
+ Inherits from the :class:`persistent.Persistent` class.
+
+
+**Example: Storing annotations on model objects**
+
+.. code-block:: python
+
+ import grok
+ from zope import interface
+
+ # Create a model and an interface you want to adapt it to
+ # and an annotation class to implement the persistent adapter.
+ class Mammoth(grok.Model):
+ pass
+
+ class ISerialBrand(interface.Interface):
+ unique = interface.Attribute("Brands")
+
+ class Branding(grok.Annotation):
+ grok.implements(IBranding)
+ unique = 0
+
+ # Grok the above code, then create some mammoths
+ manfred = Mammoth()
+ mumbles = Mammoth()
+
+ # creating Annotations work just like Adapters
+ livestock1 = ISerialBrand(manfred)
+ livestock2 = ISerialBrand(mumbles)
+
+ # except you can store data in them, this data will transparently persist
+ # in the database for as long as the object exists
+ livestock1.unique = 101
+ livestock2.unique = 102
+
+ # attributes not listed in the interface will also be persisted
+ # on the annotation
+ livestock2.foo = "something"
+
+Utilities
+~~~~~~~~~
+
+:class:`grok.GlobalUtility`
+===========================
+
+A global utility is an object which provides an interface, and can be
+looked-up by that interface and optionally the component name. The
+attributes provided by a global utility are not persistent.
+
+Examples of global utilities are database connections, XML parsers,
+and web service proxies.
+
+.. autoclass:: grok.GlobalUtility
+ :members:
+
+ Base class to define a globally registered utility. Global utilities are
+ automatically registered when a module is "grokked".
+
+ **Directives:**
+
+ :data:`grok.implements(\*interfaces)`
+ Required. Identifies the interfaces(s) the utility implements.
+
+ :data:`grok.name(name)`
+ Optional. Identifies the name used for the adapter registration. If
+ ommitted, no name will be used.
+
+ When a name is used for the global utility registration, the global
+ utility can only be retrieved by explicitely using its name.
+
+ :data:`grok.provides(name)`
+ Maybe required. If the global utility implements more than one
+ interface, :func:`grok.provides` is required to disambiguate
+ for what interface the global utility will be registered.
+
+
+:class:`grok.LocalUtility`
+==========================
+
+A local utility is an object which provides an interface, and can be
+looked-up by that interface and optionally the component name. The attributes
+provided by a local utility are transparently stored in the database (ZODB).
+This means that configuration changes to a local utility lasts between
+server restarts.
+
+An example is for database connections or web service proxies,
+where you need to dynamically provide the connection settings
+so that they can be edited through-the-web.
+
+.. autoclass:: grok.LocalUtility
+ :members:
+
+ Defines utilities that will be registered local to a
+ :class:`grok.Site` or :class:`grok.Application` object by using
+ the :func:`grok.local_utility` directive.
+
+ **Directives:**
+
+ :data:`grok.implements(\*interfaces)`
+ Optional. Identifies the interfaces(s) the utility implements.
+
+ :data:`grok.name(name)`
+ Optional. Identifies the name used for the adapter registration. If
+ ommitted, no name will be used.
+
+ When a name is used for the local utility registration, the
+ local utility can only be retrieved by explicitely using its
+ name.
+
+ :data:`grok.provides(name)`
+ Maybe required. If the local utility implements more than one
+ interface or if the implemented interface cannot be
+ determined, :func:`grok.provides` is required to disambiguate
+ for what interface the local utility will be registered.
+
+ .. seealso::
+
+ Local utilities need to be registered in the context of
+ :class:`grok.Site` or :class:`grok.Application` using the
+ :func:`grok.local_utility` directive.
+
+:class:`grok.Site`
+==================
+
+Contains a Site Manager. Site Managers act as containers for registerable
+components.
+
+If a Site Manager is asked for an adapter or utility, it checks for those
+it contains before using a context-based lookup to find another site
+manager to delegate to. If no other site manager is found they defer to
+the global site manager which contains file based utilities and adapters.
+
+.. autoclass:: grok.Site
+ :members:
+
+ .. automethod:: grok.Site.getSiteManager()
+
+ Returns the site manager contained in this object.
+
+ If there isn't a site manager, raise a component lookup.
+
+ .. automethod:: grok.Site.setSiteManager(sitemanager)
+
+ Sets the site manager for this object.
+
+Views
+~~~~~
+
+:class:`grok.View`
+==================
+
+Views handle interactions between the user and the model. The are
+constructed with context and request attributes, are responsible for
+providing a response. The request attribute in a View will always be
+for a normal HTTP Request.
+
+The determination of what :class:`View` gets used for what
+:class:`Model` is made by walking the URL in the HTTP Request object
+sepearted by the ``/`` character. This process is called "Traversal".
+
+.. autoclass:: grok.View
+
+ .. attribute:: context
+
+ The object that the view is presenting. This is often an instance of
+ a grok.Model class, but can be a grok.Application, grok.Container
+ object or any type of Python object.
+
+ .. attribute:: request
+
+ The HTTP Request object.
+
+ .. autoattribute:: grok.View.response
+
+ The HTTP Response object that is associated with the request.
+
+ This is also available as ``self.request.response``, but the
+ response attribute is provided as a convenience.
+
+ .. attribute:: static
+
+ Directory resource containing the static files of the view's
+ package.
+
+ .. autoattribute:: grok.View.body
+
+ Get the body of the associated request.
+
+ .. automethod:: grok.View.redirect
+
+ Redirect to `url`.
+
+ The headers of the :attr:`response` are modified so that the
+ calling browser gets a redirect status code. Please note, that
+ this method returns before actually sending the response to
+ the browser.
+
+ `url` is a string that can contain anything that makes sense
+ to a browser. Also relative URIs are allowed.
+
+ `status` is a number representing the HTTP status code sent
+ back. If not given or ``None``, ``302`` or ``303`` will be
+ sent, depending on the HTTP protocol version in use (HTTP/1.0
+ or HTTP/1.1).
+
+ `trusted` is a boolean telling whether we're allowed to
+ redirect to 'external' hosts. Normally redirects to other
+ hosts than the one the request was sent to are forbidden and
+ will raise a :exc:`ValueError`.
+
+ .. automethod:: grok.View.url
+
+ If no arguments given, construct URL to view itself.
+
+ If only obj argument is given, construct URL to obj.
+
+ If only name is given as the first argument, construct URL
+ to context/name.
+
+ If both object and name arguments are supplied, construct
+ URL to obj/name.
+
+ .. automethod:: grok.View.default_namespace
+
+ Returns a dictionary of namespaces that the template
+ implementation expects to always be available.
+
+ This method is *not* intended to be overridden by application
+ developers.
+
+ .. automethod:: grok.View.namespace
+
+ Returns a dictionary that is injected in the template
+ namespace in addition to the default namespace.
+
+ This method *is* intended to be overridden by the application
+ developer.
+
+ .. automethod:: grok.View.update
+
+ This method is meant to be implemented by :class:`grok.View`
+ subclasses. It will be called *before* the view's associated
+ template is rendered and can be used to pre-compute values
+ for the template.
+
+ update() can take arbitrary keyword parameters which will be
+ filled in from the request (in that case they *must* be
+ present in the request).
+
+ .. automethod:: grok.View.render
+
+ A view can either be rendered by an associated template, or
+ it can implement this method to render itself from Python.
+ This is useful if the view's output isn't XML/HTML but
+ something computed in Python (plain text, PDF, etc.)
+
+ render() can take arbitrary keyword parameters which will be
+ filled in from the request (in that case they *must* be
+ present in the request).
+
+ .. automethod:: grok.View.application_url
+
+ .. automethod:: grok.View.flash
+
+
+
+:class:`grok.ViewletManager`
+============================
+
+A ViewletManager is a component that provides access to a set of
+content providers (Viewlets). The ViewletManager's responsibilities are:
+
+ * Aggregation of all viewlets registered for the manager.
+
+ * Apply a set of filters to determine the availability of the viewlets.
+
+ * Sort the viewlets based on some implemented policy. The default is to
+ numerically sort accoring to the `grok.order([number])` directive on a
+ Viewlet.
+
+ * Provide an environment in which the viewlets are rendered.
+
+ * Render itself containing the HTML content of the viewlets.
+
+ViewletManager's also implement a read-only mapping API, so the Viewlet's
+that they contain can be read like a normal Python dictionary.
+
+.. autoclass:: grok.ViewletManager
+
+ .. XXX: undocumented: sort(), filter(), get().
+
+ .. attribute:: context
+
+ Typically the Model object for which this ViewletManager is being
+ rendered in the context of.
+
+ .. attribute:: request
+
+ The Request object.
+
+ .. attribute:: view
+
+ Reference to the View that the ViewletManager is being provided
+ in.
+
+ .. automethod:: grok.ViewletManager.default_namespace
+
+ Returns a dictionary of namespaces that the template
+ implementation expects to always be available.
+
+ This method is *not* intended to be overridden by application
+ developers.
+
+ .. automethod:: grok.ViewletManager.namespace
+
+ Returns a dictionary that is injected in the template
+ namespace in addition to the default namespace.
+
+ This method *is* intended to be overridden by the application
+ developer.
+
+ .. automethod:: grok.ViewletManager.update
+
+ This method is called before the ViewletManager is rendered, and
+ can be used to perform pre-computation.
+
+ .. automethod:: grok.ViewletManager.render
+
+ This method renders the content provided by this ViewletManager.
+ Typically this will mean rendering and concatenating all of the
+ Viewlets managed by this ViewletManager.
+
+
+**Example: Register a ViewletManager and Viewlet and use them from a template for a View**
+
+This is a very simple example, ViewletManagers and Viewlets can be used to
+support more complex HTML layout use cases, such as discriminating on the
+view or context in which a particular ViewletManager will be rendered. For
+example, a web site about caves and herds might want to show information in
+the sidebar specific to either a cave or a herd, depending upon whether a page
+is displaying information about a cave or a herd.
+
+.. code-block:: python
+
+ class ViewForACave(grok.View):
+ def render():
+ return grok.PageTemplate("""
+ <html><body>
+ <div tal:content="structure provider:cave" />
+ </body></html>
+ """)
+
+ class CaveManager(grok.ViewletManager):
+ grok.view(ViewForACave)
+ grok.name('cave')
+
+ class CaveViewlet(grok.Viewlet):
+ grok.order(30)
+ grok.viewletmanager(CaveManager)
+
+ def render(self):
+ return "Cave"
+
+
+:class:`grok.Viewlet`
+=====================
+
+Viewlets are a flexible way to compound HTML snippets.
+
+Viewlets are typically used for the layout of the web site. Often all the
+pages of the site have the same layout with header, one or two columns, the
+main content area and a footer.
+
+.. autoclass:: grok.Viewlet
+ :members:
+
+ .. attribute:: context
+
+ Typically the Model object for which this Viewlet is being
+ rendered in the context of.
+
+ .. attribute:: request
+
+ The Request object.
+
+ .. attribute:: view
+
+ Reference to the View that the Viewlet is being provided in.
+
+ .. attribute:: viewletmanager
+
+ Reference to the ViewletManager that is rendering this Viewlet.
+
+ .. automethod:: grok.Viewlet.default_namespace
+
+ Returns a dictionary of namespaces that the template
+ implementation expects to always be available.
+
+ This method is *not* intended to be overridden by application
+ developers.
+
+ .. automethod:: grok.Viewlet.namespace
+
+ Returns a dictionary that is injected in the template
+ namespace in addition to the default namespace.
+
+ This method *is* intended to be overridden by the application
+ developer.
+
+ .. automethod:: grok.Viewlet.update
+
+ This method is called before the Viewlet is rendered, and
+ can be used to perfrom pre-computation.
+
+ .. automethod:: grok.Viewlet.render
+
+ This method renders the content provided by this Viewlet.
+
+
+:class:`grok.JSON`
+==================
+
+Specialized View that returns data in JSON format.
+
+Python data returned is automatically converted into JSON format using
+the simplejson library. Every method name in a grok.JSON component is
+registered as the name of a JSON View. The exceptions are names that
+begin with an _ or special names such as __call__. The grok.require
+decorator can be used to protect methods with a permission.
+
+.. autoclass:: grok.JSON
+
+ .. attribute:: context
+
+ Object that the JSON handler presents.
+
+ .. attribute:: request
+
+ Request that JSON handler was looked up with.
+
+ .. autoattribute:: response
+
+ The response sent back to the client.
+
+ .. attribute:: body
+
+ The text of the request body.
+
+ .. automethod:: redirect
+
+ Redirect to `url`.
+
+ The headers of the :attr:`response` are modified so that the
+ calling browser gets a redirect status code. Please note, that
+ this method returns before actually sending the response to
+ the browser.
+
+ `url` is a string that can contain anything that makes sense
+ to a browser. Also relative URIs are allowed.
+
+ `status` is a number representing the HTTP status code sent
+ back. If not given or ``None``, ``302`` or ``303`` will be
+ sent, depending on the HTTP protocol version in use (HTTP/1.0
+ or HTTP/1.1).
+
+ `trusted` is a boolean telling whether we're allowed to
+ redirect to 'external' hosts. Normally redirects to other
+ hosts than the one the request was sent to are forbidden and
+ will raise a :exc:`ValueError`.
+
+ .. automethod:: url
+
+ .. automethod:: publishTraverse
+
+ Lookup a name and return an object with `self.context` as its parent.
+ The method can use the request to determine the correct object.
+
+ The `request` argument is the publisher request object. The
+ `name` argument is the name that is to be looked up. It must
+ be an ASCII string or Unicode object.
+
+ If a lookup is not possible, raise a :exc:`NotFound` error.
+
+ .. automethod:: browserDefault
+
+ Returns an object and a sequence of names.
+
+ The publisher calls this method at the end of each traversal path.
+ If the sequence of names is not empty, then a traversal step is made
+ for each name. After the publisher gets to the end of the sequence,
+ it will call browserDefault on the last traversed object.
+
+ The default behaviour in Grok is to return `self.context` for
+ the object and ``'index'`` for the default view name.
+
+ Note that if additional traversal steps are indicated (via a
+ nonempty sequence of names), then the publisher will try to adjust
+ the base href.
+
+
+**Example 1: Create a public and a protected JSON view.**
+
+.. code-block:: python
+
+ class MammothJSON(grok.JSON):
+ """
+ Returns JSON from URLs in the form of:
+
+ http://localhost/stomp
+ http://localhost/dance
+ """
+
+ grok.context(zope.interface.Interface)
+
+ def stomp(self):
+ return {'Manfred stomped.': ''}
+
+ @grok.require('zope.ManageContent')
+ def dance(self):
+ return {'Manfred does not like to dance.': ''}
+
+
+:class:`grok.REST`
+==================
+
+Specialized View for making web services that conform to the REST style.
+These Views can define methods named GET, PUT, POST and DELETE, which will
+be invoked based on the Request type.
+
+.. autoclass:: grok.REST
+
+ .. attribute:: context
+
+ Object that the REST handler presents.
+
+ .. attribute:: request
+
+ Request that REST handler was looked up with.
+
+ .. autoattribute:: response
+
+ The response sent back to the client.
+
+ .. autoattribute:: body
+
+ The text of the request body.
+
+ .. automethod:: url
+
+ .. automethod:: redirect
+
+ Redirect to `url`.
+
+ The headers of the :attr:`response` are modified so that the
+ calling browser gets a redirect status code. Please note, that
+ this method returns before actually sending the response to
+ the browser.
+
+ `url` is a string that can contain anything that makes sense
+ to a browser. Also relative URIs are allowed.
+
+ `status` is a number representing the HTTP status code sent
+ back. If not given or ``None``, ``302`` or ``303`` will be
+ sent, depending on the HTTP protocol version in use (HTTP/1.0
+ or HTTP/1.1).
+
+ `trusted` is a boolean telling whether we're allowed to
+ redirect to 'external' hosts. Normally redirects to other
+ hosts than the one the request was sent to are forbidden and
+ will raise a :exc:`ValueError`.
+
+
+:class:`grok.XMLRPC`
+====================
+
+Specialized View that responds to XML-RPC.
+
+.. autoclass:: grok.XMLRPC
+
+ .. attribute:: context
+
+ Object that the REST handler presents.
+
+ .. attribute:: request
+
+ Request that REST handler was looked up with.
+
+ .. autoattribute:: grok.XMLRPC.response
+
+ The response sent back to the client.
+
+ .. autoattribute:: grok.XMLRPC.body
+
+ The text of the request body.
+
+ .. automethod:: grok.XMLRPC.url
+
+ .. automethod:: grok.XMLRPC.redirect
+
+
+**Example 1: Create a public and a protected XML-RPC view.**
+
+The grok.require decorator can be used to protect methods with a permission.
+
+.. code-block:: python
+
+ import grok
+ import zope.interface
+
+ class MammothRPC(grok.XMLRPC):
+ grok.context(zope.interface.Interface)
+
+ def stomp(self):
+ return 'Manfred stomped.'
+
+ @grok.require('zope.ManageContent')
+ def dance(self):
+ return 'Manfred doesn\'t like to dance.'
+
+
+:class:`grok.Traverser`
+=======================
+
+A Traverser is used to map from a URL to an object being published (Model)
+and the View used to interact with that object.
+
+.. autoclass:: grok.Traverser
+
+ Override the :meth:`traverse` method to supply the desired custom
+ traversal behaviour.
+
+ .. attribute:: context
+
+ The object that is being traversed.
+
+ .. attribute:: request
+
+ The HTTP Request object.
+
+ .. automethod:: traverse
+
+ You must provide your own implementation of this method to do
+ what you want. If you return ``None``, Grok will use the
+ default traversal behaviour.
+
+ .. automethod:: browserDefault
+
+ Returns an object and a sequence of names.
+
+ The publisher calls this method at the end of each traversal path.
+ If the sequence of names is not empty, then a traversal step is made
+ for each name. After the publisher gets to the end of the sequence,
+ it will call browserDefault on the last traversed object.
+
+ The default behaviour in Grok is to return `self.context` for
+ the object and ``'index'`` for the default view name.
+
+ Note that if additional traversal steps are indicated (via a
+ nonempty sequence of names), then the publisher will try to adjust
+ the base href.
+
+ .. automethod:: publishTraverse
+
+ Lookup a name and return an object with `self.context` as its parent.
+ The method can use the request to determine the correct object.
+
+ The `request` argument is the publisher request object. The
+ `name` argument is the name that is to be looked up. It must
+ be an ASCII string or Unicode object.
+
+ If a lookup is not possible, raise a :exc:`NotFound` error.
+
+
+**Example 1: Traverse into a Herd Model and return a Mammoth Model**
+
+.. code-block:: python
+
+ import grok
+
+ class Herd(grok.Model):
+
+ def __init__(self, name):
+ self.name = name
+
+ class HerdTraverser(grok.Traverser):
+ grok.context(Herd)
+
+ def traverse(self, name):
+ return Mammoth(name)
+
+ class Mammoth(grok.Model):
+
+ def __init__(self, name):
+ self.name = name
+
+
+:class:`grok.PageTemplate`
+==========================
+
+Page Templates are the default templating system for Grok, they are an
+implementation of the Template Attribute Language (TAL). Page Templates
+are typically created from a string.
+
+.. code-block:: python
+
+ grok.PageTemplate("<h1>Hello World!</h1>")
+
+.. autoclass:: grok.PageTemplate
+
+ .. automethod:: grok.PageTemplate._initFactory
+
+ Template language specific initializations on the view factory.
+
+ .. automethod:: grok.PageTemplate.render
+
+ Renders the template.
+
+ .. automethod:: grok.PageTemplate.setFromString
+
+ .. automethod:: grok.PageTemplate.setFromFilename
+
+ .. automethod:: grok.PageTemplate.getNamespace
+
+ .. automethod:: grok.PageTemplate.namespace
+
+
+:class:`grok.PageTemplateFile`
+==============================
+
+Creates a Page Template from a filename.
+
+.. code-block:: python
+
+ grok.PageTemplateFile("my_page_template.pt")
+
+.. autoclass:: grok.PageTemplateFile
+
+ .. automethod:: grok.PageTemplateFile._initFactory
+
+ Template language specific initializations on the view factory.
+
+ .. automethod:: grok.PageTemplateFile.render
+
+ Renders the template.
+
+ .. automethod:: grok.PageTemplateFile.setFromString
+
+ .. automethod:: grok.PageTemplateFile.setFromFilename
+
+ .. automethod:: grok.PageTemplateFile.getNamespace
+
+ .. automethod:: grok.PageTemplateFile.namespace
+
+
+
+Forms
+~~~~~
+
+Forms inherit from the :class:`grok.View` class. They are a specialized type of
+View that renders an HTML Form.
+
+:class:`grok.Form`
+==================
+
+.. autoclass:: grok.Form
+
+ .. attribute:: template
+
+ Template used to display the form
+
+ .. attribute:: context
+
+ The object for which the form is rendered.
+
+ .. attribute:: prefix
+
+ Page-element prefix. All named or identified page elements in a
+ subpage should have names and identifiers that begin with a subpage
+ prefix followed by a dot.
+
+ .. automethod:: setPrefix
+
+ Update the subpage prefix
+
+ .. attribute:: label
+
+ A label to display at the top of a form.
+
+ .. attribute:: status
+
+ An update status message. This is normally generated by success or
+ failure handlers.
+
+ .. attribute:: errors
+
+ Sequence of errors encountered during validation.
+
+ .. attribute:: form_result
+
+ Return from action result method.
+
+ .. attribute:: form_reset
+
+ Boolean indicating whether the form needs to be reset.
+
+ .. attribute:: form_fields
+
+ The form's form field definitions.
+
+ This attribute is used by many of the default methods.
+
+ .. attribute:: widgets
+
+ The form's widgets.
+
+ - set by :meth:`setUpWidgets`
+
+ - used by :meth:`validate`
+
+ .. autoattribute:: actions
+
+ .. autoattribute:: body
+
+ The text of the request body.
+
+ .. autoattribute:: response
+
+ The response sent back to the client.
+
+ .. automethod:: setUpWidgets
+
+ Set up the form's widgets.
+
+ The default implementation uses the form definitions in the
+ :attr:`form_fields` attribute and :meth:`setUpInputWidgets`.
+
+ The function should set the :attr:`widgets` attribute.
+
+ .. automethod:: validate
+
+ The default form validator
+
+ If an action is submitted and the action doesn't have it's own
+ validator then this function will be called.
+
+ .. automethod:: resetForm
+
+ Reset any cached data because underlying content may have changed.
+
+ .. automethod:: grok.Form.error_views
+
+ Return views of any errors.
+
+ The errors are returned as an iterable.
+
+ .. automethod:: applyData
+
+ Save form data to an object.
+
+ This returns a dictionary with interfaces as keys and lists of
+ field names as values to indicate which fields in which
+ schemas had to be changed in order to save the data. In case
+ the method works in update mode (e.g. on EditForms) and
+ doesn't have to update an object, the dictionary is empty.
+
+ .. automethod:: application_url
+
+ .. automethod:: applyChanges
+
+ .. deprecated:: 0.13
+ Use :meth:`applyData` instead.
+
+ .. automethod:: availableActions
+
+ .. automethod:: browserDefault
+
+ .. automethod:: default_namespace
+
+ .. automethod:: flash
+
+ .. automethod:: namespace
+
+ .. automethod:: publishTraverse
+
+ .. automethod:: redirect
+
+ .. automethod:: render
+
+ .. automethod:: update
+
+ .. automethod:: update_form
+
+ .. automethod:: url
+
+
+:class:`grok.AddForm`
+=====================
+
+Add forms are used for creating new objects. The widgets for this form
+are not bound to any existing content or model object.
+
+.. autoclass:: grok.AddForm
+ :members:
+ :undoc-members:
+
+ Inherits from :class:`grok.Form`.
+
+
+:class:`grok.EditForm`
+======================
+
+Edit forms are used for editing existing objects. The widgets for this form
+are bound to the object set in the `context` attribute.
+
+.. autoclass:: grok.EditForm
+ :members:
+ :undoc-members:
+
+ Inherits from :class:`grok.Form`.
+
+
+:class:`grok.DisplayForm`
+=========================
+
+Display forms are used to display an existing object. The widgets for this
+form are bound to the object set in the `context` attribute.
+
+.. autoclass:: grok.DisplayForm
+ :members:
+ :undoc-members:
+
+ Inherits from :class:`grok.Form`.
+
+
+Security
+~~~~~~~~
+
+:class:`grok.Permission`
+========================
+
+Permissions are used to protect Views so that they can only be called
+by an authenticated principal. If a View in Grok does not have a
+:func:`grok.require` directive declaring a permission needed to use
+the View, then the default anonymously viewable `zope.View` permission
+used.
+
+.. autoclass:: grok.Permission
+
+ Base class for permissions. You must specify a unique name for
+ every permission using the :func:`grok.name` directive. The convention
+ for ensuring uniqueness is to prefix your permission name with the
+ name of your Grok package followed by a dot,
+ e.g. ``'mypackage.MyPermissionName'``.
+
+ .. attribute:: id
+
+ Id as which this permission will be known and used. This is set
+ to the value specified in the :func:`grok.name` directive.
+
+ .. attribute:: title
+
+ Human readable identifier for this permission.
+
+ .. attribute:: description
+
+ Description of the permission.
+
+ **Directives:**
+
+ :data:`grok.name(name)`
+
+ Required. Identifies the unique name (also used as the id) of the
+ permission.
+
+ :data:`grok.title(title)`
+
+ Optional. Stored as the title attribute for this permission.
+
+ :data:`grok.description(description)`
+
+ Optional. Stored as the description attribute for this permission.
+
+
+**Example 1: Define a new Permission and use it to protect a View**
+
+.. code-block:: python
+
+ import grok
+ import zope.interface
+
+ class Read(grok.Permission):
+ grok.name('mypackage.Read')
+
+ class Index(grok.View):
+ grok.context(zope.interface.Interface)
+ grok.require('mypackage.Read')
+
+
+:class:`grok.Role`
+==================
+
+Roles provide a way to group together a collection of permissions. Principals
+(aka Users) can be granted a Role which will allow them to access all Views
+protected by the Permissions that the Role contains.
+
+.. autoclass:: grok.Role
+ :members:
+ :inherited-members:
+ :undoc-members:
+
+ .. attribute:: id
+
+ Id as which this role will be known and used. This is set
+ to the value specified in the :func:`grok.name` directive.
+
+ .. attribute:: title
+
+ Human readable identifier for this permission.
+
+ .. attribute:: description
+
+ Description of the permission.
+
+ **Directives:**
+
+ :data:`grok.name(name)`
+
+ Required. Identifies the unique name (also used as the id) of the
+ role.
+
+ :data:`grok.permissions(permissions)`
+
+ Required. Declare the permissions granted to this role. These
+ can refer by permission class or by name.
+
+ :data:`grok.title(title)`
+
+ Optional. Stored as the title attribute for this role.
+
+ :data:`grok.description(description)`
+
+ Optional. Stored as the description attribute for this role.
+
+**Example 1: Define a new 'paint.Artist' Role and assign it to the 'paint.grok' principal**
+
+.. code-block:: python
+
+ import grok
+ import zope.interface
+
+ class ViewPermission(grok.Permission):
+ grok.name('paint.ViewPainting')
+
+ class EditPermission(grok.Permission):
+ grok.name('paint.EditPainting')
+
+ class ErasePermission(grok.Permission):
+ grok.name('paint.ErasePainting')
+
+ class ApprovePermission(grok.Permission):
+ grok.name('paint.ApprovePainting')
+
+ class Artist(grok.Role):
+ """
+ An Artist can view, create and edit paintings. However, they can
+ not approve their painting for display in the Art Gallery Cave.
+ """
+ grok.name('paint.Artist')
+ grok.title('Artist')
+ grok.description('An artist owns the paintings that they create.')
+ grok.permissions(ViewPermission, EditPermission, ErasePermission)
+ # alternatively, use permission names
+ # grok.permissions(
+ # 'paint.ViewPainting', 'paint.EditPainting', 'paint.ErasePainting')
+
+ class CavePainting(grok.View):
+ grok.context(zope.interface.Interface)
+ grok.require(ViewPermission)
+
+ def render(self):
+ return 'What a beautiful painting.'
+
+ class EditCavePainting(grok.View):
+ grok.context(zope.interface.Interface)
+ grok.require(EditPermission)
+
+ def render(self):
+ return 'Let\'s make it even prettier.'
+
+ class EraseCavePainting(grok.View):
+ grok.context(zope.interface.Interface)
+ grok.require(ErasePermission)
+
+ def render(self):
+ return 'Oops, mistake, let\'s erase it.'
+
+ class ApproveCavePainting(grok.View):
+ grok.context(zope.interface.Interface)
+ grok.require(ApprovePermission)
+
+ def render(self):
+ return 'Painting owners cannot approve their paintings.'
+
+ # The app variable will typically be your Application instance,
+ # but could also be a container within your application.
+ from zope.securitypolicy.interfaces import IPrincipalRoleManager
+ IPrincipalRoleManager(app).assignRoleToPrincipal(
+ 'paint.Artist', 'paint.grok')
Added: groktoolkit/branches/jw-documentation-rearangement/doc/reference/conf.py
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/reference/conf.py (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/reference/conf.py 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,139 @@
+# -*- coding: utf-8 -*-
+#
+# Grok Reference documentation build configuration file, created by
+# sphinx-quickstart.py on Wed Feb 20 02:11:17 2008.
+#
+# This file is execfile()d with the current directory set to its containing dir.
+#
+# The contents of this file are pickled, so don't put values in the namespace
+# that aren't pickleable (module imports are okay, they're removed automatically).
+#
+# All configuration values have a default value; values that are commented out
+# show the default value as assigned to them.
+
+import sys
+
+#import os
+from os import path, curdir
+import re
+
+
+version = 'Unknown'
+setupfilepath = path.join(path.dirname(
+ path.dirname(path.abspath(curdir))), 'setup.py')
+reg = re.compile("^\s*version=.(.+).,.*")
+for line in open(setupfilepath, 'r').read().split():
+ m = reg.match(line)
+ if m:
+ version = m.groups()[0]
+
+
+
+
+# If your extensions are in another directory, add it here.
+#sys.path.append('some/directory')
+
+# General configuration
+# ---------------------
+
+# Add any Sphinx extension module names here, as strings. They can be extensions
+# coming with Sphinx (named 'sphinx.addons.*') or your custom ones.
+#extensions = []
+
+# Add any paths that contain templates here, relative to this directory.
+#templates_path = []
+
+# The suffix of source filenames.
+source_suffix = '.rst'
+
+# The master toctree document.
+master_doc = 'contents'
+
+# General substitutions.
+project = 'Grok Reference'
+copyright = '2006-2008, The Zope Foundation'
+
+# The default replacements for |version| and |release|, also used in various
+# other places throughout the built documents.
+#
+# The short X.Y version.
+version = version
+# The full version, including alpha/beta/rc tags.
+release = version
+
+# There are two options for replacing |today|: either, you set today to some
+# non-false value, then it is used:
+#today = ''
+# Else, today_fmt is used as the format for a strftime call.
+today_fmt = '%B %d, %Y'
+
+# List of documents that shouldn't be included in the build.
+#unused_docs = []
+
+# If true, '()' will be appended to :func: etc. cross-reference text.
+#add_function_parentheses = True
+
+# If true, the current module name will be prepended to all description
+# unit titles (such as .. function::).
+#add_module_names = True
+
+
+# Options for HTML output
+# -----------------------
+
+# If not '', a 'Last updated on:' timestamp is inserted at every page bottom,
+# using the given strftime format.
+html_last_updated_fmt = '%b %d, %Y'
+
+# If true, SmartyPants will be used to convert quotes and dashes to
+# typographically correct entities.
+html_use_smartypants = True
+
+# Content template for the index page, filename relative to this file.
+#html_index = ''
+
+# Custom sidebar templates, maps page names to filenames relative to this file.
+#html_sidebars = {}
+
+# Additional templates that should be rendered to pages, maps page names to
+# filenames relative to this file.
+#html_additional_pages = {}
+
+# If true, the reST sources are included in the HTML build as _sources/<name>.
+#html_copy_source = True
+
+# Output file base name for HTML help builder.
+htmlhelp_basename = 'Grok Referencedoc'
+
+# The style sheet to use for HTML and HTML Help pages. A file of that name
+# must exist either in Sphinx' static/ path, or in one of the custom paths
+# given in html_static_path.
+html_style = 'default.css'
+
+# Add any paths that contain custom static files (such as style sheets) here,
+# relative to this directory. They are copied after the builtin static files,
+# so a file named "default.css" will overwrite the builtin "default.css".
+#html_static_path = [path.join(path.abspath(curdir), '.static')]
+
+
+# Options for LaTeX output
+# ------------------------
+
+# The paper size ('letter' or 'a4').
+#latex_paper_size = 'letter'
+
+# The font size ('10pt', '11pt' or '12pt').
+#latex_font_size = '10pt'
+
+# Grouping the document tree into LaTeX files. List of tuples
+# (source start file, target name, title, author, document class [howto/manual]).
+#latex_documents = []
+latex_documents = [
+ ('reference.tex', 'Grok Reference', 'The Grok Team', 'manual')
+ ]
+
+# Additional stuff for the LaTeX preamble.
+#latex_preamble = '
+
+# Documents to append as an appendix to all manuals.
+#latex_appendices = []
Added: groktoolkit/branches/jw-documentation-rearangement/doc/reference/decorators.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/reference/decorators.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/reference/decorators.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,82 @@
+**********
+Decorators
+**********
+
+Grok uses a few decorators to register functions or methods for specific
+functionality.
+
+
+:func:`grok.subscribe` -- register a function as a subscriber for an event
+==========================================================================
+
+.. function:: subscribe(*classes_or_interfaces)
+
+ Declare that the decorated function subscribes to an event or a
+ combination of objects and events.
+
+ Applicable on module-level for functions. Requires at least one
+ class or interface as argument.
+
+
+:func:`grok.action` -- declare a form submit handler
+=====================================================
+
+.. function:: action(label, **options)
+
+ Decorator that defines an action factory based on a form
+ method. The method receives the form data as keyword
+ parameters.
+
+
+:func:`grok.require` -- protect a method with a permission
+==========================================================
+
+.. function:: require(name_or_class)
+
+ The decorated method will be protected by the permission. Used in
+ web service views such as REST or XML-RPC.
+
+
+:func:`grok.adapter/grok.implementer` -- declare an adapter factory
+====================================================================
+
+These decorators are always used in tandem to declare an adapter factory.
+
+.. function:: grok.adapter(*classes_or_interfaces)
+
+ Describes that a function adapts an object or a combination
+ of objects.
+
+.. function:: grok.implementer(interface)
+
+ Describes that a function that's used as an adapter
+ implements an interface or a number of interfaces.
+
+
+**Example 1: Adapt to an interface**
+
+.. code-block:: python
+
+ @grok.adapter(ICave)
+ @grok.implementer(IHome)
+ def home_for_cave(cave):
+ return Home()
+
+**Example 2: Adapt a regular class instead of an interface**
+
+.. code-block:: python
+
+ @grok.adapter(Cave)
+ @grok.implementer(IHome)
+ def home_for_cave(cave):
+ return Home()
+
+**Example 3: Declare a multi-adapter factory**
+
+.. code-block:: python
+
+ @grok.adapter(ICave, IFire)
+ @grok.implementer(ICozy)
+ def cozy_dwelling(cave, fire):
+ return Dwelling()
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/reference/directives.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/reference/directives.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/reference/directives.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,657 @@
+
+**********
+Directives
+**********
+
+.. Here we document the generic behaviour of the module level and class level
+ directives. The context sensitive behaviour is described in the individual
+ component documentation. We do use specific example to illustrate the use
+ of the directives.
+
+The :mod:`grok` module defines a set of directives that allow you to configure
+and register your components. Most directives assume a default, based on the
+environment of a module. (For example, a view will be automatically associated
+with a model if the association can be made unambigously.)
+
+If no default can be assumed for a value, grok will explicitly tell you what
+is missing and how you can provide a default or explicit assignment for
+the value in question.
+
+Core directives
+~~~~~~~~~~~~~~~
+
+Core directives are applicable to any type of component.
+
+:func:`grok.name`
+=================
+
+Associate a component with a name.
+
+Name is a unique identifier in the form of a string. The names of
+Containers, Models and Views are used to compose the URLs of the application.
+
+.. function:: grok.name(name)
+
+ A class level directive used to associate a component with a single
+ name `name`.
+
+ Typically this directive is optional. The default behaviour when no
+ name is given depends on the component. The same applies to the
+ semantics of this directive: for what exactly a name is set when
+ using this directive, depends on the component.
+
+**Example: Specify the name of a View to make a more readable URL**
+
+A common use case is to have a URL for a view named differently than
+the name of the view class itself. In this example, the class is named
+`SomeView` but is accessible at an URL suffixed with `/index`.
+
+.. code-block:: python
+
+ import grok
+
+ class Mammoth(grok.Model):
+ pass
+
+ class SomeView(grok.View):
+ grok.name('index')
+
+
+.. seealso::
+
+ :class:`grok.Adapter`, :class:`grok.Annotation`,
+ :class:`grok.GlobalUtility`, :class:`grok.Indexes`,
+ :class:`grok.MultiAdapter`, :class:`grok.Role`,
+ :class:`grok.View`
+
+
+:func:`grok.title`
+==================
+
+Succint description.
+
+This directive is not commonly used, but along with :func:`grok.description`
+can help provide more information about a component.
+
+.. function:: grok.title(title)
+
+ A descriptive title for a component.
+
+
+:func:`grok.description`
+========================
+
+Longer description.
+
+This directive is not commonly used, but along with :func:`grok.title`
+can help provide more information about a component.
+
+.. function:: grok.description(description)
+
+ A longer description for a component.
+
+
+:func:`grok.implements`
+=======================
+
+Declare that a class implements an interface.
+
+.. function:: grok.implements(*interfaces)
+
+ A class level directive to declare one or more `interfaces`, as
+ implementers of the surrounding class.
+
+ This directive allows several parameters.
+
+ :func:`grok.implements` is currently an alias for
+ :func:`zope.interface.implements`.
+
+**Example: Create two Cave classes, one implements IPaintable the other does not**
+
+First we will create the IPaintable interface, which declares that objects
+which provide this interface will have a `paint()` method. We will make a
+plain `Cave` class as well:
+
+.. code-block:: python
+
+ import grok
+ from zope import interface
+
+ class IPaintable(interface.Interface):
+ def paint(color):
+ "Paint with a color"
+
+ class Cave(object):
+ pass
+
+You can create a `Cave` object and query the `IPaintable` interface to see if
+an object provides that interface:
+
+.. code-block:: python
+
+ >>> cave = Cave()
+ >>> IPaintable.providedBy(cave)
+ False
+
+Next we will make a `PaintableCave` class which does implement the
+`IPaintable` interface:
+
+.. code-block:: python
+
+ class PaintableCave(object):
+ grok.implements(IPaintable)
+
+ def paint(color):
+ self._painted_color = color
+
+Now we can create a `PaintableCave` object and when we query the `IPaintable`
+interface it asserts that the object does provide the interface:
+
+ >>> paintable_cave = PaintableCave()
+ >>> IPaintable.providedBy(paintable_cave)
+ True
+
+Note that interfaces, like all things in Python, are by nature of a
+"gentleman's agreement". It's possible to declare that an object provides
+a certain interface when in reality it does not. It's also possible to
+provide magic methods such as `__getattr__` to allow an object to conform
+to a declared interface without that object needing to explicitly support
+the concrete methods and attributes declared in the interface. You can
+use the functions `zope.interface.verify.verifyClass(interface, class)`
+and `zope.interface.verify.verifyObject(interface, object)` to verify if
+a class or object actually implements or provides a specific interface.
+
+:func:`grok.provides`
+=====================
+
+Disambiguate which interface is registered.
+
+.. function:: grok.provides(interface)
+
+ Explicitly specify with which interface a component will be
+ looked up. If a class declares that it implements several interfaces,
+ :func:`grok.provides` can be used to disambiguate which interface will be
+ registered with the Zope Component Architecture.
+
+.. seealso::
+
+ :func:`grok.implements`
+
+
+:func:`grok.direct`
+===================
+
+Specify that the class should be the component.
+
+Typically a class implements an interface, and the class is used as a
+factory to construct objects that provide that interface. With this
+directive, the class object can by used to provide the interface
+directly without constructing additional instance objects.
+
+.. function:: grok.direct()
+
+ Specify whether the class should be used for the component
+ or whether it should be used to instantiate the component.
+
+ This directive can be used on GlobalUtility-based classes to
+ indicate whether the class itself should be registered as a
+ utility, or an instance of it.
+
+
+:func:`grok.baseclass`
+======================
+
+Declare a class as a base class.
+
+.. function:: grok.baseclass()
+
+ A class-level directive without argument to mark something as a base
+ class. Base classes are not grokked.
+
+ The baseclass mark is not inherited by subclasses, so those
+ subclasses will be grokked (except if they are also explicitly declared as
+ baseclasses as well).
+
+**Example: Mark a View class as a Base Class**
+
+Using this example, only the :class:`WorkingView` will serve as a
+view, while calling the :class:`AnotherView` will lead to a
+:exc:`ComponentLookupError`.
+
+.. code-block:: python
+
+ import grok
+
+ class ModelBase(grok.Model):
+ pass
+
+ class AnotherView(grok.View):
+ grok.baseclass()
+
+ def render(self):
+ return "hello world"
+
+ class WorkingView(grok.View):
+ pass
+
+
+Utility directives
+~~~~~~~~~~~~~~~~~~
+
+:func:`grok.global_utility`
+===========================
+
+Register a global utility.
+
+.. function:: grok.global_utility(factory[, provides=None[, name=u'']])
+
+ A module level directive to register a global utility.
+
+ `factory` - the factory that creates the utility.
+
+ `provides` - the interface the utility should be looked up with.
+
+ `name` - the name of the utility.
+
+ The latter two parameters are optional.
+
+ To register the utility correctly, Grok must be able to identify an
+ interface provided by the utility. If none is given, Grok checks
+ whether (exactly) one interface is implemented by the factory to be
+ registered (see example below). If more than one interface is
+ implemented by a class, use :func:`grok.provides` to specify which
+ one to use. If no interface is implemented by the instances
+ delivered by the factory, use :func:`grok.implements` to specify
+ one.
+
+ Another way to register global utilities with Grok is to subclass from
+ :class:`grok.GlobalUtility`.
+
+**Example: Register two GlobalUtilities and use them**
+
+Given the following module code:
+
+.. code-block:: python
+
+ import grok
+ from zope import interface
+
+ class IFireplace(interface.Interface):
+ pass
+
+ class Fireplace(object):
+ grok.implements(IFireplace)
+
+ grok.global_utility(Fireplace)
+ grok.global_utility(Fireplace, name='hot')
+
+Then the following works:
+
+.. code-block:: python
+
+ from zope import component
+ fireplace = component.getUtility(IFireplace)
+ hot_fireplace = component.getUtility(IFireplace, name='hot')
+
+.. seealso::
+
+ :class:`grok.GlobalUtility`, :func:`grok.provides`,
+ :func:`grok.implements`
+
+
+:func:`grok.local_utility`
+==========================
+
+Register a local utility.
+
+.. function:: grok.local_utility(factory[, provides=None[, name=u''[, setup=None[, public=False[, name_in_container=None]]]]])
+
+ A class level directive to register a local utility.
+
+ `factory` -- the factory that creates the utility.
+
+ `provides` -- the interface the utility should be looked up with.
+
+ `name` -- the name of the utility.
+
+ `setup` -- a callable that receives the utility as its single
+ argument, it is called after the utility has been created
+ and stored.
+
+ `public` -- if `False`, the utility will be stored below
+ `++etc++site`. If `True`, the utility will be stored
+ directly in the site. The site should in this case be a
+ container.
+
+ `name_in_container` -- the name to use for storing the utility.
+
+ All but the first parameter are optional.
+
+ To register a local utility correctly, Grok must know about the
+ interface, the utility should be looked up with. If none is given,
+ Grok looks up any interfaces implemented by instances delivered by
+ `factory` and if exactly one can be found, it is taken. See
+ :func:`grok.global_utility`.
+
+ Every single combination of interfaces and names can only be
+ registered once per module.
+
+ It is not possible to declare a local utility as public, if the site
+ is not a container. Grok will remind you of this. To store a utility
+ in a container, a `name_in_container` is needed. If none is given,
+ Grok will make up one automatically.
+
+ An alternative way to define a local utility is to subclass from
+ :class:`grok.LocalUtility`.
+
+**Example: Register a local utility**
+
+ The following code registers a local unnamed utility `fireplace` in
+ instances of :class:`Cave`
+
+ .. code-block:: python
+
+ import grok
+ from zope import interface
+
+ class IFireplace(interface.Interface):
+ pass
+
+ class Fireplace(grok.LocalUtility):
+ grok.implements(IFireplace)
+
+ class Cave(grok.Container, grok.Site):
+ grok.local_utility(Fireplace, public=True,
+ name_in_container='fireplace')
+
+.. seealso::
+
+ :func:`grok.global_utility`, :class:`grok.LocalUtility`
+
+Adapter directives
+~~~~~~~~~~~~~~~~~~
+
+:func:`grok.context`
+====================
+
+Declare the context for views, adapters, etc.
+
+Adapters are composed from another object, this object is called the
+context object. This directive specifies the class or interface that
+this object must provide.
+
+If the context declaration is not supplied, then Grok will set the context
+to the an Application, Container or Model class in module, as long as there
+is only one class of that type in the module.
+
+.. function:: grok.context(*class_or_interface)
+
+ A class or module level directive to indicate the context for
+ something (class or module) in the same scope.
+
+ When used on module level, it will set the context for all views,
+ adapters, etc. in that module. When used on class level, it will set
+ the context for that particular class.
+
+ With Grok contexts are set automatically for some objects, if they are
+ unambigous. For example a :class:`grok.View` will get the only
+ :class:`grok.Application` or :class:`grok.Model` class as context,
+ iff there exists exactly one in the same module. If there are more
+ possible contexts or you want to set a type (class/interface) from
+ another module as context, than the one choosen by default, then you
+ have to call :func:`grok.context` explicitly.
+
+**Example: Declare a component depends upon a class or interface**
+
+Here the :func:`grok.context` directive indicates that the :class:`Index`
+View applies to the context of a :class:`Mammoth` instance, and not instances
+of :class:`Cave`. By declaring the class or interface with :func:`grok.context`
+for an object, you are stating that your object depends upon the methods
+and attributes of that context.
+
+.. code-block:: python
+
+ import grok
+
+ class Mammoth(grok.Model):
+ hair = 'Wooly'
+
+ class Cave(grok.Model):
+ texture = 'rough'
+
+ class Index(grok.View):
+ grok.context(Mammoth)
+
+ def render(self):
+ # self.context will always have the interface of a Mammoth object,
+ # since this view declares that it depends upon the context of a
+ # Mammoth class.
+ return "It feels %s" % self.context.hair
+
+.. seealso::
+
+ :class:`grok.View`, :class:`grok.Adapter`, :class:`grok.MultiAdapter`
+
+
+:func:`grok.adapts`
+===================
+
+Declare that a class adapts certain objects.
+
+In the case of a simple adapter which only requires a single object
+for adapation, the :func:`grok.context` directive is used to declare
+the interface or class the adapter is for. It is only necessary to use
+:func:`grok.adapts` to declare the adapation requirements for a multi adapter.
+
+.. function:: grok.adapts(*classes_or_interfaces)
+
+ A class-level directive to declare that a class adapts objects of
+ the classes or interfaces given in `\*classes_or_interfaces`.
+
+ This directive accepts several arguments.
+
+ It works much like the :mod:`zope.component.`:func:`adapts()`,
+ but you do not have to make a ZCML entry to register the adapter.
+
+
+Security directives
+~~~~~~~~~~~~~~~~~~~
+
+:func:`grok.require`
+====================
+
+Declare a permission.
+
+.. function:: grok.require(permission)
+
+A class level directive used to protect a View by requiring a
+certain permission.
+
+`permission` -- the class of the :class:`grok.Permission` subclass that
+ is required. Alternatively, the name of the permission that is
+ required
+
+
+**Example 1 Define a Permission and use it to protect a View, using permission class**
+
+.. code-block:: python
+
+ import grok
+ import zope.interface
+
+ class Read(grok.Permission):
+ grok.name('mypackage.Read')
+
+ class Index(grok.View):
+ grok.context(zope.interface.Interface)
+ grok.require(Read)
+
+**Example 2: Define a Permission and use it to protect a View, using permission name**
+
+.. code-block:: python
+
+ import grok
+ import zope.interface
+
+ class Read(grok.Permission):
+ grok.name('mypackage.Read')
+
+ class Index(grok.View):
+ grok.context(zope.interface.Interface)
+ grok.require('mypackage.Read')
+
+.. seealso::
+
+ :class:`grok.Permission` component, :func:`@grok.require` decorator
+
+
+Component registry directives
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+:func:`grok.site`
+=================
+
+Specify the local component registry to use for indexes.
+
+A class level directive used in `grok.Indexes` sub-classes to define
+in which local component registry the indexes should be located.
+
+.. function:: grok.site(*arg)
+
+**Example**
+
+.. code-block:: python
+
+ class MammothIndexes(grok.Indexes):
+ grok.site(Herd)
+ grok.context(IMammoth)
+
+ name = index.Field()
+
+View directives
+~~~~~~~~~~~~~~~
+
+:func:`grok.layer`
+==================
+
+Declare the layer for the view.
+
+.. function:: grok.layer(layer)
+
+ Declare the layer for the view.
+
+ This directive acts as a contraint on the 'request' of
+ grok.View. This directive can only be used on class level.
+
+
+:func:`grok.skin`
+=================
+
+Declare this layer as a named skin.
+
+.. function:: grok.skin(skin)
+
+ Declare this layer as a named skin.
+
+ This directive can only be used on class level.
+
+
+:func:`grok.template`
+=====================
+
+Specify a template name.
+
+A class level directive used to specify the template to be rendered
+for the View when no render method is defined. This allows you to
+override the default convention of naming the template file with the same
+name as the view class itself, lowercased, in the templates directory
+for this module.
+
+.. function:: grok.template(template)
+
+ `template` -- name of the template file without file extension
+
+.. seealso::
+
+ :func:`grok.templatedir`
+
+
+:func:`grok.templatedir`
+========================
+
+Specify the templates directory.
+
+A module level directive used to specify the directory where Grok
+should look for template files.
+
+The default convention is to look for template files in a directory
+named `<module>_templates` where `<module>` is the name of the current
+module.
+
+.. function:: grok.templatedir(directory)
+
+ `directory` -- the name of the directory inside the same package
+ as the module
+
+.. seealso::
+
+ :func:`grok.template`
+
+
+:func:`grok.order`
+==================
+
+Specify ordering of components.
+
+Ordering is typically used in Viewlets to determine the order in which
+they are displayed.
+
+.. function:: grok.order(order)
+
+ Control the ordering of components.
+
+ If the value is specified, the order will be determined by sorting on it.
+ If no value is specified, the order will be determined by definition
+ order within the module. If the directive is absent, the order will be
+ determined by class name.
+
+ Inter-module order is by dotted name of the module the components are in,
+ unless an explicit argument is specified to ``grok.order()``, components are
+ grouped by module.
+
+The function grok.util.sort_components can be used to sort
+components according to these rules.
+
+
+URL Traversal directives
+~~~~~~~~~~~~~~~~~~~~~~~~
+
+:func:`grok.traversable`
+========================
+
+Mark attributes or methods as traversable.
+
+A class level directive used to mark attributes or methods as traversable. An
+optional `name` argument can be used to give the attribute a different name in
+the URL.
+
+.. function:: grok.traversable(attr, name=None)
+
+**Example**
+
+.. code-block:: python
+
+ class Foo(grok.Model):
+ grok.traversable('bar')
+ grok.traversable('foo')
+ grok.traversable(attr='bar', name='namedbar')
+
+ def __init__(self, name):
+ self.name = name
+
+ foo = Bar('foo')
+ def bar(self):
+ return Bar('bar')
+
+The result is that you can now access http://localhost/foo/bar,
+http://localhost/foo/foo and http://localhost/foo/namedbar.
Added: groktoolkit/branches/jw-documentation-rearangement/doc/reference/events.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/reference/events.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/reference/events.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,412 @@
+
+******
+Events
+******
+
+Grok provides convenient access to a set of often-used events from
+Zope 3. Those events include object and containment events. All events
+are available as interface and implemented class.
+
+Subscription: Event interfaces
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+All events interfaces inherit from the base interface of IObjectEvent.
+
+.. class:: zope.component.interfaces.IObjectEvent
+
+ .. attribute:: object
+
+ The subject of the event taking place.
+
+:class:`IApplicationInitializedEvent`
+=====================================
+
+A Grok Application has been created with success and is now ready
+to be used.
+
+This event can be used to trigger the creation of contents or other tasks
+that require the application to be fully operational : utilities installed
+and indexes created in the catalog.
+
+.. class:: grok.IApplicationInitializedEvent
+
+ Interface to subscribe to application initialization.
+
+ .. attribute:: object
+
+ The application that has just been initialized.
+
+:class:`IObjectModifiedEvent`
+=============================
+
+An object has been modified. This is a general event that encompasses any
+change to a persistent object, such as adding, moving, copying, and removing
+of objects.
+
+.. class:: grok.IObjectModifiedEvent
+
+ Interface to subscribe to for object modifications.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+ .. attribute:: descriptions
+
+ A list of descriptions of the modifications.
+
+:class:`IContainerModifiedEvent`
+================================
+
+The container has been modified. Container modifications is specific to
+addition, removal or reordering of sub-objects. Inherits from
+`grok.IObjectModifiedEvent`.
+
+.. class:: grok.IContainerModifiedEvent
+
+ Interface to subscribe to for container object modifications.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+ .. attribute:: descriptions
+
+ A list of descriptions of the modifications.
+
+
+:class:`IObjectMovedEvent`
+==========================
+
+An object has been moved.
+
+.. class:: grok.IObjectMovedEvent
+
+ Interface to subscribe to for when an object is moved.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+ .. attribute:: oldParent
+
+ The container stored in before moving.
+
+ .. attribute:: oldName
+
+ The name before moving.
+
+ .. attribute:: newParent
+
+ The container stored in after moving.
+
+ .. attribute:: newName
+
+ The name after moving.
+
+:class:`IObjectAddedEvent`
+==========================
+
+An object has been added to a container.
+
+.. class:: grok.IObjectAddedEvent
+
+ Interface to subscribe to for when an object is added to the database.
+
+ Inherits from the `grok.IObjectMovedEvent` interface.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+ .. attribute:: oldParent
+
+ The container stored in before moving.
+
+ .. attribute:: oldName
+
+ The name before moving.
+
+ .. attribute:: newParent
+
+ The container stored in after moving.
+
+ .. attribute:: newName
+
+ The name after moving.
+
+:class:`IObjectCopiedEvent`
+===========================
+
+An object has been copied.
+
+.. class:: grok.IObjectCopiedEvent
+
+ Interface to subscribe to for when an object is cloned.
+
+ Inherits from `grok.IObjectCreatedEvent` interface.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+ .. attribute:: original
+
+ The original object from which the copy was made.
+
+
+:class:`IObjectCreatedEvent`
+============================
+
+An object has been created. This event is intended to happen before an
+object has been made persistent, that is it's location attributes
+(__name__ and __parent__) will usually be None.
+
+.. class:: grok.IObjectCreatedEvent
+
+ Interface to subscribe to for when an object is created.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+
+:class:`IObjectRemovedEvent`
+============================
+
+An object has been removed from a container.
+
+.. class:: grok.IObjectRemovedEvent
+
+ Interface to subscribe to for object deletions.
+
+ Inherits from `grok.IObjectMovedEvent`.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+ .. attribute:: oldParent
+
+ The container stored in before removal.
+
+ .. attribute:: oldName
+
+ The name of the removed object.
+
+:class:`IBeforeTraverseEvent`
+=============================
+
+The publisher is about to traverse into the object.
+
+.. class:: grok.IBeforeTraverseEvent
+
+ Interface to subscribe to for object traversal.
+
+ .. attribute:: object
+
+ The object being traversed throguh.
+
+ .. attribute:: request
+
+ The current request.
+
+Notification: Event implementations
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Event objects are notifications that are sent when need to "fire off" an event.
+
+All of these event objects share the same minimal implementation of an event.
+This class is defined at zope.component.interfaces.ObjectEvent and looks like
+this:
+
+.. code-block:: python
+
+ from zope import interface
+
+ class ObjectEvent(object):
+ interface.implements(IObjectEvent)
+
+ def __init__(self, object):
+ self.object = object
+
+:class:`ApplicationInitializedEvent`
+=====================================
+
+Event object to send after an application has been created.
+
+.. class:: grok.ApplicationInitializedEvent
+
+ Default event implementation of the `grok.IApplicationInitializedEvent` interface.
+
+ .. attribute:: object
+
+ The application that has just been initialized.
+
+:class:`ObjectModifiedEvent`
+============================
+
+Event object to send as a notification when an object is modified.
+
+.. class:: grok.ObjectModifiedEvent(object, *descriptions)
+
+ Default event implementation of the `grok.IObjectMovedEvent` interface.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+ .. attribute:: descriptions
+
+ A list of descriptions of the modifications.
+
+**Example 1: Send an object modification event with a modified attribute
+named "field".**
+
+.. code-block:: python
+
+ import grok
+ import zope.event
+ import zope.lifecycleevent.Attributes
+ from zope.interface import Interface
+
+ class ISample(Interface) :
+ field = Attribute("A test field")
+
+ class Sample(object) :
+ grok.implements(ISample)
+
+ obj = Sample()
+ obj.field = 42
+ zope.event.notify(
+ grok.ObjectModifiedEvent(obj,
+ zope.lifecycleevent.Attributes(ISample, "field"))
+ )
+
+:class:`ContainerModifiedEvent`
+===============================
+
+Event object to send as a notification when a container object modified.
+
+.. class:: grok.ContainerModifiedEvent(object, *descriptions)
+
+ Default event implementation of the `grok.IContainerModifiedEvent`
+ interface.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+ .. attribute:: descriptions
+
+ A list of descriptions of the modifications.
+
+
+:class:`ObjectMovedEvent`
+=========================
+
+Event object to send as a notification of when an object is moved.
+
+.. class:: grok.ObjectMovedEvent(object, oldParent, oldName, newParent, newName)
+
+ Default event implementation of the `grok.IObjectMovedEvent` interface.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+ .. attribute:: oldParent
+
+ The container stored in before moving.
+
+ .. attribute:: oldName
+
+ The name before moving.
+
+ .. attribute:: newParent
+
+ The container stored in after moving.
+
+ .. attribute:: newName
+
+ The name after moving.
+
+
+:class:`ObjectAddedEvent`
+=========================
+
+Event object to send as a notification of when an object is added.
+
+.. class:: grok.ObjectAddedEvent(object, newParent, newName)
+
+ Default event implementation of the `grok.IObjectAddedEvent` interface.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+ .. attribute:: newParent
+
+ The container stored in after moving.
+
+ .. attribute:: newName
+
+ The name after moving.
+
+
+:class:`ObjectCopiedEvent`
+==========================
+
+Event object to send as a notification of when an object is copied.
+
+.. class:: grok.ObjectCopiedEvent(object, original)
+
+ Default event implementation of the `grok.IObjectCopiedEvent` interface.
+
+ Initialize this event with the new copy and the original object as positional
+ arguments.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+ .. attribute:: original
+
+ The original object from which the copy was made.
+
+
+:class:`ObjectCreatedEvent`
+===========================
+
+Event object to send as a notification of when an object is created.
+
+.. class:: grok.ObjectCreatedEvent(object)
+
+ Default event implementation of the `grok.IObjectCreatedEvent` interface.
+
+ Initialize this event with the object created.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+:class:`grok.ObjectRemovedEvent`
+================================
+
+Event object to send as a notification of when an object is removed.
+
+.. class:: grok.ObjectRemovedEvent*(object, oldParent, oldName)
+
+ Default event implementation of the `grok.IObjectRemovedEvent` interface.
+
+ .. attribute:: object
+
+ The subject of the event.
+
+ .. attribute:: oldParent
+
+ The container stored in before removal.
+
+ .. attribute:: oldName
+
+ The name of the removed object.
Added: groktoolkit/branches/jw-documentation-rearangement/doc/reference/exceptions.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/reference/exceptions.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/reference/exceptions.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,61 @@
+
+**********
+Exceptions
+**********
+
+grok tries to inform you about errors early and with as much guidance
+as possible. grok can detect some errors already while importing a
+module, which will lead to the :class:`GrokImportError`. Other errors
+require more context and can only be detected while executing the
+:func:`grok` function.
+
+
+:class:`grok.GrokImportError` -- errors while importing a module
+================================================================
+
+This exception is raised if a grok-specific problem was found while
+importing a module of your application. :class:`GrokImportError` means
+there was a problem in how you are using a part of grok. The error
+message tries to be as informative as possible tell you why something
+went wrong and how you can fix it.
+
+:class:`GrokImportError` is a subclass of Python's
+:class:`ImportError`.
+
+Examples of situations in which a GrokImportError occurs:
+
+ * Using a directive in the wrong context (e.g. grok.templatedir on
+ class-level instead of module-level.)
+
+ * Using a decorator with wrong arguments (e.g. grok.subscribe
+ without any argument)
+
+ * ...
+
+
+:class:`grok.GrokError` -- errors while grokking a module
+=========================================================
+
+This exception is raised if an error occurs while grokking a module.
+
+Typically a :class:`GrokError` will be raised if one of your modules
+uses a feature of grok that requires some sort of unambigous context
+to establish a reasonable default.
+
+For example, the :class:`grok.View` requires exactly one model to be
+defined locally in the module to assume a default module to be
+associated with. Having no model defined, or more than one model, will
+lead to an error because the context is either underspecified or
+ambigous.
+
+The error message of a :class:`GrokError` will include the reason for
+the error, the place in your code that triggered the error, and a
+hint, to help you fix the error.
+
+
+.. class:: GrokError(Exception)
+
+ .. attribute:: GrokError.component
+
+ The component that was grokked and triggered the error.
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/reference/functions.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/reference/functions.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/reference/functions.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,158 @@
+*********
+Functions
+*********
+
+The :mod:`grok` module provides a number of convenience functions to aid in
+common tasks.
+
+
+:func:`grok.AutoFields` -- deduce and return schema fields automatically
+========================================================================
+
+.. function:: grok.AutoFields(class_or_interface)
+
+ This function is used inside :class:`Form` classes to automatically
+ deduce the form fields from the schema of the `class_or_interface`.
+
+This function is used to create a sequence of form fields from an interface
+(schema) or from the interfaces (schemas) the context object provides.
+
+**Example: Generate fields from an interface**
+
+The :func:`grok.AutoFields` is used on the IMammoth interface, and all
+attributes that inherit from IField (such as the ones supplied in the
+zope.schema package) are concatenated into a list.
+
+.. code-block:: python
+
+ import grok
+ from zope import interface, schema
+
+ class IMammoth(interface.Interface):
+ name = schema.TextLine(title=u"Name")
+ size = schema.TextLine(title=u"Size", default=u"Quite normal")
+
+ class Mammoth(grok.Model):
+ interface.implements(IMammoth)
+
+ class Edit(grok.EditForm):
+ grok.context(Mammoth)
+
+ form_fields = grok.AutoFields(Mammoth).omit('size')
+
+In this example the ``size`` attribute will not show up in the resulting
+edit view.
+
+.. seealso::
+
+ :class:`grok.EditForm`, :func:`grok.Fields`
+
+
+:func:`grok.Fields` -- declare schema fields of a form
+======================================================
+
+.. function:: grok.Fields(*args, **kw)
+
+ This function is used inside a :class:`grok.Fields` to generate fields
+ (an object providing IFormFields) from positional and keyword arguments.
+ These should be available in the definition order.
+
+**Example: Generate form fields from schema objects**
+
+When the :class:`Edit` form is rendered, the :class:`Textlines` `b` and `a`
+will appear as input fields in that order.
+
+.. code-block:: python
+
+ import grok
+ from zope import schema
+
+ class Edit(grok.EditForm):
+ fields = grok.Fields(
+ b = schema.TextLine(title=u"Beta"),
+ a = schema.TextLine(title=u"Alpha"),
+ )
+
+.. seealso::
+
+ :func:`grok.AutoFields`, :class:`grok.Form`
+
+
+:func:`grok.getApplication`
+===========================
+
+.. autofunction:: grok.getApplication()
+
+
+:func:`grok.getSite`
+====================
+
+.. function:: grok.getSite()
+
+ Get the current site object.
+
+.. seealso::
+
+ Site objects are instances of :class:`grok.Site`. Typically this will
+ also be your main :class:`grok.Application` root object, which inherits
+ from :class:`grok.Site`. Normally you will want to use
+ `grok.getApplication` to get the application object, as `grok.getSite`
+ can return enclosed sub-sites in applications with more complex
+ configuration.
+
+.. seealso::
+
+ `Web Component Development With Zope 3, second edition <http://worldcookery.com/WhereToBuy>`_
+ By Philipp von Weitershausen; Chapter 18 describes the use of Site objects.
+
+
+:func:`grok.notify`
+===================
+
+.. function:: grok.notify(event)
+
+ Send `event` to event subscribers.
+
+**Example:**
+
+.. code-block:: python
+
+ import grok
+
+ class Mammoth(object):
+ def __init__(self, name):
+ self.name = name
+
+ manfred = Mammoth('manfred')
+
+ grok.notify(grok.ObjectCreatedEvent(manfred))
+
+.. seealso::
+
+ Grok events provide a selection of common event types.
+
+.. seealso::
+
+ `Web Component Development With Zope 3, second edition <http://worldcookery.com/WhereToBuy>`_
+ By Philipp von Weitershausen; Chapter 16 describes the Zope 3
+ event system.
+
+
+:func:`grok.url`
+================
+
+.. function:: grok.url(request, object, [, name])
+
+ Construct a URL for the given `request` and `object`.
+
+ `name` may be a string that gets appended to the object
+ URL. Commonly used to construct an URL to a particular view on the
+ object.
+
+ This function returns the constructed URL as a string.
+
+.. seealso::
+
+ View classes derived from :class:`grok.View` have a similar
+ :meth:`url` method for constructing URLs.
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/reference/index.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/reference/index.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/reference/index.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,24 @@
+.. _reference-index:
+
+#################################
+ The Grok Reference
+#################################
+(keep this under your pillow)
+
+:Reference for Grok version: |version|
+:Document last updated: |today|
+
+This is the Grok reference documentation. It is organized by the Python
+artefacts that implement it's concepts.
+
+.. toctree::
+ :maxdepth: 2
+
+ components.rst
+ directives.rst
+ decorators.rst
+ functions.rst
+ utils.rst
+ events.rst
+ exceptions.rst
+ testing.rst
Added: groktoolkit/branches/jw-documentation-rearangement/doc/reference/testing.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/reference/testing.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/reference/testing.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,344 @@
+*******
+Testing
+*******
+
+Installing the testing tool
+~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+Every Grok-based project will install a test runner that can find
+and run all test cases for your project. This test runner is installed
+using Buildout with the
+`zc.recipe.testrunner <http://pypi.python.org/pypi/zc.recipe.testrunner>`_
+recipe. The default configuration is::
+
+ [test]
+ recipe = zc.recipe.testrunner
+ eggs = <my-grok-project-name>
+ defaults = ['--tests-pattern', '^f?tests$', '-v']
+
+Using the test runner
+~~~~~~~~~~~~~~~~~~~~~
+
+The test runner can be invoked by the `test` program in your projects
+`bin` directory.
+
+usage
+=====
+
+ Usage: test [options] [MODULE] [TEST]
+
+options: help
+=============
+
+ -h, --help
+ show this help message and exit
+
+options: searching and filtering
+================================
+
+ options in this group are used to define which tests to run.
+
+ -s PACKAGE, --package=PACKAGE, --dir=PACKAGE
+ Search the given package's directories for tests.
+ This can be specified more than once to run tests in
+ multiple parts of the source tree. For example, if
+ refactoring interfaces, you don't want to see the way
+ you have broken setups for tests in other packages.
+ You *just* want to run the interface tests. Packages
+ are supplied as dotted names. For compatibility with
+ the old test runner, forward and backward slashed in
+ package names are converted to dots. (In the special
+ case of packages spread over multiple directories,
+ only directories within the test search path are
+ searched. See the --path option.)
+ -m MODULE, --module=MODULE
+ Specify a test-module filter as a regular expression.
+ This is a case-sensitive regular expression, used in
+ search (not match) mode, to limit which test modules
+ are searched for tests. The regular expressions are
+ checked against dotted module names. In an extension
+ of Python regexp notation, a leading "!" is stripped
+ and causes the sense of the remaining regexp to be
+ negated (so "!bc" matches any string that does not
+ match "bc", and vice versa). The option can be
+ specified multiple test-module filters. Test modules
+ matching any of the test filters are searched. If no
+ test-module filter is specified, then all test modules
+ are used.
+ -t TEST, --test=TEST
+ Specify a test filter as a regular expression. This
+ is a case-sensitive regular expression, used in search
+ (not match) mode, to limit which tests are run. In an
+ extension of Python regexp notation, a leading "!" is
+ stripped and causes the sense of the remaining regexp
+ to be negated (so "!bc" matches any string that does
+ not match "bc", and vice versa). The option can be
+ specified multiple test filters. Tests matching any of
+ the test filters are included. If no test filter is
+ specified, then all tests are run.
+ -u, --unit
+ Run only unit tests, ignoring any layer options.
+ -f, --non-unit
+ Run tests other than unit tests.
+ --layer=LAYER
+ Specify a test layer to run. The option can be given
+ multiple times to specify more than one layer. If not
+ specified, all layers are run. It is common for the
+ running script to provide default values for this
+ option. Layers are specified regular expressions,
+ used in search mode, for dotted names of objects that
+ define a layer. In an extension of Python regexp
+ notation, a leading "!" is stripped and causes the
+ sense of the remaining regexp to be negated (so "!bc"
+ matches any string that does not match "bc", and vice
+ versa). The layer named 'unit' is reserved for unit
+ tests, however, take note of the --unit and non-unit
+ options.
+ -a AT_LEVEL, --at-level=AT_LEVEL
+ Run the tests at the given level. Any test at a level
+ at or below this is run, any test at a level above
+ this is not run. Level 0 runs all tests.
+ --all
+ Run tests at all levels.
+ --list-tests
+ List all tests that matched your filters. Do not run
+ any tests.
+
+options: reporting
+==================
+
+ Reporting options control basic aspects of test-runner output
+
+ -v, --verbose
+ Make output more verbose. Increment the verbosity
+ level.
+ -q, --quiet
+ Make the output minimal, overriding any verbosity
+ options.
+ -p, --progress
+ Output progress status
+ --no-progress
+ Do not output progress status. This is the default,
+ but can be used to counter a previous use of --progress or -p.
+ --auto-progress
+ Output progress status, but only when stdout is a terminal.
+ -c, --color
+ Colorize the output.
+ -C, --no-color
+ Do not colorize the output. This is the default, but
+ can be used to counter a previous use of --color or -c.
+ --auto-color
+ Colorize the output, but only when stdout is a terminal.
+ --slow-test=N
+ With -c and -vvv, highlight tests that take longer
+ than N seconds (default: 10).
+ -1, --hide-secondary-failures
+ Report only the first failure in a doctest. (Examples
+ after the failure are still executed, in case they do
+ any cleanup.)
+ --show-secondary-failures
+ Report all failures in a doctest. This is the
+ default, but can be used to counter a default use of
+ -1 or --hide-secondary-failures.
+ --ndiff
+ When there is a doctest failure, show it as a diff
+ using the ndiff.py utility.
+ --udiff
+ When there is a doctest failure, show it as a unified diff.
+ --cdiff
+ When there is a doctest failure, show it as a context diff.
+
+options: analysis
+=================
+
+ Analysis options provide tools for analysing test output.
+
+ -D, --post-mortem
+ Enable post-mortem debugging of test failures
+ -g GC, --gc=GC
+ Set the garbage collector generation threshold. This
+ can be used to stress memory and gc correctness. Some
+ crashes are only reproducible when the threshold is
+ set to 1 (aggressive garbage collection). Do "--gc 0"
+ to disable garbage collection altogether. The --gc
+ option can be used up to 3 times to specify up to 3 of
+ the 3 Python gc_threshold settings.
+ -G GC_OPTION, --gc-option=GC_OPTION
+ Set a Python gc-module debug flag. This option can be
+ used more than once to set multiple flags.
+ -N REPEAT, --repeat=REPEAT
+ Repeat the tests the given number of times. This
+ option is used to make sure that tests leave their
+ environment in the state they found it and, with the
+ --report-refcounts option to look for memory leaks.
+ -r, --report-refcounts
+ After each run of the tests, output a report
+ summarizing changes in refcounts by object type. This
+ option that requires that Python was built with the
+ --with-pydebug option to configure.
+ --coverage=COVERAGE
+ Perform code-coverage analysis, saving trace data to
+ the directory with the given name. A code coverage
+ summary is printed to standard out.
+ --profile=PROFILE
+ Run the tests under cProfiler or hotshot and display
+ the top 50 stats, sorted by cumulative time and number
+ of calls.
+ --pychecker
+ Run the tests under pychecker
+
+options: setup
+==============
+
+ Setup options are normally supplied by the testrunner script, although
+ they can be overridden by users.
+
+ --path=PATH
+ Specify a path to be added to Python's search path.
+ This option can be used multiple times to specify
+ multiple search paths. The path is usually specified
+ by the test-runner script itself, rather than by users
+ of the script, although it can be overridden by users.
+ Only tests found in the path will be run. This option
+ also specifies directories to be searched for tests.
+ See the search_directory.
+ --test-path=TEST_PATH
+ Specify a path to be searched for tests, but not added
+ to the Python search path. This option can be used
+ multiple times to specify multiple search paths. The
+ path is usually specified by the test-runner script
+ itself, rather than by users of the script, although
+ it can be overridden by users. Only tests found in
+ the path will be run.
+ --package-path=PACKAGE_PATH
+ Specify a path to be searched for tests, but not added
+ to the Python search path. Also specify a package for
+ files found in this path. This is used to deal with
+ directories that are stitched into packages that are
+ not otherwise searched for tests. This option takes 2
+ arguments. The first is a path name. The second is
+ the package name. This option can be used multiple
+ times to specify multiple search paths. The path is
+ usually specified by the test-runner script itself,
+ rather than by users of the script, although it can be
+ overridden by users. Only tests found in the path
+ will be run.
+ --tests-pattern=TESTS_PATTERN
+ The test runner looks for modules containing tests.
+ It uses this pattern to identify these modules. The
+ modules may be either packages or python files. If a
+ test module is a package, it uses the value given by
+ the test-file-pattern to identify python files within
+ the package containing tests.
+ --suite-name=SUITE_NAME
+ Specify the name of the object in each test_module
+ that contains the module's test suite.
+ --test-file-pattern=TEST_FILE_PATTERN
+ Specify a pattern for identifying python files within
+ a tests package. See the documentation for the
+ --tests-pattern option.
+ --ignore_dir=IGNORE_DIR
+ Specifies the name of a directory to ignore when
+ looking for tests.
+
+options: other
+==============
+
+ Other options
+
+ -k, --keepbytecode
+ Normally, the test runner scans the test paths and the
+ test directories looking for and deleting pyc or pyo
+ files without corresponding py files. This is to
+ prevent spurious test failures due to finding compiled
+ modules where source modules have been deleted. This
+ scan can be time consuming. Using this option
+ disables this scan. If you know you haven't removed
+ any modules since last running the tests, can make the
+ test run go much faster.
+ --usecompiled
+ Normally, a package must contain an __init__.py file,
+ and only .py files can contain test code. When this
+ option is specified, compiled Python files (.pyc and
+ .pyo) can be used instead: a directory containing
+ __init__.pyc or __init__.pyo is also considered to be
+ a package, and if file XYZ.py contains tests but is
+ absent while XYZ.pyc or XYZ.pyo exists then the
+ compiled files will be used. This is necessary when
+ running tests against a tree where the .py files have
+ been removed after compilation to .pyc/.pyo. Use of
+ this option implies --keepbytecode.
+ --exit-with-status
+ Return an error exit status if the tests failed. This
+ can be useful for an invoking process that wants to
+ monitor the result of a test run.
+
+Discovering Test Cases
+~~~~~~~~~~~~~~~~~~~~~~
+
+The test runner looks for modules containing tests. It uses the default
+pattern of \'^f?tests$\' to identify these modules. The test runner will
+then use the name `test_suite` in all matching modules as the object to
+provide test suites.
+
+Test Supporting API
+~~~~~~~~~~~~~~~~~~~
+
+.. .. module:: grok.testing
+
+To support testing in Grok-based projects, Grok comes with a couple of
+helpers located in the :mod:`grok.testing` module.
+
+.. automodule:: grok.testing
+ :members:
+ :undoc-members:
+ :inherited-members:
+
+ .. autofunction:: grok.testing.grok_component
+
+ Grok a single component.
+
+ This function can be used to grok individual components within a
+ doctest, such as adapters. It sets up just enough context for
+ some grokking to work, though more complicated grokkers which
+ need module context (such as view grokkers) might not work.
+
+ Returns ``True`` or ``False`` depending on whether the grokking
+ worked or not.
+
+ A sample doctest could look as follows:
+
+ This defines the object we want to provide an adapter for:
+
+ >>> class Bar(object):
+ ... pass
+
+ This is the interface that we want to adapt to:
+
+ >>> from zope.interface import Interface
+ >>> class IFoo(Interface):
+ ... pass
+
+ This is the adapter itself:
+
+ >>> import grokcore.component as grok
+ >>> class MyAdapter(grok.Adapter):
+ ... grok.provides(IFoo)
+ ... grok.context(Bar)
+
+ Now we will register the adapter using grok_component():
+
+ >>> from grok.testing import grok, grok_component
+ >>> grok('grokcore.component.meta')
+ >>> grok_component('MyAdapter', MyAdapter)
+ True
+
+ The adapter should now be available:
+
+ >>> adapted = IFoo(Bar())
+ >>> isinstance(adapted, MyAdapter)
+ True
+
+
+ .. deprecated:: 1.0
+ Use :func:`grokcore.component.testing.grok_component` instead.
\ No newline at end of file
Added: groktoolkit/branches/jw-documentation-rearangement/doc/reference/utils.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/reference/utils.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/reference/utils.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,42 @@
+.. module:: grok.util
+
+*********
+Utilities
+*********
+
+The :mod:`grok.util` module provides functions which are less commonly
+used, and so are not available for import directly from the :mod:`grok` module.
+
+:func:`grok.util.application_url`
+=================================
+
+This function is also available as a method on the :class:`grok.View` class.
+
+.. autofunction:: grok.util.application_url
+
+
+:func:`grok.util.applySkin`
+===========================
+
+.. autofunction:: grok.util.applySkin
+
+
+:func:`grok.util.create_application`
+====================================
+
+.. autofunction:: grok.util.create_application
+
+
+:func:`grok.util.getApplication`
+================================
+
+This function is also availbale in the main grok namespace and can be
+called as :func:`grok.getApplication`.
+
+.. autofunction:: grok.util.getApplication()
+
+
+:func:`grok.util.safely_locate_maybe`
+=====================================
+
+.. autofunction:: grok.util.safely_locate_maybe
Added: groktoolkit/branches/jw-documentation-rearangement/doc/resources/evencaveman.jpg
===================================================================
(Binary files differ)
Property changes on: groktoolkit/branches/jw-documentation-rearangement/doc/resources/evencaveman.jpg
___________________________________________________________________
Added: svn:mime-type
+ application/octet-stream
Added: groktoolkit/branches/jw-documentation-rearangement/doc/resources/grok-standing.jpg
===================================================================
(Binary files differ)
Property changes on: groktoolkit/branches/jw-documentation-rearangement/doc/resources/grok-standing.jpg
___________________________________________________________________
Added: svn:mime-type
+ application/octet-stream
Added: groktoolkit/branches/jw-documentation-rearangement/doc/style.tex
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/style.tex (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/style.tex 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,74 @@
+% latex include file for docutils latex writer
+% --------------------------------------------
+%
+% CVS: $Id: style.tex,v 1.1 2004/01/23 21:17:32 faassen Exp $
+%
+% This is included at the end of the latex header in the generated file,
+% to allow overwriting defaults, although this could get hairy.
+% Generated files should process well standalone too, LaTeX might give a
+% message about a missing file.
+
+% donot indent first line of paragraph.
+\setlength{\parindent}{0pt}
+\setlength{\parskip}{5pt plus 2pt minus 1pt}
+
+% sloppy
+% ------
+% Less strict (opposite to default fussy) space size between words. Therefore
+% less hyphenation.
+\sloppy
+
+% fonts
+% -----
+% times for pdf generation, gives smaller pdf files.
+%
+% But in standard postscript fonts: courier and times/helvetica do not fit.
+% Maybe use pslatex.
+\usepackage{times}
+
+% pagestyle
+% ---------
+% headings might put section titles in the page heading, but not if
+% the table of contents is done by docutils.
+% If pagestyle{headings} is used, \geometry{headheight=10pt,headsep=1pt}
+% should be set too.
+%\pagestyle{plain}
+%
+% or use fancyhdr (untested !)
+\usepackage{fancyhdr}
+\pagestyle{fancy}
+\addtolength{\headheight}{\baselineskip}
+\renewcommand{\sectionmark}[1]{\markboth{#1}{}}
+\renewcommand{\subsectionmark}[1]{\markright{#1}}
+\fancyhf{}
+\fancyhead[LE,RO]{\bfseries\textsf{\thepage}}
+\fancyhead[LO]{\textsf{\footnotesize\rightmark}}
+\fancyhead[RE]{\textsc{\textsf{\footnotesize\leftmark}}}
+%\fancyfoot[LE,RO]{\bfseries\textsf{\scriptsize Docutils}}
+%\fancyfoot[RE,LO]{\textsf{\scriptsize\today}}
+
+% geometry
+% --------
+% = papersizes and margins
+%\geometry{a4paper,twoside,tmargin=1.5cm,
+% headheight=1cm,headsep=0.75cm}
+
+% Do section number display
+% -------------------------
+%\makeatletter
+%\def\@seccntformat#1{}
+%\makeatother
+% no numbers in toc
+%\renewcommand{\numberline}[1]{}
+
+
+% change maketitle
+% ----------------
+%\renewcommand{\maketitle}{
+% \begin{titlepage}
+% \begin{center}
+% \textsf{TITLE \@title} \\
+% Date: \today
+% \end{center}
+% \end{titlepage}
+%}
Added: groktoolkit/branches/jw-documentation-rearangement/doc/template.pt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/template.pt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/template.pt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,68 @@
+<metal:block define-macro="pagelayout">
+<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
+ "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
+
+<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
+<head>
+ <title tal:content="context/title" />
+ <meta http-equiv="Content-Type" content="text/html;charset=utf-8" />
+ <meta name="description" content="Grok - now even cavemen can use Zope3" />
+ <meta name="keywords" content="Grok, internet, zope, zope3, software, web apps, web applications, python" />
+ <style type="text/css"><!-- @import url(/resources/grok.css); --></style>
+</head>
+
+<body>
+<div class="header">
+
+ <a href="http://grok.zope.org">
+ <img src="/resources/grok-header.jpg" alt="GROK"/></a>
+ <ul id="navigation">
+ <li tal:repeat="item context/menu">
+ <a tal:content="item/title"
+ tal:attributes="title item/description;
+ class item/klass;
+ href item/href">link</a></li>
+ </ul>
+</div>
+
+
+<div class="roundcont">
+
+ <div class="roundtop">
+ <img src="/resources/corner-topleft.jpg" alt=""
+ width="45" height="45" class="corner"
+ style="display: none" />
+ </div>
+
+ <div class="content">
+
+ <tal:block replace="structure context/content" />
+
+ </div>
+
+ <div class="roundbottom">
+ <img src="/resources/corner-bottomleft.jpg" alt=""
+ width="45" height="45" class="corner"
+ style="display: none" />
+ </div>
+
+</div>
+
+<div class="footer">
+
+ <table><tr><td>
+ Grok cooks around the campfire of <br />
+ <a href="http://wiki.zope.org/zope3/FrontPage"><img src="/resources/zopelogo.gif" alt="Zope" style="padding: 0.5em;" /></a>
+ </td><td>
+ and roams free on the savannah of<br />
+ <a href="http://www.python.org"><img src="/resources/python-logo.gif" style="padding: 0.5em;" alt="Python" /></a>
+ </td></tr>
+ </table>
+
+ <p>Hosting provided by <a href="http://quintagroup.com/"><b>Quintagroup</b></a></p>
+</div>
+
+</body>
+</html>
+</metal:block>
+
Added: groktoolkit/branches/jw-documentation-rearangement/doc/tutorial.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/tutorial.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/tutorial.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,1343 @@
+=============
+Grok tutorial
+=============
+
+.. raw:: html
+
+ Also available as <a href="./tutorial.pdf">PDF</a>.
+
+.. contents::
+
+Welcome to the Grok tutorial!
+=============================
+
+.. sidebar:: Getting started with Zope Page Templates
+
+ You can find introductions and more information about Zope Page Templates
+ (ZPT, sometimes also called TAL) in various places:
+
+ http://plone.org/documentation/tutorial/zpt
+
+ http://wiki.zope.org/ZPT/FrontPage
+
+ Note that some of the information in these introductions may refer to
+ concepts not available in Grok or the Zope Toolkit, in particular variables
+ like ``here`` or ``template``. The basic principles will work with Grok
+ however; try reading ``context`` or ``view`` instead.
+
+Grok is a powerful and flexible web application framework for Python
+developers. In this tutorial we will show you the various things you can do
+with Grok, and how Grok can help you build your web application. We'll start
+out simple, and will slowly go to more complex usage patterns.
+
+All you're expected to know is the Python programming language and an
+understanding of basic web programming (HTML, forms, URLs). It also helps if
+you are familiar with Zope Page Templates, though most of the examples should
+be fairly obvious if you are already familiar with another templating language.
+
+We recommend that beginners follow the tutorial from top to bottom. The
+tutorial is designed to explain important concepts in order and slowly builds
+up from there.
+
+If you are more experienced, or just curious, you may want to skip around
+instead and read the pieces which interest you most. If something is unclear,
+you can always backtrack to previous sections.
+
+Grok is based on the `Zope Toolkit`_. You do not need to know about the Zope
+Toolkit at all to follow this tutorial. Grok builds on existing Zope Toolkit
+technology but exposes it in a special way to the developer. We believe Grok
+makes developing with Zope Toolkit technology easier and more fun for beginners
+and experienced developers alike.
+
+.. _`Zope Toolkit`: http://docs.zope.org/zopetoolkit/
+
+
+Getting started with Grok
+=========================
+
+This chapter will help you get up and running with Grok, using the
+``grokproject`` tool. We create a new project with ``grokproject`` and tell you
+how to get that project running so you can access it with a web browser.
+
+Setting up grokproject
+----------------------
+
+.. sidebar:: Installing ``easy_install``
+
+ If you don't already have ``easy_install`` available, you can find the script
+ to set it up on the `PEAK EasyInstall page`_.
+
+ .. _`PEAK EasyInstall page`: http://peak.telecommunity.com/DevCenter/EasyInstall#installing-easy-install
+
+ You need to download `ez_setup.py`_. Then, you run it like this to install
+ ``easy_install`` into your system Python::
+
+ $ sudo python2.6 ez_setup.py
+
+ .. _`ez_setup.py`: http://peak.telecommunity.com/dist/ez_setup.py
+
+ This will make ``easy_install`` available to you.
+
+ **Note**: Sometimes you have ``easy_install`` installed but you need a newer
+ version of the underlying setuptools infrastructure to make Grok work. You
+ can upgrade setuptools with::
+
+ $ sudo easy_install -U setuptools
+
+Setting up grok on a Unix-like (Linux, Mac OS X) environment is easy. Most of
+these instructions should work in a Windows environment as well.
+
+Let's go through the prerequisites first. You need a computer connected to the
+internet, as Grok installs itself over the network. You also need Python 2.6
+(or Python 2.5) installed.
+
+Because Grok uses a source distribution of the Zope Toolkit libraries, you may
+need to install your operating system's Python "dev" package (``python-dev`` on
+Debian and Ubuntu, ``python2.6-dev`` for Python 2.6). You also need a working C
+compiler (typically ``gcc``) installed, as we compile bits of the Zope Toolkit
+during setup (``build-essential`` on Debian and Ubuntu).
+
+On Windows such a build environment is not necessary, as grokproject will
+download and automatically install precompiled libraries for Windows. Finally,
+you also need ``easy_install`` installed so it becomes easy to install Python
+packages.
+
+Once you are done with the prerequisites, you can install grokproject itself::
+
+ $ easy_install grokproject
+
+If you are on a Unixy environment and you are not working from a `virtualenv`_
+virtualenv or custom compiled python installation, you will need to request
+admin rights using ``sudo``, as this will install new libraries into your
+system Python.
+
+ .. _`virtualenv`: http://foo
+
+We're ready to create our first grok project now!
+
+Creating a new Grok project
+---------------------------
+
+.. sidebar:: Using paster
+
+ For those who know paster_: ``grokproject`` is just a wrapper around a paster
+ template. So instead of running the ``grokproject`` command, you can also
+ run::
+
+ $ paster create -t grok Sample
+
+ .. _paster: http://pythonpaste.org/script/
+
+Let's create a first Grok project. A Grok project is a working environment for
+a developer of an web application based using Grok. In essence, a directory
+with a lot of files and subdirectories in it. Let's create a Grok project
+called Sample::
+
+ $ grokproject Sample
+
+This tells grokproject to create a new subdirectory called ``Sample`` and set
+up the project in there. grokproject will automatically download and install
+the Zope Toolkit libraries as well as the Grok Toolkit into the project area.
+
+Grok asks you for an initial username and password for the server. We'll use
+``grok`` for both in this example::
+
+ Enter user (Name of an initial administrator user): grok
+ Enter passwd (Password for the initial administrator user): grok
+
+Now you have to wait while grokproject downloads and installs the various tools
+and libraries that are needed in a Grok project. The second time you create a
+Grok project it will be faster as it can reuse the previously installed
+libraries. After all that your Grok project is ready to go.
+
+.. sidebar:: Common problems installing Grok
+
+ *No Python development environment*
+
+ Grok includes dependencies that need to be compiled against Python.
+ This happens automatically in the installation process, but a Python
+ development environment does need to be installed, unless you are on
+ Windows, where we supply binary versions of the required libraries.
+
+ On Debian and Ubuntu this is the ``python-dev`` package
+ (``python2.6-dev for Python 2.6). You also need ``build-essential``.
+
+Starting up the web server
+--------------------------
+
+You can go into the ``Sample`` project directory now and start up the web
+server for our project::
+
+ $ cd Sample
+ $ bin/paster serve parts/etc/deploy.ini
+
+This will make Grok available on port 8080. You can log in with username
+``grok`` and password ``grok``. Assuming you've started up the web server on
+your development computer, you can go to it here:
+
+ http://localhost:8080
+
+This first pops up a login dialog (username: ``grok`` and password: ``grok``).
+It will then show a simple Grok admin interface. This user interface allows you
+to install new Grok applications.
+
+Our sample application (``sample.app.Sample``) will be available for adding.
+Let's try this out. Go to the Grok admin page:
+
+ http://localhost:8080
+
+and add a Sample application. Give it the name ``test``.
+
+You can now go to the installed application if you click on its link. This will
+bring you to the following URL:
+
+ http://localhost:8080/test
+
+You should see a simple web page with the following text on it::
+
+ Congratulations!
+
+ Your Grok application is up and running. Edit
+ sample/app_templates/index.pt to change this page.
+
+You can shut down the server at any time by hitting ``CTRL-c``. Shut it down
+now. We will be shutting down and starting up the server often in this tutorial.
+
+Practice restarting the server now, as you'll end up doing it a lot during this
+tutorial. It's just stopping and starting it again: ``CTRL-c`` and then
+``bin/paster serve parts/etc/deploy.ini`` from your Sample project directory.
+
+Alternatively, you can use the --reload flag to start up paster with a monitor
+that scans your code base (python files only) for changes and automatically
+restarts the server every time you make a change::
+
+ $ bin/paster serve --reload parts/etc/deploy.ini
+
+An empty Grok project
+---------------------
+
+.. sidebar:: What about the other directories and files in our project?
+
+ What about the other files and subdirectories in our ``Sample`` project
+ directory? Grokproject sets up the project using a system called
+ `zc.buildout`_. The ``eggs``, ``develop-eggs``, ``bin`` and ``parts``
+ directories are all set up and maintained by zc.buildout. See its
+ documentation for more information about how to use it. The configuration of
+ the project and its dependency is in ``buildout.cfg``. For the moment
+ however, you can ignore these details however.
+
+ .. _`zc.buildout`: http://buildout.org
+
+Let's take a closer look at what's been created in the Sample project directory.
+
+One of the things grokproject created was a ``setup.py`` file. This file
+contains information about your project. This information is used by buildout
+to download your project's dependencies and to install it. You can also use the
+``setup.py`` file to upload your project to the Python Package Index (PyPI).
+
+We have already seen the ``bin`` directory. It contains the startup script for
+the web server (``bin/paster``) as well as the executable for the buildout
+system (``bin/buildout``) which can be used to re-build your project (to update
+it or to install a new dependency).
+
+The ``parts` directory contain configuration and data created and managed by
+``buildout``, such as the Zope object database (ZODB) storage, and the ``.ini``
+files to be used with ``paster``.
+
+The actual code of the project will all be inside the ``src`` directory. In it
+is a Python package directory called ``sample`` with the ``app.py`` file that
+grokproject said it would create. Let's look at this file:
+
+.. include:: groktut/an_empty_grok_project/src/sample/app.py
+ :literal:
+
+Not very much yet, but enough to make an installable Grok application and
+display its welcome page. We'll go into the details of what this means later.
+
+Besides this, there is an empty ``__init__.py`` file to make this directory a
+Python package.
+
+There is also a directory called ``app_templates``. It contains a single
+template called ``index.pt``:
+
+.. include:: groktut/an_empty_grok_project/src/sample/app_templates/index.pt
+ :literal:
+
+This is the template for your project's welcome page.
+
+There is also a ``configure.zcml`` file. This file will normally only contain a
+few lines that load dependencies and then register this application with Grok.
+This means we can typically completely ignore it, but we'll show it here once
+for good measure:
+
+.. include:: groktut/an_empty_grok_project/src/sample/configure.zcml
+ :literal:
+
+.. sidebar:: ``configure.zcml`` in non-Grok applications
+
+ In non-Grok applications that use the Zope Toolkit (such as something created
+ with Zope 2 or Zope 3), the ZCML file usually plays a much bigger role. It
+ contains directives which registers particular Python objects (typically
+ classes, such as views) with the component architecture that is central to
+ the Zope Toolkit. Grok however automates this registration by putting more
+ information into the Python code directly, so that the ZCML file can remain
+ small.
+
+There is also a ``static`` directory. This contains static files that can be
+used in the web application, such as images, css files and javascript files.
+
+Besides these files, there is an ``app.txt``, ``ftesting.zcml`` and
+``tests.py``. These all have to do with the automatic testing environment and
+can be ignored for now.
+
+Showing pages
+=============
+
+Showing web pages is what puts the *web* in "web applications". Typically HTML
+templates are used for this, but Grok doesn't stop at templates. Most web pages
+in a real-world web application will contain complex presentation logic that is
+better handled by separate Python code in conjunction with templates. This
+becomes especially important in more complex interactions with the user, such
+as form handling. After reading this chapter, you should already be able to
+write simple web applications with Grok.
+
+Publishing a simple web page
+----------------------------
+
+Let's publish a simple static web page. Grok is geared towards web applications
+and therefore is not really meant for publishing a large number of static
+(pregenerated) web pages. For that you're better off to use a specialized
+system such as Apache. Nonetheless, in order to develop any web application we
+need to know how to put some simple HTML on the web.
+
+As you saw previously, our ``Sample`` application has a stock front page,
+generated by grokproject. Let's change that.
+
+To do this, go to the ``app_templates`` directory in ``src/sample/``. This
+directory contains the templates used for anything defined in the ``app``
+module. Grok knows to associate the directory to the module by its name
+(``<module_name>_templates``).
+
+In this directory we will edit the ``index`` template for our ``Sample``
+application object. To do this, open the ``index.pt`` file in a text editor.
+The ``.pt`` extension indicates that this file is a Zope Page Template (ZPT).
+We're just going to put HTML in it now, but this allows us to make page dynamic
+later on.
+
+Change the ``index.pt`` file to contain the following (very simplistic) HTML:
+
+.. include:: groktut/publishing_a_simple_web_page/src/sample/app_templates/index.pt
+ :literal:
+
+Then reload the page:
+
+ http://localhost:8080/test
+
+You should now see the following text::
+
+ Hello world!
+
+Note that you can change templates and see the effects instantly: there is no
+need to restart the web server to see the effect. This is not true for changes
+on the Python level, for instance when you add a template. We show an example
+of this next.
+
+A second view
+-------------
+
+Our view is named ``index``. This in fact means something slightly special:
+it's the default view of our application object. We can also access it
+explicitly by naming the view:
+
+ http://localhost:8080/test/index
+
+If you view that URL in your browser, you should see the same result as before.
+This is the way all other, non-index views are accessed.
+
+Often, your application needs more than one view. A document for instance may
+have an ``index`` view that displays it, but another ``edit`` view to change
+its contents. To create a second view, create another template called
+``bye.pt`` in ``app_templates``. Make it have the following content:
+
+.. include:: groktut/a_second_view/src/sample/app_templates/bye.pt
+ :literal:
+
+Now we need to tell Grok to actually use this template. To do this,
+modify ``src/sample/app.py`` so that it reads like this:
+
+.. include:: groktut/a_second_view/src/sample/app.py
+ :literal:
+
+As you can see, all we did was add a class called ``Bye`` that subclasses from
+``grok.View``. This indicates to Grok that we want a view named ``bye`` for the
+application, just like the ``Index`` class that was already created for us
+indicates that we want a view named ``index``. A *view* is a way to view some
+model, in this case installations of our ``Sample`` application. Note that the
+view name in the URL is always going to be lowercase, while the class name
+normally starts with an uppercase letter.
+
+The empty class definition above is enough for Grok to go look in the
+``app_templates`` directory for ``bye.pt``. The rule is that a the template
+should have the same name as the class, but lowercased and with the ``.pt``
+postfix.
+
+.. sidebar:: Other templating languages
+
+ You can also install extensions to allow the use of other templating
+ languages in Grok, see for instance `megrok.genshi`_.
+
+ .. _`megrok.genshi`: http://pypi.python.org/pypi/megrok.genshi/
+
+Restart the web server (``Ctrl + C``, then ``bin/paster serve
+parts/etc/deploy.ini``). You can now go to a new web page called ``bye``:
+
+ http://localhost:8080/test/bye
+
+When you load this web page in a browser, you should see the following text::
+
+ Bye world!
+
+Making our page dynamic
+-----------------------
+
+Static web pages are not very helpful if we want to make a dynamic web
+application. Let's make a page that shows the result of a very simple
+calculation: ``1 + 1``.
+
+We will use a Zope Page Templates (ZPT) directive to do this calculation inside
+``index.pt`` template. Change the ``index.pt`` to read like this:
+
+.. include:: groktut/making_our_page_dynamic/src/sample/app_templates/index.pt
+ :literal:
+
+We've used the ``tal:content`` page template directive to replace the content
+between the ``<p>`` and ``</p>`` tags with something else, in this case the
+result of the Python expression ``1 + 1``.
+
+Since restarting the server is not necessary for changes that are limited to
+the page templates, you can just reload the web page:
+
+ http://localhost:8080/test
+
+You should see the following result::
+
+ 2
+
+Looking at the source of the web page shows us this::
+
+ <html>
+ <body>
+ <p>2</p>
+ </body>
+ </html>
+
+As you can see, the content of the ``<p>`` tag was indeed replaced with the
+result of the expression ``1 + 1``.
+
+Static resources for our web page
+---------------------------------
+
+In real-world web pages, we almost never publish a web page that just contains
+bare-bones HTML. We also want to refer to other resources, such as images, CSS
+files or Javascript files. As an example, let's add some style to our web page.
+
+To do this, create a new directory called ``static`` in the ``sample`` package
+(so, ``src/sample/static``). In it, place a file called ``style.css`` and put
+in the following content:
+
+.. include:: groktut/static_resources_for_our_web_page/src/sample/static/style.css
+ :literal:
+
+In order to use it, we also need to refer to it from our ``index.pt``. Change
+the content of ``index.pt`` to read like this:
+
+.. include:: groktut/static_resources_for_our_web_page/src/sample/app_templates/index.pt
+ :literal:
+
+Now restart the server and reload the page:
+
+ http://localhost:8080/test
+
+The web page should now show up with a red background.
+
+You will have noticed we used the ``tal:attributes`` directive in our
+``index.pt`` now. This uses Zope Page Templates to dynamically generate the
+link to our file ``style.css``.
+
+Let's take a look at the source code of the generated web page::
+
+ <html>
+ <link rel="stylesheet" type="text/css"
+ href="http://localhost:8080/test/@@/sample/style.css" />
+ <body>
+ <p>Hello world!</p>
+ </body>
+ </html>
+
+As you can see, the ``tal:attributes`` directive is gone and has been replaced
+with the following URL to the actual stylesheet:
+
+ http://localhost:8080/test/@@/sample/style.css
+
+We will not go into the details of the structure of the URL here, but we will
+note that because it's generated this way, the link to ``style.css`` will
+continue to work no matter where you install your application (i.e. in a
+virtual hosting setup).
+
+Pulling in images or javascript is very similar. Just place your image files
+and `.js` files in the ``static`` directory, and create the URL to them using
+``static/<filename>`` in your page template.
+
+Using view methods
+------------------
+
+.. sidebar:: Unassociated templates
+
+ If you have followed the tutorial so far, you will have an extra template
+ called ``bye.pt`` in your ``app_templates`` directory. Since in the given
+ ``app.py`` we we have no more class using it, the ``bye.pt`` template will
+ have become *unassociated*. When you try to restart the server, Grok will
+ give you a warning like this::
+
+ UserWarning: Found the following unassociated template(s) when grokking
+ 'sample.app': bye. Define view classes inheriting from grok.View to enable
+ the template(s).
+
+ To get rid of this warning, simply remove ``bye.pt`` from your
+ ``app_templates`` directory.
+
+ZPT is deliberately limited in what it allows you to do with Python. It is good
+application design practice to use ZPT for fairly simple templating purposes
+only, and to do anything a bit more complicated in Python code. Using ZPT with
+arbitrary Python code is easy: you just add methods to your view class and use
+them from your template.
+
+Let's see how this is done by making a web page that displays the current date
+and time. We will use our Python interpreter to find out what works::
+
+ $ python
+ Python 2.6.2
+ Type "help", "copyright", "credits" or "license" for more information.
+ >>>
+
+We will need Python's ``datetime`` class, so let's import it::
+
+ >>> from datetime import datetime
+
+Note that this statement brings us beyond the capabilities of simple ZPT use;
+it is not allowed to import arbitrary Python modules from within a ZPT
+template; only Python *expressions* (with a result) are allowed, not
+*statements* such as ``from .. import ..``.
+
+Let's get the current date and time::
+
+ >>> now = datetime.now()
+
+This gives us a date time object; something like this::
+
+ >>> now
+ datetime.datetime(2007, 2, 27, 17, 14, 40, 958809)
+
+Not very nice to display on a web page, so let's turn it into a prettier string
+using the formatting capabilities of the ``datetime`` object::
+
+ >>> now.strftime('%Y-%m-%d %H:%M')
+ '2007-02-27 17:14'
+
+That looks better.
+
+So far nothing new; just Python. We will integrate this code into our Grok
+project now. Go to ``app.py`` and change it to read like this:
+
+.. include:: groktut/using_view_methods/src/sample/app.py
+ :literal:
+
+We've simply added a method to our view that returns a string representing the
+current date and time. Now to get this string in our page template. Change
+``index.pt`` to read like this:
+
+.. include:: groktut/using_view_methods/src/sample/app_templates/index.pt
+ :literal:
+
+Restart the server. This is needed as we changed the content of a Python file
+(``app.py``). Now reload our index page to see whether it worked:
+
+ http://localhost:8080/test
+
+You should see a web page with a date and time like this on your screen now::
+
+ 2007-02-27 17:21
+
+What happened here? When viewing a page, the view class (in this case ``Index``
+is instantiated by the framework. The name ``view`` in the template is always
+made available and is associated with this instance. We then simply call the
+method on it in our template.
+
+There is another way to write the template that is slightly shorter and may be
+easier to read in some cases, using a ZPT path expression::
+
+ <html>
+ <body>
+ <p tal:content="view/current_datetime"></p>
+ </body>
+ </html>
+
+Running this has the same result as before.
+
+Generating HTML from Python
+---------------------------
+
+While usually you will be using templates to generate HTML, sometimes you want
+to generate complicated HTML in Python and then include it in an existing web
+page. For reasons of security against cross-site scripting attacks, TAL will
+automatically escape any HTML into `>` and `<`. With the ``structure``
+directive, you can tell TAL explicitly to not escape HTML this way, so it is
+passed literally into the template. Let's see how this is done. Change
+``app.pt`` to read like this:
+
+.. include:: groktut/generating_html_from_python/src/sample/app.py
+ :literal:
+
+and then change ``index.pt`` to read like the following:
+
+.. include:: groktut/generating_html_from_python/src/sample/app_templates/index.pt
+ :literal:
+
+Let's take another look at our web page:
+
+ http://localhost:8080/test
+
+You should see the following text (in bold):
+
+ **ME GROK BOLD**
+
+This means the HTML we generated from the ``some_html`` method was indeed
+successfully integrated in our web page. Without the the ``structure``
+directive, you would've seen the following instead::
+
+ <b>ME GROK BOLD</b>
+
+Completely Python-driven views
+------------------------------
+
+.. sidebar:: Setting the content-type
+
+ When generating the complete content of a page yourself, it's often useful to
+ change the content-type of the page to something else than ``text/plain``.
+ Let's change our code to return simple XML and set the content type to
+ ``text/xml``:
+
+ .. include:: groktut/setting_the_content_type/src/sample/app.py
+ :literal:
+
+ All views in Grok have a ``response`` property that you can use to manipulate
+ response headers.
+
+Sometimes it is inconvenient to have to use a template at all. Perhaps we are
+not returning a HTML page at all, for instance. In this case, we can use the
+special ``render`` method on a view.
+
+Modify ``app.py`` so it reads like this:
+
+.. include:: groktut/completely_python_driven_views/src/sample/app.py
+ :literal:
+
+If you were to start up the server with an ``index.pt`` template still inside
+``app_templates`` you would get a an error::
+
+ GrokError: Multiple possible ways to render view <class
+ 'sample.app.Index'>. It has both a 'render' method as well as an
+ associated template.
+
+In the face of ambiguity Grok, like Python, refuses to guess. To resolve this
+error, remove ``index.pt`` from the ``app_templates`` directory.
+
+Now take another look at our test application:
+
+ http://localhost:8080/test
+
+You should see the following::
+
+ ME GROK NO TEMPLATE
+
+You should see this even when you view the source of the page. When looking at
+the content type of this page, you will see that it is ``text/plain``.
+
+Doing some calculation before viewing a page
+--------------------------------------------
+
+Instead of calculating some values in a method call from the template, it is
+often more useful to calculate just before the web page's template is
+calculated. This way you are sure that a value is only calculated once per
+view, even if you use it multiple times.
+
+You can do this by defining an ``update`` method on the view class. Modify
+``app.py`` to read like this:
+
+.. include:: groktut/doing_some_calculation_before_viewing_a_page/src/sample/app.py
+ :literal:
+
+This sets a name ``alpha`` on the view just before the template is being
+displayed, so we can use it from the template. You can set as many names on
+``self`` as you like.
+
+Now we need a template ``index.pt`` that uses ``alpha``:
+
+.. include:: groktut/doing_some_calculation_before_viewing_a_page/src/sample/app_templates/index.pt
+ :literal:
+
+Restart the server and then let's take another look at our application:
+
+ http://localhost:8080/test
+
+You should see 256, which is indeed 2 raised to the power 8.
+
+Reading URL parameters
+----------------------
+
+When developing a web application, you don't just want to output data, but also
+want to use input. One of the simplest ways for a web application to receive
+input is by retrieving information as a URL parameter. Let's devise a web
+application that can do sums for us. In this application, if you enter the
+following URL into that application:
+
+ http://localhost:8080/test?value1=3&value2=5
+
+you should see the sum (8) as the result on the page.
+
+Modify ``app.py`` to read like this:
+
+.. include:: groktut/reading_url_parameters/src/sample/app.py
+ :literal:
+
+We need an ``index.pt`` that uses ``sum``:
+
+.. include:: groktut/reading_url_parameters/src/sample/app_templates/index.pt
+ :literal:
+
+Restart the server. Now going to the following URL should display 8:
+
+ http://localhost:8080/test?value1=3&value2=5
+
+Other sums work too, of course:
+
+ http://localhost:8080/test?value1=50&value2=50
+
+What if we don't supply the needed parameters (``value1`` and
+``value2``) to the request? We get an error:
+
+ http://localhost:8080/test
+
+You can look at the window where you started up the server to see the error
+traceback. This is the relevant complaint::
+
+ TypeError: Missing argument to update(): value1
+
+We can modify our code so it works even without input for either parameter:
+
+.. include:: groktut/reading_url_parameters2/src/sample/app.py
+ :literal:
+
+Restart the server, and see it can now deal with missing parameters (they
+default to ``0``).
+
+Simple forms
+------------
+
+.. sidebar:: Automatic forms
+
+ Creating forms and converting and validating user input by hand, as shown in
+ this section, can be rather cumbersome. With Grok, you can use the Zope
+ Toolkit's *schema* and *formlib* systems to automate this and more. This will
+ be discussed in a later section. TDB
+
+Entering the parameters through URLs is not very pretty. Let's use a form for
+this instead. Change ``index.pt`` to contain a form, like this:
+
+.. include:: groktut/simple_forms/src/sample/app_templates/index.pt
+ :literal:
+
+One thing to note here is that we dynamically generate the form's ``action``.
+We make the form submit to itself, basically. Grok views have a special method
+called ``url`` that you can use to retrieve the URL of the view itself (and
+other URLs which we'll go into later).
+
+Leave the ``app.py`` as in the previous section, for now. You can now go to the
+web page::
+
+ http://localhost:8080/test
+
+You can submit the form with some values, and see the result displayed below.
+
+We still have a few bugs to deal with however. For one, if we don't fill in any
+parameters and submit the form, we get an error like this::
+
+ File "../app.py", line 8, in update
+ self.sum = int(value1) + int(value2)
+ ValueError: invalid literal for int():
+
+This is because the parameters were empty strings, which cannot be converted to
+integers. Another thing that is not really pretty is that it displays a sum (0)
+even if we did not enter any data. Let's change ``app.py`` to take both cases
+into account:
+
+.. include:: groktut/simple_forms2/src/sample/app.py
+ :literal:
+
+We catch any TypeError and ValueError here so that wrong or missing data does
+not result in a failure. Instead we display the text "No sum". If we don't get
+any error, the conversion to integer was fine, and we can display the sum.
+
+Restart the server and go to the form again to try it out:
+
+ http://localhost:8080/test
+
+Models
+======
+
+Now we know how to show web pages, we need to go into what we are actually
+showing: the models. The models contain the display-independent logic of your
+application. In this chapter we will discuss a number of issues surrounding
+models: how your views connect to models, and how you can make sure the data in
+your models is stored safely. As the complexity of our sample applications
+grows, we will also go into a few more issues surrounding form handling.
+
+A view for a model
+------------------
+
+So far, we have only seen views that do the work all by themselves. In typical
+applications this is not the case however - views display information that is
+stored elsewhere. In Grok applications, views work for models: subclasses of
+``grok.Model`` or ``grok.Container``. For the purposes of this discussion, we
+can treat a ``grok.Container`` as another kind of ``grok.Model`` (more about
+what makes ``grok.Container`` special later XXX).
+
+Our ``Sample`` class is a ``grok.Container``, so let's use ``Sample`` to
+demonstrate the basic principle. Let's modify ``app.py`` so that ``Sample``
+actually makes some data available:
+
+.. include:: groktut/a_view_for_a_model/src/sample/app.py
+ :literal:
+
+In this case, the information (``"This is important information!"``) is just
+hardcoded, but you can imagine information is retrieved from somewhere else,
+such as a relational database or the filesystem.
+
+We now want to display this information in our template ``index.pt``:
+
+.. include:: groktut/a_view_for_a_model/src/sample/app_templates/index.pt
+ :literal:
+
+Restart the server. When you view the page:
+
+ http://localhost:8080/test
+
+You should now see the following::
+
+ This is important information!
+
+Previously we have seen that you can access methods and attributes on the view
+using the special ``view`` name in a template. Similarly, the name ``context``
+is also available in each template. ``context`` allows us to access information
+on the context object the view is displaying. In this case this is an instance
+of ``Sample``, our application object.
+
+Separating the model from the view that displays it is an important concept in
+structuring applications. The view, along with the template, is responsible for
+displaying the information and its user interface. The model represents the
+actual information (or content) the application is about, such as documents,
+blog entries or wiki pages. The model should not know anything about the way it
+is displayed.
+
+This way of structuring your applications allows you to change the way your
+model is displayed without modifying the model itself, just the way it is
+viewed.
+
+Let's do that by making the view do something to the information. Change
+``app.py`` again:
+
+.. include:: groktut/a_view_for_a_model2/src/sample/app.py
+ :literal:
+
+You can see that it is possible to access the context object (an instance of
+``Sample``) from within the view class, by accessing the ``context`` attribute.
+This gets the same object as when we used the ``context`` name in our template
+before.
+
+What we do here is reverse the string returned from the ``information()``
+method. You can try it on the Python prompt::
+
+ >>> ''.join(reversed('foo'))
+ 'oof'
+
+Now let's modify the ``index.pt`` template so that it uses the
+``reversed_information`` method:
+
+.. include:: groktut/a_view_for_a_model2/src/sample/app_templates/index.pt
+ :literal:
+
+Restart the server. When you view the page:
+
+ http://localhost:8080/test
+
+You should now see the following:
+
+ The information: This is important information!
+
+ The information, reversed: !noitamrofni tnatropmi si sihT
+
+Storing data
+------------
+
+So far we have only displayed either hardcoded data, or calculations based on
+end-user input. What if we actually want to *store* some information, such as
+something the user entered? The easiest way to do this with Grok is to use the
+Zope Object Database (ZODB).
+
+The ZODB is a database of Python objects. You can store any Python object in
+it, though you do need to follow a few simple rules (the "rules of
+persistence", which we will go into later). Our ``Sample`` application object
+is stored in the object database, so we can store some information on it.
+
+Let's create an application that stores a bit of text for us. We will use one
+view to view the text (``index``) and another to edit it (``edit``).
+
+Modify ``app.py`` to read like this:
+
+.. include:: groktut/storing_data/src/sample/app.py
+ :literal:
+
+The ``Sample`` class gained a class attribute with some default text. In the
+``update`` method of the ``Edit`` view you can see we actually set the ``text``
+attribute on the context, if at least a ``text`` value was supplied by a form.
+This will set the ``text`` attribute on the instance of the ``Sample`` object
+in the object database, and thus will override the default ``text`` class
+attribute.
+
+Change the ``index.pt`` template to read like this:
+
+.. include:: groktut/storing_data/src/sample/app_templates/index.pt
+ :literal:
+
+This is a very simple template that just displays the ``text`` attribute of the
+``context`` object (our ``Sample`` instance).
+
+Create an ``edit.pt`` template with the following content:
+
+.. include:: groktut/storing_data/src/sample/app_templates/edit.pt
+ :literal:
+
+This template display a form asking for a bit of text. It submits to itself.
+
+Restart the server. Let's first view the index page:
+
+ http://localhost:8080/test
+
+You should see ``default text``.
+
+Now let's modify the text by doing to the edit page of the application:
+
+ http://localhost:8080/test/edit
+
+Type in some text and press the "Store" button. Since it submits to itself, we
+will see the form again, so go to the index page manually:
+
+ http://localhost:8080/test
+
+You should now see the text you just entered on the page. This means that your
+text was successfully stored in the object database!
+
+You can even restart the server and go back to the index page, and your text
+should still be there.
+
+Redirection
+-----------
+
+Let's make our application a bit easier to use. First, let's change
+``index.pt`` so it includes a link to the edit page. To do this, we will use
+the ``url`` method on the view:
+
+.. include:: groktut/redirection/src/sample/app_templates/index.pt
+ :literal:
+
+Giving ``url`` a single string argument will generate a URL to the view named
+that way on the same object (``test``), so in this case ``test/edit``.
+
+Now let's change the edit form so that it redirects back to the ``index`` page
+after you press the submit button:
+
+.. include:: groktut/redirection/src/sample/app.py
+ :literal:
+
+The last line is the new one. We use the ``url`` method on the view to
+construct a URL to the ``index`` page. Since we're in the template, we can
+simply call ``url`` on ``self``. Then, we pass this to another special method
+available on all ``grok.View`` subclasses, ``redirect``. We tell the system to
+redirect to the ``index`` page.
+
+Showing the value in the form
+-----------------------------
+
+Let's change our application so it displays what we stored the edit form as
+well, not just on the index page.
+
+To make this work, change edit.pt so it reads like this:
+
+.. include:: groktut/showing_the_value_in_the_form/src/sample/app_templates/edit.pt
+ :literal:
+
+The only change is that we have used ``tal:attributes`` to include the value of
+the ``text`` attribute of the context object in the form.
+
+The rules of persistence
+------------------------
+
+These are the "rules of persistence":
+
+* You should subclass classes that want to store data from
+ ``persistent.Persistent`` so that it's easy to store them in the ZODB. The
+ simplest way to do this with Grok is to subclass from ``grok.Model`` or
+ ``grok.Container``.
+
+* Instances that you want to store should be connected to other persistent
+ classes that are already stored. The simplest way to do this with Grok is to
+ attach them somehow to the ``grok.Application`` object, directly or
+ indirectly. This can be done by setting them as an attribute, or by putting
+ them in a container (if you made your application subclass
+ ``grok.Container``).
+
+* To make sure that the ZODB knows you changed a mutable attribute (such as a
+ simple Python list or dictionary) in your instance, set the special
+ ``_p_changed`` attribute on that instance to ``True``. This is only necessary
+ if that attribute is not ``Persistent`` itself. It is also not necessary when
+ you create or overwrite an attribute directly using ``=``.
+
+If you construct your application's content out of ``grok.Model`` and
+``grok.Container`` subclasses you mostly follow the rules already. Just
+remember to set ``_p_changed`` in your methods if you find yourself modifying a
+Python list (with ``append``, for instance) or dictionary (by storing a value
+in it).
+
+The code in the section `Storing data`_ is a simple example. We in fact have to
+do nothing special at all to obey the rules of persistence in that case.
+
+If we use a mutable object such as a list or dictionary to store data instead,
+we do need to take special action. Let's change our example code (based on the
+last section) to use a mutable object (a list):
+
+.. include:: groktut/the_rules_of_persistence/src/sample/app.py
+ :literal:
+
+We have now changed the ``Sample`` class to do something new: it has an
+``__init__`` method. Whenever you create the ``Sample`` application object now,
+it will be created with an attribute called ``list``, which will contain an
+empty Python list.
+
+We also make sure that the ``__init__`` method of the superclass still gets
+executed, by using the regular Python ``super`` idiom. If we didn't do that,
+our container would not be fully initialized.
+
+You will also notice a small change to the ``update`` method of the ``Edit``
+class. Instead of just storing the text as an attribute of our ``Sample``
+model, we add each text we enter to the new ``list`` attribute on.
+
+Note that this code has a subtle bug in it, which is why we've added the
+comment. We will see what bug this is in a little bit. First, though, let's
+change our templates.
+
+We change ``index.pt`` so that it displays the list:
+
+.. include:: groktut/the_rules_of_persistence/src/sample/app_templates/index.pt
+ :literal:
+
+We've also changed the text of the link to the ``edit`` page to reflect the new
+adding behavior of our application.
+
+We need to undo the change to the ``edit.pt`` template that we made in the last
+section, as each time we edit a text we now *add* a new text, instead of
+changing the original. There is therefore no text to show in as the input value
+anymore:
+
+.. include:: groktut/the_rules_of_persistence/src/sample/app_templates/edit.pt
+ :literal:
+
+.. sidebar:: evolution
+
+ What to do when you change an object's storage structure while your
+ application is already in production? In a later section, we will introduce
+ Zope Toolkit's object evolution mechanism that allows you to update objects
+ in an existing object database. TDB
+
+Let's restart the server. If you have followed the tutorial from the last
+section, you will now see an error when you look at the front page of the
+application::
+
+ A system error occurred.
+
+Look at the output we got when we tried to load our page::
+
+ AttributeError: 'Sample' object has no attribute 'list'
+
+But we just changed our object to have an attribute ``list``, right? Yes we
+did, but only for *new* instances of the Sample object. What we are looking at
+is the sample object from before, still stored in the object database. It has
+no such attribute. This isn't a bug by the way (for our actual bug, see later
+in this section): it is just a database problem.
+
+What to do now? The simplest action to take during development is to simply
+remove our previously installed application, and create a new one that *does*
+have this attribute. Go to the Grok admin screen:
+
+ http://localhost:8080
+
+Select the application object (``test``) and delete it. Now install it again,
+as ``test``. Now go to its edit screen and add a text:
+
+ http://localhost:8080/test/edit
+
+Click on ``add a text`` and add another text. You will see the new texts appear
+on the ``index`` page.
+
+Everything is just fine now, right? In fact, not so! Now we will get to our
+bug. Restart the server and look at the index page again:
+
+ http://localhost:8080/test
+
+None of the texts we added were saved! What happened? We broke the third rule
+of persistence as described above: we modified a mutable attribute and did not
+notify the database that we made this change. This means that the object
+database was not aware of our change to the object in memory, and thus never
+saved it to disk.
+
+.. sidebar: The ZODB only stores instance data
+
+ Note that the ZODB only stores ("persists") instance data. This means that
+ any data you have directly associated with a class, as opposed to the
+ instance, won't be persisted. Normally you only associate immutable data with
+ the class, so this is not a problem::
+
+ class Foo(object):
+ mydata = 'some text'
+
+ That data will be there when the module is imported, and since it will never
+ be changed, there isn't a problem. Now let's check what happens with mutable
+ data::
+
+ class Foo(object):
+ mydata = []
+
+ Appending an item to mydata (through ``self.mydata.append('bar')``, for
+ instance) have an effect, but only until you restart the server. Then your
+ changes will be lost.
+
+ It is good Python design practice not to use mutable class-data, so this
+ property of the ZODB shouldn't cramp your style.
+
+We can easily amend this by adding one line to the code:
+
+.. include:: groktut/the_rules_of_persistence2/src/sample/app.py
+ :literal:
+
+We've now told the server that the context object has changed (because we
+modified a mutable sub-object), by adding the line::
+
+ self.context._p_changed = True
+
+If you now add some texts and then restart the server, you will notice the data
+is still there: it has successfully been stored in the object database.
+
+The code shown so far is a bit ugly in the sense that typically we would want
+to manage our state in the model code (the ``Sample`` object in this case), and
+not in the view. Let's make one final change to show what that would look like:
+
+.. include:: groktut/the_rules_of_persistence3/src/sample/app.py
+ :literal:
+
+As you can see, we have created a method ``addText`` to the model that takes
+care of amending the list and informing the ZODB about it. This way, any view
+code can safely use the API of ``Sample`` without having to worry about the
+rules of persistence itself, as that is the model's responsibility.
+
+Explicitly associating a view with a model
+------------------------------------------
+
+How does Grok know that a view belongs to a model? In the previous examples,
+Grok has made this association automatically. Grok could do this because there
+was only a single model defined in the module (``Sample``). In this case, Grok
+is clever enough to automatically associate all views defined elsewhere in the
+same module to the only model. Behind the scenes Grok made the model the
+*context* of the views.
+
+Everything that Grok does implicitly you can also tell Grok to do explicitly.
+This will come in handy later, as you may sometimes need (or want) to tell Grok
+what to do, overriding its default behavior. To associate a view with a model
+automatically, you use the ``grok.context`` class annotation.
+
+What is a class annotation? A class annotation is a declarative way to tell
+grok something about a Python class. Let's look at an example. We will change
+``app.py`` in the example from `A second view` to demonstrate the use of
+``grok.context``:
+
+.. include:: groktut/explicitly_associating_a_view_with_a_model/src/sample/app.py
+ :literal:
+
+This code behaves in exactly the same way as the previous example in `A second
+view`, but has the relationship between the model and the view made explicit,
+using the ``grok.context`` class annotation.
+
+``grok.context`` is just one class annotation out of many. We will see another
+one (``grok.name``) in the next section.
+
+A second model
+--------------
+
+.. sidebar:: How to combine models into a single application?
+
+ Curious now about how to combine models into a single application? Can't
+ wait? Look at the section `Containers` coming up next, or `Traversal` later
+ on. TDB
+
+We will now extend our application with a second model. Since we haven't
+explained yet how to combine models together into a single application, we will
+just create a second application next to our first one. Normally we probably
+wouldn't want to define two applications in the same module, but we are trying
+to illustrate a few points, so please bear with us. Change ``app.py`` so it
+looks like this:
+
+.. include:: groktut/a_second_model/src/sample/app.py
+ :literal:
+
+You can see we now defined a second application class, ``Another``. It
+subclasses from ``grok.Application`` to make it an installable application.
+
+It also subclasses from ``grok.Model``. There is a difference between
+``grok.Model`` and ``grok.Container``, but for the purpose of the discussion we
+can ignore it for now. We just figured we should use ``grok.Model`` for some
+variety, though we could have indeed subclassed from ``grok.Container`` instead.
+
+We also define two templates, one called ``sampleindex.pt``:
+
+.. include:: groktut/a_second_model/src/sample/app_templates/sampleindex.pt
+ :literal:
+
+And one called ``anotherindex.pt``:
+
+.. include:: groktut/a_second_model/src/sample/app_templates/anotherindex.pt
+ :literal:
+
+We have named the templates the name as the lowercased class names as the
+views, so that they get associated with them.
+
+You will have noticed we have used ``grok.context`` to associate the views with
+models. We actually *have* to do this here, as Grok refuses to guess in the
+face of ambiguity. Without the use of ``grok.context``, we would have seen an
+error like this when we start up::
+
+ GrokError: Multiple possible contexts for <class
+ 'sample.app.AnotherIndex'>, please use grok.context.
+
+So, we use ``grok.context`` to explicitly associate ``SampleIndex`` with the
+``Sample`` application, and again to associate ``AnotherIndex`` with the
+``Another`` application.
+
+We have another problem: the intent is for these views to be ``index`` views.
+This cannot be deduced automatically from the name of the view classes however,
+and left to its own devices, Grok would have called the views ``sampleindex``
+and ``anotherindex``.
+
+Luckily we have another class annotation that can help us here: ``grok.name``.
+We can use it on both view classes (``grok.name('index')``) to explicitly
+explain to Grok what we want.
+
+You can now try to restart the server and create both applications in the Grok
+Admin interface. They should display the correct index pages when you look at
+them.
+
+We can see that the introduction of a second model has complicated our code a
+bit, though you will hopefully agree with us that it is still quite readable.
+We could have avoided the whole problem by simply placing ``Another`` and its
+views in another module such as ``another.py``. Its associated templates would
+then need to be placed in a directory ``another_templates``. Often you will
+find it possible to structure your application so you can use Grok's default
+conventions.
+
+Containers
+----------
+
+A container is a special kind of model object that can contain other objects.
+Our ``Sample`` application is already a container, as it subclasses
+``grok.Container``. What we will do in this section is build an application
+that actually puts something into that container.
+
+Grok applications are typically composed of containers and models. Containers
+are objects that can contain models. This includes other containers, as a
+container is just a special kind of model.
+
+From the perspective of Python, you can think of containers as dictionaries.
+They allow item access (``container['key']``) to get at its contents. They also
+define methods such as ``keys()`` and ``values()``. Containers do a lot more
+than Python dictionaries though: they are persistent, and when you modify them,
+you don't have to use `_p_changed` anywhere to notice you changed them. They
+also send out special events that you can listen to when items are placed in
+them or removed from them. For more on that, see the section on events (TDB).
+
+Our application object will have a single index page that displays the list of
+items in the container. You can click an item in the list to view that item.
+Below the list, it will display a form that allows you to create new items.
+
+Here is the ``app.py`` of our new application:
+
+.. include:: groktut/containers/src/sample/app.py
+ :literal:
+
+As you can see, ``Sample`` is unchanged. We have also created our first non-
+application object, ``Entry``. It is just a ``grok.Model``. It needs to be
+created with an argument ``text`` and this text is stored in it. We intend to
+place instances of ``Entry`` in our ``Sample`` container.
+
+Next are the views. We have an ``index`` page for the ``Sample`` container.
+When its ``update()`` is triggered with two values, ``name`` and ``text``, it
+will create a new ``Entry`` instance with the given text, and place it under
+the container under the name ``name``. We use the dictionary-like interface of
+our ``Sample`` container to put our new ``Entry`` in the container.
+
+Here is the associated template for ``SampleIndex``, ``sampleindex.pt``:
+
+.. include:: groktut/containers/src/sample/app_templates/sampleindex.pt
+ :literal:
+
+The first section in the template (``<h2>Existing entries</h2>``) displays a
+list of the items in the container. We again use dictionary-like access using
+``keys()`` to get a list of all the names of the items in the container. We
+create a link to these items using ``view.url()``.
+
+The next section (``<h2>Add a new entry</h2>``) displays a simple form that
+submits to the index page itself. It has two fields, ``name`` and ``text``,
+which we already have seen handled by ``update()``.
+
+Finally, we have an ``index`` page for ``Entry``. It just has a template to
+display the ``text`` attribute:
+
+.. include:: groktut/containers/src/sample/app_templates/entryindex.pt
+ :literal:
+
+Restart the server and try this application. Call your application ``test``.
+Pay special attention to the URLs.
+
+First, we have the index page of our application:
+
+ http://localhost:8080/test
+
+When we create an entry called ``hello`` in the form, and then click on it in
+the list, you see an URL that looks like this:
+
+ http://localhost:8080/test/hello
+
+We are now looking at the index page of the instance of ``Entry`` called
+``hello``.
+
+What kind of extensions to this application can we think of? We could create an
+``edit`` form that allows you to edit the text of entries. We could modify our
+application so that you can not just add instances of ``Entry``, but also other
+containers. If you made those modifications, you would be on your way to
+building your own content management system with Grok.
Added: groktoolkit/branches/jw-documentation-rearangement/doc/tutorial_outline.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/tutorial_outline.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/tutorial_outline.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,236 @@
+================
+Tutorial outline
+================
+
+This is not the tutorial itself, but a sketch of what the tutorial
+could look like. This hopefully inspires people to contribute to the
+tutorial. The structure of the tutorial is very much use-case driven
+and about getting things done. This means we tend to discuss the
+component architecture itself very late.
+
+Note that while I've indicated the overal aim of sections in chapters,
+that doesn't mean a chapter is absolutely decicated to a single
+topic. If for instance in the course of explaining search it becomes
+important to override traversal, it can be discussed right there.
+
+Main tutorial
+=============
+
+Getting started with Grok
+-------------------------
+
+This section aims to get a beginner up and running with Grok, using
+grokproject. It doesn't really go into any code yet, except to
+describe what grokproject creates.
+
+ * Setting up grokproject
+
+ * Creating a grok project
+
+ * Starting up Zope
+
+ * An empty Grok project
+
+Showing pages
+-------------
+
+We get beginners up to speed with writing view logic in Grok. This is
+basically the first thing beginners want - just get some HTML on the
+screen. Basic templating, supplementing templating with view-level
+methods, and various basic interaction patterns. Models are still out
+of scope. Armed with this knowledge people should already be able to
+write simple web applications with Grok, if at least they don't have
+to worry much about storing data.
+
+ * Publishing a simple web page
+
+ * A second view
+
+ * Making our page dynamic
+
+ * Static resources for our web page
+
+ * Using view methods
+
+ * Generating HTML from Python
+
+ * Completely Python-driven views
+
+ * Doing some calculation before viewing a page
+
+ * Reading URL parameters
+
+ * Simple forms
+
+Models
+------
+
+Once we know how to show things, we need to go into what we're
+actually showing: the model. This involves view/model separation,
+dealing with the ZODB and persistence, and constructing applications
+from models and containers.
+
+Note that we also include some more advanced view use cases which only
+tend to become relevant with more complicated applications (such as
+redirection).
+
+ * A view for a model
+
+ * Storing data
+
+ * Redirection
+
+ * Showing the value in the form
+
+ * The rules of persistence
+
+ * Containers
+
+Some notes:
+
+* What if a container already contains an item with the same name? We will
+ get an error. How to handle this error elegantly?
+
+Forms
+-----
+
+Now that we've seen the form and storage basics, we go a step further
+and show the power of automatic form generation from schemas.
+
+Building on the patterns we've seen before, we develop a simple CRUD
+application with an overview screen and add and edit forms. This will
+also include at least a glance at interfaces in the context of
+schemas.
+
+Search
+------
+
+We have a way for a user to enter information. Now we need to build an
+application that does something with it. We extend our CRUD
+application with indexing and search, using the catalog.
+
+By now the application should also be advanced enough to explain
+overriding traversal, for instance to enable simple 'tag' based
+browsing mechanism based on search. We need to show a pattern where
+non-persistent objects are created in traversal.
+
+This will also lead into a brief introduction of utility lookup and
+sites.
+
+XXX setting up the catalog is easy now, but it can be automated a bit
+ further still in Grok.
+
+XXX We probably need hurry.query. This needs some work on the Grok end
+ to expose this nicely.
+
+Custom widgets
+--------------
+
+The defaults are never enough when it comes to web forms. This is a
+nice point to introduce making your own custom form widgets.
+
+We will also show how you can use AJAX with Grok so you can give your
+widget some dynamic behavior.
+
+XXX we need to make it easy to make widgets in Grok.
+
+XXX this needs work on the Grok end to at least expose JSON, and perhaps
+ we need to ship with a 'recommended' Javascript library.
+
+Security
+--------
+
+Explain how Grok allows you to protect your views. In the course of
+this we also need to explain a bit about Zope 3's user authentication
+system, as we need users to test this with.
+
+XXX We need to flesh out user authentication issues in Grok.
+
+Extending our application
+-------------------------
+
+We show one of Zope 3's main strengths: we create a separate codebase
+in a completely separate project that extends the first. Then we
+demonstrate many extension patterns Zope 3 offers:
+
+ * creating an extension project (using buildout and SVN externals?)
+
+ * a new look for old models (skins)
+
+ * the benefit of interfaces
+
+ * events
+
+ * adapters
+
+Appendices
+==========
+
+While these topics may not presuppose a lot of knowledge, we probably
+do not want to scatter all of this through the tutorial itself so as
+not to distract from the main story (though we may change our minds if
+it seems to come out naturally).
+
+Explicit configuration
+----------------------
+
+Should give an introduction on the principles of Grok: explicit
+configuration using directives, with defaults so you can leave them
+off if you follow the grok patterns.
+
+I'm not sure yet whether this can be part of the main flow of the
+text. We at the very least will refer to this at some point in the
+text though, and we need to refer people to this for more information.
+
+The Component Architecture
+--------------------------
+
+Explain how many bits and pieces we've seen so far are actually
+aspects of the component architecture.
+
+Automatic testing
+-----------------
+
+A brief introduction to automatic testing. Introduce how to unit test
+and functional test with doctests.
+
+XXX We probably need to do some development work on a test grokker.
+
+XMLRPC
+------
+
+Show how to do XMLRPC with Grok.
+
+Extending grok
+--------------
+
+Grok can be extended using Grokkers. Explain how to do it here.
+
+Development issues
+------------------
+
+We describe best practices on how to manage your code when developing
+with Grok. This touches topics like setup.py, buildout, and also
+version control systems.
+
+ * Pulling in new dependencies from the Cheeseshop.
+
+ * Putting your project into SVN
+
+ * Uploading your project to the Python Cheeseshop
+
+Items I'm not sure where to place yet
+=====================================
+
+These items will need to find a place in the main narrative or the
+appendices. They're listed here so we don't forget about them:
+
+ * Constructing urls with view.url()
+
+ * base classes
+
+ * Events
+
+ * Showing error pages.
+
+ * Discussion on viewlets/portlets.
Added: groktoolkit/branches/jw-documentation-rearangement/doc/upgrade.rst
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/upgrade.rst (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/upgrade.rst 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1 @@
+.. include:: upgrade.txt
Added: groktoolkit/branches/jw-documentation-rearangement/doc/upgrade.txt
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/doc/upgrade.txt (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/doc/upgrade.txt 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,619 @@
+.. _upgrade_notes:
+
+
+Upgrade notes
+=============
+
+This document outlines how to update Grok applications so that they continue to
+work with newer versions of the Grok Toolkit. This document only describes
+changes involving incompatibilities or deprecations, not new features (please
+refer to ``CHANGES.txt`` for those).
+
+**Warning**. Please be sure to always backup your data (especially the
+``Data.fs`` file) before you perform upgrades.
+
+.. _upgrade_notes_1.2:
+
+Upgrading to 1.2 (2010-10-26)
+-----------------------------
+
+To upgrade your Grok based project, make sure your project's ``buildout.cfg``
+extends from the ``versions.cfg`` of the latest Grok Toolkit release. This file
+can be found here::
+
+ http://grok.zope.org/releaseinfo/1.2/versions.cfg
+
+Then re-run ``bootstrap.py`` in your project to prevent potential
+``zc.buildout`` version conflicts. Then run ``bin/buildout`` to get the latest
+versions of all of the packages that comprise the Grok Toolkit.
+
+Extra notes:
+
+* In Grok 1.2 the "zdaemon" support has been removed. If your project still
+ relied on this method of starting and stopping the server you will need to
+ update your prokject.
+
+ The easiest way for find what parts and file to add, is to create a new
+ project using the ``grokproject`` tool and then to compare its structure to
+ your project's structure. Look for the "debug_ini" and "deploy_ini" parts in
+ the ``buildout.cfg`` file and the corresponding configuration file templates.
+
+* A large numner of ``zope.app.`` dependencies have been removed. Even though
+ most of these packages just contained backwards compatibility imports, your
+ application might still contain imports from these ``zope.app.`` packages.
+
+ The best way to update this, is to carefully search for ``zope.app.`` imports
+ in your project and to rewrite them to the new import locations. Note though,
+ that in rare cases, this might break persisted object in your database.
+
+ If this is the case, you will need to add the particular ``zope.app.``
+ package to the ``install_requires`` section in the ``setup.py`` of your
+ project. After a re-run of ``./bin/buildout`` these package are now again
+ available to your project.
+
+ In general it is good practice to explicitely list the dependencies of your
+ project in the ``setup.py``. In other words: if your project imports from
+ packages, these packages should be listed in the ``install_requires`` of your
+ project's ``setup.py``.
+
+* One specific case of a ``zope.app.`` depdendency that got removed and
+ replaced is ``zope.app.testing`` that is used in the test setup of your
+ project. Most of the functionality in ``zope.app.testing`` has been rebuild
+ in ``zope.component.testlayer``, ``zope.app.appsetup``, and
+ ``zope.app.wsgi.testlayer``.
+
+ Again, the easiest way to upgrade this part of your project, is to look a
+ freshly created project using the ``grokproject`` tool. There, the test setup
+ code uses the "new style" test layers for functional testing.
+
+* In some case the configuration step of a dependency is not triggered
+ anymore, where it used to be before most of the ``zope.app.`` dependencies
+ got removed. If this is the case (for example for components in in
+ zope.pluggableauth.plugins), you will need to trigger the configuration
+ yourself from your project's ``configure.zcml`` like so::
+
+ <include package="[PACKAGE_TO_CONFIGURE]" />
+
+ or, for a specific ``*.zcml`` file in package::
+
+ <include package="[PACKAGE_TO_CONFIGURE]" file="[ZCML_FILE]"/>
+
+.. _upgrade_notes_1.1:
+
+Upgrading to 1.1 (2010-05-18)
+-----------------------------
+
+* `z3c.testsetup` dependency has been removed from grok. If you use
+ grok.testing.register_all_tests in your testsetup, make sure to
+ require ``z3c.testsetup`` (and also ``zope.app.testing``, if you use
+ functional tests) in `setup.py` of your project and use::
+
+ import z3c.testsetsetup
+ z3c.testsetup.register_all_tests(...)
+
+ where you used ``grok.testing.register_all_tests(...)`` before.
+
+.. _upgrade_notes_1.1rc1:
+
+Upgrading to 1.1rc1 (2010-02-25)
+--------------------------------
+
+* When upgrading to a newer version of Grok, you should refer to the
+ newest list of versions as defined for this release of Grok.
+
+ For Grok 1.1rc1, download the following file::
+
+ http://grok.zope.org/releaseinfo/grok-1.1rc1.cfg
+
+ And replace ``versions.cfg`` in your project with this file. Then run::
+
+ ./bin/buildout
+
+.. _upgrade_notes_1.1a2:
+
+Upgrading to 1.1a2 (2009-12-22)
+-------------------------------
+
+* When upgrading to a newer version of Grok, you should refer to the
+ newest list of versions as defined for this release of Grok.
+
+ For Grok 1.1a2, download the following file::
+
+ http://grok.zope.org/releaseinfo/grok-1.1a2.cfg
+
+ And replace ``versions.cfg`` in your project with this file. Then run::
+
+ ./bin/buildout
+
+.. _upgrade_notes_1.1a1:
+
+Upgrading to 1.1a1 (2009-11-17)
+-------------------------------
+
+* When upgrading to a newer version of Grok, you should refer to the
+ newest list of versions as defined for this release of Grok.
+
+ For Grok 1.1a1, download the following file::
+
+ http://grok.zope.org/releaseinfo/grok-1.1a1.cfg
+
+ And replace ``versions.cfg`` in your project with this file. Then run::
+
+ ./bin/buildout
+
+.. _upgrade_notes_1.0b2:
+
+Upgrading to 1.0b2 (2009-09-15)
+-------------------------------
+
+* The default permission is now ``zope.View`` as a replacement for
+ ``zope.Public``. You need to add this permission as a default
+ permission to all users (use ``zope.Anybody``). This requires a
+ change to ``site.zcml`` as follows::
+
+ <grant permission="zope.View"
+ principal="zope.Anybody" />
+
+ **If you do not make this change, all of your views will be
+ unavailable for anonymous and the system will ask the user for a
+ password.**
+
+ This change allows you to protect Grok views that come with the
+ default permission by modifying your ``site.zcml``.
+
+ If you used a previous version of Grok or grokproject you may still
+ have a reference to ``grok.View`` in ``site.zcml`` or
+ ``ftesting.zcml``. This will lead to an error, as Grok does not
+ define ``grok.View`` anymore. It's safe to remove such references.
+
+* When upgrading to a newer version of Grok, you should refer to the
+ newest list of versions as defined for this release of Grok.
+
+ For Grok 1.0b2, download the following file::
+
+ http://grok.zope.org/releaseinfo/grok-1.0b2.cfg
+
+ And replace ``versions.cfg`` in your project with this file.
+
+* There have been a lot of changes in grokproject and the project
+ layout it generates. This gives you a short description of how you
+ can upgrade your existing Grok project that was generated with an
+ older version of grokproject.
+
+ You should upgrade grokproject as follows::
+
+ $ easy_install -U grokproject
+
+ grokproject now creates a project based on `Paste Deploy`_, along
+ with a few other changes to the way various files are managed.
+
+ .. _`Paste Deploy`: http://pythonpaste.org/deploy/
+
+ **Warning**. Please be aware that the ``parts/data`` and
+ ``parts/log`` directories are deprecated and will not be used
+ anymore. The only reasons there are still ``[data]`` and ``[log]``
+ sections in the new ``buildout.cfg``structure is to make sure we
+ don't accidentally throw away important data. Back up at least any
+ important ``Data.fs`` (which contains the ZODB object database of
+ your app) *before* making any changes to a project, or when you
+ upgrade any deployment.
+
+ To switch over your project to use a new layout, create a new, empty
+ project with grokproject and compare it with your current
+ layout. You can then compare it with your existing project layout
+ and make the appropriate changes to your project.
+
+ There have been changes to ``setup.py``, ``buildout.cfg`` and a new
+ ``etc`` directory has appeared.
+
+ The templates for config files are now in ``etc`` - these get
+ generated by buildout into ``parts/etc``. Find more information on
+ configuration and settings in ``etc/README.txt``.
+
+ The ``Data.fs`` file is now placed in ``var/filestorage``. Please
+ copy your backed-up version of ``Data.fs`` in there to reuse your
+ older ZODB database.
+
+ Log files are now placed in ``var/log``.
+
+ Before re-running buildout to generate the new templates, please be
+ aware that ``parts/zopectl`` and ``parts/app`` will be deleted when
+ you re-run buildout. This means that ``parts/zopectl/access.log``
+ will be removed, and you may want to backup this file first.
+
+ After making these adjustments, you can now run ``buildout`` for the
+ project.
+
+ Start the instance now like::
+
+ bin/paster serve parts/etc/deploy.ini
+
+ or with::
+
+ bin/projectname-ctl fg
+
+ Alternatively there's a profile available that can help debugging errors in
+ your application::
+
+ bin/paster serve parts/etc/debug.ini
+
+ When using this profile it is not the ``zope.publisher`` that handles the
+ exceptions that are raised, but a special middleware is. This middleware
+ then provides a pdb-like debugging user interface in the browser.
+
+ Note that this includes IUnauthorized exceptions not being handled by zope,
+ that would've prevented any login mechanism to work when debugging.
+
+ However, there is a configuration option called ``exempt-exceptions``
+ available in the debug.ini that determines what exceptions should still be
+ handled by zope. By default debug.ini files created by grokproject will
+ exempt the IUnauthorized exceptions from being reraised and thus normal
+ authentication mechanism continue to work::
+
+ [app:zope]
+ use = egg:${egg}#debug
+ filter-with = translogger
+ exempt-exceptions = zope.security.interfaces.IUnauthorized
+
+ Interpreter name has been changed from ``bin/python`` to
+ ``bin/grokpy`` to avoid conflicts with virtualenv.
+
+
+* Old ``buildout.cfg`` contain a ``find-links`` line like this::
+
+ find-links = http://download.zope.org/distribution/
+
+ You should be able to safely remove this, as this points to a
+ repository of old releases that Grok doesn't depend on any more.
+
+ If you have problems after removing it and re-running ``bin/buildout``,
+ you can add it again however. We know that ``megrok.form`` for instance
+ depends on a release that was only available in this repository.
+
+* Note: in 1.0b1 we used to have a split between ``View`` and
+ ``CodeView``. This split got reverted. Grok's behavior is still the
+ same as in the 1.0a versions - views and the ``render`` method continue
+ to work as they did before.
+
+.. _upgrade_notes_1.0a1:
+
+Upgrading to 1.0b1 (2009-09-14)
+-------------------------------
+
+* This release happened was never completed. See the upgrade
+ documentation for 1.0b2 instead.
+
+Upgrading to 1.0a1
+------------------
+
+* The ``grok.RESTProtocol`` class has been removed in favour of a
+ ``grok.restskin()`` directive for interfaces. For instance, if you
+ previously registered a REST layer as a skin like so::
+
+ class IMyLayer(grok.IRESTLayer):
+ pass
+
+ class MyRestProtocol(grok.RESTProtocol):
+ grok.layer(IMyLayer)
+
+ You can now simply write::
+
+ class IMyLayer(grok.IRESTLayer):
+ grok.restskin('myskin')
+
+ As you can see, ``IRESTLayer`` has been introduced as a baseclass for
+ defining REST layers.
+
+.. _upgrade_notes_0.14:
+
+Upgrading to 0.14
+-----------------
+
+* The ``grok.Skin`` class has been removed in favour of a
+ ``grok.skin()`` directive for interfaces. For instance, if you
+ previously registered a browser layer as a skin like so::
+
+ class IMyLayer(grok.IGrokLayer):
+ pass
+
+ class MySkin(grok.Skin):
+ grok.layer(IMyLayer)
+
+ You can now simply write::
+
+ class IMyLayer(grok.IBrowserRequest):
+ grok.skin('myskin')
+
+ As you can see, ``IGrokLayer`` has also been removed, in favour of
+ the exposure of ``IBrowserRequest``.
+
+* The ``grok.admin`` subpackage has been factored out to a separate
+ package ``grokui.admin``. To have the Grok admin UI available in
+ your environment, add ``grokui.admin`` to the required packages in
+ the ``setup.py`` of your package.
+
+ A new Grok application will have an install_requires parameter that
+ looks like this::
+
+ install_requires=['setuptools',
+ 'grok',
+ 'grokui.admin',
+ 'z3c.testsetup',
+ # Add extra requirements here
+ ],
+
+.. _upgrade_notes_0.13:
+
+Upgrading to 0.13
+-----------------
+
+* The directive implementations changed tremendously with the upgrade
+ to Martian 0.10. Custom implementations of both directives (see
+ next bullet point) and grokkers will have to be adjusted.
+
+ Since the vast majority of directives are class directives, the most
+ common places where information set by directives has to be read are
+ class grokkers (``martian.ClassGrokker``). For instance, you may
+ have written something like this to implement a custom class grokker
+ previously::
+
+ class RobotGrokker(martian.ClassGrokker):
+ component_class = Robot
+
+ def grok(self, name, factory, module_info, config, **kw):
+ robot_name = martian.util.class_annotation(factory, 'grok.name', '')
+ title = martian.util.class_annotation(factory, 'grok.title', 'A robot')
+ provides = martian.util.class_annotation(factory, 'grok.provides', None)
+ if provides is None:
+ martian.util.check_implements_one(factory)
+ provides = list(zope.interface.implementedBy(factory))[0]
+ config.action(
+ descriminator=('robot', provides, robot_name),
+ callable=provideRobot,
+ args=(factory, provides, robot_name, title),
+ )
+ return True
+
+ As you can see, this grokker needs to retrieve three values from the
+ class it's grokking (``factory``) which are all set by directives:
+
+ - ``grok.name`` with the standard default, an empty string,
+
+ - ``grok.title`` with a custom default, the string ``A robot``,
+
+ - ``grok.provides`` with a computed default.
+
+ With the new directive implementation and the extensions to
+ Martian's ``ClassGrokker``, you are now able to write (and you
+ should write!)::
+
+ def default_provides(factory, module, **data):
+ # This function is available for import from grokcore.component.meta.
+ # It's shown here simply to illustrate how the original grokker would
+ # have been refactored.
+ martian.util.check_implements_one(factory)
+ return list(zope.interface.implementedBy(factory))[0]
+
+ class RobotGrokker(martian.ClassGrokker):
+ martian.component(Robot)
+ martian.directive(grok.name, name='robot_name')
+ martian.directive(grok.title, default='A Robot')
+ martian.directive(grok.provides, get_default=default_provides)
+
+ def execute(self, factory, config, robot_name, title, provides, **kw):
+ config.action(
+ descriminator=('robot', provides, robot_name),
+ callable=provideRobot,
+ args=(factory, provides, robot_name, title),
+ )
+ return True
+
+ What you need to do is provide the directives in the grokker class
+ using ``martian.directive`` and then implement the ``execute``
+ method which will get the class (``factory``) and the configuration
+ context (``config``) as positional arguments and then the values of
+ the directives as keyword parameters.
+
+ Note that when using ``martian.directive``, you may
+
+ - set the name of the keyword parameter if you want it to be
+ different than the directive's name,
+
+ - set a default value if you want it to be different from the
+ directive's standard default,
+
+ - pass in a factory for a computed default value (``get_default``).
+
+ If you need still need to manually retrieve directive values from an
+ object (a class, an instance or a module), you can do so by
+ explicitly calling ``bind`` on the directive (which accepts the same
+ optional parameters as ``martian.directive``), and then the ``get``
+ method of the bound directive, e.g.::
+
+ class_context = grok.context.bind().get(factory, module=module)
+ just_module_context = grok.context.bind().get(module=module)
+
+ In most cases it's possible to avoid this though, and use the
+ ``martian.directive`` directive on the class level.
+
+ You can look at ``src/grok/meta.py`` in Grok to see examples.
+
+* Your custom grokker could previously use ``component_class`` and
+ ``priority`` as class-level variables. These have been changed to
+ the ``martian.component`` and the ``martian.priority`` directives
+ that take the value as its first argument. The new
+ ``martian.directive`` directive was introduced above.
+
+* Custom directives need to be re-implemented using Martian's new
+ ``Directive`` base class. The directive scope, the type of storage,
+ the validator and a potential default value are all defined as
+ class-level variables:
+
+ - The directive scope can either one of ``martian.CLASS``,
+ ``martian.MODULE``, ``martian.CLASS_OR_MODULE``.
+
+ - The type of storage can be either one of ``martian.ONCE``,
+ ``martian.MULTIPLE``, ``martian.DICT``.
+
+ - An optional validator may be one of ``validateText``,
+ ``validateInterface``, ``validateInterfaceOrClass`` or a custom
+ method.
+
+ - Unless set with a different value, the standard default value will
+ be ``None``.
+
+ For example, consider the implementation of the ``grok.name``
+ directive::
+
+ class name(martian.Directive):
+ scope = martian.CLASS
+ store = martian.ONCE
+ default = u''
+ validate = martian.validateText
+
+ Or a bit more involved (and made-up) example::
+
+ class bases(martian.Directive):
+ scope = martian.CLASS
+ scope = martian.ONCE
+ default = []
+
+ # The factory is called with the parameters of the directive
+ # and may transform the values into whatever should be stored.
+ def factory(self, *values):
+ return list(values)
+
+ # This validator makes sure that the directive can only take
+ # a list of classes an argument
+ def validate(self, *values):
+ for value in values:
+ if not isinstance(value, type):
+ raise GrokError("%r is not a class!" % value)
+
+* We moved to newer versions of zope packages. Grok's versions for
+ Zope packages are now based on the KGS list for Zope 3.4c1 (the
+ latest list). This means your code can now get some new deprecation
+ warnings for imports that have been moved. Please check your code
+ and fix your imports if you get those warnings.
+
+* If you were using ``zope.publisher.http.applySkin``, you now must
+ use ``grok.util.applySkin``. This because
+ ``zope.publisher.http.appySkin`` was removed again in later versions
+ of ``zope.publisher``.
+
+* The ``url`` method on ``ViewletManager`` and ``Viewlet`` was
+ removed. Instead you can easily access the ``url`` method of the
+ view itself from within a viewlet or viewlet manager, and the
+ ``view`` name is also available in viewlet templates. There are also
+ new ``viewlet`` and ``viewletmanager`` namespaces in the viewlet
+ templates. Note that ``view`` in a viewlet thus means something else
+ than what it does before. Previous uses of ``view`` in a viewlet
+ template should be renamed to ``viewlet``.
+
+.. _upgrade_notes_0.12:
+
+Upgrading to 0.12
+-----------------
+
+* Please upgrade grokproject::
+
+ $ easy_install -U grokproject
+
+* If you have existing Grok projects and you want to make use of
+ Grok's new autoinclusion functionality in them, you can place
+ the following line in your project's ``configure.zcml``:
+
+ <includeDependencies package="." />
+
+ This will cause the ZCML for ``setup.py`` dependencies of your
+ package to be loaded automatically. You can now get rid of any
+ manual ``include`` statements (except the one that includes ``grok``
+ itself).
+
+ For new projects created by ``grokproject``, this line will be
+ automatically be added for you and you don't have to do anything except
+ to upgrade ``grokproject``::
+
+ $ easy_install -U grokproject
+
+* The convention that classes ending with -Base automatically become base
+ classes has been removed with martian 0.9.4. Please add the grok.baseclass()
+ directive to these classes explicitly where the 'Base' class convention was
+ relied upon to preserve existing functionality.
+
+.. _upgrade_notes_0.11:
+
+Upgrading to 0.11
+-----------------
+
+* ``grok.define_permission`` has been removed in favour of a
+ ``grok.Permission`` base class, for reasons of symmetry. Instead of
+ writing::
+
+ grok.define_permission('myapp.ViewCavePainting')
+
+ you should now write::
+
+ class View(grok.Permission):
+ grok.name('myapp.ViewCavePainting')
+
+ If you also want to supply a title and description for the
+ permission, use the ``grok.title()`` and ``grok.description()``
+ directives on the class.
+
+* ``grok.grok`` and ``grok.grok_component`` have been deprecated. If
+ you need them for tests (which is their only legimitate use), you
+ should import them both from ``grok.testing``.
+
+* Grokkers should now emit configuration actions instead of
+ registering components right away. For that they now get a new
+ keyword argument called ``config``, the configuration context. For
+ example, a grokker that used to do this::
+
+ registerSomeComponent(foo, name)
+
+ should now be doing this::
+
+ config.action(
+ discriminator=('somecomponent', name),
+ callable=registerSomeComponent,
+ args=(name,)
+ )
+
+ The discriminator should be chosen so that registrations with the
+ same discriminator conflict (in the above example, if somebody tried
+ to register two different components under the same name, you'd get
+ a conflict).
+
+* Grokkers no longer get the ``context`` and ``templates`` keyword
+ arguments. If they need access to these values, they can now get
+ them as module annotations from the ``module_info`` object like
+ this::
+
+ context = module_info.getAnnotation('grok.context')
+ templates = module_info.getAnnotation('grok.templates')
+
+* Note that grokkers must always take arbitrary keyword arguments
+ (``**kw``), as specified by the ``martian.interfaces.IGrokker``
+ interface. A minimal specification of the ``grok()`` method is
+ therefore::
+
+ def grok(self, name, obj, **kw):
+ ...
+
+ though grokkers will likely want to take ``module_info`` as well as
+ ``config`` explicitly::
+
+ def grok(self, name, obj, module_info, config, **kw):
+ ...
+
+ If your application defines custom grokkers and you're getting a
+ ``TypeError`` about unexpected arguments to ``grok``, you likely
+ need to update the signature of the ``grok()`` method like described
+ above.
+
+
+Upgrading to 0.10
+-----------------
+
+There were no incompatible changes.
Copied: groktoolkit/branches/jw-documentation-rearangement/documentation.cfg (from rev 119533, grok/branches/jw-documentation-rearangement/documentation.cfg)
===================================================================
--- groktoolkit/branches/jw-documentation-rearangement/documentation.cfg (rev 0)
+++ groktoolkit/branches/jw-documentation-rearangement/documentation.cfg 2011-01-12 16:38:04 UTC (rev 119545)
@@ -0,0 +1,18 @@
+[buildout]
+extends = grok.cfg
+develop = .
+parts =
+ grokpy
+ docs
+versions = versions
+
+[grokpy]
+recipe = z3c.recipe.scripts
+interpreter = grokpy
+eggs = grok
+
+[docs]
+recipe = collective.recipe.sphinxbuilder
+source = ${buildout:directory}/doc
+build = ${buildout:directory}/doc/_build
+interpreter = ${buildout:bin-directory}/grokpy
More information about the checkins
mailing list