--- a/doc/book/en/admin/cubicweb-ctl.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/admin/cubicweb-ctl.rst Fri Oct 28 10:32:48 2011 +0200
@@ -109,14 +109,3 @@
Other commands
--------------
* ``delete``, deletes an instance (configuration files and database)
-
-Command to create an instance for Google AppEngine datastore source
--------------------------------------------------------------------
-* ``newgapp``, creates the configuration files for an instance
-
-This command needs to be followed by the commands responsible for
-the database initialization. As those are specific to the `datastore`,
-specific Google AppEgine database, they are not available for now
-in cubicweb-ctl, but they are available in the instance created.
-
-For more details, please see :ref:`GoogleAppEngineSource` .
--- a/doc/book/en/admin/gae.rst Thu Oct 27 18:19:00 2011 +0200
+++ /dev/null Thu Jan 01 00:00:00 1970 +0000
@@ -1,235 +0,0 @@
-.. -*- coding: utf-8 -*-
-
-.. _GoogleAppEngineSource:
-
-CubicWeb in Google AppEngine
-============================
-
-What is `Google AppEngine` ?
-------------------------------
-
-`Google AppEngine`_ is provided with a partial port of the `Django`
-framework, but Google stated at Google IO 2008 that it would not
-support a specific Python web framework and that all
-community-supported frameworks would be more than welcome [1]_.
-
-Therefore `Logilab`_ ported *CubicWeb* to run on top of `Google AppEngine`'s
-datastore.
-
-.. _`Google AppEngine`: http://code.google.com/appengine/docs/whatisgoogleappengine.html
-.. _Logilab: http://www.logilab.fr/
-.. [1] for more on this matter, read our blog at http://www.logilab.org/blogentry/5216
-
-Download the source
--------------------
-
-- The `Google AppEngine SDK` can be downloaded from:
- http://code.google.com/appengine/downloads.html
-
-
-Please follow instructions on how to install *CubicWeb* framework
-(:ref:`SetUpEnv`).
-
-Installation
-------------
-
-Once ``cubicweb-ctl`` is installed, then you can create a Google
-App Engine extension of our framework by running the command ::
-
- cubicweb-ctl newgapp <myapp>
-
-This will create a directory containing ::
-
- `-- myapp/
- |-- app.conf
- |-- app.yaml
- |-- bin/
- | `-- laxctl
- |-- boostrap_cubes
- |-- cubes/
- | |-- addressbook/
- | ..
- | |-- comment
- | ..
- | `-- zone/
- |-- cubicweb/
- |-- custom.py
- |-- cw-cubes/
- |-- dateutil/
- |-- docutils/
- |-- fckeditor/
- |-- i18n/
- |-- index.yaml
- |-- loader.py
- |-- logilab/
- |-- main.py
- |-- migration.py
- |-- mx/
- |-- roman.py
- |-- rql/
- |-- schema.py
- |-- simplejson/
- |-- tools/
- |-- views.py
- |-- vobject/
- |-- yams/
- `-- yapps/
-
-
-This skeleton directory is a working `AppEngine` application. You will
-recognize the files ``app.yaml`` and ``main.py``. All the rest is the
-*CubicWeb* framework and its third-party libraries. You will notice that
-the directory ``cubes`` is a library of reusable cubes.
-
-The main directories that you should know about are:
-
- - ``cubes`` : this is a library of reusable yams cubes. To use
- those cubes you will list them in the variable
- `included-yams-cubes` of ``app.conf``. See also :ref:`cubes`.
- - [WHICH OTHER ONES SHOULD BE LISTED HERE?]
-
-Dependencies
-~~~~~~~~~~~~
-
-Before starting anything, please make sure the following packages are installed:
- - yaml : by default google appengine is providing yaml; make sure you can
- import it. We recommend you create a symbolic link yaml instead of installing
- and using python-yaml:
- yaml -> full/path/to/google_appengine/lib/yaml/lib/yaml/
- - gettext
-
-Setup
-~~~~~
-
-Once you executed ``cubicweb-ctl newgapp <myapp>``, you can use that ``myapp/``
-as an application directory and do as follows.
-
-This installation directory provides a configuration for an instance of *CubicWeb*
-ported for Google App Engine. It is installed with its own command ``laxctl``
-which is a port of the command tool ``cubicweb-ctl`` originally developped for
-*CubicWeb*.
-
-You can have the details of available commands by running ::
-
- $ python myapp/bin/laxctl --help
-
-
-Generating translation files
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
-*CubicWeb* is fully internationalized. Translation catalogs are found in
-``myapp/i18n``. To compile the translation files, use the `gettext` tools
-or the ``laxctl`` command ::
-
- $ python myapp/bin/laxctl i18ncube
- $ python myapp/bin/laxctl i18ninstance
-
-Ignore the errors that print "No translation file found for domain
-'cubicweb'". They disappear after the first run of i18ninstance.
-
-.. note:: The command myapp/bin/laxctl i18ncube needs to be executed
- only if your instance is using cubes from cubicweb-apps.
- Otherwise, please skip it.
-
-You will never need to add new entries in the translation catalog. Instead we
-would recommand you to use ``self._cw._("msgId")`` in your code to flag new
-message id to add to the catalog, where ``_`` refers to xgettext that is used to
-collect new strings to translate. While running ``laxctl i18ncube``, new string
-will be added to the catalogs.
-
-Generating the data directory
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
-In order to generate the ``myapp/data`` directory that holds the static
-files like stylesheets and icons, you need to run the command::
-
- $ python myapp/bin/laxctl populatedata
-
-Generating the schema diagram
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
-There is a view named ``schema`` that displays a diagram of the
-entity-relationship graph defined by the schema. This diagram has to
-be generated from the command line::
-
- $ python myapp/bin/laxctl genschema
-
-Instance configuration
--------------------------
-
-Authentication
-~~~~~~~~~~~~~~
-
-You have the option of using or not google authentication for your instance.
-This has to be define in ``app.conf`` and ``app.yaml``.
-
-In ``app.conf`` modify the following variable::
-
- # does this instance rely on google authentication service or not.
- use-google-auth=no
-
-In ``app.yaml`` comment the `login: required` set by default in the handler::
-
- - url: .*
- script: main.py
- # comment the line below to allow anonymous access or if you don't want to use
- # google authentication service
- #login: required
-
-
-
-
-Quickstart : launch the instance
------------------------------------
-
-On Mac OS X platforms, drag that directory on the
-`GoogleAppEngineLauncher`.
-
-On Unix and Windows platforms, run it with the dev_appserver::
-
- $ python /path/to/google_appengine/dev_appserver.py /path/to/myapp/
-
-Once the local server is started, visit `http://MYAPP_URL/_load <http://localhost:8080/_load>`_ and sign in as administrator.
-This will initialize the repository and enable you to log in into
-the instance and continue the installation.
-
-You should be redirected to a page displaying a message `content initialized`.
-
-Initialize the datastore
-~~~~~~~~~~~~~~~~~~~~~~~~
-
-You, then, want to visit `http://MYAPP_URL/?vid=authinfo <http://localhost:8080/?vid=authinfo>`_ .
-If you selected not to use google authentication, you will be prompted to a
-login form where you should initialize the administrator login (recommended
-to use admin/admin at first). You will then be redirected to a page providing
-you the value to provide to ``./bin/laxctl --cookie``.
-
-If you choosed to use google authentication, then you will not need to set up
-and administrator login but you will get the cookie value as well.
-
-This cookie values needs to be provided to ``laxctl`` commands
-in order to handle datastore administration requests.
-
-.. image:: ../images/lax-book_02-cookie-values_en.png
- :alt: displaying the detailed view of the cookie values returned
-
-
-.. note:: In case you are not redirected to a page providing the
- option --cookie value, please visit one more time
- `http://MYAPP_URL/?vid=authinfo <http://localhost:8080/?vid=authinfo>`_ .
-
-Once, you have this value, then return to the shell and execute ::
-
- $ python myapp/bin/laxctl db-init --cookie='dev_appserver_login=test@example.com:True; __session=7bbe973a6705bc5773a640f8cf4326cc' localhost:8080
-
-.. note:: In the case you are not using google authentication, the value returned
- by `http://MYAPP_URL/?vid=authinfo <http://localhost:8080/?vid=authinfo>`_
- will look like :
- --cookie='__session=2b45d1a9c36c03d2a30cedb04bc37b6d'
-
-Log out by clicking in the menu at the top right corner
-and restart browsing from `http://MYAPP_URL/ <http://localhost:8080>`_
-as a normal user.
-
-Unless you did something to change it, http://MYAPP_URL should be
-http://localhost:8080/
--- a/doc/book/en/admin/instance-config.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/admin/instance-config.rst Fri Oct 28 10:32:48 2011 +0200
@@ -169,6 +169,8 @@
file to write messages
+.. _PersistentProperties:
+
Configuring persistent properties
---------------------------------
Other configuration settings are in the form of entities `CWProperty`
--- a/doc/book/en/admin/pyro.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/admin/pyro.rst Fri Oct 28 10:32:48 2011 +0200
@@ -1,8 +1,8 @@
+.. _UsingPyro:
+
Working with a distributed client (using Pyro)
==============================================
-.. _UsingPyro:
-
In some circumstances, it is practical to split the repository and
web-client parts of the application for load-balancing reasons. Or
one wants to access the repository from independant scripts to consult
@@ -14,7 +14,7 @@
For this to work, several steps have to be taken in order.
You must first ensure that the appropriate software is installed and
-running (see ref:`setup`)::
+running (see :ref:`ConfigEnv`)::
pyro-nsd -x -p 6969
@@ -52,14 +52,11 @@
cur.execute('INSERT Tag T: T name %(n)s', {'n': name})
cnx.commit()
-Calling :meth:`cubicweb.dbapi.load_appobjects`, will populates The `cubicweb
-registries`_ with the application objects installed on the host where the script
-runs. You'll then be allowed to use the ORM goodies and custom entity methods and
-views. Of course this is optional, without it you can still get the repository
-data through the connection but in a roughly way: only RQL cursors will be
-available, e.g. you can't even build entity objects from the result set.
-
-
-
-.. _cubicweb registries: VRegistryIntro_
-
+Calling :meth:`cubicweb.dbapi.load_appobjects`, will populate the
+cubicweb registrires (see :ref:`VRegistryIntro`) with the application
+objects installed on the host where the script runs. You'll then be
+allowed to use the ORM goodies and custom entity methods and views. Of
+course this is optional, without it you can still get the repository
+data through the connection but in a roughly way: only RQL cursors
+will be available, e.g. you can't even build entity objects from the
+result set.
--- a/doc/book/en/annexes/faq.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/annexes/faq.rst Fri Oct 28 10:32:48 2011 +0200
@@ -150,9 +150,7 @@
How to load data from a python script ?
---------------------------------------
-Please, refer to the `Pyro chapter`_.
-
-.. _`Pyro chapter`: UsingPyro_
+Please, refer to :ref:`UsingPyro`.
How to format an entity date attribute ?
--- a/doc/book/en/annexes/rql/language.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/annexes/rql/language.rst Fri Oct 28 10:32:48 2011 +0200
@@ -55,6 +55,8 @@
**is** in the restrictions.
+.. _VirtualRelations:
+
Virtual relations
~~~~~~~~~~~~~~~~~
@@ -66,7 +68,7 @@
* `identity`: relation to use to tell that a RQL variable is the same as another
when you've to use two different variables for querying purpose. On the
- opposite it's also useful together with the :ref:`NOT` operator to tell that two
+ opposite it's also useful together with the ``NOT`` operator to tell that two
variables should not identify the same entity
@@ -83,12 +85,12 @@
* floats separator is dot '.'
-* boolean values are :keyword:`TRUE` and :keyword:`FALSE` keywords
+* boolean values are ``TRUE`` and ``FALSE`` keywords
* date and time should be expressed as a string with ISO notation : YYYY/MM/DD
- [hh:mm], or using keywords :keyword:`TODAY` and :keyword:`NOW`
+ [hh:mm], or using keywords ``TODAY`` and ``NOW``
-You may also use the :keyword:`NULL` keyword, meaning 'unspecified'.
+You may also use the ``NULL`` keyword, meaning 'unspecified'.
.. _RQLOperators:
@@ -167,7 +169,9 @@
`VARIABLE attribute VALUE`
-The operator `IN` provides a list of possible values: ::
+The operator `IN` provides a list of possible values:
+
+.. sourcecode:: sql
Any X WHERE X name IN ('chauvat', 'fayolle', 'di mascio', 'thenault')
@@ -180,28 +184,32 @@
LIKE, ILIKE, ~=, REGEXP
-The :keyword:`LIKE` string operator can be used with the special character `%` in
-a string as wild-card: ::
+The ``LIKE`` string operator can be used with the special character `%` in
+a string as wild-card:
+
+.. sourcecode:: sql
- # match every entity whose name starts with 'Th'
+ -- match every entity whose name starts with 'Th'
Any X WHERE X name ~= 'Th%'
- # match every entity whose name endswith 'lt'
+ -- match every entity whose name endswith 'lt'
Any X WHERE X name LIKE '%lt'
- # match every entity whose name contains a 'l' and a 't'
+ -- match every entity whose name contains a 'l' and a 't'
Any X WHERE X name LIKE '%l%t%'
-:keyword:`ILIKE` is the case insensitive version of :keyword:`LIKE`. It's not
+``ILIKE`` is the case insensitive version of ``LIKE``. It's not
available on all backend (e.g. sqlite doesn't support it). If not available for
-your backend, :keyword:`ILIKE` will behave like :keyword:`LIKE`.
+your backend, ``ILIKE`` will behave like ``LIKE``.
-`~=` is a shortcut version of :keyword:`ILIKE`, or of :keyword:`LIKE` when the
+`~=` is a shortcut version of ``ILIKE``, or of ``LIKE`` when the
former is not available on the back-end.
-The :keyword:`REGEXP` is an alternative to :keyword:`LIKE` that supports POSIX
-regular expressions::
+The ``REGEXP`` is an alternative to ``LIKE`` that supports POSIX
+regular expressions:
- # match entities whose title starts with a digit
+.. sourcecode:: sql
+
+ -- match entities whose title starts with a digit
Any X WHERE X title REGEXP "^[0-9].*"
@@ -253,7 +261,9 @@
There will be as much column in the result set as term in this clause, respecting
order.
-Syntax for function call is somewhat intuitive, for instance: ::
+Syntax for function call is somewhat intuitive, for instance:
+
+.. sourcecode:: sql
Any UPPER(N) WHERE P firstname N
@@ -261,28 +271,28 @@
Grouping and aggregating
````````````````````````
-The :keyword:`GROUPBY` keyword is followed by a list of terms on which results
+The ``GROUPBY`` keyword is followed by a list of terms on which results
should be grouped. They are usually used with aggregate functions, responsible to
aggregate values for each group (see :ref:`RQLAggregateFunctions`).
For grouped queries, all selected variables must be either aggregated (i.e. used
-by an aggregate function) or grouped (i.e. listed in the :keyword:`GROUPBY`
+by an aggregate function) or grouped (i.e. listed in the ``GROUPBY``
clause).
Sorting
```````
-The :keyword:`ORDERBY` keyword if followed by the definition of the selection
-order: variable or column number followed by sorting method (:keyword:`ASC`,
-:keyword:`DESC`), :keyword:`ASC` being the default. If the sorting method is not
+The ``ORDERBY`` keyword if followed by the definition of the selection
+order: variable or column number followed by sorting method (``ASC``,
+``DESC``), ``ASC`` being the default. If the sorting method is not
specified, then the sorting is ascendant (`ASC`).
Pagination
``````````
-The :keyword:`LIMIT` and :keyword:`OFFSET` keywords may be respectively used to
+The ``LIMIT`` and ``OFFSET`` keywords may be respectively used to
limit the number of results and to tell from which result line to start (for
instance, use `LIMIT 20` to get the first 20 results, then `LIMIT 20 OFFSET 20`
to get the next 20.
@@ -291,34 +301,34 @@
Restrictions
````````````
-The :keyword:`WHERE` keyword introduce one of the "main" part of the query, where
+The ``WHERE`` keyword introduce one of the "main" part of the query, where
you "define" variables and add some restrictions telling what you're interested
in.
It's a list of triplets "subject relation object", e.g. `V1 relation
(V2 | <static value>)`. Triplets are separated using :ref:`RQLLogicalOperators`.
-.. Note:
+.. note::
- About the negation operator (:keyword:`NOT`):
+ About the negation operator (``NOT``):
- * "NOT X relation Y" is equivalent to "NOT EXISTS(X relation Y)"
+ * ``NOT X relation Y`` is equivalent to ``NOT EXISTS(X relation Y)``
- * `Any X WHERE NOT X owned_by U` means "entities that have no relation
- `owned_by`".
+ * ``Any X WHERE NOT X owned_by U`` means "entities that have no relation
+ ``owned_by``".
- * `Any X WHERE NOT X owned_by U, U login "syt"` means "the entity have no
- relation `owned_by` with the user syt". They may have a relation "owned_by"
+ * ``Any X WHERE NOT X owned_by U, U login "syt"`` means "the entity have no
+ relation ``owned_by`` with the user syt". They may have a relation "owned_by"
with another user.
-In this clause, you can also use :keyword:`EXISTS` when you want to know if some
+In this clause, you can also use ``EXISTS`` when you want to know if some
expression is true and do not need the complete set of elements that make it
true. Testing for existence is much faster than fetching the complete set of
-results, especially when you think about using `OR` against several expressions. For instance
+results, especially when you think about using ``OR`` against several expressions. For instance
if you want to retrieve versions which are in state "ready" or tagged by
"priority", you should write :
-::
+.. sourcecode:: sql
Any X ORDERBY PN,N
WHERE X num N, X version_of P, P name PN,
@@ -327,7 +337,7 @@
not
-::
+.. sourcecode:: sql
Any X ORDERBY PN,N
WHERE X num N, X version_of P, P name PN,
@@ -356,7 +366,9 @@
You must use the `?` behind a variable to specify that the relation toward it
is optional. For instance:
-- Bugs of a project attached or not to a version ::
+- Bugs of a project attached or not to a version
+
+ .. sourcecode:: sql
Any X, V WHERE X concerns P, P eid 42, X corrected_in V?
@@ -364,26 +376,34 @@
version in which it's corrected or None for tickets not related to a version.
-- All cards and the project they document if any ::
+- All cards and the project they document if any
+
+ .. sourcecode:: sql
Any C, P WHERE C is Card, P? documented_by C
Notice you may also use outer join:
-- on the RHS of attribute relation, e.g. ::
+- on the RHS of attribute relation, e.g.
+
+ .. sourcecode:: sql
Any X WHERE X ref XR, Y name XR?
so that Y is outer joined on X by ref/name attributes comparison
-- on any side of an `HAVING` expression, e.g. ::
+- on any side of an ``HAVING`` expression, e.g.
+
+ .. sourcecode:: sql
Any X WHERE X creation_date XC, Y creation_date YC
HAVING YEAR(XC)=YEAR(YC)?
so that Y is outer joined on X by comparison of the year extracted from their
- creation date. ::
+ creation date.
+
+ .. sourcecode:: sql
Any X WHERE X creation_date XC, Y creation_date YC
HAVING YEAR(XC)?=YEAR(YC)
@@ -394,20 +414,26 @@
Having restrictions
```````````````````
-The :keyword:`HAVING` clause, as in SQL, may be used to restrict a query
-according to value returned by an aggregate function, e.g.::
+The ``HAVING`` clause, as in SQL, may be used to restrict a query
+according to value returned by an aggregate function, e.g.
+
+.. sourcecode:: sql
Any X GROUPBY X WHERE X relation Y HAVING COUNT(Y) > 10
-It may however be used for something else: In the :keyword:`WHERE` clause, we are
+It may however be used for something else: In the ``WHERE`` clause, we are
limited to triplet expressions, so some things may not be expressed there. Let's
take an example : if you want to get people whose upper-cased first name equals to
another person upper-cased first name. There is no proper way to express this
-using triplet, so you should use something like: ::
+using triplet, so you should use something like:
+
+.. sourcecode:: sql
Any X WHERE X firstname XFN, Y firstname YFN, NOT X identity Y HAVING UPPER(XFN) = UPPER(YFN)
-Another example: imagine you want person born in 2000: ::
+Another example: imagine you want person born in 2000:
+
+.. sourcecode:: sql
Any X WHERE X birthday XB HAVING YEAR(XB) = 2000
@@ -419,19 +445,21 @@
Sub-queries
```````````
-The :keyword:`WITH` keyword introduce sub-queries clause. Each sub-query has the
+The ``WITH`` keyword introduce sub-queries clause. Each sub-query has the
form:
V1(,V2) BEING (rql query)
-Variables at the left of the :keyword:`BEING` keyword defines into which
+Variables at the left of the ``BEING`` keyword defines into which
variables results from the sub-query will be mapped to into the outer query.
Sub-queries are separated from each other using a comma.
Let's say we want to retrieve for each project its number of versions and its
number of tickets. Due to the nature of relational algebra behind the scene, this
can't be achieved using a single query. You have to write something along the
-line of: ::
+line of:
+
+.. sourcecode:: sql
Any X, VC, TC WHERE X identity XX
WITH X, VC BEING (Any X, COUNT(V) GROUPBY X WHERE V version_of X),
@@ -439,19 +467,24 @@
Notice that we can't reuse a same variable name as alias for two different
sub-queries, hence the usage of 'X' and 'XX' in this example, which are then
-unified using the special `identity` relation (see :ref:`XXX`).
+unified using the special `identity` relation (see :ref:`VirtualRelations`).
-.. Warning:
+.. warning::
Sub-queries define a new variable scope, so even if a variable has the same name
- in the outer query and in the sub-query, they technically **aren't* the same
- variable. So ::
+ in the outer query and in the sub-query, they technically **aren't** the same
+ variable. So:
+
+ .. sourcecode:: sql
Any W, REF WITH W, REF BEING
(Any W, REF WHERE W is Workcase, W ref REF,
W concerned_by D, D name "Logilab")
+
could be written:
+ .. sourcecode:: sql
+
Any W, REF WITH W, REF BEING
(Any W1, REF1 WHERE W1 is Workcase, W1 ref REF1,
W1 concerned_by D, D name "Logilab")
@@ -459,14 +492,18 @@
Also, when a variable is coming from a sub-query, you currently can't reference
its attribute or inlined relations in the outer query, you've to fetch them in
the sub-query. For instance, let's say we want to sort by project name in our
- first example, we would have to write ::
+ first example, we would have to write:
+
+ .. sourcecode:: sql
Any X, VC, TC ORDERBY XN WHERE X identity XX
WITH X, XN, VC BEING (Any X, COUNT(V) GROUPBY X,XN WHERE V version_of X, X name XN),
XX, TC BEING (Any X, COUNT(T) GROUPBY X WHERE T ticket_of X)
- instead of ::
+ instead of:
+
+ .. sourcecode:: sql
Any X, VC, TC ORDERBY XN WHERE X identity XX, X name XN,
WITH X, XN, VC BEING (Any X, COUNT(V) GROUPBY X WHERE V version_of X),
@@ -479,10 +516,10 @@
`````
You may get a result set containing the concatenation of several queries using
-the :keyword:`UNION`. The selection of each query should have the same number of
+the ``UNION``. The selection of each query should have the same number of
columns.
-::
+.. sourcecode:: sql
(Any X, XN WHERE X is Person, X surname XN) UNION (Any X,XN WHERE X is Company, X name XN)
@@ -514,7 +551,7 @@
+--------------------+----------------------------------------------------------+
All aggregate functions above take a single argument. Take care some aggregate
-functions (e.g. :keyword:`MAX`, :keyword:`MIN`) may return `None` if there is no
+functions (e.g. ``MAX``, ``MIN``) may return `None` if there is no
result row.
.. _RQLStringFunctions:
@@ -522,26 +559,26 @@
String transformation functions
```````````````````````````````
-+-------------------------+-----------------------------------------------------------------+
-| :func:`UPPER(String)` | upper case the string |
-+-------------------------+-----------------------------------------------------------------+
-| :func:`LOWER(String)` | lower case the string |
-+-------------------------+-----------------------------------------------------------------+
-| :func:`LENGTH(String)` | return the length of the string |
-+-------------------------+-----------------------------------------------------------------+
-| :func:`SUBSTRING( | extract from the string a string starting at given index and of |
-| String, start, length)`| given length |
-+-------------------------+-----------------------------------------------------------------+
-| :func:`LIMIT_SIZE( | if the length of the string is greater than given max size, |
-| String, max size)` | strip it and add ellipsis ("..."). The resulting string will |
-| | hence have max size + 3 characters |
-+-------------------------+-----------------------------------------------------------------+
-| :func:`TEXT_LIMIT_SIZE( | similar to the above, but allow to specify the MIME type of the |
-| String, format, | text contained by the string. Supported formats are text/html, |
-| max size)` | text/xhtml and text/xml. All others will be considered as plain |
-| | text. For non plain text format, sgml tags will be first removed|
-| | before limiting the string. |
-+-------------------------+-----------------------------------------------------------------+
++---------------------------------------------------+-----------------------------------------------------------------+
+| :func:`UPPER(String)` | upper case the string |
++---------------------------------------------------+-----------------------------------------------------------------+
+| :func:`LOWER(String)` | lower case the string |
++---------------------------------------------------+-----------------------------------------------------------------+
+| :func:`LENGTH(String)` | return the length of the string |
++---------------------------------------------------+-----------------------------------------------------------------+
+| :func:`SUBSTRING(String, start, length)` | extract from the string a string starting at given index and of |
+| | given length |
++---------------------------------------------------+-----------------------------------------------------------------+
+| :func:`LIMIT_SIZE(String, max size)` | if the length of the string is greater than given max size, |
+| | strip it and add ellipsis ("..."). The resulting string will |
+| | hence have max size + 3 characters |
++---------------------------------------------------+-----------------------------------------------------------------+
+| :func:`TEXT_LIMIT_SIZE(String, format, max size)` | similar to the above, but allow to specify the MIME type of the |
+| | text contained by the string. Supported formats are text/html, |
+| | text/xhtml and text/xml. All others will be considered as plain |
+| | text. For non plain text format, sgml tags will be first removed|
+| | before limiting the string. |
++---------------------------------------------------+-----------------------------------------------------------------+
.. _RQLDateFunctions:
@@ -588,61 +625,63 @@
~~~~~~~~
- *Search for the object of identifier 53*
- ::
- Any WHERE X
- X eid 53
+ .. sourcecode:: sql
+
+ Any WHERE X eid 53
- *Search material such as comics, owned by syt and available*
- ::
+
+ .. sourcecode:: sql
- Any X WHERE X is Document
- X occurence_of F, F class C, C name 'Comics'
- X owned_by U, U login 'syt'
- X available TRUE
+ Any X WHERE X is Document,
+ X occurence_of F, F class C, C name 'Comics',
+ X owned_by U, U login 'syt',
+ X available TRUE
- *Looking for people working for eurocopter interested in training*
- ::
+
+ .. sourcecode:: sql
- Any P WHERE
- P is Person, P work_for S, S name 'Eurocopter'
- P interested_by T, T name 'training'
+ Any P WHERE P is Person, P work_for S, S name 'Eurocopter',
+ P interested_by T, T name 'training'
- *Search note less than 10 days old written by jphc or ocy*
- ::
+
+ .. sourcecode:: sql
- Any N WHERE
- N is Note, N written_on D, D day> (today -10),
- N written_by P, P name 'jphc' or P name 'ocy'
+ Any N WHERE N is Note, N written_on D, D day> (today -10),
+ N written_by P, P name 'jphc' or P name 'ocy'
- *Looking for people interested in training or living in Paris*
- ::
+
+ .. sourcecode:: sql
- Any P WHERE
- P is Person, (P interested_by T, T name 'training') OR
- (P city 'Paris')
+ Any P WHERE P is Person, (P interested_by T, T name 'training') OR
+ (P city 'Paris')
- *The surname and firstname of all people*
- ::
- Any N, P WHERE
- X is Person, X name N, X firstname P
+ .. sourcecode:: sql
+
+ Any N, P WHERE X is Person, X name N, X firstname P
Note that the selection of several entities generally force
the use of "Any" because the type specification applies otherwise
to all the selected variables. We could write here
- ::
- String N, P WHERE
- X is Person, X name N, X first_name P
+ .. sourcecode:: sql
+
+ String N, P WHERE X is Person, X name N, X first_name P
Note: You can not specify several types with * ... where X is FirstType or X is SecondType*.
To specify several types explicitly, you have to do
- ::
- Any X where X is in (FirstType, SecondType)
+ .. sourcecode:: sql
+
+ Any X WHERE X is IN (FirstType, SecondType)
.. _RQLInsertQuery:
@@ -662,19 +701,22 @@
*each line result returned by the restriction*.
- *Insert a new person named 'foo'*
- ::
+
+ .. sourcecode:: sql
INSERT Person X: X name 'foo'
- *Insert a new person named 'foo', another called 'nice' and a 'friend' relation
between them*
- ::
+
+ .. sourcecode:: sql
INSERT Person X, Person Y: X name 'foo', Y name 'nice', X friend Y
- *Insert a new person named 'foo' and a 'friend' relation with an existing
person called 'nice'*
- ::
+
+ .. sourcecode:: sql
INSERT Person X: X name 'foo', X friend Y WHERE name 'nice'
@@ -690,13 +732,15 @@
each result line returned by the restriction*.
- *Renaming of the person named 'foo' to 'bar' with the first name changed*
- ::
+
+ .. sourcecode:: sql
SET X name 'bar', X firstname 'original' WHERE X is Person, X name 'foo'
- *Insert a relation of type 'know' between objects linked by
the relation of type 'friend'*
- ::
+
+ .. sourcecode:: sql
SET X know Y WHERE X friend Y
@@ -713,12 +757,14 @@
each line result returned by the restriction*.
- *Deletion of the person named 'foo'*
- ::
+
+ .. sourcecode:: sql
DELETE Person X WHERE X name 'foo'
- *Removal of all relations of type 'friend' from the person named 'foo'*
- ::
+
+ .. sourcecode:: sql
DELETE X friend Y WHERE X is Person, X name 'foo'
--- a/doc/book/en/devrepo/entityclasses/adapters.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/devrepo/entityclasses/adapters.rst Fri Oct 28 10:32:48 2011 +0200
@@ -133,8 +133,8 @@
return sum(captain.age for captain in self.captains)
class FooView(EntityView):
- __regid__ = 'mycube.fooview'
- __select__ = implements('IFoo')
+ __regid__ = 'mycube.fooview'
+ __select__ = implements('IFoo')
def cell_call(self, row, col):
entity = self.cw_rset.get_entity(row, col)
@@ -152,8 +152,8 @@
return sum(captain.age for captain in self.entity.captains)
class FooView(EntityView):
- __regid__ = 'mycube.fooview'
- __select__ = adaptable('IFoo')
+ __regid__ = 'mycube.fooview'
+ __select__ = adaptable('IFoo')
def cell_call(self, row, col):
entity = self.cw_rset.get_entity(row, col)
--- a/doc/book/en/devrepo/entityclasses/application-logic.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/devrepo/entityclasses/application-logic.rst Fri Oct 28 10:32:48 2011 +0200
@@ -97,7 +97,7 @@
`fetch_attrs` configures which attributes should be prefetched when using ORM
methods retrieving entity of this type. In a same manner, the `cw_fetch_order` is
-a class method allowing to control sort order. More on this in :ref:FetchAttrs.
+a class method allowing to control sort order. More on this in :ref:`FetchAttrs`.
We can observe the big TICKET_DEFAULT_STATE_RESTR is a pure
application domain piece of data. There is, of course, no limitation
--- a/doc/book/en/devrepo/entityclasses/load-sort.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/devrepo/entityclasses/load-sort.rst Fri Oct 28 10:32:48 2011 +0200
@@ -33,7 +33,8 @@
In you want something else (such as sorting on the result of a registered
procedure), here is the prototype of those methods:
-.. autofunction:: cubicweb.entity.Entity.cw_fetch_order
+
+.. automethod:: cubicweb.entity.Entity.cw_fetch_order
-.. autofunction:: cubicweb.entity.Entity.cw_fetch_unrelated_order
+.. automethod:: cubicweb.entity.Entity.cw_fetch_unrelated_order
--- a/doc/book/en/devweb/edition/examples.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/devweb/edition/examples.rst Fri Oct 28 10:32:48 2011 +0200
@@ -165,7 +165,7 @@
msg = format_mail({'email' : self._cw.user.get_email(),
'name' : self._cw.user.dc_title()},
recipients, body, subject)
- if not self._cw.vreg.config.sendmails([(msg, recipients]):
+ if not self._cw.vreg.config.sendmails([(msg, recipients)]):
msg = self._cw._('could not connect to the SMTP server')
else:
msg = self._cw._('emails successfully sent')
--- a/doc/book/en/devweb/internationalization.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/devweb/internationalization.rst Fri Oct 28 10:32:48 2011 +0200
@@ -26,7 +26,9 @@
In the Python code and cubicweb-tal templates translatable strings can be
marked in one of the following ways :
- * by using the *built-in* function `_` ::
+ * by using the *built-in* function `_`:
+
+ .. sourcecode:: python
class PrimaryView(EntityView):
"""the full view of an non final entity"""
@@ -35,7 +37,9 @@
OR
- * by using the equivalent request's method ::
+ * by using the equivalent request's method:
+
+ .. sourcecode:: python
class NoResultView(View):
"""default view when no result has been found"""
@@ -79,9 +83,12 @@
particular instance's schema as they are generated automatically. String for
various actions are also generated.
-For exemple the following schema ::
+For exemple the following schema:
- Class EntityA(EntityType):
+.. sourcecode:: python
+
+
+ class EntityA(EntityType):
relation_a2b = SubjectRelation('EntityB')
class EntityB(EntityType):
--- a/doc/book/en/devweb/views/primary.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/devweb/views/primary.rst Fri Oct 28 10:32:48 2011 +0200
@@ -180,7 +180,7 @@
from cubicweb.web.views.primary import Primaryview
class BlogEntryPrimaryView(PrimaryView):
- __select__ = PrimaryView.__select__ & is_instance('BlogEntry')
+ __select__ = PrimaryView.__select__ & is_instance('BlogEntry')
def render_entity_attributes(self, entity):
self.w(u'<p>published on %s</p>' %
--- a/doc/book/en/devweb/views/table.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/devweb/views/table.rst Fri Oct 28 10:32:48 2011 +0200
@@ -56,7 +56,7 @@
By the same way, you can display additional actions for the selected entities
by setting `add_view_actions` layout option to `True`. This will add actions
-returned by the view's :meth:`~cubicweb.web.views.TableMixIn.table_actions`.
+returned by the view's :meth:`~cubicweb.web.views.tableview.TableMixIn.table_actions`.
You can notice that all columns of the result set are not displayed. This is
because of given `headers`, implying to display only columns from 0 to
@@ -72,6 +72,7 @@
So another option would be to write this view using
:class:`~cubicweb.web.views.tableview.EntityTableView`, as below.
+.. sourcecode:: python
class ResourcesTable(EntityTableView):
__regid__ = 'resource.table'
--- a/doc/book/en/devweb/views/urlpublish.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/devweb/views/urlpublish.rst Fri Oct 28 10:32:48 2011 +0200
@@ -52,7 +52,7 @@
dict(rql=('Any X ORDERBY CD DESC LIMIT 20 WHERE X is BlogEntry,'
'X creation_date CD, X created_by U, '
'U login "%(user)s"'
- % {'user': r'\1'}, vid='rss'))),
+ % {'user': r'\1'}), vid='rss'))
]
When a url matches the regular expression, the view with the __regid__
--- a/doc/book/en/devweb/views/xmlrss.rst Thu Oct 27 18:19:00 2011 +0200
+++ b/doc/book/en/devweb/views/xmlrss.rst Fri Oct 28 10:32:48 2011 +0200
@@ -20,7 +20,9 @@
++++++++++++++++++++
Assuming you have several blog entries, click on the title of the
-search box in the left column. A larger search box should appear. Enter::
+search box in the left column. A larger search box should appear. Enter:
+
+.. sourcecode:: sql
Any X ORDERBY D WHERE X is BlogEntry, X creation_date D
@@ -38,14 +40,18 @@
That's it, you have a RSS channel for your blog.
-Try again with::
+Try again with:
+
+.. sourcecode:: sql
Any X ORDERBY D WHERE X is BlogEntry, X creation_date D,
X entry_of B, B title "MyLife"
Another RSS channel, but a bit more focused.
-A last one for the road::
+A last one for the road:
+
+.. sourcecode:: sql
Any C ORDERBY D WHERE C is Comment, C creation_date D LIMIT 15
--- a/selectors.py Thu Oct 27 18:19:00 2011 +0200
+++ b/selectors.py Fri Oct 28 10:32:48 2011 +0200
@@ -424,7 +424,7 @@
- else the number of matching values
- Notice `mode`='any' with a single expected value has no effect at all.
+ Notice `mode` = 'any' with a single expected value has no effect at all.
"""
def __init__(self, *expected, **kwargs):
assert expected, self
@@ -654,7 +654,7 @@
Page size is searched in (respecting order):
* a `page_size` argument
* a `page_size` form parameters
- * the :ref:`navigation.page-size` property
+ * the `navigation.page-size` property (see :ref:`PersistentProperties`)
"""
def __init__(self, nbpages=1):
assert nbpages > 0
--- a/server/hook.py Thu Oct 27 18:19:00 2011 +0200
+++ b/server/hook.py Fri Oct 28 10:32:48 2011 +0200
@@ -444,8 +444,8 @@
"""accept if parameters specified as initializer arguments are specified
in named arguments given to the selector
- :param *expected: parameters (eg `basestring`) which are expected to be
- found in named arguments (kwargs)
+ :param \*expected: parameters (eg `basestring`) which are expected to be
+ found in named arguments (kwargs)
"""
def __init__(self, *expected, **more):
self.expected = expected
--- a/web/request.py Thu Oct 27 18:19:00 2011 +0200
+++ b/web/request.py Fri Oct 28 10:32:48 2011 +0200
@@ -381,7 +381,7 @@
def user_callback(self, cb, cbargs, *args, **kwargs):
"""register the given user callback and return a URL which can
be inserted in an HTML view. When the URL is accessed, the
- callback function will be called (as 'cb(req, *cbargs)', and a
+ callback function will be called (as 'cb(req, \*cbargs)', and a
message will be displayed in the web interface. The third
positional argument must be 'msg', containing the message.
@@ -575,7 +575,8 @@
self.html_headers.add_onload(jscode)
def add_js(self, jsfiles, localfile=True):
- """specify a list of JS files to include in the HTML headers
+ """specify a list of JS files to include in the HTML headers.
+
:param jsfiles: a JS filename or a list of JS filenames
:param localfile: if True, the default data dir prefix is added to the
JS filename
@@ -591,7 +592,7 @@
iespec=u'[if lt IE 8]'):
"""specify a CSS file to include in the HTML headers
- :param cssfiles: a CSS filename or a list of CSS filenames
+ :param cssfiles: a CSS filename or a list of CSS filenames.
:param media: the CSS's media if necessary
:param localfile: if True, the default data dir prefix is added to the
CSS filename
--- a/web/views/tableview.py Thu Oct 27 18:19:00 2011 +0200
+++ b/web/views/tableview.py Fri Oct 28 10:32:48 2011 +0200
@@ -34,12 +34,12 @@
.. autoclass:: cubicweb.web.views.tableview.EntityTableView
:members:
-.. autoclass:: cubicweb.web.views.pyview.PyValTableView
+.. autoclass:: cubicweb.web.views.pyviews.PyValTableView
:members:
All those classes are rendered using a *layout*:
-.. autoclass:: cubicweb.web.views.pyview.TableLayout
+.. autoclass:: cubicweb.web.views.tableview.TableLayout
:members:
There is by default only on table layout, using the 'table_layout' identifier,
@@ -56,7 +56,7 @@
class below that is the common abstract base class for the three views defined
above and implements you own class.
-.. autoclass:: cubicweb.web.views.pyview.TableMixIn
+.. autoclass:: cubicweb.web.views.tableview.TableMixIn
:members:
"""
@@ -166,8 +166,8 @@
@cachedproperty
def initial_load(self):
- """We detect a bit heuristically if we are built for the first time of
- from subsequent calls by the form filter or by the pagination hooks
+ """We detect a bit heuristically if we are built for the first time.
+ or from subsequent calls by the form filter or by the pagination hooks.
"""
form = self._cw.form
return 'fromformfilter' not in form and '__start' not in form
@@ -307,10 +307,10 @@
class AbstractColumnRenderer(object):
"""Abstract base class for column renderer. Interface of a column renderer follows:
- .. automethod:: bind
- .. automethod:: render_header
- .. automethod:: render_cell
- .. automethod:: sortvalue
+ .. automethod:: cubicweb.web.views.tableview.AbstractColumnRenderer.bind
+ .. automethod:: cubicweb.web.views.tableview.AbstractColumnRenderer.render_header
+ .. automethod:: cubicweb.web.views.tableview.AbstractColumnRenderer.render_cell
+ .. automethod:: cubicweb.web.views.tableview.AbstractColumnRenderer.sortvalue
Attributes on this base class are:
@@ -323,7 +323,7 @@
:attr: `_cw`, the request object
:attr: `colid`, the column identifier
:attr: `attributes`, dictionary of attributes to put on the HTML tag when
- the cell is rendered
+ the cell is rendered
"""
attributes = {}
empty_cell_content = u' '
@@ -408,7 +408,7 @@
You may also want to overridde:
- .. automethod:: table_size
+ .. autoattribute:: cubicweb.web.views.tableview.TableMixIn.table_size
The :attr:`has_headers` boolean attribute tells if the table has some
headers to be displayed. Default to `True`.
@@ -464,7 +464,7 @@
"""Return a list of column renderers, one for each column to be
rendered. Prototype of a column renderer is described below:
- .. autoclass:: AbstractColumnRenderer
+ .. autoclass:: cubicweb.web.views.tableview.AbstractColumnRenderer
"""
raise NotImplementedError()
@@ -671,7 +671,7 @@
You may use the :meth:`entity` method to retrieve the main entity for a
given row number.
- .. automethod:: entity
+ .. automethod:: cubicweb.web.views.tableview.EntityTableColRenderer.entity
"""
def __init__(self, renderfunc=None, sortfunc=None, **kwargs):
if renderfunc is None:
@@ -759,9 +759,9 @@
:class:`RelatedEntityColRenderer` renderer for a column in the
:attr:`column_renderers` dictionary.
- .. autoclass:: EntityTableColRenderer
- .. autoclass:: MainEntityColRenderer
- .. autoclass:: RelatedEntityColRenderer
+ .. autoclass:: cubicweb.web.views.tableview.EntityTableColRenderer
+ .. autoclass:: cubicweb.web.views.tableview.MainEntityColRenderer
+ .. autoclass:: cubicweb.web.views.tableview.RelatedEntityColRenderer
"""
__abstract__ = True
default_column_renderer_class = EntityTableColRenderer