5 |
5 |
6 The Python API developped to interface with RQL is inspired from the standard db-api, |
6 The Python API developped to interface with RQL is inspired from the standard db-api, |
7 with a Connection object having the methods cursor, rollback and commit essentially. |
7 with a Connection object having the methods cursor, rollback and commit essentially. |
8 The most important method is the `execute` method of a cursor : |
8 The most important method is the `execute` method of a cursor : |
9 |
9 |
10 `execute(rqlstring, args=None, eid_key=None, build_descr=True)` |
10 `execute(rqlstring, args=None, cachekey=None, build_descr=True)` |
11 |
11 |
12 :rqlstring: the RQL query to execute (unicode) |
12 :rqlstring: the RQL query to execute (unicode) |
13 :args: if the query contains substitutions, a dictionary containing the values to use |
13 :args: if the query contains substitutions, a dictionary containing the values to use |
14 :eid_key: |
14 :cachekey: |
15 an implementation detail of the RQL cache implies that if a substitution |
15 an implementation detail of the RQL cache implies that if a substitution |
16 is used to introduce an eid *susceptible to raise the ambiguities in the query |
16 is used to introduce an eid *susceptible to raise the ambiguities in the query |
17 type resolution*, then we have to specify the corresponding key in the dictionary |
17 type resolution*, then we have to specify the corresponding key in the dictionary |
18 through this argument |
18 through this argument |
19 |
19 |
25 |
25 |
26 .. note:: |
26 .. note:: |
27 While executing update queries (SET, INSERT, DELETE), if a query generates |
27 While executing update queries (SET, INSERT, DELETE), if a query generates |
28 an error related to security, a rollback is automatically done on the current |
28 an error related to security, a rollback is automatically done on the current |
29 transaction. |
29 transaction. |
|
30 |
|
31 Executing RQL queries from a view or a hook |
|
32 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
|
33 When you're within code of the web interface, the db-api like connexion is |
|
34 handled by the request object. You should not have to access it directly, but |
|
35 use the `execute` method directly available on the request, eg: |
|
36 |
|
37 rset = self._cw.execute(rqlstring, kwargs) |
|
38 |
|
39 Similarly, on the server side (eg in hooks), there is no db-api connexion (since |
|
40 you're directly inside the data-server), so you'll have to use the execute method |
|
41 of the session object. |
|
42 |
|
43 |
|
44 Important note about proper usage of .execute |
|
45 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ |
|
46 |
|
47 Let's say you want to get T which is in configuration C, this translates to: |
|
48 |
|
49 .. sourcecode:: python |
|
50 |
|
51 self._cw.execute('Any T WHERE T in_conf C, C eid %s' % entity.eid) |
|
52 |
|
53 But it can also be written in a syntax that will benefit from the use |
|
54 of a cache on the RQL server side: |
|
55 |
|
56 .. sourcecode:: python |
|
57 |
|
58 self._cw.execute('Any T WHERE T in_conf C, C eid %(x)s', {'x': entity.eid}, 'x') |
|
59 |
|
60 Beside proper usage of the `args` argument, notice the latest argument: this is what's called |
|
61 the cache key. The cache key should be either a string or a tuple containing the names of keys |
|
62 in args which are referencing eids. *YOU MUST SET THIS PROPERLY* if you don't want weird result |
|
63 on queries which have ambigous solutions deambiguified by specifing an eid. So the good habit is: |
|
64 *always put in the cache key all eid keys*. |
|
65 |
|
66 The syntax tree is build once for the "generic" RQL and can be re-used |
|
67 with a number of different eid. |
|
68 |
|
69 Alternativelly, some of the common data related to an entity can be obtained from |
|
70 the top-level `entity.related()` method (which is used under the hood by the orm |
|
71 when you use attribute access notation on an entity to get a relation. The above |
|
72 would then be translated to: |
|
73 |
|
74 .. sourcecode:: python |
|
75 |
|
76 entity.related('in_conf', 'object') |
|
77 |
|
78 The `related()` method, as more generally others orm methods, makes extensive use |
|
79 of the cache mechanisms so you don't have to worry about them. Additionnaly this |
|
80 use will get you commonly used attributes that you will be able to use in your |
|
81 view generation without having to ask the data backend. |
|
82 |