Moved markdown parser to a module

This commit is contained in:
Starbeamrainbowlabs 2015-05-27 10:32:13 +01:00
parent 6bf33a415a
commit 5f33d9a6a4
5 changed files with 297 additions and 234 deletions

122
core.php
View File

@ -316,117 +316,6 @@ class page_renderer
}
}
////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////// Slimdown /////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////// %slimdown% //
////////////////////////////////////////////////////////////////////////////////////////////
/**
* Slimdown - A very basic regex-based Markdown parser. Supports the
* following elements (and can be extended via Slimdown::add_rule()):
*
* - Headers
* - Links
* - Bold
* - Emphasis
* - Deletions
* - Quotes
* - Inline code
* - Blockquotes
* - Ordered/unordered lists
* - Horizontal rules
*
* Author: Johnny Broadway <johnny@johnnybroadway.com>
* Website: https://gist.github.com/jbroadway/2836900
* License: MIT
*/
/**
* Modified by Starbeamrainbowlabs (starbeamrainbowlabs)
*
* Changed bold to use single asterisks
* Changed italics to use single underscores
* Added one to add the heading levels (no <h1> tags allowed)
* Added wiki style internal link parsing
* Added wiki style internal link parsing with display text
*/
class Slimdown {
public static $rules = array (
'/\r\n/' => "\n", // new line normalisation
'/(#+)(.*)/' => 'self::header', // headers
'/(\*)(.*?)\1/' => '<strong>\2</strong>', // bold
'/(_)(.*?)\1/' => '<em>\2</em>', // emphasis
// todo test these
'/!\[(.*)\]\(([^\s]+)\s(\d+.+)\s(left|right)\)/' => '<img src="\2" alt="\1" style="max-width: \3; float: \4;" />', // images with size
'/!\[(.*)\]\(([^\s]+)\s(\d+.+)\)/' => '<img src="\2" alt="\1" style="max-width: \3;" />', // images with size
'/!\[(.*)\]\((.*)\)/' => '<img src="\2" alt="\1" />', // basic images
// todo end
'/\[\[([a-zA-Z0-9\_\- ]+)\|([a-zA-Z0-9\_\- ]+)\]\]/' => '<a href=\'index.php?page=\1\'>\2</a>', //internal links with display text
'/\[\[([a-zA-Z0-9\_\- ]+)\]\]/' => '<a href=\'index.php?page=\1\'>\1</a>', //internal links
'/\[([^\[]+)\]\(([^\)]+)\)/' => '<a href=\'\2\' target=\'_blank\'>\1</a>', // links
'/\~\~(.*?)\~\~/' => '<del>\1</del>', // del
'/\:\"(.*?)\"\:/' => '<q>\1</q>', // quote
'/`(.*?)`/' => '<code>\1</code>', // inline code
'/\n\s*(\*|-)(.*)/' => 'self::ul_list', // ul lists
'/\n[0-9]+\.(.*)/' => 'self::ol_list', // ol lists
'/\n(&gt;|\>)(.*)/' => 'self::blockquote', // blockquotes
'/\n-{3,}/' => "\n<hr />", // horizontal rule
'/\n([^\n]+)\n\n/' => 'self::para', // add paragraphs
'/<\/ul>\s?<ul>/' => '', // fix extra ul
'/<\/ol>\s?<ol>/' => '', // fix extra ol
'/<\/blockquote><blockquote>/' => "\n" // fix extra blockquote
);
private static function para ($regs) {
$line = $regs[1];
$trimmed = trim ($line);
if (preg_match ('/^<\/?(ul|ol|li|h|p|bl)/', $trimmed)) {
return "\n" . $line . "\n";
}
return sprintf ("\n<p>%s</p>\n", $trimmed);
}
private static function ul_list ($regs) {
$item = $regs[2];
return sprintf ("\n<ul>\n\t<li>%s</li>\n</ul>", trim($item));
}
private static function ol_list ($regs) {
$item = $regs[1];
return sprintf ("\n<ol>\n\t<li>%s</li>\n</ol>", trim($item));
}
private static function blockquote ($regs) {
$item = $regs[2];
return sprintf ("\n<blockquote>%s</blockquote>", trim($item));
}
private static function header ($regs) {
list ($tmp, $chars, $header) = $regs;
$level = strlen ($chars);
return sprintf ('<h%d>%s</h%d>', $level + 1, trim($header), $level + 1);
}
/**
* Add a rule.
*/
public static function add_rule ($regex, $replacement) {
self::$rules[$regex] = $replacement;
}
/**
* Render some Markdown into HTML.
*/
public static function render ($text) {
foreach (self::$rules as $regex => $replacement) {
if (is_callable ( $replacement)) {
$text = preg_replace_callback ($regex, $replacement, $text);
} else {
$text = preg_replace ($regex, $replacement, $text);
}
}
return trim ($text);
}
}
////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////
//////////////// Functions ////////////////
///////////////////////////////////////////
@ -486,6 +375,17 @@ function add_action($action_name, $func)
$actions->$action_name = $func;
}
// Function to register a new parser. If multiple parsers are registered then
// only the last parser registered will actually be used.
$parse_page_source = function() {
throw new Exception("No parser registered!");
};
function add_parser($parser_code)
{
global $parse_page_source;
$parse_page_source = $parser_code;
}
//////////////////////////////////////////////////////////////////

260
index.php
View File

@ -470,117 +470,6 @@ class page_renderer
}
}
////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////// Slimdown /////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////// %slimdown% //
////////////////////////////////////////////////////////////////////////////////////////////
/**
* Slimdown - A very basic regex-based Markdown parser. Supports the
* following elements (and can be extended via Slimdown::add_rule()):
*
* - Headers
* - Links
* - Bold
* - Emphasis
* - Deletions
* - Quotes
* - Inline code
* - Blockquotes
* - Ordered/unordered lists
* - Horizontal rules
*
* Author: Johnny Broadway <johnny@johnnybroadway.com>
* Website: https://gist.github.com/jbroadway/2836900
* License: MIT
*/
/**
* Modified by Starbeamrainbowlabs (starbeamrainbowlabs)
*
* Changed bold to use single asterisks
* Changed italics to use single underscores
* Added one to add the heading levels (no <h1> tags allowed)
* Added wiki style internal link parsing
* Added wiki style internal link parsing with display text
*/
class Slimdown {
public static $rules = array (
'/\r\n/' => "\n", // new line normalisation
'/(#+)(.*)/' => 'self::header', // headers
'/(\*)(.*?)\1/' => '<strong>\2</strong>', // bold
'/(_)(.*?)\1/' => '<em>\2</em>', // emphasis
// todo test these
'/!\[(.*)\]\(([^\s]+)\s(\d+.+)\s(left|right)\)/' => '<img src="\2" alt="\1" style="max-width: \3; float: \4;" />', // images with size
'/!\[(.*)\]\(([^\s]+)\s(\d+.+)\)/' => '<img src="\2" alt="\1" style="max-width: \3;" />', // images with size
'/!\[(.*)\]\((.*)\)/' => '<img src="\2" alt="\1" />', // basic images
// todo end
'/\[\[([a-zA-Z0-9\_\- ]+)\|([a-zA-Z0-9\_\- ]+)\]\]/' => '<a href=\'index.php?page=\1\'>\2</a>', //internal links with display text
'/\[\[([a-zA-Z0-9\_\- ]+)\]\]/' => '<a href=\'index.php?page=\1\'>\1</a>', //internal links
'/\[([^\[]+)\]\(([^\)]+)\)/' => '<a href=\'\2\' target=\'_blank\'>\1</a>', // links
'/\~\~(.*?)\~\~/' => '<del>\1</del>', // del
'/\:\"(.*?)\"\:/' => '<q>\1</q>', // quote
'/`(.*?)`/' => '<code>\1</code>', // inline code
'/\n\s*(\*|-)(.*)/' => 'self::ul_list', // ul lists
'/\n[0-9]+\.(.*)/' => 'self::ol_list', // ol lists
'/\n(&gt;|\>)(.*)/' => 'self::blockquote', // blockquotes
'/\n-{3,}/' => "\n<hr />", // horizontal rule
'/\n([^\n]+)\n\n/' => 'self::para', // add paragraphs
'/<\/ul>\s?<ul>/' => '', // fix extra ul
'/<\/ol>\s?<ol>/' => '', // fix extra ol
'/<\/blockquote><blockquote>/' => "\n" // fix extra blockquote
);
private static function para ($regs) {
$line = $regs[1];
$trimmed = trim ($line);
if (preg_match ('/^<\/?(ul|ol|li|h|p|bl)/', $trimmed)) {
return "\n" . $line . "\n";
}
return sprintf ("\n<p>%s</p>\n", $trimmed);
}
private static function ul_list ($regs) {
$item = $regs[2];
return sprintf ("\n<ul>\n\t<li>%s</li>\n</ul>", trim($item));
}
private static function ol_list ($regs) {
$item = $regs[1];
return sprintf ("\n<ol>\n\t<li>%s</li>\n</ol>", trim($item));
}
private static function blockquote ($regs) {
$item = $regs[2];
return sprintf ("\n<blockquote>%s</blockquote>", trim($item));
}
private static function header ($regs) {
list ($tmp, $chars, $header) = $regs;
$level = strlen ($chars);
return sprintf ('<h%d>%s</h%d>', $level + 1, trim($header), $level + 1);
}
/**
* Add a rule.
*/
public static function add_rule ($regex, $replacement) {
self::$rules[$regex] = $replacement;
}
/**
* Render some Markdown into HTML.
*/
public static function render ($text) {
foreach (self::$rules as $regex => $replacement) {
if (is_callable ( $replacement)) {
$text = preg_replace_callback ($regex, $replacement, $text);
} else {
$text = preg_replace ($regex, $replacement, $text);
}
}
return trim ($text);
}
}
////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////
//////////////// Functions ////////////////
///////////////////////////////////////////
@ -640,6 +529,17 @@ function add_action($action_name, $func)
$actions->$action_name = $func;
}
// Function to register a new parser. If multiple parsers are registered then
// only the last parser registered will actually be used.
$parse_page_source = function() {
throw new Exception("No parser registered!");
};
function add_parser($parser_code)
{
global $parse_page_source;
$parse_page_source = $parser_code;
}
//////////////////////////////////////////////////////////////////
@ -1202,13 +1102,13 @@ register_module([
register_module([
"name" => "Page viewer",
"version" => "0.6",
"version" => "0.7",
"author" => "Starbeamrainbowlabs",
"description" => "Allows you to view pages. You should include this one.",
"id" => "page-view",
"code" => function() {
add_action("view", function() {
global $pageindex, $settings, $page;
global $pageindex, $settings, $page, $parse_page_source;
//check to make sure that the page exists
if(!isset($pageindex->$page))
@ -1231,11 +1131,11 @@ register_module([
$title = "$page - $settings->sitename";
$content = "<h1>$page</h1>";
$slimdown_start = microtime(true);
$parsing_start = microtime(true);
$content .= Slimdown::render(file_get_contents("$page.md"));
$content .= $parse_page_source(file_get_contents("$page.md"));
$content .= "\n\t<!-- Took " . (microtime(true) - $slimdown_start) . " seconds to parse markdown -->\n";
$content .= "\n\t\t<!-- Took " . (microtime(true) - $parsing_start) . " seconds to parse page source -->\n";
if(isset($_GET["printable"]) and $_GET["printable"] === "yes")
exit(page_renderer::render_minimal($title, $content));
@ -1247,6 +1147,134 @@ register_module([
register_module([
"name" => "Deault Parser",
"version" => "0.7",
"author" => "Johnny Broadway & Starbeamrainbowlabs",
"description" => "The default parser for Pepperminty Wiki. Based on Johnny Broadway's Slimdown (with more than a few modifications). This parser's features are documented in the help page.",
"id" => "parser-default",
"code" => function() {
add_parser(function($markdown) {
return Slimdown::render($markdown);
});
}
]);
////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////// Slimdown /////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////// %slimdown% //
////////////////////////////////////////////////////////////////////////////////////////////
/**
* Slimdown - A very basic regex-based Markdown parser. Supports the
* following elements (and can be extended via Slimdown::add_rule()):
*
* - Headers
* - Links
* - Bold
* - Emphasis
* - Deletions
* - Quotes
* - Inline code
* - Blockquotes
* - Ordered/unordered lists
* - Horizontal rules
*
* Author: Johnny Broadway <johnny@johnnybroadway.com>
* Website: https://gist.github.com/jbroadway/2836900
* License: MIT
*/
/**
* Modified by Starbeamrainbowlabs (starbeamrainbowlabs)
*
* Changed bold to use single asterisks
* Changed italics to use single underscores
* Added one to add the heading levels (no <h1> tags allowed)
* Added wiki style internal link parsing
* Added wiki style internal link parsing with display text
* Added image support
*/
class Slimdown {
public static $rules = array (
'/\r\n/' => "\n", // new line normalisation
'/(#+)(.*)/' => 'self::header', // headers
'/(\*)(.*?)\1/' => '<strong>\2</strong>', // bold
'/(_)(.*?)\1/' => '<em>\2</em>', // emphasis
// todo test these
'/!\[(.*)\]\(([^\s]+)\s(\d+.+)\s(left|right)\)/' => '<img src="\2" alt="\1" style="max-width: \3; float: \4;" />', // images with size
'/!\[(.*)\]\(([^\s]+)\s(\d+.+)\)/' => '<img src="\2" alt="\1" style="max-width: \3;" />', // images with size
'/!\[(.*)\]\((.*)\)/' => '<img src="\2" alt="\1" />', // basic images
// todo end
'/\[\[([a-zA-Z0-9\_\- ]+)\|([a-zA-Z0-9\_\- ]+)\]\]/' => '<a href=\'index.php?page=\1\'>\2</a>', //internal links with display text
'/\[\[([a-zA-Z0-9\_\- ]+)\]\]/' => '<a href=\'index.php?page=\1\'>\1</a>', //internal links
'/\[([^\[]+)\]\(([^\)]+)\)/' => '<a href=\'\2\' target=\'_blank\'>\1</a>', // links
'/\~\~(.*?)\~\~/' => '<del>\1</del>', // del
'/\:\"(.*?)\"\:/' => '<q>\1</q>', // quote
'/`(.*?)`/' => '<code>\1</code>', // inline code
'/\n\s*(\*|-)(.*)/' => 'self::ul_list', // ul lists
'/\n[0-9]+\.(.*)/' => 'self::ol_list', // ol lists
'/\n(&gt;|\>)(.*)/' => 'self::blockquote', // blockquotes
'/\n-{3,}/' => "\n<hr />", // horizontal rule
'/\n([^\n]+)\n\n/' => 'self::para', // add paragraphs
'/<\/ul>\s?<ul>/' => '', // fix extra ul
'/<\/ol>\s?<ol>/' => '', // fix extra ol
'/<\/blockquote><blockquote>/' => "\n" // fix extra blockquote
);
private static function para ($regs) {
$line = $regs[1];
$trimmed = trim ($line);
if (preg_match ('/^<\/?(ul|ol|li|h|p|bl)/', $trimmed)) {
return "\n" . $line . "\n";
}
return sprintf ("\n<p>%s</p>\n", $trimmed);
}
private static function ul_list ($regs) {
$item = $regs[2];
return sprintf ("\n<ul>\n\t<li>%s</li>\n</ul>", trim($item));
}
private static function ol_list ($regs) {
$item = $regs[1];
return sprintf ("\n<ol>\n\t<li>%s</li>\n</ol>", trim($item));
}
private static function blockquote ($regs) {
$item = $regs[2];
return sprintf ("\n<blockquote>%s</blockquote>", trim($item));
}
private static function header ($regs) {
list ($tmp, $chars, $header) = $regs;
$level = strlen ($chars);
return sprintf ('<h%d>%s</h%d>', $level + 1, trim($header), $level + 1);
}
/**
* Add a rule.
*/
public static function add_rule ($regex, $replacement) {
self::$rules[$regex] = $replacement;
}
/**
* Render some Markdown into HTML.
*/
public static function render ($text) {
foreach (self::$rules as $regex => $replacement) {
if (is_callable ( $replacement)) {
$text = preg_replace_callback ($regex, $replacement, $text);
} else {
$text = preg_replace ($regex, $replacement, $text);
}
}
return trim ($text);
}
}
////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////
// %next_module% //

View File

@ -81,10 +81,18 @@
},
{
"name": "Page viewer",
"version": "0.6",
"version": "0.7",
"author": "Starbeamrainbowlabs",
"description": "Allows you to view pages. You should include this one.",
"id": "page-view",
"lastupdate": 1432497918
"lastupdate": 1432719098
},
{
"name": "Deault Parser",
"version": "0.7",
"author": "Johnny Broadway & Starbeamrainbowlabs",
"description": "The default parser for Pepperminty Wiki. Based on Johnny Broadway's Slimdown (with more than a few modifications). This parser's features are documented in the help page.",
"id": "parser-default",
"lastupdate": 1432718472
}
]

View File

@ -1,13 +1,13 @@
<?php
register_module([
"name" => "Page viewer",
"version" => "0.6",
"version" => "0.7",
"author" => "Starbeamrainbowlabs",
"description" => "Allows you to view pages. You should include this one.",
"id" => "page-view",
"code" => function() {
add_action("view", function() {
global $pageindex, $settings, $page;
global $pageindex, $settings, $page, $parse_page_source;
//check to make sure that the page exists
if(!isset($pageindex->$page))
@ -30,11 +30,11 @@ register_module([
$title = "$page - $settings->sitename";
$content = "<h1>$page</h1>";
$slimdown_start = microtime(true);
$parsing_start = microtime(true);
$content .= Slimdown::render(file_get_contents("$page.md"));
$content .= $parse_page_source(file_get_contents("$page.md"));
$content .= "\n\t<!-- Took " . (microtime(true) - $slimdown_start) . " seconds to parse markdown -->\n";
$content .= "\n\t\t<!-- Took " . (microtime(true) - $parsing_start) . " seconds to parse page source -->\n";
if(isset($_GET["printable"]) and $_GET["printable"] === "yes")
exit(page_renderer::render_minimal($title, $content));

127
modules/parser-default.php Normal file
View File

@ -0,0 +1,127 @@
<?php
register_module([
"name" => "Deault Parser",
"version" => "0.7",
"author" => "Johnny Broadway & Starbeamrainbowlabs",
"description" => "The default parser for Pepperminty Wiki. Based on Johnny Broadway's Slimdown (with more than a few modifications). This parser's features are documented in the help page.",
"id" => "parser-default",
"code" => function() {
add_parser(function($markdown) {
return Slimdown::render($markdown);
});
}
]);
////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////// Slimdown /////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////// %slimdown% //
////////////////////////////////////////////////////////////////////////////////////////////
/**
* Slimdown - A very basic regex-based Markdown parser. Supports the
* following elements (and can be extended via Slimdown::add_rule()):
*
* - Headers
* - Links
* - Bold
* - Emphasis
* - Deletions
* - Quotes
* - Inline code
* - Blockquotes
* - Ordered/unordered lists
* - Horizontal rules
*
* Author: Johnny Broadway <johnny@johnnybroadway.com>
* Website: https://gist.github.com/jbroadway/2836900
* License: MIT
*/
/**
* Modified by Starbeamrainbowlabs (starbeamrainbowlabs)
*
* Changed bold to use single asterisks
* Changed italics to use single underscores
* Added one to add the heading levels (no <h1> tags allowed)
* Added wiki style internal link parsing
* Added wiki style internal link parsing with display text
* Added image support
*/
class Slimdown {
public static $rules = array (
'/\r\n/' => "\n", // new line normalisation
'/(#+)(.*)/' => 'self::header', // headers
'/(\*)(.*?)\1/' => '<strong>\2</strong>', // bold
'/(_)(.*?)\1/' => '<em>\2</em>', // emphasis
// todo test these
'/!\[(.*)\]\(([^\s]+)\s(\d+.+)\s(left|right)\)/' => '<img src="\2" alt="\1" style="max-width: \3; float: \4;" />', // images with size
'/!\[(.*)\]\(([^\s]+)\s(\d+.+)\)/' => '<img src="\2" alt="\1" style="max-width: \3;" />', // images with size
'/!\[(.*)\]\((.*)\)/' => '<img src="\2" alt="\1" />', // basic images
// todo end
'/\[\[([a-zA-Z0-9\_\- ]+)\|([a-zA-Z0-9\_\- ]+)\]\]/' => '<a href=\'index.php?page=\1\'>\2</a>', //internal links with display text
'/\[\[([a-zA-Z0-9\_\- ]+)\]\]/' => '<a href=\'index.php?page=\1\'>\1</a>', //internal links
'/\[([^\[]+)\]\(([^\)]+)\)/' => '<a href=\'\2\' target=\'_blank\'>\1</a>', // links
'/\~\~(.*?)\~\~/' => '<del>\1</del>', // del
'/\:\"(.*?)\"\:/' => '<q>\1</q>', // quote
'/`(.*?)`/' => '<code>\1</code>', // inline code
'/\n\s*(\*|-)(.*)/' => 'self::ul_list', // ul lists
'/\n[0-9]+\.(.*)/' => 'self::ol_list', // ol lists
'/\n(&gt;|\>)(.*)/' => 'self::blockquote', // blockquotes
'/\n-{3,}/' => "\n<hr />", // horizontal rule
'/\n([^\n]+)\n\n/' => 'self::para', // add paragraphs
'/<\/ul>\s?<ul>/' => '', // fix extra ul
'/<\/ol>\s?<ol>/' => '', // fix extra ol
'/<\/blockquote><blockquote>/' => "\n" // fix extra blockquote
);
private static function para ($regs) {
$line = $regs[1];
$trimmed = trim ($line);
if (preg_match ('/^<\/?(ul|ol|li|h|p|bl)/', $trimmed)) {
return "\n" . $line . "\n";
}
return sprintf ("\n<p>%s</p>\n", $trimmed);
}
private static function ul_list ($regs) {
$item = $regs[2];
return sprintf ("\n<ul>\n\t<li>%s</li>\n</ul>", trim($item));
}
private static function ol_list ($regs) {
$item = $regs[1];
return sprintf ("\n<ol>\n\t<li>%s</li>\n</ol>", trim($item));
}
private static function blockquote ($regs) {
$item = $regs[2];
return sprintf ("\n<blockquote>%s</blockquote>", trim($item));
}
private static function header ($regs) {
list ($tmp, $chars, $header) = $regs;
$level = strlen ($chars);
return sprintf ('<h%d>%s</h%d>', $level + 1, trim($header), $level + 1);
}
/**
* Add a rule.
*/
public static function add_rule ($regex, $replacement) {
self::$rules[$regex] = $replacement;
}
/**
* Render some Markdown into HTML.
*/
public static function render ($text) {
foreach (self::$rules as $regex => $replacement) {
if (is_callable ( $replacement)) {
$text = preg_replace_callback ($regex, $replacement, $text);
} else {
$text = preg_replace ($regex, $replacement, $text);
}
}
return trim ($text);
}
}
////////////////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////////////////
?>