Navigation Menu

Skip to content
This repository has been archived by the owner on Dec 31, 2022. It is now read-only.

Commit

Permalink
Added support for multiple content segments in pages.
Browse files Browse the repository at this point in the history
Optimized access to app configuration (a bit).
  • Loading branch information
ludovicchabant committed Mar 1, 2011
1 parent b3ccae2 commit 336b8c5
Show file tree
Hide file tree
Showing 15 changed files with 288 additions and 121 deletions.
21 changes: 15 additions & 6 deletions tests/test-cases/PageContentsParsingTest.php
Expand Up @@ -61,12 +61,21 @@ public function testParsePageContents($testFilename, $expectedResultsFilename)
$yamlParser = new sfYamlParser();
$expectedResults = $yamlParser->parse(file_get_contents($expectedResultsFilename));
$expectedConfig = $p->validateConfig($expectedResults['config']);
foreach ($expectedResults as $key => $content) // Add the segment names.
{
if ($key == 'config') continue;
$expectedConfig['segments'][] = $key;
}

// Assert!
$this->assertEquals($expectedConfig, $p->getConfig());
$expectedContents = $expectedResults['contents'];
$actualContents = $p->getContents();
//die("/".$expectedContents."/".$actualContents."/");
$this->assertEquals($expectedContents, $actualContents);
// Start asserting!
$this->assertEquals($expectedConfig, $p->getConfig(), 'The configurations are not equivalent.');
$actualSegments = $p->getContentSegments();
foreach ($expectedResults as $key => $content)
{
if ($key == 'config') continue;

$this->assertArrayHasKey($key, $actualSegments, 'Expected a content segment named: ' . $key);
$this->assertEquals($content, $actualSegments[$key], 'The content segments are not equivalent.');
}
}
}
20 changes: 20 additions & 0 deletions tests/test-data/complex-header-page.html
@@ -0,0 +1,20 @@
---
this: is
a:
somewhat:
complicated: header
for: a
piecrust: page
but: that
is: not
too: bad
now: |
let's see if
---
stuff like this
---
won't break the parsing.
okay: now it should be good.
---
Yep, I don't think it's really that complicated, but you never know, it could break.
Hopefully it doesn't!
22 changes: 22 additions & 0 deletions tests/test-data/complex-header-page.yml
@@ -0,0 +1,22 @@
config:
this: is
a:
somewhat:
complicated: header
for: a
piecrust: page
but: that
is: not
too: bad
now: |
let's see if
---
stuff like this
---
won't break the parsing.
okay: now it should be good.

content: |
Yep, I don't think it's really that complicated, but you never know, it could break.
Hopefully it doesn't!
3 changes: 1 addition & 2 deletions tests/test-data/empty-page.yml
@@ -1,3 +1,2 @@
config:
contents: '.'
end: here.
content: '.'
5 changes: 2 additions & 3 deletions tests/test-data/just-content-page.yml
@@ -1,7 +1,6 @@
config:
contents: |
content: |
This is a page with stuff in it.
There's not much, but still this is something.
end: here.
2 changes: 1 addition & 1 deletion tests/test-data/simple-header-page.yml
@@ -1 +1 @@
config: title: Some simple pagecontents: | And now we have some content. Not much, still, but whatever, we are just testing stuff, here. end: here.
config: title: Some simple pagecontent: | And now we have some content. Not much, still, but whatever, we are just testing stuff, here.
Expand Down
11 changes: 11 additions & 0 deletions tests/test-data/two-segments-page.html
@@ -0,0 +1,11 @@
---
title: Two segments page
---
This is the default ('content') segment.

It should have those 2 paragraphs.
---menu---
This is the menu segment:
* with
* stuff
* in it
12 changes: 12 additions & 0 deletions tests/test-data/two-segments-page.yml
@@ -0,0 +1,12 @@
config:
title: Two segments page
content: |
This is the default ('content') segment.
It should have those 2 paragraphs.
menu: |
This is the menu segment:
* with
* stuff
* in it
105 changes: 86 additions & 19 deletions website/_piecrust/Page.class.php
Expand Up @@ -94,7 +94,7 @@ public function getCacheTime()
}
else
{
$this->cacheTime = $this->cache->getCacheTime($this->uri, 'html');
$this->cacheTime = $this->cache->getCacheTime($this->uri, 'json');
}
}
return $this->cacheTime;
Expand All @@ -118,19 +118,34 @@ public function getConfig()
*/
public function getConfigValue($key)
{
$config = $this->getConfig();
if (!isset($config[$key]))
if ($this->config === null)
{
$this->loadConfigAndContents();
}
if (!isset($this->config[$key]))
{
return null;
}
return $config[$key];
return $this->config[$key];
}

protected $contents;
/**
* Gets the page's formatted contents.
* Gets the page's formatted content.
*/
public function getContentSegment($segment = 'content')
{
if ($this->contents === null)
{
$this->loadConfigAndContents();
}
return $this->contents[$segment];
}

/**
* Gets all the page's formatted content segments.
*/
public function getContents()
public function getContentSegments()
{
if ($this->contents === null)
{
Expand Down Expand Up @@ -205,7 +220,7 @@ public function __construct(PieCrust $pieCrust, $uri)
}

$this->cache = null;
if ($pieCrust->getConfigValue('site', 'enable_cache') === true)
if ($pieCrust->getConfigValueUnchecked('site', 'enable_cache') === true)
{
$this->cache = new Cache($pieCrust->getCacheDir() . 'pages_r');
}
Expand Down Expand Up @@ -247,12 +262,12 @@ public static function parseUri(PieCrust $pieCrust, $uri)
$path = null;
$isPost = false;
$matches = array();
$postsPattern = Paginator::buildPostUrlPattern($pieCrust->getConfigValue('site', 'posts_urls'));
$postsPattern = Paginator::buildPostUrlPattern($pieCrust->getConfigValueUnchecked('site', 'posts_urls'));
if (preg_match($postsPattern, $uri, $matches))
{
// Requesting a post.
$baseDir = $pieCrust->getPostsDir();
$postsFs = $pieCrust->getConfigValue('site', 'posts_fs');
$postsFs = $pieCrust->getConfigValueUnchecked('site', 'posts_fs');
switch ($postsFs)
{
case 'hierarchy':
Expand Down Expand Up @@ -290,33 +305,48 @@ protected function loadConfigAndContents()
if ($enableCache and $this->isCached())
{
// Get the page from the cache.
$this->contents = $this->cache->read($this->uri, 'html');
$configText = $this->cache->read($this->uri, 'json');
$config = json_decode($configText, true);
$this->config = $this->buildValidatedConfig($config);

$this->contents = array();
foreach ($this->config['segments'] as $key)
{
$this->contents[$key] = $this->cache->read($this->uri, $key . '.html');
}
}
else
{
// Re-format/process the page.
$rawContents = file_get_contents($this->path);
$this->config = $this->parseConfig($rawContents);

$segments = $this->parseContentSegments($rawContents);
$this->contents = array();
$data = $this->getPageData();
$data = array_merge($data, $this->pieCrust->getSiteData());
$templateEngine = $this->pieCrust->getTemplateEngine();
ob_start();
$templateEngine->renderString($rawContents, $data);
$rawContents = ob_get_clean();

$this->contents = $this->pieCrust->formatText($rawContents, $this->config['format']);
foreach ($segments as $key => $content)
{
ob_start();
$templateEngine->renderString($content, $data);
$renderedContent = ob_get_clean();

$this->config['segments'][] = $key;
$this->contents[$key] = $this->pieCrust->formatText($renderedContent, $this->config['format']);
}

// Do not cache the page if 'volatile' data was accessed (e.g. the page displays
// the latest posts).
if ($enableCache and $this->cache != null and $this->wasVolatileDataAccessed($data) == false)
{
$this->cache->write($this->uri, 'html', $this->contents);
$yamlMarkup = json_encode($this->config);
$this->cache->write($this->uri, 'json', $yamlMarkup);

foreach (array_keys($segments) as $key)
{
$this->cache->write($this->uri, $key . '.html', $this->contents);
}
}
}
if (!isset($this->config) or $this->config == null or
Expand All @@ -334,7 +364,7 @@ protected function wasVolatileDataAccessed($data)
protected function parseConfig(&$rawContents)
{
$yamlHeaderMatches = array();
$hasYamlHeader = preg_match('/^(---\s*\n)((.*\n)*?)^(---\s*\n)/m', $rawContents, $yamlHeaderMatches);
$hasYamlHeader = preg_match('/\A(---\s*\n)((.*\n)*?)^(---\s*\n)/m', $rawContents, $yamlHeaderMatches);
if ($hasYamlHeader == true)
{
// Remove the YAML header from the raw contents string.
Expand All @@ -358,16 +388,53 @@ protected function parseConfig(&$rawContents)

return $this->buildValidatedConfig($config);
}

protected function parseContentSegments($rawContents)
{
$end = strlen($rawContents);
$matches = array();
$matchCount = preg_match_all('/^---(\w+)---\s*\n/m', $rawContents, $matches, PREG_PATTERN_ORDER | PREG_OFFSET_CAPTURE);
if ($matchCount > 0)
{
$contents = array();

if ($matches[0][0][1] > 0)
{
// There's some default content at the beginning.
$contents['content'] = substr($rawContents, 0, $matches[0][0][1]);
}

for ($i = 0; $i < $matchCount; ++$i)
{
// Get each segment as the text that's between the end of the current captured string
// and the beginning of the next captured string (or the end of the input text if
// the current is the last capture).
$matchStart = $matches[0][$i][1] + strlen($matches[0][$i][0]);
$matchEnd = ($i < $matchCount - 1) ? $matches[0][$i+1][1] : $end;
$segmentName = $matches[1][$i][0];
$segmentContent = substr($rawContents, $matchStart, $matchEnd - $matchStart);
$contents[$segmentName] = $segmentContent;
}

return $contents;
}
else
{
// No segments, just the content.
return array('content' => $rawContents);
}
}

protected function buildValidatedConfig($config)
{
// Add the default page config values.
$validatedConfig = array_merge(
array(
'layout' => ($this->isPost == true) ? PIECRUST_DEFAULT_POST_TEMPLATE_NAME : PIECRUST_DEFAULT_PAGE_TEMPLATE_NAME,
'format' => $this->pieCrust->getConfigValue('site', 'default_format'),
'format' => $this->pieCrust->getConfigValueUnchecked('site', 'default_format'),
'content_type' => 'html',
'title' => 'Untitled Page'
'title' => 'Untitled Page',
'segments' => array()
),
$config);
return $validatedConfig;
Expand Down
6 changes: 3 additions & 3 deletions website/_piecrust/PageRenderer.class.php
Expand Up @@ -16,7 +16,7 @@ public function render(Page $page, $extraData = null, $outputHeaders = true)

// Get the template engine and the page data.
$templateEngine = $this->pieCrust->getTemplateEngine();
$data = array('content' => $page->getContents());
$data = $page->getContentSegments();
$data = array_merge($data, $page->getPageData(), $this->pieCrust->getSiteData());
if ($extraData != null)
{
Expand Down Expand Up @@ -70,7 +70,7 @@ public static function setHeaders($contentType)
header("Content-type: text/plain; charset=utf-8");
break;
case 'css':
header('Content-type: text/css; charset=utf-8');
header("Content-type: text/css; charset=utf-8");
break;
case 'atom':
header("Content-type: application/atom+xml; charset=utf-8");
Expand All @@ -79,7 +79,7 @@ public static function setHeaders($contentType)
header("Content-type: application/rss+xml; charset=utf-8");
break;
case 'json':
header('Content-type: application/json; charset=utf-8');
header("Content-type: application/json; charset=utf-8");
break;
}
}
Expand Down
10 changes: 5 additions & 5 deletions website/_piecrust/Paginator.class.php
Expand Up @@ -112,9 +112,9 @@ public function buildPaginationData(array $postInfos)
if (count($postInfos) > 0)
{
// Load all the posts for the requested page number (page numbers start at '1').
$postsUrlFormat = $this->pieCrust->getConfigValue('site', 'posts_urls');
$postsPerPage = $this->pieCrust->getConfigValue('site', 'posts_per_page');
$postsDateFormat = $this->pieCrust->getConfigValue('site', 'posts_date_format');
$postsUrlFormat = $this->pieCrust->getConfigValueUnchecked('site', 'posts_urls');
$postsPerPage = $this->pieCrust->getConfigValueUnchecked('site', 'posts_per_page');
$postsDateFormat = $this->pieCrust->getConfigValueUnchecked('site', 'posts_date_format');
$offset = ($this->pageNumber - 1) * $postsPerPage;
$upperLimit = min($offset + $postsPerPage, count($postInfos));
for ($i = $offset; $i < $upperLimit; ++$i)
Expand All @@ -134,7 +134,7 @@ public function buildPaginationData(array $postInfos)
$postDateTime = strtotime($postInfo['year'] . '-' . $postInfo['month'] . '-' . $postInfo['day']);
$postData['date'] = date($postsDateFormat, $postDateTime);

$postContents = $post->getContents();
$postContents = $post->getContentSegment();
$postContentsSplit = preg_split('/^<!--\s*(more|(page)?break)\s*-->\s*$/m', $postContents, 2);
$postData['content'] = $postContentsSplit[0];

Expand All @@ -159,7 +159,7 @@ public function buildPaginationData(array $postInfos)
protected function getPostInfos()
{
$fs = new FileSystem($this->pieCrust);
$postsFs = $this->pieCrust->getConfigValue('site', 'posts_fs');
$postsFs = $this->pieCrust->getConfigValueUnchecked('site', 'posts_fs');
switch ($postsFs)
{
case 'hierarchy':
Expand Down

0 comments on commit 336b8c5

Please sign in to comment.