===========
 Changelog
===========

.. _changelog:


Changes between 1.4.3 and 1.5
=============================

Pertinent to users:
-------------------

1. Renamed ``pyblcmd`` to ``pyblosxom-cmd``.

2. PyBlosxom now requires Python 2.3.  We've removed the _logging
   module that provided logging facilities to pre-Python 2.3 versions.

3. To install PyBlosxom on your system, you will now need setuptools.

4. The ``pyblosxom.cgi`` file has changed significantly---if you're
   using it you should grab the new one that comes with this
   distribution.  We've gutted the ``pyblosxom.cgi`` script and turned
   it into a stub.  This will reduce the need for you to update your
   ``pyblosxom.cgi`` in the future when you upgrade PyBlosxom.

5. pyblosxom-cmd now has an option to create the blog directory
   structure and skeleton files for you.  This makes it much faster to
   get a new blog up and running.  Syntax is this::

      pyblosxom-cmd create <path>

   Some examples::

      pyblosxom-cmd create .
      pyblosxom-cmd create /home/joe/blog

6. Template variable syntax ``$id_escaped`` and ``$id_urlencoded`` has
   been removed.  Use ``$escape(id)`` and ``$urlencode(id)`` instead.

7. Switched to using Python's optparse module instead of our
   home-brewed one.  There are some changes in command line syntax.
   Do ``pyblosxom-cmd --help`` for command line help.

8. Changed around ``INSTALL``, ``README`` and added ``UPGRADE``.

9. Removed ``blog_title_with_path`` variable.  If you were using this
   variable in your templates, replace it.  i.e. instead of::

       $blog_title_with_path

   do::

       $blog_title : $pi_bl

10. Re-worked PyBlosxom so that it uses the same encoding throughout.
    This means you need to use the same encoding for all your data
    files and that encoding has to match the ``blog_encoding``
    property in ``config.py``.  This defaults to UTF-8.

11. Re-worked documentation to use Sphinx.  The end result is that the
    "source" for the docs is in ``docs/source/``, there's an HTML
    version that's built by Sphinx in ``docs/build/html/``, and it's a
    lot easier to read and use now.  Thank you to the Sphinx team!

12. Reworked the command line for static rendering.  It now works like
    this::

        pyblosxom-cmd staticrender \
                      [--config <path/to/config/file>] \
                      [--incremenal]

    If the ``config.py`` file is in your ``PYTHONPATH``, then you can
    skip the ``--config <path/to/config/file>`` stuff.

13. Removed portalocker code.  This will cause any plugins using the
    locking code to fail.  The only one I saw like this was the
    logstats plugin which had a lot of other problems.

14. Added a ``--silent`` flag to pyblcmd so that it quells all stdout.
    This is useful for cron jobs.

15. Added ``truncate_date`` config variable.  When set to True, it
    causes date-based archives to be truncated to ``num_entries`` entries.
    Defaults to False.

    Example::

        py["truncate_date"] = True

16. Added ``truncate_category`` config variable.  When set to True, it
    causes category-based archives to be truncated to ``num_entries``
    entries.  Defaults to True.

    Example::

        py["truncate_category"] = True

17. Added ``truncate_frontpage`` config variable.  When set to True, it
    causes the front page ``num_entries`` entries.  Defaults to True.

    Example::

        py["truncate_frontpage"] = True

18. Plugins are included in the PyBlosxom source tarball again.

19. Templates in a flavourdir directory no longer require the flavour
    as the file extension.  e.g. This will work fine::
        
        blog/
         |- flavourdir/
             |- html.flav/
                 |- content_type
                 |- head
                 |- story
                 |- ...

20. We moved the main PyBlosxom site to
    http://pyblosxom.bluesock.org/ .  There's a "powered by
    pyblosxom" image at
    http://pyblosxom.bluesock.org/images/pb_pyblosxom.gif

    You should adjust your templates accordingly.

21. The following plugins have been added to the pyblosxom release
    tarball:

    * archives/
      * pyarchives
      * yeararchives (was wbgarchives)
    * categories/
      * pycategories
    * comments/plugins/
      * akismetcomments
      * comments
      * no_old_comments
      * trackback
      * xmlrpc_pingback
    * date/
      * pycalendar
      * firstdaydiv
      * pyfilenamemtime
      * w3cdate
    * display/
      * paginate (was wbgpager)
      * entrytitle
    * headers/
      * conditionalhttp
    * tags/
      * tags (was wbgtags)
    * text/
      * acronyms

    If you have older versions of these plugins, better to switch to
    the new versions.


Pertinent to developers:
------------------------

1. ``Pyblosxom.tools.VariableDict`` is no more.

2. If you have template variables that end in ``_urlencoded`` and
   ``_escaped``, it's better to instead call
   ``tools.escape_text(...)`` and ``tools.urlencode_text(...)`` or use
   filter functions ``$escape(var)`` and ``$urlencode(var)``.

3. The blosxom renderer has undergone a bunch of fixes.  If you
   depended on functions that started with ``_``, then you'll probably
   need to rework your plugin.  These functions were not intended for
   outside use.

   Additionally, we fixed the bug where the renderer was adding the
   contents of the config and data dicts to each entry when it was
   rendered as a story.  Now the items in the entrylist are untouched
   during rendering.

4. Added a lot of tests and rewrote everything to ditch the nose
   requirement.  Tests can be run with::

      python setup.py test

5. Added a lot of documentation.

6. Plugins can now do command-line things.  See the ``commandline``
   callback in the documentation.

7. Removed the portalocker code so PyBlosxom no longer provides a way
   to lock/unlock text files.

8. Changed a lot of camel-case function/method names to PEP-8
   versions.  Camel case names are deprecated and will be removed in a
   future version:

   ``tools.py``:

   * Walk -> walk
   * getLogger -> get_logger
   * generateRandStr -> generate_rand_str

   ``pyblosxom/Pyblosxom.py``:

   * PyBlosxom: getRequest -> get_request
   * PyBlosxom: getResponse -> get_response
   * PyBlosxom: runCallback -> run_callback
   * PyBlosxom: runRenderOne -> run_render_one
   * PyBlosxom: runStaticRenderer removed
   * Request: setResponse -> set_response
   * Request: getResponse -> get_response
   * Request: getForm -> get_form
   * Request: getConfiguration -> get_configuration
   * Request: getHttp -> get_http
   * Request: getData -> get_data
   * Request: addHttp -> add_http
   * Request: addData -> add_data
   * Request: addConfiguration -> add_configuration
   * Response: setStatus -> set_status
   * Response: addHeader -> add_header
   * Response: getHeaders -> get_headers
   * Response: sendBody -> send_body
   * Response: sendHeaders -> send_headers

   ``pyblosxom/renderers/base.py``:

   * RendererBase: addHeader -> add_header
   * RendererBase: setContent -> set_content
   * RendererBase: needsContentType -> needs_content_type
   * RendererBase: showHeaders -> show_headers

   ``pyblosxom/renderers/blosxom.py``:

   * BlosxomRenderer: renderContent -> render_content
   * BlosxomRenderer: renderTemplate -> render_template
   * BlosxomRenderer: getContent -> get_content
   * BlosxomRenderer: outputTemplate -> output_template

9. Changed ``add_header`` in the ``Response`` class to take a key and
   value instead of a list of strings that it has to use * magic and
   then munge through.

10. Added a commandline callback for allowing plugins to add to the
    command line.

11. Added a truncatelist callback allowing plugins to augment the
    truncate (``num_entries``) behavior.

12. Added a sortlist callback allowing plugins to augment entrylist sorting
    behavior.


Changes between 1.4.2 and 1.4.3
===============================

Pertinent to users:
-------------------

1. Adjusted the code that parses blog.ini values so that it can take
   values like::

      foo = 'a'                 # string
      foo = "a"                 # string
      foo = 23                  # integer
      foo = [ "a", 23, "b" ]    # list of strings and integers

   as well as::

      foo = a                   # string

   Note: if you want the string "23", then you MUST enclose it in
   quotes, otherwise it will be parsed as an integer.

   blog.ini is used when you set up PyBlosxom using Paste.

2. Fixed PyBlosxomWSGIApp so that it's WSGI compliant as an
   application.  Thanks Michael!

3. Template variables can be parenthesized.  Examples::

      $foo                      - variable is "foo"
      $(foo)                    - variable is "foo"
      $(url)index.atom          - variable is "url"

   This reduces ambiguity which was causing problems with recognition
   of variables.


Pertinent to developers:
------------------------

1. Fixed tools.importname---it now logs errors to the logger.

2. Fixed PyBlosxomWSGIApp so that it's WSGI compliant as an
   application.  Thanks Michael!

3. Added more unit tests and corrected more behavior.  Details on
   running unit tests are in the REDAME.


Changes between 1.4.1 and 1.4.2
===============================

Pertinent to users:
-------------------

1. Fixed another bug with the WSGI application creation code.  (Thanks
   Christine!)

2. Added instructions for installing PyBlosxom with mod_wsgi to
   ``install_wsgi.txt``.  This includes a basic wsgi script for
   PyBlosxom.  (Thanks Christine!)

3. Fixed up the Python Paste installation document.  (Thanks Liz!)

4. Fixed the ``month2num`` code in tools so that PyBlosxom runs on
   Windows (Windows doesn't have ``nl_langinfo`` in the ``locale``
   module).  (Thanks Liz!)


Changes between 1.4 and 1.4.1
=============================

Pertinent to users:
-------------------

1. Fixed a problem where running PyBlosxom under Paste won't pick up
   the ``config.py`` file.  Be sure to add a ``configpydir`` property
   to your ``blog.ini`` file which points to the directory your
   ``config.py`` file is in.

2. Fixed a problem where running PyBlosxom in Python 2.5 won't pick up
   the ``config.py`` file.

3. Merged Ryan's optimization to Walk (removes an os.listdir call).

4. Updated documentation.


Changes between 1.3.2 and 1.4
=============================

Pertinent to users:
-------------------

1. Added a pyblcmd command line program for PyBlosxom command line
   things.  This now handles static rendering, rendering a single url
   to stdout, testing your blog setup, ...

2. The Atom story template now has a $default_flavour bit in the link.
   Bug 1667937.  (Thanks Michael!)

3. PyBlosxom is now locale aware in respects to dates, months, days of
   the week and such.  Users should set the locale config property to
   a valid locale if they don't want English.

4. Added a ``blog_icbm`` config variable for use in the ICBM meta tag.
   See config_variables.txt for more information.

5. Changed the ``num_entries`` property in config.py from 40 to a much
   more conservative 5.  Also changed the default value from 0 to 5 if
   you happened not to set ``num_entries`` at all.
   http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=373658 (Thanks
   Jon!)

6. Changed the self link in the atom feed to be of type
   application/atom+xml.
   http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=403008 (Thanks
   Brian!)

7. Added DOCUMENT_ROOT to the python path per Martin's suggestion.
   http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=367127 (Thanks
   Martin!)

8. Translated all documentation from Docbook to reST.  reST
   documentation is easier to read in "source-form" and a lot easier
   to convert to HTML and other formats using the Python docutils
   tools.  (Thanks John!)

9. Added support for Paste and brought the WSGI support into the
   codebase.  (Thanks Steven and Yury!)

Pertinent to developers:
------------------------

1. Lots of code clean-up, documentation, test-code, and some
refactoring.

2. cb_filestat will only do an os.stat if no plugin handles the
   filestat.  Previously, cb_filestat did an os.stat and ran through
   all the plugins allowing them to over-ride it.

3. Added some testing framework pieces.  This requires nose.  To run
   the tests, do::

      nosetests --verbose --include unit
      nosetests --verbose --include functional


Changes between 1.3.1 and 1.3.2
===============================

Pertinent to users:
-------------------

1. Fixes a security issue where the path_info can come in with
   multiple / at the beginning.  Whether this happens or not depends
   on the web-server you're using and possibly other things.  Some
   people have the issue and some don't.  If you're in doubt, upgrade.
   Thanks FX!


Changes between 1.3 and 1.3.1
=============================

Pertinent to users:
-------------------

1. The ``num_entries`` property now affects the home page and category
   index pages.  It no longer affects archive index pages.

2. Fixed the RSS 0.9.1 feed templates.  It has the correct link url
   and shows the entry bodies.  Thanks Norbert!

3. The version string is correct.

4. Added support for ``$body_escaped`` .

5. Fixed the blog encoding on the RSS 2.0 feed so that it uses the
   value provided in the config.py ``$blog_encoding`` variable.

6. Fixed the Atom 1.0 story flavour to use ``$body_escaped`` instead
   of ``<![CDATA[ $body ]]>``

7. Fixed a problem with static rendering where we'd render
   ``/index.html`` and ``//index.html`` if the user had entries in
   their root category.


Pertinent to developers:
------------------------

1. If you have plugins that use the logger functions in PyBlosxom 1.2,
   you need to update those plugins to use the new logger functions in
   PyBlosxom 1.3.  Read through the API for details.

2. Moved documentation in ReadMeForPlugins.py over to the manual.


Changes between 1.2 and 1.3
===========================

Pertinent to users:
-------------------

1. We added a ``blog_rights`` property.  This holds a textual
   description of the rights you give to others who read your blog.
   Leaving this blank or not filling it in will affect the RSS 2.0 and
   Atom 1.0 feeds.

2. If you set ``flavourdir``in your config.py file, you have to put
   your flavour files in that directory tree.  If you don't set
   ``flavourdir``, then PyBlosxom expects to find your flavour files
   in your ``datadir``.

   The flavour overhaul is backwards compatible with previous
   PyBlosxom versions.  So if you want to upgrade your blog, but don't
   want to move your flavour files to a new directory, DON'T set your
   ``flavourdir`` property.

3. Moved the content that was in README to CHANGELOG.

4. You can now organize the directory hierarchy of your blog by date.
   For example, you could create a category for each year and put
   posts for that year in that year (2003, 2004, 2005, ...).
   Previously URLs requesting "2003", "2004", ... would get parsed as
   dates and would pull blog entries by mtime and not by category.

5. Logging works now.  The following configuration properties are
   useful for determining whether events in PyBlosxom are logged and
   what will get logged:

   * "log_file" - the file that PyBlosxom events will be logged
     to---the web-server MUST be able to write to this file.

   * "log_level" - the level of events to write to the log.  options
     are "critical", "error", "warning", "info", and "debug"

   * "log_filter" - the list of channels that should have messages
     logged.  if you set the log_filter and omit "root", then
     app-level messages are not logged.

   It's likely you'll want to set log_file and log_level and that's
   it.  Omit log_file and logging will fall back to stderr which
   usually gets logged to your web-server's error log.


Pertinent to developers and plugin developers:
----------------------------------------------

1. Plugins that used logging in 1.2 need to be changed to use the new
   logging utilities in 1.3.  Until that happens, they won't work.


Changes between 1.1 and 1.2
===========================

Pertinent to users:
-------------------

1. We added a ``blog_email`` item to config.py and changed
   ``blog_author`` to just the author's name.  Examples:

      py["blog_email"] = "joe@blah.com"
      py["blog_author"] = "Joe Man"

2. We no longer adjust blog_title from what you set in ``config.py``.
   Now we have a ``blog_title_with_path`` variable which is in the
   data dict which is the ``blog_title`` with the path information.
   People who want the title of their blog to be the title and not
   include the path should use ``$blog_title``.  Folks who want the
   old behavior where the path was appended to the title should use
   ``$blog_title_with_path`` .

3. We now support WSGI, mod_python, and Twisted in addition to CGI.

4. Upped our Python requirement to Python 2.2.  If you have an earlier
   version than that, you won't be able to use PyBlosxom 1.2.

5. Changed ``defaultFlavour`` to ``default_flavour``.  This property
   allows you to specify the flavour to use by default if the URI
   doesn't specify one.  It default to ``html``.

6. We moved the main PyBlosxom site to
   http://pyblosxom.sourceforge.net/ .  There's a "powered by
   pyblosxom" image at
   http://pyblosxom.sourceforge.net/images/pb_pyblosxom.gif

   You should adjust your templates accordingly.


Pertinent to developers and plugin developers:
----------------------------------------------

1. We now have a Request and a Response object.  See API documentation
   for more details.

2. Don't use ``os.environ`` directly---use the http dict.  For
   example, this is bad::

      path_info = os.environ["HTTP_PATHINFO"]

   This is what you should be doing::

      http = request.getHttp()
      path_info = http["HTTP_PATHINFO"]

   If you use os.environ directly, it's likely your plugin won't work
   with non-CGI installations of PyBlosxom.

3. We added __iter__, read, readline, readlines, seek, and tell to the
   Request object.  All of them access the input stream.  You should
   not use sys.stdin directly.

   Usage::

      data = request.read()
      data_part = request.read(1024)
      one_line = request.readline()
      lines = request.readlines()

4. The output stream should be accessed through the PyBlosxom Response
   object.  The following methods are implemented in the Response
   object: __iter__, close, flush, read, readline, readlines, seek,
   tell, write, writelines, setStatus, and addHeader.  You should not
   use sys.stdout directly. See the API for more details.

   Usage::

      response = request.getResponse()
      response.addHeader('Status', '200 Ok')
      response.addHeader('Content-type', 'text/html')
      response.write("Hello World")
      response.writelines(["list", "of", "data"])

5. Instead of doing::

      form = request.getHttp()["form"]

   you can now do::

      form = request.getForm()

6. Plugins should not be importing the config module and looking at
   the ``py`` dict directly.  You should instead use the Request
   getConfiguration() method to get the config py dict.


Changes between 1.0 and 1.1
===========================

Pertinent to users:
-------------------

1. We no longer include contributed plugins and flavours.  To find
   plugins and flavours, go to the PyBlosxom registry located at
   http://pyblosxom.sourceforge.net/ .

2. We changed how ``num_entries`` is handled internally.  If
   ``num_entries`` is set to 0, the blosxom default file handler will
   display all the entries.  If ``num_entries`` is set to a positive
   number, then the blosxom default file handler will display at most
   that many entries.


Pertinent to developers and plugin developers:
----------------------------------------------

1. Plugins that implement cb_filelist are now in charge of adjusting
   the number of entries to be displayed based on the ``num_entries``
   configuration variable.  This is no longer done in the renderer.

2. We added HTTP_COOKIE to the list of things that get added to the
   http dict in the Request object.


Changes between 0.9 and 1.0
===========================

Pertinent to users:
-------------------

1. We ditched ``blosxom_custom_flavours``---you can remove it from your
   ``config.py`` file.

2. We added static rendering---see the howto in the PyBlosxom manual.

3. Rewrote comments to use the new handler system.  You should replace
   the comments, pingbacks, trackbacks, and other comments-oriented
   plugins with the new versions from ``contrib/plugins/comments/``.

4. pingbacks plugin is now ``xmlrpc_pingbacks.py`` .

5. Adjusted the default templates for HTML and RSS.  Removed all other
   default templates.  Look at the flavour_examples directory for
   flavour examples.

6. Added an ``ignore_properties`` property to ``config.py`` which
   allows you to specify which directories in your datadir should be
   ignored.  For example::

      py["ignore_directories"] = ["CVS", ".svn"]

7. Added a template variable ``pyblosxom_version`` which points to
   ``pyblosxom/Pyblosxom/pyblosxom.VERSION_DATE`` .

8. Fixed some code in pyarchives so it worked with Python 2.1.  Thanks
   to Wilhelm.

9. Fixed template retrieving code so that you can specify templates to
   use for a given category or parent categories.  Thanks to Nathan
   for fixing this.

10. We added a ``logdir`` property to config.  PyBlosxom (and plugins)
    will create logs in this directory so the directory has to have
    write access for whatever user the webserver uses to run the
    script.


Pertinent to developers and plugin developers:
----------------------------------------------

1. Rewrote the startup for PyBlosxom request handling---we ditched the
   common_start function and picked up a common initialize function.

2. Unhardcoded where contrib and web files go when doing a multi-user
   installation using ``python setup.py install``.

3. Adjusted the comments plugin so that if a given entry has a
   ``nocomments`` property, then it won't get comments.

4. Moved the Request object into ``pyblosxom/Pyblosxom/pyblosxom.py``.

5. Fixed variable parsing so that if the variable value is a function
   that takes arguments, we pass the request in as the first argument.

6. Added VERSION, VERSION_DATE, and VERSION_SPLIT.  This allows you to
   verify that your plugin works with the version of PyBlosxom the
   user is using.
