From df82d4838f9c2aeddd3f976f68703c3afac83bc0 Mon Sep 17 00:00:00 2001 From: Giuseppe Di Terlizzi Date: Thu, 26 Mar 2015 00:48:00 +0100 Subject: [PATCH] first commit --- README.md | 1 + action.php | 201 +++++++++++++++++++++++++++++++++++++++++++ conf/default.php | 13 +++ conf/metadata.php | 13 +++ lang/en/settings.php | 14 +++ plugin.info.txt | 7 ++ syntax.php | 48 +++++++++++ 7 files changed, 297 insertions(+) create mode 100644 README.md create mode 100644 action.php create mode 100644 conf/default.php create mode 100644 conf/metadata.php create mode 100644 lang/en/settings.php create mode 100644 plugin.info.txt create mode 100644 syntax.php diff --git a/README.md b/README.md new file mode 100644 index 0000000..37f1e34 --- /dev/null +++ b/README.md @@ -0,0 +1 @@ +# dokuwiki-plugin-semantic diff --git a/action.php b/action.php new file mode 100644 index 0000000..d200773 --- /dev/null +++ b/action.php @@ -0,0 +1,201 @@ + + * @copyright (C) 2015, Giuseppe Di Terlizzi + */ + +// must be run within Dokuwiki +if(!defined('DOKU_INC')) die(); + +/** + * Class Semantic Action Plugin + * + * Add semantic data to DokuWiki + */ +class action_plugin_semantic extends DokuWiki_Action_Plugin { + + /** + * Register events + * + * @param Doku_Event_Handler $controller + */ + public function register(Doku_Event_Handler $controller) { + + if ($this->getConf('useJSONLD')) { + $controller->register_hook('TPL_METAHEADER_OUTPUT', 'BEFORE', $this, 'json_ld'); + } + + if ($this->getConf('useDescription')) { + $controller->register_hook('TPL_METAHEADER_OUTPUT', 'BEFORE', $this, 'meta_description'); + } + + if ($this->getConf('useMetaAuthor')) { + $controller->register_hook('TPL_METAHEADER_OUTPUT', 'BEFORE', $this, 'meta_author'); + } + + } + + /** + * JSON-LD Event handler + * + * @param Doku_Event &$event + */ + public function json_ld(Doku_Event &$event, $param) { + + global $INFO; + global $ID; + + if ((bool) preg_match_all('/'.$this->getConf('excludedPages').'/', $ID)) { + return false; + } + + if ($INFO['perm'] > 0) { + + global $license; + global $auth; + global $conf; + + $meta = $INFO['meta']; + + if (isset($meta['semantic']['enabled']) && ! $meta['semantic']['enabled']) { + return false; + } + + if (isset($meta['date'])) { + + $type = ((isset($meta['semantic']['schema.org']['type'])) + ? $meta['semantic']['schema.org']['type'] + : $this->getConf('defaultSchemaOrgType')); + $user_data = $auth->getUserData($meta['user']); + $license_url = $license[$conf['license']]['url']; + $page_url = wl($ID, '', true); + $image_url = (($meta['relation']['firstimage']) ? ml($meta['relation']['firstimage'], '', true, '&', true) : null); + $description = trim(ltrim($meta['description']['abstract'], $meta['title'])); + $created = date(DATE_W3C, $meta['date']['created']); + $modified = date(DATE_W3C, $meta['date']['modified']); + + $json_ld = array( + '@context' => 'http://schema.org', + '@type' => $type, + 'headline' => $meta['title'], + 'name' => $meta['title'], + 'image' => array($image_url), + 'datePublished' => $created, + 'dateCreated' => $created, + 'dateModified' => $modified, + 'description' => $description, + 'license' => $license_url, + 'url' => $page_url, + ); + + if (isset($meta['creator']) && $meta['creator'] !== '') { + $json_ld['creator'] = array( + '@context' => 'http://schema.org', + '@type' => 'Person', + 'name' => $meta['creator'], + 'email' => $user_data['mail'] + ); + + foreach ($meta['contributor'] as $uid => $fullname) { + $contributor_data = $auth->getUserData($uid); + $json_ld['contributor'][] = array( + '@context' => 'http://schema.org', + '@type' => 'Person', + 'name' => $fullname, + 'email' => $contributor_data['mail'] + ); + } + + } + + if (isset($meta['relation']['references'])) { + + $json_ld_webpage = array( + '@context' => 'http://schema.org', + '@type' => 'WebPage' + ); + + foreach ($meta['relation']['references'] as $page => $status) { + if ($status) { + $json_ld_webpage['relatedLink'][] = wl($page, '', true); + } + } + + $event->data["script"][] = array ( + "type" => "application/ld+json", + "_data" => json_encode($json_ld_webpage), + ); + + } + + $event->data["script"][] = array ( + "type" => "application/ld+json", + "_data" => json_encode($json_ld), + ); + + } + } + + } + + + public function meta_description(Doku_Event &$event, $params) { + + global $INFO; + global $ID; + + if ((bool) preg_match_all('/'.$this->getConf('excludedPages').'/', $ID)) { + return false; + } + + if ($INFO['perm'] > 0) { + + $meta = $INFO['meta']; + + if ($meta['date'] && $meta['semantic']['enabled']) { + + $description = str_replace("\n", ' ', trim(ltrim($meta['description']['abstract'], $meta['title']))); + + $event->data['meta'][] = array( + 'name' => 'description', + 'content' => $description, + ); + + } + + } + + } + + + public function meta_author(Doku_Event &$event, $params) { + + global $INFO; + global $ID; + + if ((bool) preg_match_all('/'.$this->getConf('excludedPages').'/', $ID)) { + return false; + } + + if ($this->getConf('useMetaAuthor') && $INFO['perm'] > 0) { + + if ($meta['date'] && $meta['semantic']['enabled']) { + + $meta = $INFO['meta']; + + $event->data['meta'][] = array( + 'name' => 'author', + 'content' => $meta['creator'], + ); + + } + + } + + } + +} + diff --git a/conf/default.php b/conf/default.php new file mode 100644 index 0000000..b676ebf --- /dev/null +++ b/conf/default.php @@ -0,0 +1,13 @@ + + */ + +$conf['useJSONLD'] = 1; +$conf['defaultSchemaOrgType'] = 'Article'; +$conf['useMetaDescription'] = 1; +$conf['useMetaAuthor'] = 1; +$conf['excludedPages'] = '(wiki|playground)'; + diff --git a/conf/metadata.php b/conf/metadata.php new file mode 100644 index 0000000..b97ff92 --- /dev/null +++ b/conf/metadata.php @@ -0,0 +1,13 @@ + + */ + +$meta['useMetaDescription'] = array('onoff'); +$meta['useMetaAuthor'] = array('onoff'); +$meta['useJSONLD'] = array('onoff'); +$meta['defaultSchemaOrgType'] = array('multichoice','_choices' => array('Article', 'NewsArticle', 'TechArticle', 'BlogPosting')); +$meta['excludedPages'] = array('regex'); + diff --git a/lang/en/settings.php b/lang/en/settings.php new file mode 100644 index 0000000..f86bff2 --- /dev/null +++ b/lang/en/settings.php @@ -0,0 +1,14 @@ + + */ + +// for the configuration manager +$lang['useMetaDescription'] = 'Add description meta tag'; +$lang['useMetaAuthor'] = 'Add author meta tag'; +$lang['useJSONLD'] = 'Add JSON-LD'; +$lang['defaultSchemaOrgType'] = 'Default Schema.org type for JSON-LD'; +$lang['excludedPages'] = 'Excluded pages (insert a regex)'; diff --git a/plugin.info.txt b/plugin.info.txt new file mode 100644 index 0000000..8c67f9c --- /dev/null +++ b/plugin.info.txt @@ -0,0 +1,7 @@ +base semantic +author Giuseppe Di Terlizzi +email giuseppe.diterlizzi@gmail.com +date 2015-03-19 +name Semantic Plugin +desc Add Semantic Data in Dokuwiki +url http://www.dokuwiki.org/plugin:semantic diff --git a/syntax.php b/syntax.php new file mode 100644 index 0000000..a61fd49 --- /dev/null +++ b/syntax.php @@ -0,0 +1,48 @@ + + */ +// must be run within Dokuwiki +if (!defined('DOKU_INC')) die(); + +if (!defined('DOKU_PLUGIN')) define('DOKU_PLUGIN',DOKU_INC.'lib/plugins/'); + +class syntax_plugin_semantic extends DokuWiki_Syntax_Plugin { + + function getType() { return 'substition'; } + function getSort() { return 99; } + + function connectTo($mode) { + $this->Lexer->addSpecialPattern('~~NewsArticle~~', $mode, 'plugin_semantic'); + $this->Lexer->addSpecialPattern('~~Article~~', $mode, 'plugin_semantic'); + $this->Lexer->addSpecialPattern('~~TechArticle~~', $mode, 'plugin_semantic'); + $this->Lexer->addSpecialPattern('~~BlogPosting~~', $mode, 'plugin_semantic'); + $this->Lexer->addSpecialPattern('~~NOSEMANTIC~~', $mode, 'plugin_semantic'); + } + + function handle($match, $state, $pos, Doku_Handler $handler) { + return array($match, $state, $pos); + } + + function render($mode, Doku_Renderer $renderer, $data) { + + if ($mode == 'xthml') { + return true; // don't output anything + } elseif ($mode == 'metadata') { + + list($match, $state, $pos) = $data; + + if ($match == '~~NOSEMANTIC~~') { + $renderer->meta['semantic']['enabled'] = false; + } else { + $renderer->meta['semantic']['schema.org']['type'] = trim(str_replace('Schema.org/', '', $match), '~~'); + $renderer->meta['semantic']['enabled'] = true; + } + + } + } + +}