
- A client browser sent a request to DBPrism CMS like this http://localhost/dbprism/doc/Home.html, this request is routed to an Apache WebServer, for example, which is listening into the default port (80).
- The Apache WebServer is configured with mod_proxy to route every url starting at /dbprism/ to a Servlet container listening on the port 8888. mod_proxy rewrites the previous one url to a new url like this http://localhost:8888/dbprism/doc/Home.html.
- In this example an OC4J is configured with the dbprism.ear application file which defines the mount point /dbprism/ with an instance of Cocoon.
- OC4J pass the url to zone interpreted by Cocoon, Cocoon receives an url without the mount point (/dbprism/), that is /doc/Home.html. At this point Cocoon check for this page in his own cache and if the page is valid return the cached version, if not executes the steps 5 and 6.
- Based on the sitemap.xmap definition Cocoon resolves the url /doc/Home.html as a content generated by DBPrism, then DBPrism receives a request for an stored CMS page named /Home.html, note that doc was extracted because is used as DAD information (information for connecting to the database such as username, password, connect string and so on).
- A CMS stored procedure is executed to retrieve the specific page (/Home.html) and the page is returned to DBPrism engine, then the page returns in the inverted path passing to Cocoon (which formats the page and stores it in his Cache System), OC4J and Apache, finishing in the client browser.
- At this point a Content Writer (like me) writes a new version of the document /Home.xml (CMS version of /Home.html), and upload it with the CMS Upload Utility or with JDeveloper using CMS Addin utility.
- The table CONTENT which stores the XML document has a trigger after update which sends an http message to the Cocoon engine invalidating the cached content. The invalidation message is sent to the Container directly (not through Apache) and Cocoon routes the url /dbprism/x-dbprism-cache-invalidate to an XSP page which parses this message and contacts the DBPrism External Invalidator Server to mark the page /doc/Home.html as no longer valid. Note that the post message includes an username and password encode in a Base64 form. An example of invalidation message is showed below. After this step a new request comming from the client browser will be routed following the steps 4,5 and 6.
The triggers below are examples of invalidation triggers and are implemented on webcache.sql file, the purpose of these triggers are to control the cache coherence betwen Cocoon External Cache Invalidator Server and the content of the CMS tables.
These triggers are fired when a Content Writer updates information on the table PAGES which affects information on the page header, such as the author name, modification date and so on.
CREATE OR REPLACE TRIGGER CMS_PAGES_HEADER_TRIG
AFTER UPDATE
on pages
for each row
BEGIN
/* These triggers invalidate Cocoon's cms/sitemap.xmap entry:
<map:match pattern="header/**.xml">
<map:generate type="db" src="/header/{1}.xml">
<map:parameter name="Cache-Control" value="External"/>
<map:parameter name="printable" value="no"/>
</map:generate>
<map:serialize/>
</map:match>
<!-- personalided pages, note that header information about the user
and password is used to identified the page
-->
<map:match pattern="header/**.xml">
<map:generate src="/lheader/{1}.xml">
<map:parameter name="Copy-Request-Arguments" value="HeaderPattern=AUTHORIZATION"/>
<map:parameter name="Cache-Control" value="External"/>
<map:parameter name="printable" value="no"/>
</map:generate>
<map:serialize/>
</map:match>
*/
-- invalidates new neighbors
cache.invalidate('$cachehost',$cacheport,'/header'||:new.path,'.*\.xml$');
-- invalidates live are without parameter, then all personalized pages
cache.invalidate('$cachehost',$cacheport,'/lheader'||:new.path,'.*\.xml$');
-- invalidates old neighbors including old location of this page
if :new.path <> :old.path then
cache.invalidate('$cachehost',$cacheport,'/header'||:old.path,'.*\.xml$');
cache.invalidate('$cachehost',$cacheport,'/lheader'||:old.path,'.*\.xml$');
end if;
-- register id_page,parent for post chech trigger
pagesPak.g_id_page := :new.id_page;
pagesPak.g_parent := :new.parent;
pagesPak.g_old_id_page := :old.id_page;
pagesPak.g_old_parent := :old.parent;
END;
/
CREATE OR REPLACE TRIGGER CMS_PAGES_HEADER_POST_TRIG
AFTER UPDATE ON PAGES
DECLARE
v_name pages.name%TYPE;
v_path pages.path%TYPE;
begin
if pagesPak.g_parent is not null then
-- invalidate new parent
select name,path into v_name,v_path from pages where id_page=pagesPak.g_parent;
cache.invalidate('$cachehost',$cacheport,'/header'||v_path,v_name||'\.xml$');
cache.invalidate('$cachehost',$cacheport,'/lheader'||v_path,v_name||'\.xml$');
end if;
if pagesPak.g_old_parent is not null then
-- invalidate old parent
select name,path into v_name,v_path from pages where id_page=pagesPak.g_old_parent;
cache.invalidate('$cachehost',$cacheport,'/header'||v_path,v_name||'\.xml$');
cache.invalidate('$cachehost',$cacheport,'/lheader'||v_path,v_name||'\.xml$');
end if;
end;
This trigger is fired when a Content Writer updates information on the table CONTENT. This is mainly the content that the user see, note that the triggers is asociated to the table pages, but unlike the previous one this trigger is asociated to the column current_version and the security information these columns are updated when the Content Writer makes public an specific version of the document or change the permitions of the page.
CREATE OR REPLACE TRIGGER CMS_PAGES_CONTENT_TRIG
AFTER UPDATE
of current_version,u_read,u_write,u_admin,
g_read,g_write,g_admin,
o_read,o_write,o_admin
on pages
for each row
BEGIN
/* This triggers invalidate Cocoon's sitemap entry:
<map:match pattern="content/**.xml">
<map:generate type="db" src="/content/{1}.xml">
<map:parameter name="Cache-Control" value="External"/>
<map:parameter name="printable" value="no"/>
</map:generate>
<map:serialize/>
</map:match>
*/
cache.invalidate('$cachehost',$cacheport,'/content'||:new.path,:new.name||'\.xml$');
END;




