Release 0.9.0
-------------

:Release: 0.9.0
:Date: December 17th, 2015

New Expressions
~~~~~~~~~~~~~~~

* Add a :func:`~blaze.expr.collections.shift` expression for shifting
  data backwards or forwards by *N* rows (:issue:`1266`).

Improved Expressions
~~~~~~~~~~~~~~~~~~~~

New Backends
~~~~~~~~~~~~

* Initial support for dask.dataframe has been added, see (:issue:`1317`).
  Please send feedback via an issue or pull request if we missed any
  expressions you need.

Improved Backends
~~~~~~~~~~~~~~~~~

* Adds support for :func:`~blaze.expr.collections.tail` in the sql backend
  (:issue:`1289`).
* Blaze Server now supports dynamically adding datasets (:issue:`1329`).
* Two new keyword only arguments are added to :func:`~blaze.compute` for use
  when computing against a :class:`~blaze.Client` object:

  1. ``compute_kwargs``: This is a dictionary to send to the server to use as
     keyword arguments when calling ``compute`` on the server.
  2. ``odo_kwargs``: This is a dictionary to send to the server to use as
     keyword arguments when calling ``odo`` on the server.

  This extra information is completely optional and will have different meanings
  based on the backend of the data on the server (:issue:`1342`).
* Can now point :func:`~blaze.interactive.Data` to URLs of CSVs
  (:issue:`1336`).

Experimental Features
~~~~~~~~~~~~~~~~~~~~~

* There is now support for joining tables from multiple sources. This
  is **very experimental** right now, so use it at your own risk. It
  currently only works with things that fit in memory (:issue:`1282`).
* Foreign columns in database tables that have foreign key relationships
  can now be accessed with a more concise syntax (:issue:`1192`).

API Changes
~~~~~~~~~~~

* Removed support for Python 2.6 (:issue:`1267`).
* Removed support for Python 3.3 (:issue:`1270`).
* When a CSV file consists of all strings, you must pass
  ``has_header=True`` when using the ``Data`` constructor (:issue:`1254`).
* Comparing ``date`` and ``datetime`` datashaped things to the empty
  string now raises a ``TypeError`` (:issue:`1308`).
* ``Like`` expressions behave like a predicate, and operate on columns,
  rather than performing the selection for you on a table
  (:issue:`1333`, :issue:`1340`).
* :meth:`blaze.server.Server.run` no longer retries binding to a new port by
  default. Also, positional arguments are no longer forwarded to the inner flask
  app's ``run`` method. All keyword arguments not consumed by the blaze server
  ``run`` are still forwarded (:issue:`1316`).
* :class:`~blaze.server.Server` represents datashapes in a canonical form with
  consistent linebreaks for use by non-Python clients (:issue:`1361`).

Bug Fixes
~~~~~~~~~

* Fixed a bug where ``Merge`` expressions would unpack option types in their
  fields. This could cause you to have a table where ``expr::{a: int32}`` but
  ``expr.a::?int32``. Note that the dotted access is an option (:issue:`1262`).
* Explicitly set ``Node.__slots__`` and ``Expr.__slots__`` to ``()``.  This
  ensures instances of slotted subclasses like ``Join`` do not have a useless
  empty ``__dict__`` attribute (:issue:`1274` and :issue:`1268`).
* Fixed a bug that prevented creating a
  :class:`~blaze.interactive.InteractiveSymbol` that wrapped ``nan`` if the
  dshape was ``datetime``. This now correctly coerces to `NaT` (:issue:`1272`).
* Fixed an issue where blaze client/server could not use `isin` expressions
  because the ``frozenset`` failed to serialize. This also added support for
  rich serialization over json for things like datetimes (:issue:`1255`).
* Fixed a bug where ``len`` would fail on an interactive expression whose
  resources were sqlalchemy objects (:issue:`1273`).
* Use aliases instead of common table expressions (CTEs) because MySQL doesn't
  have CTEs (:issue:`1278`).
* Fixed a bug where we couldn't display an empty string identifier
  in interactive mode (:issue:`1279`).
* Fixed a bug where comparisons with optionals that should have resulted in
  optionals did not (:issue:`1292`).
* Fixed a bug where ``Join.schema`` would not always be instantiated
  (:issue:`1288`).
* Fixed a bug where comparisons to a empty string magically converted
  the empty string to ``None`` (:issue:`1308`).
* Fix the ``retry`` kwarg to the blaze server. When ``retry`` is False, an
  exception is now properly raised if the port is in use. (:issue:`1316`).
* Fixed a bug where leaves that only appeared in the predicate of a selection
  would not be in scope in time to compute the predicate. This would cause whole
  expressions like ``a[a > b]`` to fail because ``b`` was not in scope
  (:issue:`1275`).
* Fix a broken test on machines that don't allow postgres to read from the
  local filesystem (:issue:`1323`).
* Updated a test to reflect changes from odo
  `#366 <https://github.com/blaze/odo/issues/366>`_ (:issue:`1323`).
* Fixed pickling of blaze expressions with interactive symbols (:issue:`1319`).
* Fixed repring partials in blaze expression to show keyword arguments
  (:issue:`1319`).
* Fixed a memory leak that would preserve the lifetime of any blaze expression
  that had cached an attribute access (:issue:`1335`).
* Fixed a bug where :func:`~blaze.expr.core.common_subexpression` gave the
  wrong answer (:issue:`1325`, :issue:`1338`).
* ``BinaryMath`` operations without numba installed were failing (:issue:`1343`).
* win32 tests were failing for ``hypot`` and ``atan2`` due to slight differences
  in numpy vs numba implementations of those functions (:issue:`1343`).
* Only start up a ``ThreadPool`` when using the h5py backend
  (:issue:`1347`, :issue:`1331`).
* Fix return type for sum and mean reductions whose children have a
  ``Decimal`` dshape.

Miscellaneous
~~~~~~~~~~~~~

* :meth:`blaze.server.Server.run` now uses :func:`warnings.warn` instead of
  ``print`` when it fails to bind to a port and is retrying (:issue:`1316`).
* Make expressions (subclasses of Expr) weak referencable (:issue:`1319).
* Memoize dshape and schema methods (:issue:`1319`).
* Use ``pandas.DataFrame.sort_values()`` with pandas version >= 0.17.0
  (:issue:`1321`).
