« New 'Back in Business' FOAF specification | Main | Calling one page template inside another »
April 18, 2005
How to do RDF with Zope / ZPT
I've been trying to generate FOAF RDF from a Page Template. This has proven quite tricky. Zope 2.7 seems to stop wanting to parse and render the template if you change the content-type to text/xml
from text/html
.
This is not only a pain but is also intermittent.
The first thing I had to do therefore was re-set the content-type in the response header as follows, leaving the template content-type as text/html
so the ZPT engine would parse it:
<tal:block tal:define="
dummy python: container.REQUEST.RESPONSE.setHeader('Content-Type', 'text/xml');" />
Then I had to use tal:replace
to put the XML declaration back in:
<tal:block tal:define="dummy python:
container.REQUEST.RESPONSE.setHeader('Content-Type', 'text/xml');"
tal:replace="structure
string:<?xml version="1.0"?>"/>
Because I wanted to use the same template for single FOAFs and multiples I had to test for a foaf_email
parameter in the request. This is doable with has_key
.
However, because tal:condition
affects both subsequent tal:define
statements and the rendering of any child nodes within the block where it is called, and scope of tal:define
vars is limited to the current block, I've had to resort to passing variables up into the request namespace. This is due to the lack of a syntactic equivalent of <dtml-if>..<dtml-else>
. This gives very obfuscatory code:
<tal:block tal:define="
request python: container.REQUEST;
email python: None;
where_clause string: where 1;
wc python: request.set('where_clause', where_clause);
">
<tal:block tal:condition="python:request.has_key('foaf_email')">
<tal:block tal:define="
email python: request['foaf_email'];
where_clause python:' where foaf_email=\'' + str(email) + '\'';
wc python: request.set('where_clause', where_clause);
"/>
</tal:block>
<rdf:RDF
xmlns:tal="http://xml.zope.org/namespaces/tal"
xmlns:vcard="http://www.w3.org/2001/vcard-rdf/3.0#"
xmlns:mofoaf="http://minnesota.ncl.ac.uk/mofoaf/1.0/"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:rdfs="http://www.w3.org/"
xmlns:foaf="http://xmlns.com/foaf/0.1/"
xmlns:dc="http://purl.org/dc/elements/1.1"
tal:define="
foaf_recs
python:root.generic_query(query_sql='select * from ltsn01_ng.01_foafs' + request['where_clause']);
work_url string:http://www.ltsn-01.ac.uk;
info_url_stem python: work_url + '/new_site/contact/person_details?foaf_id=';
">
.....RDF stuff here.....
</rdf:RDF>
</tal:block>
You'll see the where clause for the SQL is fished out of the request namespace.
The full template is here:
Hmmm.. Seems if I'd read my own posts I could have done it with a PHP like global
statement instead.
Posted by pj at April 18, 2005 01:24 PM