What changed in version 3.2¶
Bootstrap¶
This release extends Reahl with (experimental) Bootstrap support.
Going forward (Reahl 4.0 onwards) we will base all our Widgets and styling on the Bootstrap web frontend library with the aim of sporting a better look and better layout tools.
This release is a transitional release: it has Bootstrap based Widgets and Layouts added side-by-side to what already exists. However, since Bootstrap 4 was still in alpha at the time of this release, this support is labelled as experimental and it is not enabled by default.
The addition of Bootstrap-based Widget
s is the major change
prompting this release. How it works, how its different and how you can
enable it are all discussed in the tutorial and won’t be repeated here.
Configuration and DANGEROUS defaults¶
Some configuration settings in Reahl are defaulted. This means that you can easily run a development server without having to create lots of configuration files because these default settings will be used instead.
Defaults are thus chosen to work in a development environment. Some of these defaults do not make sense in a production environment. For this reason, when a Reahl server starts up, it warns about such “Dangerous defaults”–values that are defaulted for a development environment. The idea is that in a production system, you are expected to set these explicitly, and not rely on the defaulted value.
In Reahl 3.2 when you run a system in production it will fail to start up if any such dangerous default value is not set explicitly. Previously it would start, but with a warning.
Furthermore, some important configuration settings that previously were not defaulted are now defaulted:
Setting | Config file | Dangerous default |
---|---|---|
reahlsystem.debug | reahl.config.py | True |
mail.smtp_port | mailutil.config.py | 8025 |
If you are running a production system, you will have to explicitly set these after upgrading before your system will start again.
Elixir¶
The Reahl 3.1 series allowed use of the reahl-web-elixirimpl egg which was distributed with Reahl 2.x to ease transition from the 2 to 3 series. In Reahl 3.2 this usage of some older 2.x version eggs is no longer supported.
Changes to existing layout tools¶
In the process of having to support Bootstrap, our existing concept of
PageColumnLayout
has grown too.
PageColumnLayout
has too much responsibility. It structures a page
with header, footer etc but it also structures the content area of the
page into columns. In order to do this, PageColumnLayout
hard-codes the use of a reahl.web.pure.ColumnLayout
and we wanted to be able
to use it with a reahl.web.bootstrap.grid.ColumnLayout
too.
The new reahl.web.layout.PageLayout
solves this problem by
only taking responsibility for the page itself (header, content,
footer). You can optionally also set up a PageLayout
with a separate
Layout
for each of it parts (header, document, content,
footer). Detailed layout of each part is thus decoupled from the
PageLayout
itself and delegated to whatever Layout
you specify for
that part.
This arrangement makes it possible to use PageLayout
with either a
reahl.web.pure.ColumnLayout
or the new reahl.web.bootstrap.grid.ColumnLayout
in addition to
other possibilities.
Updated dependencies¶
Some thirdparty JavaScript libraries were updated:
- jQuery from 1.8.1 to 1.11.2 (with jquery-migrate 1.2.1 added)
- jquery-blockui to 2.70.0
The versions of some external dependencies were updated:
- Babel from 1.3 to 2.1
- docutils max version 1.12 to < 1.13
- selenium max version from < 2.43 to < 3
Development web server¶
The development web server (invoked with reahl serve
) now has the
ability to watch for file changes in multiple directories, and restart
itself when a change is detected.
See:
reahl serve -h
Holder¶
The reahl.web.holder.holder
module was added to be able to use
holder.js to generate images on
the fly in a client browser.
Dealing with front-end libraries¶
Reahl is written in Python, but it has a lot of JavaScript and CSS code under the covers. Reahl also makes use of other “front-end libraries” (projects that live in the JavaScript/CSS world).
The reahl.web.libraries
module was added for dealing with such
front-end libraries. The same mechanism is now also used internally by
Reahl to ship its own JavaScript and CSS.
If you develop your own Widgets that include CSS of JavaScript code, you should now use this mechanism to distribute such front-end code as your own front-end library.
Miscellaneous¶
Bookmark¶
For Bookmark
, a locale argument was added to force the created
Bookmark
to be in a specific locale, possibly different from the
current one.
Widget¶
Many Widget
s inconsistently could receive a css_id kwarg upon
construction. This is now deprecated. Instead only simple Widget
s
that are subclasses from HTMLElement
now support this interface.
HTMLElement¶
Previously, an HTMLElement
could be set up so that it is refreshed
via ajax if any of its query_fields()
changed. This was done by
calling enable_refresh()
. These ideas were refined a little:
enable_refresh()
can now be given a list of the query_fields()
so that
the HTMLElement
will only be refreshed if the changing query_field
is included in the list sent to enable_refresh()
. Others are ignored.
Label¶
The constructor of Label
now takes an additional optional keyword
argument: for_input to indicate which Input
it labels.
FieldSet¶
A FieldSet
could be constructed with the keyword argument label_text
in which case a Label
would be added at the
start of the FieldSet
. This is an incorrect usage of Label
according to the HTML specification, hence this usage is now deprecated.
Instead, a legend_text keyword argument was added. If legend_text is
given, a Legend
will be added to the FieldSet
with the given text.
Table¶
A Table
could previously be created pre-populated with a set of
defined columns and a bunch of rows generated from given data by
using from_columns()
.
This method has now been deprecated. The same effect can now be
achieved by calling with_data()
on an
already created Table
.
This was done to allow one to use a Layout
on the Table
, which
would not be possible before. (A Layout
has to be attached
to its Table
before data is added to the Table
so that the
added rows adhere to the Layout
.)
Tofu¶
One of the defining features of a Fixture
is that it can have
methods for creating new objects for use in the test. All the
arguments of these methods are keyword arguments with default values
so that you can easily create a new object with default setup or
choose to create a instance that only customises values important to
the test.
For example:
def new_person(self, name='Jane', surname='Doe):
return Person(name, surname)
Such a method can be called in different ways:
jane = fixture.new_person()
john = fixture.new_person(name=John)
If you access an attribute on a Fixture
with the new_ prefix
chopped off, the corresponding new_ method is called without
arguments to create and instance to be returned. This instance is
then stored so that subsequent calls keep returning that same
“singleton” instance:
assert fixture.person is fixture.person
In the past, singleton instances created like this were never torn
down. In most cases it is not necessary to tear them down because the
entire Fixture
is thrown away after a test. We also abort the
database between each of our tests, so that database-persisted
instances are also cleaned up.
Sometimes (albeit rarely) it is useful to be able to tear down some of
these singleton instances explicitly when the Fixture
itself is
being torn down. In order to do this, you can now have a corresponding
method prefixed with del_ which will be called at Fixture
tear
down time:
def del_person(self, person): # do stuff to clean up after person
The del_ methods are called when tearing down the Fixture
before
any other tear down mechanisms are invoked, and in reverse order of
creation of each singleton instance.