Site Generation
Page Generation
Page class hierarchy
Creating xml content
Make transform
Write result
Make Self Page Class
Site Generation
There is classes Page, PageFactory, SiteGenerator and PageRepository.
Main class SiteGenerator and function generate()
he take from PageRepository by interface IEnumeratePageId
each pageId of site, and by this pageId take from
PageFactory object of class Page, and call method
generate() of class Page:
from SiteGenerator.php
function generate(){
$this->pageRepository->pageIdEnumerator->reset();
while( $this->pageRepository->pageIdEnumerator->moveNext() ){
$id = $this->pageRepository->pageIdEnumerator->getElement();
$page = $this->pageFactory->getPageById( $id );
$page->generate();
}
}
|
But PageFactory return not Page :):
from PageFactory.php
function getPageById( $id ){
switch ( $id ){
case 'fp':
$page = new PageFP();
break;
default:
$page = new PageSite( $id );
break;
}
return $page;
}
|
i.e. for pageId = 'fp' PageFactory return object of
PageFP, for other: PageSite.
Some words about PageRepository he generate pageIdArray
from pages.xml by xslt transformation pages2text.xsl
(content/xslt/other/). But 'fp' dont exists in pages.xml it pageId
adds by hands:
from PageRepository.php
function PageRepository(){
$this->pageIdEnumerator = new Enumerator();
$this->pageIdEnumerator->setElements( $this->pageIdArray );
$this->pageIdArray = $this->getPagesId(); // from xml file pages.xml
$this->pageIdArray[] = 'fp'; // add first page
}
|
Page Generation
Page class hierarchy
There is hierarchy of pages:
Page <- PageBase <- PageFP
<- PageSite
Page - abstract
PageBase - abstract
PageFP - first page of site
PageSite - any page of site
Inheritance classes differs from Page only by constructor.
class Page makes next:
- make self xml-content
- make transformation by xslt
- write result
Creating xml content
Xml content are created by aggregation different xml sources.
xml-content start from
from Page.php
$this->xml = '<?xml version="1.0"?'.'>'."\n";
$this->xml .= '<page-of-site>'."\n";
$this->xml .= '#add_elements_here#'."\n";
$this->xml .= '</page-of-site>'."\n";
|
Class Page contain array of objects of class Element.
They are added in constructors of inheritance classes (PageBase, PageFP, PageSite).
Function makeXml() are dead simple:
from Page.php
function makeXml(){
foreach( $this->elements as $this->element ){
$this->element->makeContent();
$this->insertIntoXml();
}
}
|
Each object of class Element have attributes
name and content. And in function
insertIntoXml() by his name
xml-content-of-page are replaced by content of
element:
from Page.php
function insertIntoXml(){
$name = '#'.$this->element->getName().'#';
$this->xml = str_replace(
$name, $this->element->getContent(), $this->xml
);
}
|
Hierarchy of elements:
Element <- ElementFromFile
<- ElementFromText <- ElementForStub
<- ElementPageId
By manipulation this elements perform creating xml-content-of-page.
F.e. class PageBase constructor:
function PageBase(){
$this->Page();
$this->elements[] = new ElementForStub(
array( 'params' => array( 'text' => "#common#\n#pages#\n#add_elements_here#\n" ) )
);
// #common#
$this->elements[] = new ElementFromFile(
array( 'name' => 'common', 'params' => array( 'fileName' => 'db-xml:common.xml' ) )
);
// #pages#
$this->elements[] = new ElementFromFile(
array( 'name' => 'pages', 'params' => array( 'fileName' => 'db-xml:pages.xml' ) )
);
}
|
Element ElementForStub replace #add_elements_here#,
then each next element replace self token: first ElementFromFile
replace #common# (which was added by previous
ElementForStub element),
second ElementFromFile replace #pages#
(note different between params passed in constructors).
Element ElementFromFile working with class Content
which have function getContent():
from Content.php
function getContent( $fileRequest ){
list( $area, $file ) = explode( ':', $fileRequest );
$fileName = $this->root . $area . '/' . $file;
$this->file->setFileName( $fileName );
$this->file->load();
return $this->file->getData();
}
|
where $this->root are path to 'content' folder.
In that folder (if you remember) we have 3 folders (directories):
db-xml, pages, xslt.
And $fileRequest for function getContent()
are formed as {area}:{fileName}. F.e. if we want to get content of
file pages.xml in directory db-xml, we must make call:
$contentOfPagesXml = $objContent->getContent( 'xml:pages.xml' );.
And by same manner to directory pages or xslt.
And again about PageBase.
As you may note element ElementForStub add token
#add_elements_here# in xml-content-of-page. This mean that
we have not finished xml-content. And we must to make inheritance from
this class.
Let's inheritance PageFP class. His constructor:
from PageFP.php
function PageFP(){
$this->PageBase();
$this->pageId = 'index';
$this->elements[] = new ElementForStub(
array( 'params' => array( 'text' => "#page_content#\n#news#" ) )
);
// #page_content#
$this->elements[] = new ElementFromFile(
array( 'name' => 'page_content', 'params' => array( 'fileName' => 'pages:fp.xml' ) )
);
// #news#
$this->elements[] = new ElementFromFile(
array( 'name' => 'news', 'params' => array( 'fileName' => 'db-xml:news.xml' ) )
);
$this->xsltName = 'fp-page.xsl';
}
|
As you may note in this case element ElementForStub
(which replace token #add_elements_here#) dosnt have token
#add_elements_here#, i.e. in result we have finished xml-content.
xml-content will be contain files pages/fp.xml, db-xml/news.xml.
And xslt transformation will be made by fp-page.xsl.
For Page-package class PageSite, constructor:
from PageSite.php
function PageSite( $pageId ){
$this->PageBase();
$this->pageId = $pageId;
$this->elements[] = new ElementForStub(
array( 'params' => array( 'text' => "#page_id#\n#page_content#\n" ) )
);
// #page_id#
$this->elements[] = new ElementPageId( $pageId );
// #page_content#
$this->elements[] = new ElementFromFile(
array( 'name' => 'page_content', 'params' => array( 'fileName' => 'pages:'.$pageId.'.xml' ) )
);
$this->xsltName = 'site-page.xsl';
}
|
Note that there is element ElementPageId which add tag <pageId>.
After makeXml() we will have (i add comments):
from result of makeXml()
<?xml version="1.0"?>
<page-of-site>
<!-- xml-header and 'page-of-site' are from Page -->
<!-- 'common' was added in PageBase -->
<!-- this is file '/content/db-xml/common.xml' -->
<common>
<year>2003</year>
<name>xmlSiteMaker</name>
<email>nemilya@mail.ru</email>
</common>
<!-- 'pages' was added in PageBase -->
<!-- this is file '/content/db-xml/pages.xml' -->
<pages>
<page id="123" name="Name" descr="Description"/>
...
</pages>
<!-- 'pageId' was added in PageSite -->
<!-- this parameter passed in constructor by PageFactory -->
<pageId>about</pageId>
<!-- 'page-content' was added in PageSite -->
<!-- this is file '/content/page/{pageId}.xml' -->
<page-content>
<p>
This application for offline generation.
From xml documents by xslt transformation.
</p>
<p>
<sectionList/>
</p>
...
</page-content>
</page-of-site>
|
Make transform
Each class Page have attribute xsltName by which
xml-content are transformed: PageFP - 'fp-page.xsl',
PageSite - 'site-page.xsl'. You can see this in constructor.
Write result
For writing result there is class PageWriter. Class Page
in function write() call them:
from Page.php
function writePage(){
echo "write page: {$this->pageId}\n";
$this->pageWriter->setContent( $this->page );
$this->pageWriter->setPageId( $this->pageId );
$this->pageWriter->write();
}
|
Make Self Page Class
Of course you can write self class. Inheritance them from Page
or PageBase. And add to PageFactory in function
getPageById case for your pageId.
|