Silva 1.5 developer changes
Martijn Faassen <[email protected]>
| Newsgroups | gmane.comp.web.zope.silva.devel |
|---|---|
| Message-ID | <[email protected]> |
Hi there,
Posted previously to this list separately, here are the main
developer-level changes in Silva 1.5. In general, Silva 1.5 is the first
Silva release that really starts using Zope 3 technology in the core,
and this means extension writers can start using Zope 3/Five in their
extensions as well.
Five
----
Zope 2.8 includes a significant portion of Zope 3, and includes Five. Silva
does need a later version of Five than included with Zope 2.8 however,
namely Five 1.2, which can be easily installed as a product and which
ships with the Five tarball.
Zope 3 interfaces
-----------------
Silva now uses Zope 3 interfaces throughout, instead of Zope 2 interfaces.
If you use interfaces in your own code, import the `Interface` base
class like
this::
from zope.interface import Interface
Instead of using `__implements__`, state that your class implements
interfaces using the `implements` class annotation::
from zope.interface import implements
...
class Foo:
implements(IFoo)
You can check whether an instance provides an interface (i.e. whether
its class implements an interface or the interface directly provides
an interface) using `providedBy` (in Zope 2 this used to be
'isImplementedBy')::
IFoo.providedBy(instance)
In the rare case you want to check whether a *class* implements an
interface (i.e. whether its instances will provide that interface), you
use `implementedBy` (this used to be `isImplementedByInstancesOf` in
Zope 2)::
IFoo.implementedBy(some_class)
Five-based i18n
---------------
Silva now uses Zope 3 based i18n infrastructure, and
PlacelessTranslationService is not in use anymore.
All the translations of a product (such as `Silva`, `SilvaDocument`,
etc) are now in a directory, i18n which is registered in that
product's `configure.zcml` with the following simple directive::
<!-- i18n -->
<i18n:registerTranslations directory="i18n" />
The i18n directory has the following structure::
* a `.pot` file, such as `silva.pot`
* an `__init__.py` file.
* for each language, a subdirectory, such as `de`.
This language subdirectory follows a standard pattern derives from the
standard `gettext` tool. It contains a single subdirectory called
`LC_MESSAGES`. This directory contains a `.po` file and a `.mo` file,
such as `silva.mo` and `silva.po`.
The `.mo` file is a compiled version of the `.po` file. Zope only
consults the `.mo` files when looking for translations, so be sure to
update the `.mo` file whenever you change the `.po` file. You can do
this (on linux) with the standard `msgfmt` tool, with a command like
this::
msgfmt silva.po -o silva.mo
Zope 3 will likely evolve ways to make the generation of `.mo` files
more automatic in the future and Silva will follow.
Zope 3 adapters
---------------
Quite a few adapters in the `adapters` directory have been converted
to use Zope 3 patterns. That is, Silva looks them up by interface now
in the standard Zope 3 pattern. They also get registered through ZCML.
Here's an example of some ZCML registrations::
<adapter
for="Products.Silva.interfaces.IGhost"
provides=".interfaces.IIndexable"
factory=".indexable.GhostIndexableAdapter"
/>
<adapter
for="Products.Silva.interfaces.IContainer"
provides=".interfaces.IIndexable"
factory=".indexable.ContainerIndexableAdapter"
/>
<adapter
for="Products.Silva.interfaces.ISilvaObject"
provides=".interfaces.IIndexable"
factory=".indexable.IndexableAdapter"
/>
And here's how you look it up in Python code::
indexable = IIndexable(my_content_object)
You can then call methods on 'indexable'; to see which methods exist
you can consult `adapters/interfaces.py`.