**CHANGES** for PLIB3.IO 0.10.5

:Author:        Peter A. Donis
:Release Date:  20 Oct 2021

Version 0.10.5
--------------

- Require ``plib3.stdlib`` version less than 2.0 (this library
  will not be updated to compatibility with that version).

Version 0.10.4
--------------

- The server in the ``clientserver3`` example program now
  correctly handles the custom ``InterruptSleep`` exception.

Version 0.10.3
--------------

- The ``clientserver3`` example program now exchanges
  actual data between the client and the server, to show
  how the data exchange is interrupted by a termination
  signal.

Version 0.10.2
--------------

- Fixed the ``clientserver3`` example program to properly
  handle Python 3's automatic restart of system calls on
  EINTR.

Version 0.10.1
--------------

- Fixed import of ``multiprocessing`` module used on
  Windows for the ``ProcessWrapper`` class.

- Fixed bug in the ``test_fork`` test module.

Version 0.10
------------

- Renamed ``async`` sub-package to ``nonblocking`` to avoid
  keyword conflict in Python 3.6+.

- Child processes forked using ``ProcessWrapper`` now reset
  handling of defined termination signal to its default.

Version 0.9.8
-------------

- Fixed handling of long description when running the ``sdist``
  command.

- Switched references in README to gitlab.

- Updated to ``setuputils3`` 1.0.4.

Version 0.9.7
-------------

- Added ``comm`` sub-package, including ``sigtools`` module,
  transferred from ``plib3.stdlib``. Fixed references and
  test suite to correspond. Added ``server`` example programs
  to demonstrate added code.

Version 0.9.6
-------------

- Adjusted ``SigChldServerMixin`` to use the new ``SigChldMixin``
  API in ``plib.stdlib`` 0.9.6.

- Removed the ``.py`` extension from post-install script that
  sets up example programs.

Version 0.9.5
-------------

No functional changes; update release file generation.

Version 0.9.4
-------------

- The ``__module__`` class attribute is now set correctly for
  classes that are auto-constructed by ``IOModuleProxy``.

Version 0.9.3
-------------

**Ported PLIB.IO to Python 3 as PLIB3.IO.**

- Enhanced ``IOModuleProxy`` so the ``async`` and ``blocking``
  sub-packages now show allowed read-write enhanced classes
  when the ``dir()`` function is called.

- Added ``handle_error`` method to blocking ``SocketServer``.

Version 0.9.2
-------------

- Switched to all new-style string formatting.

- Minor fixups to reduce changes needed for Python 3 version.

Version 0.9.1
-------------

- The async ``loop`` function now matches the signature of
  the standard Python ``asyncore.loop`` function. The async
  module now monkey-patches asyncore to use its loop function.

- Switched to the new ``fifo`` API from ``plib.stdlib`` 0.9.1.

Version 0.9
-----------

Beta release.

- Reorganized code as needed to work as separate package.

**Separated PLIB.IO into its own distribution.**

Version 0.8.9
-------------

- Added optional functions to be called on socket connect
  and socket close to the ``chat_replies`` class in
  ``plib.io.classes``.

- Changed usages of deprecated ``new.instancemethod`` to
  use ``types.MethodType`` instead.

- Added ``filefinder`` function to ``plib.stdlib.ostools``,
  finds directories in a subtree that contain a file whose
  name is in a specified list of names.

- Added some more tests to the PLIB3 test suite.

- Fixed bug in handling of doctests in text files in PLIB3
  test suite; the test-running code was not reliably finding
  them, now it does.

- Reorganized test suite so that each PLIB3 sub-package has
  its own corresponding ``plib.test`` sub-package.

- The ``plib.test`` package is now runnable directly, so the
  test suite can be run using ``python -m plib.test``. The
  ``plib.test.runtests`` module is now ``plib.test.support``,
  and provides the boilerplate test-running routine, which
  can now be used generally.

- Fixed up code formatting per PEP 8 guidelines.

Version 0.8.8
-------------

- Added separate GUI toolkit for PySide, since its API
  is no longer sufficiently close to the PyQt 4 API.

- Changed default target signal handler method name for
  check boxes to ``<name>_toggled`` (the old default was
  ``<name>_checked``).

- Changed the check box signal handler API to include the
  current checked state in the handler arguments.

- Changed the signal handler API for all sequence-type
  widgets (except list views) to include the sequence index
  instead of the current item in the handler arguments.
  Getting the item from the index is faster than vice
  versa, except for list views since they are really tree
  widgets under the hood and all the toolkit event handlers
  give the item directly.

- Changed code in ``plib.gui.specs`` and associated
  machinery elsewhere in ``plib.gui`` so that the widget
  modules are not imported when the specs module is
  imported, but only when specific widgets are actually
  instantiated.

- Expanded list of attributes that a ``plib.gui`` main
  window can read from its client widget, so that they
  can be declared in the client class instead of having
  to derive a subclass of ``PMainWindow``.

- List view items in ``plib.gui`` now support equality
  testing so that the default sequence algorithms will
  work with them.

- Added sorted combo box widget to ``plib.gui``. The
  ``pyidserver-gui`` example program now uses this widget.

- Added sorted list view and list box widgets to ``plib.gui``.

- Moved message box and file dialog functionality into
  the base ``plib.gui.app`` module so they are always
  available even if you're not using a main window.

- Implemented "lazy" construction of application dialogs:
  message box, file dialog, and preferences dialog. They
  are now not actually constructed unless/until they are
  used.

- There is now a standardized way to add new actions in
  ``plib.gui`` and have them appear in the appropriate
  menus and toolbars. The ``scrips-edit`` example program
  now uses the standardized method. This removes the need
  to override captions or icons for standard actions, which
  had the undesirable side effect of doing so everywhere,
  including standard dialogs where that is not desired.

- The tab changed signal for the ``plib.gui`` tab widget
  now sends the new tab index to its handler instead of the
  newly selected widget.

- Standardized GUI signal handler parameters.

- Standardized ordering of base classes for GUI widgets.

- Added GUI signal tester example program to demonstrate
  handling of all defined GUI signals.

- Removed ``__init__`` constructor from ``SortMixin``
  class; changed doctest for ``SortMixin`` to implement a
  basic constructor as an example.

- Changed API of ``split_n`` function in ``plib.stdlib.iters``
  to always return a 2-tuple of lists, even if one is empty.

- The ``plib.test`` sub-package is now importable as a
  package; the PLIB3 test suite can now be run using
  ``python -m plib.test.runtests``.

- Codebase cleanup: removed unused imports.

Version 0.8.7
-------------

- Sequence-type widgets in ``plib.gui`` no longer include
  ``SortMixin`` by default; if sorted widgets are desired
  by a specific application, ``SortMixin`` can be used by
  that application.

- Reimplemented ``SortMixin`` class from ``plib.stdlib.coll``
  to use the ``bisect`` module and to overlay the standard
  sequence methods of the base sequence class, instead of
  adding an ``insert_sorted`` method.

- Fixed GUI example programs to no longer use the removed
  ``plib.stdlib.version`` module.

Version 0.8.6
-------------

- Moved the ``SelfPipe``, ``SigChldMixin``, and ``SigIntMixin``
  classes from ``plib.io.mixins`` to ``plib.stdlib.classes``.

- Changed API of ``SigIntMixin`` class to define a method,
  ``terminate_process``, that is called when a termination
  signal is received. The specific use of a ``terminate_flag``
  variable is now moved to ``SigIntServerMixin`` since it is
  specific to PLIB3 servers, and the API of ``SigIntMixin`` is
  intended to be general.

- Added ``first_subclass`` and ``first_instance`` functions to
  ``plib.stdlib.classtools``, to return the first attribute on
  an object that is a subclass or instance of a given class.

- Removed ``partition`` function from ``plib.stdlib.iters``;
  most of its functionality is duplicated by the ``group_into``
  function in the same module; added ``split_n`` function to
  ``plib.stdlib.iters`` to cover the remaining functionality
  (the case of splitting just the first n items from an
  iterable). Fixed doctests to correspond.

- The ``sendmail`` function from ``plib.stdlib.mail`` now
  accepts a list of "To" address strings as well as a single
  "To" address string.

- Added ``data_changed`` function to ``plib.stdlib.ostools``,
  checks if data is changed from file data at a given path.
  Data comparison is binary (sequence of bytes).

- Added ``dirfinder`` function to ``plib.stdlib.ostools``,
  finds all directories in tree starting at given root (by
  default, the current directory) that have a subdirectory with
  a name in a given list of names.

- Added ``tmp_chdir`` context manager to ``plib.stdlib.ostools``,
  temporarily changes the current directory.

- Added ``process_call`` function to ``plib.stdlib.proc``, to
  return the process exit code as well as its output.

- Updated the ``process_output`` function in ``plib.stdlib.proc``
  to use ``subprocess.check_output``.

- Added ``tmp_sys_path`` context manager to ``plib.stdlib.systools``,
  temporarily changes sys.path.

- The ``ModuleProxy`` class now uses a ``try/except`` block to
  test whether proxied attributes are callable in the "lazy
  loading" code. This is more robust than testing for the
  ``__call__`` attribute.

- Removed ``plib.stdlib.version`` module. The convention now
  seems to be to use strings as the fundamental format for
  version values, rather than tuples, so this module is no longer
  useful.

Version 0.8.5
-------------

- Bug fix in ``plib.gui`` when using the ``plib.stdlib.ini``
  sub-package; an import was not updated to the new package
  layout, now updated.

Version 0.8.4
-------------

- Factored out more API methods in ``plib.stdlib.options``
  for convenience when doing incremental or customized
  parsing.

Version 0.8.3
-------------

- Added ``local_tzname`` function to ``tztools``
  module in ``plib.stdlib``, returns name of the
  local system timezone.

- Fixed two doctests that did not work on 64-bit
  builds; all tests now pass on 64-bit.

Version 0.8.2
-------------

- Fixed metaclass conflicts in ``plib.gui`` widgets
  in the GTK and KDE4 toolkits that use the ``plib``
  collection classes.

- The QT4 toolkit in ``plib.gui`` now supports PySide
  as well as the "legacy" PyQt4 bindings. Note that the
  KDE4 toolkit does *not* work with PySide; it requires
  PyQt4. (This is a limitation of PyKDE, not PLIB3.)

- Fixed bug in ``plib.gui`` Wx combo box with abstract
  method not being implemented.

- Moved the ``BaseCommunicator``, ``BaseData``, and
  ``BaseIO`` classes in ``plib.io`` into their own
  sub-package, ``plib.io.base``, to clean up the
  ``plib.io`` namespace.

- Moved the ``chat_replies`` class out of ``plib.io``
  into ``plib.io.classes``, so the base ``plib.io``
  namespace contains no public API objects, only
  sub-packages and the ``utils`` module, which is
  intended for internal use.

- Added ``fdtools`` module to ``plib.stdlib``, with
  useful utilities for working with file descriptors.

- Added ``sigtools`` module to ``plib.stdlib`` with
  a low-level implementation of the self-pipe trick
  for signal handling. The I/O classes in ``plib.io``
  now wrap this API.

- Added ``tztools`` module to ``plib.stdlib`` with
  useful ``tzinfo`` subclasses based on those given in
  the Python docs for the ``datetime`` module.

- PLIB3's ``setup.py`` script now uses the ``setuputils``
  helper module instead of the old ``SetupHelper``
  module.

- Renamed the ``plib.setuputils`` helper module for
  PLIB3's post-install scripts to ``plib.postinstall``.

Version 0.8.1
-------------

- Added ``localize`` module to ``plib.stdlib``, with
  useful functions for getting locale-specific
  information.

- Added ``remove_delimiters`` argument to ``split_string``
  function in ``plib.stdlib.strings``.

Version 0.8
-----------

- Removed support for "legacy" Python versions (anything
  before 2.7), and updated code to support the latest
  Python 2 idioms and features.

- Removed the ``plib.classes`` sub-package; all of the
  classes in it are moved to other sub-packages as noted
  below.

- Moved the ``plib.extensions`` sub-package into the
  ``plib.stdlib`` namespace, as ``plib.stlib.extensions``.

- Moved the ``NotifierClient`` class from ``plib.classes``
  into ``plib.gui``, since it is only useful for GUI
  programs.

- Some of the ``plib.gui`` widgets in the Qt/KDE toolkits
  are affected by the change to the collection classes in
  ``plib.stdlib.coll`` (see below). These widgets have been
  updated to use a custom metaclass to avoid a metaclass
  conflict between the collection ABCs and the Qt widget
  classes.

- Moved ``plib.ini`` into the ``plib.stdlib`` namespace as
  a sub-package, ``plib.stdlib.ini``. Also factored out the
  classes in this sub-package into modules and added
  ``ModuleProxy`` functionality for the sub-package.

- Moved ``plib.stdlib.io`` up into its own sub-package,
  ``plib.io``. Moved related mixin classes from ``plib.stdlib``
  into sub-package ``plib.io.mixins``; also moved the
  ``EchoRequestMixin`` class from ``plib.classes`` into
  ``plib.io.mixins``.

- Moved the ``chatgen`` module from ``plib.utils`` into
  ``plib.io``.

- Added ``plib.io.classes`` sub-package, and moved all the
  I/O related classes from ``plib.classes`` into it (except
  for `` NotifierClient``, as above).

- Added ``plib.stdlib.builtins`` module; importing this
  module now does the same thing as the ``upgrade_builtins``
  function used to do, but no explicit function call is
  needed. The extra built-in functions also appear in this
  module's namespace, if more explicit importing is desired.

- Added ``plib.stdlib.classes`` sub-package, and moved the
  non-I/O related classes from ``plib.classes`` into it.

- Added ``plib.stdlib.classtools`` module and moved the
  ``Singleton`` class into it. Also moved two functions
  from ``plib.utils``, ``recursedict`` and ``recurselist``,
  into this module.

- Made ``plib.stdlib.coll`` into a sub-package, and moved
  all collection classes into that namespace, including
  the abstract collection classes, ``SortMixin``, and the
  ``AttrDict`` and ``AttrList`` utility classes. Also, the
  sequence and slice-related utilities from ``plib.stdlib``
  are now in this sub-package.

- The PLIB3 collection abstract classes in ``plib.stdlib.coll``
  are now subclassed from the standard Python collection
  abstract base classes in the ``collections`` module, and
  overlay some additional functionality onto those ABCs.

- Added ``plib.stdlib.comm`` sub-package, and moved the child
  thread and process management and communication modules
  from ``plib.utils`` into it.

- Made ``plib.stdlib.decotools`` into a sub-package, and
  moved all decorator classes into that namespace.

- Added ``convert`` decorator to ``plib.stdlib.decotools``,
  to facilitate enforcing a common return type for functions
  and methods.

- Added ``prefixed_items`` and ``suffixed_items`` to
  ``plib.stdlib.iters``, to facilitate filtering of iterables
  of strings by a string prefix or suffix.

- Streamlined implementation of ``unzip`` function in
  ``plib.stdlib.iters``.

- Added support for incremental option parsing to
  ``plib.stdlib.options``. Also added canonicalization of
  option specs, improved canonicalization of argument
  specs, and factored out API functions for each step
  of the parsing process.

- Added ``plib.stdlib.ostools`` module and moved the
  ``locate`` function from ``plib.utils`` into it.

- Added ``subdirs`` function to ``plib.stdlib.ostools``, a
  simple way of getting all subdirectories of a path.

- Added ``plib.stdlib.strings`` module and moved string
  utilities from ``plib.stdlib`` into it.

- Updated the API of the ``split_string`` function (now in
  ``plib.stdlib.strings``) to remove the need to supply a
  newline character unless it is different from the default
  (the ``universal_newline`` constant).

- Added ``plib.stdlib.systools`` module and moved the
  path variables from ``plib.stdlib`` into it.

- With all of the other moves above, the ``plib.stdlib``
  base sub-package itself now contains nothing; this ensures
  that importing any given module within it does not bring
  in objects from any other module.

- Moved the ``ModuleProxy`` class into ``plib.stdlib.util``,
  a separate sub-package; it is the only object appearing in
  that sub-package, so importing it will not bring in any
  other objects (since the ``plib.stdlib`` package itself
  now imports nothing, as above).

- The ``ModuleProxy`` utility now automatically excludes
  private names (ones that start with an underscore ``_``).
  This behavior can be changed by subclassing and overriding
  the ``_exclude`` method.

- Moved the ``version`` module from ``plib.utils`` into
  ``plib.stdlib``.

- Removed the ``plib.utils`` sub-package; its modules are now
  in other sub-packages as noted above.

Version 0.7.3
-------------

- Small optimizations to various abstract container classes
  in ``plib.stdlib``.

- Added ``cmdline`` module to ``plib.stdlib``, with two
  functions: ``setup_history``, for setting up command line
  history handling for interactive shells (I use this in my
  ``.pystartup`` file); and ``run_shell``, which allows you
  to run an interactive shell with a particular environment
  already set up (this is useful for debugging scripts).

- Added ``typed_namedtuple`` to ``plib.stdlib.coll``,
  an enhanced named tuple that coerces each field to
  a given type.

- Added ``merge_dict`` function to ``plib.stdlib.coll``;
  this was previously an internal function in the
  ``plib.stdlib.decotools`` module.

- Added more doctests for the ``cached_function``
  decorator in ``plib.stdlib.decotools``.

- Added a ``wraps_class`` decorator, which works like the
  standard ``wraps`` decorator, but knows not to try to
  overwrite the class's docstring when wrapping.

- Added a ``cached_method`` decorator, which is a version
  of ``cached_function`` specialized to handle some issues
  particular to methods, in ``plib.stdlib.decotools``.

- Fixed ``cached_class`` decorator to ensure it
  will work when a cached class is subclassed.

- Renamed the ``decorator_with_f`` meta-decorator in
  ``plib.stdlib.decotools`` to ``decorator_with_args``.
  Also simplified usage.

- Added ``cachelimit`` keyword argument to the
  generator decorators in ``plib.stdlib.decotools.``

- The ``partition`` and ``unzip`` functions in
  ``plib.stdlib.iters`` now work with any iterable.

- Added ``group_into`` function to ``plib.stdlib.iters``,
  generates tuples of every ``n`` elements from an
  iterable. Useful for saving typing parentheses when
  declaring lists of tuples. It is also used to
  streamline the implementation of the ``partition``
  function.

- Canonicalized some doctests in ``plib.stdlib.iters``
  whose results were dependent on dict key ordering;
  the tests now sort the ``iteritems`` output to
  guarantee stable results.

- Changed some doctests in ``plib.stdlib.iters`` to use\
  ``list(xrange())`` instead of ``range()``, for
  consistency with other tests and to make the desired
  semantics explicit.

Version 0.7.2
-------------

- Added support in ``plib.gui`` for detecting when
  the active screen is a virtual desktop spread
  across multiple monitors, and adjusting the
  behavior of the top/main window sizing options
  appropriately so that the window only appears
  centered or sized to the screen on one monitor
  (currently the "primary" monitor is the only one
  supported, this may be expanded in future).

- Added support for ``PTopWindow`` and ``PMainWindow``
  getting captions from child panels (so the panel
  code doesn't have to set the caption by hand).

- Added ``extend_flat`` and ``extend_list`` methods
  to ``PListView`` as well as ``PListBox`` classes
  in ``plib.gui``.

- Added ``width`` parameter to functions for labels
  in ``plib.gui.specs``.

- Streamlined default implementation of some of the
  methods of the abstract container classes in
  ``plib.stdlib``.

- Moved the ``cached_property`` decorator to
  ``plib.stdlib.decotools``.

- Added ``cached_function`` decorator in
  ``plib.stdlib.decotools``, to cache function results
  by arguments.

- Added ``cached_class`` decorator in
  ``plib.stdlib.decotools``, to cache class instances
  by constructor arguments.

- Added ``delay`` decorator in ``plib.stdlib.decotools``,
   to defer actually creating a decorated function
  until the function is called.

- Added ``memoize_generator`` decorator in
  ``plib.stdlib.decotools``, to wrap a generator so
  that each term is only computed once, even if the
  generator function is realized multiple times.

- Added ``indexable_generator`` decorator in
  ``plib.stdlib.decotools``, to make a generaor
  indexable like a sequence; this decorator extends
  ``memoize_generator`` so it memoizes the generator
  it wraps as well (it needs to anyway to support
  accessing the element at a given index multiple
  times without realizing the generator each time).

- Added handling of a ``None`` ``count`` parameter
  in the ``normalize_slice`` function in ``plib.stdlib``,
  so that ``AbstractContainerMixin`` can provide slice
  handling to sequences that do not "know" their length
  (such as an indexable generator per the above, if
  the generator has not been exhausted--once it is
  exhausted the length is known and the generator acts
  accordingly, see the doctests in ``decotools``).

- Added alternate implementation of the ``bin`` and
  ``next`` builtins for older Python versions,
  installed by ``plib.stdlib.upgrade_builtins``.

- Simplified implementation of the ``iterfile`` function
  in ``plib.stdlib``. (This function is also moved to
  a new module, see next item.)

- Moved the ``iterfile`` function from ``plib.stdlib``
  into a new module, ``plib.stdlib.iters``; this module
  also adds a number of useful functions for working
  with iterables (including backported implementations
  of some itertools functions for older Python versions).
  It also imports all the contents of ``itertools``, so
  it can be used as a substitute for that module, similar
  to the ``coll`` and ``func`` modules in ``plib.stdlib``,
  so you can write the same code to work in all Python 2.x
  versions.

- Moved the ``gcd`` and ``lcm`` functions from
  ``plib.stdlib`` into a new module, ``plib.stdlib.mathlib.``

- Added handling of required and optional arguments
  to the ``plib.stdlib.options`` module for Python
  versions earlier than 2.7 (i.e., when the ``argparse``
  standard library module is not available).

- Added the ``timer`` module to ``plib.stdlib``,
  to provide functions for timing code, with an
  alternate API to the standard library's ``timeit``
  module that is easier to use when timing functions
  that you already have as objects, instead of source
  code strings.

- Added the ``net`` module to ``plib.utils`` to provide
  useful network-related functions; currently the only
  function implemented is ``found_network``, which
  takes a string giving an IP address prefix and
  determines if the machine is on a network with that
  prefix.

- Added the ``proc`` module to ``plib.utils`` to provide
  useful process-related functions; currently the only
  function implemented is ``process_output``, which calls
  an external program and returns its output as a string.

- Fixed bug in ``pyidserver.py`` example program with
  error message output.

Version 0.7.1
-------------

- Added a ``BaseWindow`` class to ``plib.gui`` so
  that "top" windows that are not application top
  windows can inherit from it without adding all
  the extra baggage for application top windows.
  The dialog classes in ``plib.gui``, for example
  ``PPrefsDialog``, now inherit from this class
  instead of ``PTopWindow`` (as does ``PTopWindow``
  itself, of course).

- Added a ``choose_directory`` method to ``plib.gui``
  top and main windows, which brings up a directory
  selection dialog box and returns the directory
  chosen by the user (or an empty value if the user
  cancels without selecting one).

- Added the ability in ``plib.gui`` for application
  top windows and main windows to "remember" their
  size and/or position when last closed, and re-open
  at the same size and/or position. This is done by
  setting the size and/or position specs in the
  ``placement`` class field to ``SIZE_SETTINGS``
  and/or ``MOVE_SETTINGS``. If you also specify a
  ``prefsdata`` class field, the preferences dialog
  that the window constructs will have an additional
  group of "Window Placement" controls that show the
  stored size and position (and you can also change
  them through the dialog if desired). (If the class
  field is not specified, the settings will still be
  stored, but they won't be accessible through a
  dialog; they'll just be saved on program exit and
  reloaded on program startup.)

- Top windows and main windows in ``plib.gui`` now
  have a ``preferences`` method which shows their
  preferences dialog if one is defined.

- Top windows and main windows in ``plib.gui`` now
  check their client widgets for an ``acceptclose``
  method, and call it if present to determine whether
  they can close.

- The ``PDialogBase`` class in ``plib.gui`` now
  always populates its controls from data before
  showing (previously it only did this when shown
  for the first time, but this behavior led to
  problems with the preferences dialog).

- Added alternate API to ``plib.gui.specs`` module
  that allows more readable declarations of GUI
  specs; the ``pyidserver-gui.py`` example program
  illustrates the new API.

- Added an option to have GUI widgets automatically
  look for event handler methods with standard names,
  but do nothing if the methods are not found (so
  that event handler declarations don't have to be
  made explicitly in the GUI specs, you just define
  the methods you need on the panel or top window
  class and everything works). This is easiest to
  use with the new specs API, which uses this
  mechanism by default.

- Allowed alternate ordering of ``prefsdata`` class
  field for GUI top windows to improve readability.
  The ``scrips-edit.py`` example program shows the
  new ordering (the definitions of the individual
  prefs items and labels can now be last in the
  3-tuple, so they can appear on continued lines
  as shown in that example).

- Also added the ability to combine the specs for
  the prefs dialog and the actual INI file in the
  ``prefsdata`` class field.

- Fixed bug in the ``PListView`` and ``PListBox``
  classes where the ``clear`` method did not work
  properly with some GUI toolkits; that method now
  always points to the ``plib.stdlib`` implementation
  of ``clear`` from the ``abstractlist`` class, even
  if the GUI widget class from the toolkit in use
  has an implementation that (supposedly) does the
  same thing (remove all items from the list). (Note
  that this method is pure Python, meaning that it
  may be slower than a "native" method for large
  lists; but since this is for GUI widgets it should
  not have to deal with lists that are too long.)

- Added ``SIGNAL_CELLSELECTED`` to the ``plib.gui``
  table widget, to signal when a table cell is
  selected. The ``scrips-edit.py`` example program
  now uses this signal (which fixes a previous bug
  in its behavior where it did not properly enable
  and disable the Submit action).

- The ``PIniFile`` constructor now takes an ``options``
  parameter, so you don't have to subclass if all you
  want to do is define an option list (which should
  cover most use cases).

- Fixed bug in ``plib.ini`` with writing integer
  and boolean values on Windows.

- Added ``plib.stdlib.mail`` module, to contain
  useful email-related utility functions. The
  ``scrips.py`` example program now uses the
  ``sendmail`` function from this module.

- Added two functions and one variable to ``plib.stdlib``
  for dealing with strings and newlines: the functions
  ``fix_newlines`` and ``split_string``, and the
  constant ``universal_newline``. These are useful
  when files have to be written with a different newline
  convention than the one used to read them. See the
  docstring for the ``plib.stdlib`` sub-package for
  details.

- Updated the ``plib.stdlib.options`` module to use
  the ``argparse`` standard library module if it is
  available (Python 2.7 and later), instead of the
  deprecated ``optparse`` module. The ``argparse``
  module adds some additional functionality for
  checking arguments, which can be accessed by making
  the ``arglist`` parameter to the ``parse_options``
  function a sequence of 2-tuples to include keyword
  arguments, similar to what is done with options.

- The ``args`` object returned by the ``parse_options``
  function in ``plib.stdlib.options`` now supports
  referencing arguments by name as well as position.
  The name to position correspondence is determined
  using the list of arguments passed to the function.

- Added ``description`` and ``epilog`` parameters to the
  ``parse_options`` function in ``plib.stdlib.options``,
  to allow a brief description before options, and an
  epilog string after options, to be printed when help
  is requested. (Note that for older Python versions,
  the ``optparse`` module does not include the ``epilog``
  parameter, so the option parser is monkeypatched in
  the ``plib.stdlib.options`` code to deal with it in
  order to present consistent functionality.)

- Added the ``AttrDelegate``, ``AttrDict``, and
  ``AttrList`` classes to the ``plib.stdlib`` namespace.
  These classes are used by the ``options`` module (the
  ``parse_options`` function returns an ``AttrDict`` of
  the option values, and an ``AttrList`` of the argument
  values, allowing you to access options and arguments
  either by a key or sequence index, or by their name
  as attributes of the returned objects).

- Refactored the ``pyidserver.py`` and
  ``pyidserver-gui.py`` example programs to simplify
  the code and make the order of function arguments
  make more sense.

- Added a ``--test`` option to the ``scrips.py``
  example program that sends a test email to verify
  that the email settings work.

Version 0.7
-----------

*Release 0.7 Note: This release has significant changes
in the ``plib.stdlib.io`` sub-package, which has been
refactored considerably to make the code and API clearer;
also, there are a number of file deletions/additions
from previous versions. If you have a previous version
installed, it is recommended that you uninstall it
before installing this version, to avoid any potential
issues with old files being left in the PLIB3 directory
tree.*

- Updated various classes and functions to take
  advantage of the upgraded builtins provided by
  ``upgrade_builtins`` (see below).

- Added ``EchoRequestMixin`` to ``plib.classes``
  to provide simple "echo" functionality for
  servers/request handlers. This is mainly for
  demonstration (the new ``echo_server`` example
  program uses it--see below), but it is also
  used by the PLIB3 test suite.

- Added support in ``plib.classes.NotifierClient``
  for calling the ``do_loop`` method of the
  client in Qt/KDE (which use the GUI event loop
  and socket notifiers to multiplex the GUI with
  async I/O). This allows user code to be written
  portably without having to know whether the
  async I/O client is multiplexed with a GUI or
  not; the ``plib.utils.chat_replies`` class, as
  used by the ``pyidserver-gui`` example program,
  shows an example of how this works (the "chat"
  class is written as a simple generator that
  calls ``do_loop`` to retrieve data; the GUI
  then just drops ``NotifierClient`` in as a
  mixin class, and everything works).

- Fixed bug in ``plib.classes.PServerBase``
  with handling of log files and redirection
  of standard file descriptors.

- The ``StateMachine`` class in ``plib.classes``
  now raises ``InvalidState`` in the constructor
  if the ``initial_state`` parameter is not a
  valid state.

- Added convenience functions in ``plib.gui.common``
  to query and mutate the ``actiondict``, which
  stores captions and icon names for the various
  standard GUI actions.

- Added mechanism in KDE/KDE 4 to use some standard
  action icons without using the KDE standard action
  objects (since some standard action objects do
  other stuff we don't want). The mechanism is also
  used by "action buttons" (non-toolbar buttons that
  implement standard actions) to retrieve their icons.

- Moved the ``dotted_import`` and ``dotted_from_import``
  functions from ``plib.stdlib`` to their own
  sub-package, ``plib.stdlib.imp``. This allows them
  to be used without importing the rest of the stdlib
  code, for reduced memory footprint (e.g., when used
  by ``fork_server``--see below).

- Added ``abstractkeyed``, ``abstractmapping``, and
  ``abstractdict`` classes to ``plib.stdlib``; these
  are mapping-style (i.e., keyed) equivalents to
  ``abstractcontainer``, ``abstractsequence``, and
  ``abstractlist``. Also added ``AbstractKeyedMixin``
  and ``AbstractMappingMixin`` as equivalents to the
  corresponding mixins for abstract sequences, and
  ``basekeyed``, ``basemapping``, and ``basedict``
  which use the mixins to provide partial implementations
  of the abstract methods. Like the abstract containers,
  the abstract mapping classes are registered with the
  appropriate ABCs for Python 2.6 and later; the test
  code for this is expanded to cover the additional
  test cases.

- The ``coll`` module in ``plib.stdlib`` now
  includes the contents of the ``collections``
  module from the standard library, so you don't
  have to import both modules.

- The ``coll`` module now also provides
  equivalents for earlier Python versions to
  classes that are present in later versions
  (but not including the abstract base classes,
  since that whole package of functionality is
  too extensive, and anyway it's meant to be a
  kind of "gateway" to Python 3).

- Added ``decotools`` module to ``plib.stdlib``,
  functions and factories for decorators.

- Added ``func`` module to ``plib.stdlib``, to
  make an equivalent to the ``functools`` module
  in the standard library for Python 2.5 and later
  available in earlier versions (in 2.5 and later
  this module is just a proxy copy of ``functools``,
  so you can always import from it and use the
  same functionality).

- Added ``upgrade_builtins`` convenience function
  to ``plib.stdlib``; calling this function adds
  equivalents to the ``__builtin__`` module namespace
  for built-in functions that are not present in
  the running version of Python but are present in
  later versions. This is more convenient than having
  to worry about importing such equivalents from
  ``plib.stdlib``; as a consequence, a number of
  functions are now removed from the ``plib.stdlib``
  namespace and are instead provided by this function
  when the built-in equivalents are not present. In
  this version of ``plib``, you need to call this
  function somewhere in your code (but only once);
  future versions may automagically invoke it as long
  as you import anything from ``plib``. I should
  also note that I have snuck in a few extra
  "built-ins" that are not in the Python standard
  library but IMHO should be. :-)

- Removed the ``invertdict`` class from the
  ``plib.stdlib`` namespace. (With the ``inverted``
  function now provided as one of the extra
  "built-ins", there isn't enough of a use case for
  ``invertdict`` to justify it being there.)

- The ``closure`` function from plib.stdlib is now
  just a reference to ``plib.stdlib.func.partial``.

- Added the ``SelfPipe`` class to ``plib.stdlib``.
  This class implements the self-pipe trick in a
  general way that can be used by any application
  wanting to multiplex socket I/O with signals.
  (Note that the trick only works with pipes on
  Unix-type systems; on Windows, even though pipes
  are available, pipe file descriptors do not work
  with the select function, which only accepts
  sockets. Thus, sockets are used to emulate pipes
  for the Windows implementation of this class.)
  Also added the ``SelfPipeServerMixin`` class,
  which provides "drop-in" usage of ``SelfPipe``
  for servers that conform to the PLIB3 I/O server
  API (this class is therefore placed in the
  ``plib.stdlib.io`` sub-package). The socket
  server classes in the I/O sub-package of
  ``plib.stdlib`` now use this class (see below).

- Added ``SigChldMixin`` to ``plib.stdlib`` to
  factor out SIGCHLD handling for general use.
  Also added the ``SigChldServerMixin`` class,
  which customizes ``SigChldMixin`` for use with
  servers conforming to the PLIB3 I/O server API
  (this class is therefore placed in the
  ``plib.stdlib.io`` sub-package). (The blocking
  ``SocketServer`` in ``plib.stdlib.io`` now
  subclasses this class on Unix, but note that it
  does not on Windows--see further notes below.)
  Note that the ``SigChldMixin`` functionality
  that deals with tracking and reaping children
  works on Windows as well as Unix-type systems,
  even though Windows has no SIGCHLD signal, but
  this is only available in Python 2.6 and later,
  since the Windows functionality requires the
  ``multiprocessing`` module.

- Added ``SigIntMixin`` to ``plib.stdlib`` to
  provide simple termination signal handling
  for servers. Also added the ``SigIntServerMixin``
  class, which customizes ``SigIntMixin`` for use
  with servers conforming to the PLIB3 I/O server
  API (this class is therefore placed in the
  ``plib.stdlib.io`` sub-package). The
  ``PServerBase`` class now subclasses
  ``SigIntServerMixin``, but the latter is useful
  for simple servers that don't require logging
  and the other ``PServerBase`` bells and whistles.

- Added ``BaseCommunicator`` class to ``plib.stdlib.io`` to
  factor out common communication functionality (e.g, the
  ``query_done`` and ``check_done`` methods that determine
  when the channel is done processing). This class also
  provides a ``keep_alive`` flag which, if set to ``True``
  (the default for the async Persistent classes), allows
  the class to support multiple round-trip data exchanges
  (see below for more on this).

- Added a ``plib.stdlib.io.comm`` sub-package to factor
  out common functionality for each specific type of
  communication channel: client, server, and persistent.

- Added ``wait_for`` method to I/O clients to allow waiting
  for initial "greeting" message from server before starting
  to send data.

- Added ``server_start`` method to socket servers to allow
  initialization before the server socket is created.

- The ``BaseData`` class in ``plib.stdlib.io`` now sets
  the ``shutdown_received`` flag when a zero-byte read is
  detected, and provides the ``channel_closed`` method to
  tell when the channel has been automatically closed on
  a zero-byte read. The ``ReadWriteMonitor`` class in
  ``plib.classes`` is updated to output the value of
  these items for diagnostic purposes.

- Added ``BaseIO`` class to ``plib.stdlib.io`` to define
  the basic interface for I/O types (current types that
  implement this interface are ``serial`` and ``socket``).

- Changed the default functionality for the server-side I/O
  classes; they now all do nothing with received data.
  (Previously some of them echoed data received back to the
  client, but this should be a specific application decision,
  not a default.) The ``plib.classes.EchoRequestMixin``
  class (see above) can be used as a mixin for simple echo
  functionality.

- Fixed client/server classes to ensure support for multiple
  round-trip data exchanges; full-duplex interleaved data
  channels are still best done with the async Persistent
  classes, but the others can how handle, e.g., multiple
  simple "echo" exchanges. Added test cases to exercise
  this functionality.

- Improved commonality of method structure between the async
  and blocking I/O classes in ``plib.stdlib.io``, to make it
  easier to write code that is portable between both modes.
  Also added and standardized a more logical set of "event
  handlers" for notification of key events, and hooks for
  derived classes to customize processing.

- The async I/O socket server now uses the self-pipe trick
  to trap signals that should break it out of its loop. This
  enables the default timeout for async I/O to be changed to
  ``None`` (i.e., a timeout is no longer required unless a
  callback function is being used, e.g., to multiplex a GUI
  event loop with the async loop).

- There are now three blocking I/O socket servers. The base
  ``SocketServer`` class is now a "one connection at a time"
  server (like the one in the Python standard library), even
  though this will rarely be useful; however, it also serves
  as a base class and provides the base API for the useful
  classes, ``ForkingServer`` and ``ThreadingServer``. These
  use the private child process/thread management code in
  ``plib.utils`` (see below) to portably manage their child
  request handlers.

- The blocking I/O socket servers also now use the self-pipe
  trick, by adding a select call before each accept call
  (so the "idle" time is now spent in select instead of
  accept). This eliminates a potential race if the terminate
  signal handler gets called between the keep_running check
  and the accept call. This is somewhat similar to the
  change that was made to the basic socket server in the
  Python standard library in (I believe) Python 2.6.

- Factored out various private utility modules and functions
  in ``plib.utils`` for child process/thread management.
  These are not part of the public PLIB3 API, and it is not
  guaranteed that their structure will stay stable, but
  various parts of PLIB3 make use of them (e.g., the new
  blocking I/O socket server classes--see above).

- Modified the ``fork_server`` function in ``plib.utils`` to
  accept a tuple (<module_name>, <class_name>) in place of
  the server and/or handler classes; the code then imports the
  named class(es) from the named module(s) in the child
  process. This usage reduces the memory footprint of the code
  before forking.

- The forking functions in ``plib.utils`` now allow the
  functions to be run in the child process to determine the
  child's return code. If the functions do not return a value
  (i.e., they default to ``None``), the return code will be 0.

- Streamlined the ``ModuleProxy`` class to remove the need
  for boilerplate code in modules using it.

- Separated tests of persistent async I/O classes into their
  own test suite in ``plib.test``. This makes it easier to
  ferret out issues that are particular to this set of I/O
  classes.

- Added more test modules for the I/O classes to exercise
  various API behaviors and errors/unusual conditions.

- Some changes in how the test suite is run to avoid
  potential issues that are unrelated to PLIB3.

- Added more info in docstrings and standardized docstring
  formatting (e.g., argument descriptions for public functions
  and methods); also moved closer to standardizing code and
  docstring formatting to PEP 7/8.

- Added more example programs: an "echo" client and server,
  both of which can be told at run time which I/O type to
  use (async or blocking), to demonstrate how easily code can
  be written that is portable between both types; a "chat"
  client and server, to demonstrate the use of "persistent"
  async I/O; and a GUI display demo, which does nothing but
  displays all of the standard menu and toolbar actions.

Version 0.6.5
-------------

- The server classes in ``plib.classes`` now use the
  ``logging`` module in the standard library if it
  is present (i.e., in Python 2.3 and later). The
  standard functionality still logs to a file whose
  name is determined by the ``log_root``, ``log_namestr``,
  and ``server_name`` class fields; however, the
  ``init_logging`` method can be overridden to return
  a customized ``Logger`` object if desired.

- Corrected the import of the base class for
  ``plib.classes.PTCPClient`` to match the new
  ``plib.stdlib.io`` namespace setup.

- Added mechanism to specify to the GUI ``runapp``
  method whether the main window should be a
  full-fledged main window or just a top window (the
  default), when the class passed to ``runapp`` is a
  client widget class. The ``scrips-edit`` example
  program shows typical usage.

- Added ``PFileEditor`` to list of mixins supported if
  ``gui_test`` is true.

- Added the ``gcd``, ``lcm``, and ``prod`` functions to
  ``plib.stdlib``.

- Streamlined implementations of ``strtobool`` and
  ``strtodate`` functions in ``plib.stdlib``.

- Made minor changes in ``PersistentMixin`` in the
  ``plib.stdlib.io.async`` I/O sub-package to catch
  possible conditions that could result in an endless
  do loop without ever sending any data; added test
  cases and changed the test library code to cover the
  new conditions.

- Changed ``use_poll`` in ``plib.stdlib.io.async`` to
  a function, with the actual variable now stored in a
  private flag. Testing revealed that having it as a
  public global variable didn't work.

- Streamlined the async I/O test framework to make the
  intended usage clearer from reading the test code.

Version 0.6.4
-------------

- Automated the linking of target event handlers to
  controls defined by specs from ``specs.py``. The
  event handlers are identified in the specs by
  method name, with defaults based on the type of
  control. See ``specs.py``, the ``pyidserver-gui.py``
  example program, and the code for the preferences
  dialog in ``_dialogs.py`` in the ``plib.gui``
  sub-package, for details and examples of usage.

- Automated the construction of the preferences dialog
  (by adding a ``prefsdata`` class field to the top
  window).

- Added some more templates for standard widget API
  methods.

- Removed unnecessary method calls from the ``show_init``
  method of Qt 4 main windows (the calls were apparently
  preventing top windows from coming to the front when
  shown in OpenSuSE 11.2).

- Simplified the ``pxmlview`` example program so it no
  longer uses ``gui.PEditor`` (which really didn't add
  anything to the functionality).

- Added more edit-related actions to the standard action
  lists and images. (Note that implementation is still
  incomplete; each toolkit has some functionality that
  I haven't yet found an API for.)

- Added more action images, mainly for Qt/KDE 4.

- Added ``PTextMixin`` object to handle the standard text
  editing actions, and ``PTextFileMixin`` to handle the
  standard text file I/O actions.

- Added the ``pnotepad`` example program, a simple plain
  text editor. This illustrates usage of the ``PFileEditor``
  and ``PTextFileMixin`` objects and their associated
  actions.

- Fixed bug in SIGCHLD detection in the ``SigMixin`` class
  in the ``plib.stdlib.io.blocking`` sub-package.

- Updated copyright notices in about data of example
  programs to reflect 2010 release.

Version 0.6.3
-------------

- Fixed copyright notice to reflect 2010 release.

Version 0.6.2
-------------

- Fixed signal-aware code in ``plib.classes`` and
  ``plib.stdlib.io.blocking`` so that it only uses signals
  that are defined under the OS in which the code is running.

- Fixed algorithm for sizing to client in main windows so that
  the sizes of the menu, toolbar, and status bar are properly
  accounted for. (This also fixed issues with getting the main
  window properly centered on screen.)

- Fixed default colors in Qt/KDE 3/4 and standardized color
  setting methods.

- Fixed bugs in font setting code and expanded it to allow
  different fonts in list view/table headers and body.

- Fixed bugs in setting basic widget foreground/background
  colors in Qt/KDE 4. Also added methods for setting
  background color and for setting both colors at once, in
  all toolkits.

- Refactored code for various controls to reduce duplication
  and standardize the API.

- Fixed large toolbar icons in Qt 4 and KDE 3/4.

- Fixed setting of application icons in Qt/KDE (3 and 4) so
  that icons specified in about data are displayed in the
  about dialog.

- Changed KDE "About" action icon and text to be consistent
  with KDE guidelines. (Tried doing this using the KDE 3
  ``KStdAction`` and KDE 4 ``KStandardAction`` classes, but
  the behavior was not consistent with the documentation.)

- Fixed bug in KDE 4 app startup when no about data is
  provided.

- Implemented auto-sizing of list view columns in wxWidgets
  when column width is set to -1.

- Added "about toolkit" action that displays a dialog with
  info about the GUI toolkit being used. (Not available in
  all toolkits.)

- Expanded use of "standard" or "stock" actions, text, and
  images in toolkits.

- Changed standard widget ``update`` API method to
  ``update_widget`` to avoid method name collision in the
  KDE/Qt toolkits.

- Added templates for standard widget API methods to base
  widget classes. (This makes it easier to see what needs to
  be implemented in a toolkit.)

- Fixed bug in ``plib-setup-gui`` post-install script that
  would throw ``RuntimeError`` if Qt 3 and KDE 4 were both
  present; now correctly detects KDE 4 when this happens.

- Uses version 0.5.1 of SetupHelper.

Version 0.6.1
-------------

- Added KDE 4 GUI toolkit support. Also fixed a number of
  bugs in the Qt/KDE 4 toolkits (much of the code is common
  between these two).

- Added detection of KDE 4 in logic to select GUI toolkit.

- Added ``COLORNAMES`` global to ``plib.gui.defs`` so the
  string names of all supported colors are accessible as
  a single list.

- Extended widget enable and focus functionality to a
  wider range of widgets in ``plib.gui``.

- Added support for focus in and focus out widget events
  in ``plib.gui``.

- Added ``panelclass`` class field to the panel mixin
  class underlying ``PAutoPanel`` in ``plib.gui``, to
  fix bug in handling of sub-panels that are derived
  from ``PPanel`` but not ``PAutoPanel``.

- Fixed potential bugs in list view code where signatures
  of toolkit-specific list view items did not match the
  standard ``PListViewItemBase`` signature.

- Updated to version 0.4.4 of ``SetupHelper``.

- Added support for authentication and TLS when sending
  reminder e-mails in the ``scrips.py`` example program.

Version 0.6
-----------

- Added the ``NotifierClient`` class to ``plib.classes``
  and the ``PSocketNotifier`` class to ``plib.gui``. These
  classes work together to allow asynchronous socket I/O
  events to be multiplexed in with GUI event loops. (Note:
  these classes work best with the Qt-derived toolkits--Qt,
  Qt 4, and KDE. The other toolkits don't provide anything
  like Qt's ``QSocketNotifier`` class, so the multiplexing
  is done the kludgy way with timeouts.)

- Added the ``RecursiveTransition`` exception to the
  ``StateMachine`` class in ``plib.classes`` to flag when
  state transitions overlap. Added tests to correspond.

- Added the ``default_appclass`` global variable to the
  ``main`` module in ``plib.gui``; this allows overriding
  the ``PApplication`` default with something else. This is
  mainly for internal use (e.g., by the kludgy method of
  multiplexing socket I/O described above), but it is
  available if desired. (Note, however, that the actual
  ``default_appclass`` variable must *not* be overwritten,
  since it is a container; instead, assign your new class to
  index 0, thus: ``gui.default_appclass[0] = MyAppClass``.
  This is necessary for now because of how the ``ModuleProxy``
  class retrieves attributes from the module it wraps; at
  some point I may fix that so this hack is no longer
  needed.)

- Added the ``SerialPseudoSocket`` and ``SerialTelnet``
  classes to ``plib.classes``.

- Refactored the I/O classes in ``plib.stdlib`` to make the
  overall API and inheritance tree easier to use. This is a
  significant API change; see the ``README`` file and the
  ``plib.stdlib.io`` sub-package docstring for information
  about how it works. The ``ModuleProxy`` class is used
  throughout the new sub-package layout to make classes
  automatically appear in the proper namespace, and also to
  generate "standard" mixin classes on the fly when needed.

- Added the ``ShutdownReadWrite`` alternate data handling
  class.

- The socket I/O class ``close`` methods now catch more
  exceptions.

- Added test cases to more thoroughly exercise multiple and
  concurrent requests for the socket I/O classes.

- Much expansion of docstrings.

Version 0.5.2
-------------

- Where Python 2.4 and later syntax is used
  (mainly generator expressions), added alternate
  implementations (selected based on ``sys.version``)
  to support versions 2.2 and 2.3.

- Changed behavior of the abstract container
  classes to match Python 2.6/3.0 semantics in the
  handling of extended slices; extended slices
  with ``step == 1`` are now treated exactly
  the same as non-extended slices. The
  ``normalize_slice`` function in ``plib.stdlib``
  also changes its semantics to correspond.

- Added the ``__reversed__`` method to the abstract
  container types if the Python version is 2.6 or
  later.

- The abstract container types are now registered
  with the appropriate abstract base classes if the
  Python version is 2.6 or later; added test case
  to confirm that this works.

- Added the ``first`` and ``last`` functions in
  ``plib.stdlib``, and corresponding tests.

- The ``insert_sorted`` method of the ``SortMixin``
  class in ``plib.stdlib`` now has a ``key``
  argument, which works the same as the ``key``
  argument for the ``sorted`` builtin. Also,
  added a backport implementation of the ``sorted``
  builtin for Python versions < 2.4.

- Changed the ``SigSocketServer`` module in
  ``plib.stdlib`` to provide a complete alternate
  implementation of a forking TCP server and base
  request handler, instead of subclassing the Python
  standard library classes.

- Fixed the ``ClientServer`` blocking I/O mixin
  classes in ``plib.stdlib`` to ensure that sockets
  are closed even if an exception occurs.

- Made a number of improvements to the I/O classes
  to increase robustness.

- Modified the ``chat_replies`` class in
  ``plib.utils.chatgen`` to not send any data
  on startup if the first item in its data
  queue is ``None``; instead, just listen for
  an initial message from the server. Added a
  test case for this behavior.

- Added unit tests for the ``StateMachine`` class.

- Changed the test cases for the abstract
  containers to test for the new semantics for
  extended slices with ``step == 1``.

- Added test cases for the I/O classes to test for
  handling of multiple/concurrent requests and
  small I/O buffer sizes. 

Version 0.5.1
-------------

- Added the ``ReadWriteMonitor`` class to
  ``plib.classes``. This is a useful testing
  class for client/server I/O channels; it
  prints notifications of significant read
  and write method calls to standard output.

- Set the default for the ``use_poll`` global
  in ``plib.stdlib.async`` to ``True``; there
  is no reason to default to ``False`` since the
  ``loop`` function still checks to make sure
  the running OS supports the ``poll`` function,
  and falls back to ``select`` if it doesn't.

- Added the ``chatgen`` module to ``plib.utils``,
  containing the ``chat_replies`` class; this
  wraps an asynchronous I/O client in a generator
  that sends messages to the server one by one
  and yields the replies. The ``pyidserver.py``
  example program now uses this class to do its
  communication to the server; the generator
  form makes the code for the display of the
  results much easier.

- Made improvements to the behavior of instances
  of the ``ModuleProxy`` class from ``plib.utils``;]
  the builtin ``help`` command now correctly displays
  docstrings of proxy modules, and their ``repr``
  output is more informative.

- Added tests for the ``chat_replies`` class and
  the ``fork_wait`` and ``fork_socketpair``
  functions to the test suite.

- Added tests of the asynchronous I/O classes
  with the ``poll`` function disabled (see the
  item on ``async.use_poll`` above.

- Added unit tests for the ``ModuleProxy`` class.

Version 0.5
-----------

- The ``PTCPClient`` class in ``plib.classes``
  is simplified, using the refactored socket
  I/O functionality in ``plib.stdlib`` (see
  below).

- The ``PRequestHandler`` and ``SendReceiveMixin``
  classes are removed from ``plib.classes``;
  their functionality is no longer needed with
  the refactoring of the socket I/O classes
  in ``plib.stdlib`` (see below).

- Added the ``PListBox`` control to ``plib.gui``,
  a list view specialized for use in dialogs.
  This class also includes convenience methods to
  add items to the list box for common special
  cases (no child items, and single-column with
  no child items).

- Added ``PersistentMixin`` class to the
  ``plib.stdlib.async`` module, to handle cases
  where a persistent, full-duplex connection is
  desired instead of a pure client or server.
  This class supports overlapping reads and writes
  and implements a simple queue for write data to
  ensure all writes are in the correct order and
  no data is clobbered. Added corresponding
  persistent classes to the asynchronous I/O
  modules based on ``async``.

- Added the ``io`` module to the ``plib.stdlib``
  sub-package to provide common base classes
  for all I/O modes, factored out from the
  asynchronous and serial I/O classes.

- Added the ``pyserial`` module to the
  ``plib.stdlib`` sub-package to provide
  a thin wrapper around the ``Serial`` class
  and give a common base class for the
  ``SerialIO`` and ``AsyncSerial`` modules.
  The thin wrapper also adds the option to
  choose blocking or non-blocking mode for
  the serial device (the ``SerialIO`` and
  ``AsyncSerial`` modules each make the
  appropriate choice).

- Added the ``socketio`` module to ``plib.stdlib``
  to factor out socket-specific I/O functionality
  that is useful for both blocking and non-blocking
  I/O modes.

- Added the ``ClientServer`` module to ``plib.stdlib``
  to implement common functionality for blocking I/O
  clients and servers. This also factors out some
  code that was duplicated in other modules.

- Added the ``SocketClient`` module to ``plib.stdlib``
  to implement a simple blocking socket I/O client.

- Added the ``BaseRequestHandler`` class to the
  ``SigSocketServer`` module in ``plib.stdlib``; same
  functionality as the corresponding class from the
  Python standard library, but using the ``ClientServer``
  module blocking I/O scheme.

- Standardized the API for the various client/server
  classes: ``self.client_communicate(data)`` now
  always works for clients (possibly with the address
  socket clients or the device ID for serial clients,
  and a callback for async clients), and
  ``self.serve_forever()`` now always works for
  servers (possibly with a callback for async servers).

- Ensured that the ``close`` method of all async
  I/O classes is idempotent, since it is called from
  several places to ensure that it gets called at
  least once for any event that should trigger a
  close, but we don't want to call ``handle_close``
  multiple times.

- Removed the ``sitepath`` variable from the
  ``plib.stdlib`` sub-package globals; nothing
  in PLIB3 uses it and the heuristics for making
  sure it was correct were too hairy.

- Removed much cruft from the abstract container
  classes in ``plib.stdlib``, and added the
  ``basecontainer`` class to provide a partial
  implementation of ``abstractcontainer``. Also
  made the APIs of the abstract containers more
  complete and logical, and fixed logic to ensure
  the same semantics as list and tuple, including
  end case behavior.

- Added the ``closure`` function to ``plib.stdlib``,
  returns a simple closure of the given function with
  the given args and kwargs.

- Added the ``slice_len`` function to ``plib.stdlib``,
  returns the number of indexes that would be affected
  if the slice were used as a sequence index.

- Added the ``coll`` module to ``plib.stdlib``, with
  two convenience collection classes, ``fifo`` (based
  on ``collections.deque``) and ``stack`` (based on
  ``list``); the only changes are to define the ``next``
  method for each to retrieve the "next" object in
  the collection, as appropriate (i.e., the first item
  for ``fifo`` and the last item for ``stack``).

- Added tests in ``plib.test`` for most of the functions,
  classes, and modules in ``plib.stdlib``, and the
  ``specs`` module in ``plib.gui``.

- Added the ``forkwait``, ``forkserver``, and ``socketpair``
  modules to ``plib.utils``, containing the ``fork_wait``,
  ``fork_server``, and ``fork_socketpair`` functions. These
  fork subprocesses with extra functionality: ``fork_wait``
  waits until the subprocess has signaled successful startup
  before continuing, ``fork_server`` is a convenience function
  to do the same with a server class and its appropriate
  parameters given, and ``fork_socketpair`` lets the subprocess
  and the parent communicate via a socket pair.

- Fixed the ``plib-setup-paths.py`` post-install
  script to more reliably find paths, particularly
  on Mac OS X.

- The ``pyidserver.py`` example program now uses the
  asynchronous socket I/O ``ClientCommunicator`` class
  from ``plib.stdlib``.

- Minor refactoring of the ``scrips.py`` example
  progam (so it doesn't define the email-related
  code unless it's sending notification e-mail).

- Most docstrings now have more complete information than
  before.

Version 0.4.7
-------------

- Added new ``StateMachine`` class to
  ``plib.classes``, implements a simple
  state machine using a mapping of states
  to maps of input/output relations.

- Changed base async I/O classes to raise
  exceptions instead of logging warnings
  (e.g., raise NotImplementedError if a
  necessary event handler is not overridden).
  This also eliminates logging from the base
  classes--logging functionality is left as
  a "policy" for higher-level classes (such
  as ``plib.classes.PServerBase``).

- Made changes to async ``BaseDispatcher`` to
  mirror improvements made in Python 2.6 to
  ``asyncore.dispatcher``.

- Added exception handling to ``do_loop`` method
  of the async serial server classes; the
  ``close`` method is now called whenever an
  exception breaks out of the loop (similar to
  the protection added in ``SigSocketServer``).

- Added a new module in ``plib.stdlib`` for
  blocking serial I/O (i.e., no async/select
  loop). This module is now called ``SerialIO``;
  the async serial classes are now in the
  ``AsyncSerial`` module.

Version 0.4.6
-------------

- Refactored the ``plib.stdlib.async`` and
  ``plib.stdlib.AsyncServer`` modules to allow
  the core asynchronous I/O logic to be used with
  any object that has a Unix file descriptor;
  the classes in ``plib.stdlib.AsyncServer`` now
  inherit the core functionality and specialize
  it for network sockets.

- Added a global ``loop`` function to the ``async``
  module to allow a callback function (instead of
  requiring the use of ``AsyncBase.do_loop`` to
  get this functionality). Otherwise gives the same
  functionality as ``asyncore.loop``.

- Added the ``SerialIO`` module to ``plib.stdlib``
  to provide an asynchronous serial port I/O
  handler based on ``AsyncBase``. Note that this
  class requires the ``pyserial`` package, which
  is available from SourceForge.

- Moved the ``ReadWrite`` class from ``plib.classes``
  to ``plib.stdlib`` and made ``ReadWrite`` a
  module containing all the various mixin classes
  for data read/write handling.

- Fixed bug in the ``plib-setup-paths.py`` post-install
  script that was prepending the drive letter twice
  on Windows.

Version 0.4.5
-------------

- Fixed bugs in the post-install scripts: the
  boolean variables in the generated file
  ``plib.gui._setup.py`` were being incorrectly
  written as strings, and ``plib-setup-examples.py``
  was scanning too many directories in the
  ``$PREFIX/share`` tree.

Version 0.4.4
-------------

- Fixed minor errors in output from the
  ``plib.setuputils`` post-install script
  helper function, and made some other
  enhancements in script outputs.

Version 0.4.3
-------------

- Added a ``plib-setup-paths.py`` post-install
  script to determine the standard path names
  that are exported in ``plib.stdlib``, instead
  of determining them on the fly each time that
  package is imported (which is overkill since
  they should not change). Also added some new
  heuristics for determining the path names.

- Added a ``setuputils`` module in the base
  ``plib`` package to provide common code for
  the post-install scripts.

- Added code to the ``BaseDispatcher`` class in
  ``plib.stdlib.async`` to fix a number of minor
  issues with ``asyncore.dispatcher``.

- Moved the ``ReadWrite`` mixin class from
  ``plib.stdlib.async`` to ``plib.classes``, and
  moved the other async classes in ``plib.stdlib``
  into a new ``AsyncServer`` module. The client
  and server communicator classes are now mixins
  so that they can be used with different protocol
  read/write mixin classes.

Version 0.4.2
-------------

- Added support for Qt 4 as a GUI toolkit (it is
  different enough from Qt 3 that it's easier to make
  it separate than to try and extend the current Qt
  support to cover it). *NOTE: Qt 4 support is still
  experimental; some widgets (in particular the table
  widget) are still buggy.*

- Added ``process_events`` method to ``PApplication``
  objects to allow GUI events to be handled while
  other processing is going on--the typical use case
  is to call this method as a callback from an
  asynchronous I/O loop. Note that this method should
  not be called from event handlers or any other code
  that might recursively call into the GUI event loop.

- Added action images for the ``darwin`` platform to
  the GUI images available.

Version 0.4.1
-------------

- Added ``PServerBase`` class to ``plib.classes`` to
  factor out functionality common to all types of
  servers (sync, async, and forking).

- Added ``PAsyncServer`` class to ``plib.classes``,
  mixes ``PServerBase`` and ``ServerDispatcher`` from
  the ``plib.stdlib.async`` module.

- Added a clause in the ``do_loop`` method of
  ``BaseDispatcher`` in ``plib.stdlib.async`` to
  allow the callback function to break out of the
  polling loop by returning ``False``.

- Added ``AsyncRequestHandler`` class to the
  ``plib.stdlib.async`` module so that the
  ``ServerCommunicator`` class can remain general.

- Added a ``try/finally`` clause to the ``serve_forever``
  method of ``ServerDispatcher`` in ``plib.stdlib.async``
  and added a similar method to ``SigMixin`` in
  ``plib.stdlib.SigSocketServer`` to ensure that
  ``server_close`` gets called if an exception is thrown
  (previously only ``PTCPServer`` had this included).

- Added ``_panels.py`` unit to ``plib.gui``, containing
  the ``PMainPanel`` class, a ``PAutoPanel`` specialized
  for use as the main panel of your application (i.e.,
  the client widget of the main window). Changed the
  ``pyidserver-gui.py`` example program to use the new
  main panel class.

- Added ``PTextFile`` class to ``plib.gui.classes`` to
  allow read/write to a PTextDisplay as a file-like
  object (this was previously implemented only in the
  ``pyidserver-gui`` example program).

Version 0.4
-----------

- ``PTCPServer`` now correctly calls ``server_close``
  whenever it receives a signal that is in its list of
  terminating signals; this ensures that it shuts
  itself down properly and also ensures that the
  inherited ``server_close`` gets called to close the
  socket.

- Added ``PGroupBox`` widget to ``plib.gui``: basically
  a ``PPanel`` with a box and caption around its child
  widgets. Also added ``PAutoGroupBox`` to allow
  specification of child widgets using Python data
  structures.

- Added ``PTextDisplay`` widget, which is basically a
  read-only version of PEditControl. The example program
  ``pyidserver-gui.py`` now uses this widget to display
  output.

- Changed ``PTopWindow`` class fields for window
  placement on screen: the ``placement`` class field
  is now a 2-tuple ``(size_type, pos_type)``, where
  the ``size_type`` can be:
  
  * ``SIZE_NONE``,
  * ``SIZE_CLIENTWRAP``,
  * ``SIZE_MAXIMIZED``,
  * ``SIZE_OFFSET``,
  
  and the ``pos_type`` can be:
  
  * ``MOVE_NONE``,
  * ``MOVE_CENTER``.

- Enabled font settings on all widgets (previously only
  "control" type widgets had them).

- The ``plib.gui.specs`` module now allows you to use
  custom widget classes when building specs, by setting
  module variables.

- Also added ``get_listview`` to ``plib.gui.specs``.

- ``PPrefsDialog`` now supports all three types of INI
  file option specs.

- The preferences dialog now also allows two choices
  for the section grouping: each section can be a tab
  in a tab widget (the default), or a group box (just
  pass ``SECTION_GROUPBOX`` as the ``style`` parameter
  to the constructor).

- Added a ``gui_test`` variable in ``plib.gui._gui`` to
  allow testing of experimental additional toolkits that
  are not installed in PLIB3. See the comments in the
  ``plib.gui._gui`` module for details.

- Fixed bug in ``plib.ini`` where int and boolean values
  were not being written correctly to INI files.

- Added ``async.py`` module in ``plib.stdlib``, providing
  basic asynchronous client/server classes (building on
  the ``asyncore`` module in the Python standard library).

- Updated to version 0.4.2 of ``SetupHelper``.

Version 0.3
-----------

- Added ``__version__`` variable to the
  top-level ``plib`` namespace. All of the
  example programs now use the plib version
  as their version number by importing this
  variable.

- Added ``PPrefsDialog`` to ``PLIB3.GUI``: a
  preferences dialog that automatically builds
  its interface from a ``PIniFile``. Added a
  preferences dialog to the ``scrips-edit``
  example program to demonstrate this
  functionality.

- Added ``specs`` module to ``PLIB3.GUI`` to provide
  helper variables and functions for specifying
  GUI layouts. The ``PPrefsDialog`` class above
  uses this module, and the ``pyidserver-gui.py``
  example program is also modified to use this
  functionality.

- Added ``clientwrap`` class field to ``PTopWindow``
  to automatically size the window to fit its
  client widget; this is now the default behavior.

- Added ``SIGNAL_CLOSING`` signal in ``PLIB3.GUI``
  to allow notification when window has accepted
  a close but has not yet closed.

- Moved the ``ModuleProxy`` class from
  ``PLIB3.CLASSES`` to ``PLIB.UTILS``, since the
  latter is intended to be closer to the 'root'
  of the dependency tree.

- Added the ``dotted_import`` function to
  ``PLIB3.STDLIB`` for convenience when using the
  ``__import__`` builtin with dotted names (the
  code for this function originally came from
  the Python 2.6 documentation).

- Moved the ``options`` module from ``PLIB3.UTILS``
  to ``PLIB3.STDLIB`` since it basically wraps
  the standard library ``optparse`` module.

- Added the ``version`` module to ``PLIB3.UTILS``,
  providing some extensions of the Python
  distutils version number functionality. Also
  added a doctest for this module.

- Added support in ``PLIB3.XML`` for manually
  controlling the XML declaration and doctype
  string during serialization.

- The protocol and port number controls in the
  ``pyidserver-gui.py`` example are now disabled
  if DNS only is checked (this alerts the user
  that protocol and port number parameters are
  ignored by ``pyidserver`` in DNS only mode).

- The license for ``plib/test/runtests.py``, the
  generic test-running script, is changed to the
  PSF license so it can be detached from the rest
  of PLIB3 and used in non-GPL projects.

- Updated to version 0.4 of ``SetupHelper``.

Version 0.2.1
-------------

- Fixed bug in ``PLIB3.GUI`` that was appending
  spurious text to ``PMainWindow`` captions.

- Updated to version 0.3.1 of ``SetupHelper``.

Version 0.2
-----------

- Added status bar to ``PMainWindow``, and added demo
  functionality for the status bar to ``pxmlview``.

- Added support for more widget signals (selection
  changed signals for combo box, list view, and tab
  widget), and ensured that all signal-handling
  widgets derive from either ``_PDialogControl`` or
  ``_PNotifyControl``.

- Corrected tab add/delete behavior for tab widget.

- Added private ``_parent`` class field to tab widget,
  for consistency with other non-dialog control
  widgets.

- Added checks to ``PEditor`` to make sure main widget
  supports the editor protocol.

- Improved handling of widget geometry; passing ``None``
  as one of the geometry parameters means that
  parameter doesn't get changed from its previous
  value (which will usually be the default).

- Changed ``PLabel`` to ``PHeaderLabel``, and made
  ``plib.gui.classes`` and ``plib.gui.edit`` into
  private modules; their classes now appear in the
  ``plib.gui.main`` namespace with all the others.

- Added support in ``PIniFile`` for linking options to
  named attributes on the ``PIniFile`` object, instead of
  having get/set functions.

- Added tab widget to ``pxmlview.py`` example program to
  allow viewing multiple files; added support for
  passing multiple file names on the command line.

- Added basic URL parsing to the pyidserver.py example
  program; it now extracts the protocol and port
  number from URLs of the form::

    <protocol>://<url>:<port>

  Protocol and port specifiers in the URL override
  any specifiers in command-line options.

- Added new example program, ``scrips.py``, and its GUI,
  ``scrips-edit.py``; these are programs to keep track
  of prescriptions, demonstrating the table widget
  and INI file functionality in PLIB3.

- The ``setup.py`` script now uses a 'generic' helper
  module, ``SetupHelper``; all that is done in setup.py
  itself is to define variables and then call the
  helper module entry point. The SetupHelper module
  is available as its own PyPI project, ``setuphelper``.

- Since SetupHelper handles running post-install
  scripts, the ``install-all`` shell script is no longer
  needed and has been removed.

Version 0.1
-----------

Initial release.
