4 Copyright 2005,2007 $ThePhpWikiProgrammingTeam
6 This file is part of PhpWiki.
8 PhpWiki is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
13 PhpWiki is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with PhpWiki; if not, write to the Free Software
20 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
24 * Template: Parametrized blocks.
25 * Include text from a wiki page and replace certain placeholders by parameters.
26 * Similiar to CreatePage with the template argument, but at run-time.
27 * Similiar to the mediawiki templates but not with the "|" parameter seperator.
28 * Usage: <?plugin Template page=TemplateFilm vars="title=rurban&year=1999" ?>
30 * See also: http://meta.wikimedia.org/wiki/Help:Template
32 * Parameter expansion:
33 * vars="var1=value1&var2=value2"
34 * We only support named parameters, not numbered ones as in mediawiki, and
35 * the placeholder is %%var%% and not {{{var}}} as in mediawiki.
37 * The following predefined uppercase variables are automatically expanded if existing:
39 * MTIME - last modified date + time
40 * CTIME - creation date + time
41 * AUTHOR - last author
43 * CREATOR - first author
44 * SERVER_URL, DATA_PATH, SCRIPT_NAME, PHPWIKI_BASE_URL and BASE_URL
46 * <noinclude> .. </noinclude> is stripped from the template expansion.
47 * <includeonly> .. </includeonly> is only expanded in pages using the template,
48 * not in the template itself.
51 * - ENABLE_MARKUP_TEMPLATE = true: (lib/InlineParser.php)
52 * Support a mediawiki-style syntax extension which maps
53 * {{TemplateFilm|title=Some Good Film|year=1999}}
55 * <?plugin Template page=TemplateFilm vars="title=Some Good Film&year=1999" ?>
58 class WikiPlugin_Template
65 function getDescription() {
66 return _("Parametrized page inclusion.");
69 function getVersion() {
70 return preg_replace("/[Revision: $]/", '',
74 function getDefaultArguments() {
76 'page' => false, // the page to include
77 'vars' => false, // TODO: get rid of this, all remaining args should be vars
78 'rev' => false, // the revision (defaults to most recent)
79 'section' => false, // just include a named section
80 'sectionhead' => false // when including a named section show the heading
83 function allow_undeclared_arg($name, $value) {
84 // either just allow it or you can store it here away also.
85 $this->vars[$name] = $value;
86 return $name != 'action';
89 // TODO: check if page can really be pulled from the args, or if it is just the basepage.
90 function getWikiPageLinks($argstr, $basepage) {
91 $args = $this->getArgs($argstr);
92 $page = @$args['page'];
94 // Expand relative page names.
95 $page = new WikiPageName($page, $basepage);
97 if (!$page or !$page->name)
99 return array(array('linkto' => $page->name, 'relation' => 0));
102 function run($dbi, $argstr, &$request, $basepage) {
103 $this->vars = array();
104 $args = $this->getArgs($argstr, $request);
105 $vars = $args['vars'] ? $args['vars'] : $this->vars;
106 $page = $args['page'];
108 // Expand relative page names.
109 $page = new WikiPageName($page, $basepage);
113 return $this->error(_("no page specified"));
116 // Protect from recursive inclusion. A page can include itself once
117 static $included_pages = array();
118 if (in_array($page, $included_pages)) {
119 return $this->error(sprintf(_("recursive inclusion of page %s"),
123 $p = $dbi->getPage($page);
125 $r = $p->getRevision($args['rev']);
127 return $this->error(sprintf(_("%s(%d): no such revision"),
128 $page, $args['rev']));
131 $r = $p->getCurrentRevision();
133 $initial_content = $r->getPackedContent();
135 if ($args['section']) {
136 $c = explode("\n", $initial_content);
137 $c = extractSection($args['section'], $c, $page, $quiet, $args['sectionhead']);
138 $initial_content = implode("\n", $c);
140 // exclude from expansion
141 if (preg_match('/<noinclude>.+<\/noinclude>/s', $initial_content)) {
142 $initial_content = preg_replace("/<noinclude>.+?<\/noinclude>/s", "",
146 $initial_content = preg_replace("/<includeonly>(.+)<\/includeonly>/s", "\\1",
148 $this->doVariableExpansion($initial_content, $vars, $basepage, $request);
150 array_push($included_pages, $page);
151 include_once('lib/BlockParser.php');
152 $content = TransformText($initial_content, $r->get('markup'), $page);
154 array_pop($included_pages);
156 return HTML::div(array('class' => 'template'), $content);
160 * Expand template variables. Used by the TemplatePlugin and the CreatePagePlugin
162 function doVariableExpansion(&$content, $vars, $basepage, &$request) {
163 if (preg_match('/%%\w+%%/', $content)) // need variable expansion
165 $dbi =& $request->_dbi;
167 if (is_string($vars) and !empty($vars)) {
168 foreach (split("&",$vars) as $pair) {
169 list($key,$val) = split("=",$pair);
172 } elseif (is_array($vars)) {
175 $thispage = $dbi->getPage($basepage);
176 // pagename and userid are not overridable
177 $var['PAGENAME'] = $thispage->getName();
178 if (preg_match('/%%USERID%%/', $content))
179 $var['USERID'] = $request->_user->getId();
180 if (empty($var['MTIME']) and preg_match('/%%MTIME%%/', $content)) {
181 $thisrev = $thispage->getCurrentRevision(false);
182 $var['MTIME'] = $GLOBALS['WikiTheme']->formatDateTime($thisrev->get('mtime'));
184 if (empty($var['CTIME']) and preg_match('/%%CTIME%%/', $content)) {
185 if ($first = $thispage->getRevision(1,false))
186 $var['CTIME'] = $GLOBALS['WikiTheme']->formatDateTime($first->get('mtime'));
188 if (empty($var['AUTHOR']) and preg_match('/%%AUTHOR%%/', $content))
189 $var['AUTHOR'] = $thispage->getAuthor();
190 if (empty($var['OWNER']) and preg_match('/%%OWNER%%/', $content))
191 $var['OWNER'] = $thispage->getOwner();
192 if (empty($var['CREATOR']) and preg_match('/%%CREATOR%%/', $content))
193 $var['CREATOR'] = $thispage->getCreator();
194 foreach (array("SERVER_URL", "DATA_PATH", "SCRIPT_NAME", "PHPWIKI_BASE_URL") as $c) {
195 // constants are not overridable
196 if (preg_match('/%%'.$c.'%%/', $content))
197 $var[$c] = constant($c);
199 if (preg_match('/%%BASE_URL%%/', $content))
200 $var['BASE_URL'] = PHPWIKI_BASE_URL;
202 foreach ($var as $key => $val) {
203 //$content = preg_replace("/%%".preg_quote($key,"/")."%%/", $val, $content);
204 $content = str_replace("%%".$key."%%", $val, $content);
211 // $Log: not supported by cvs2svn $
212 // Revision 1.10 2007/06/07 17:03:38 rurban
213 // minor optimization: move explode("\n", $initial_content) to section code
215 // Revision 1.9 2007/03/04 14:09:13 rurban
216 // silence missing page warning
218 // Revision 1.8 2007/01/25 07:42:29 rurban
219 // Changed doVariableExpansion API. Uppercase default vars. Use str_replace.
221 // Revision 1.7 2007/01/04 16:42:41 rurban
222 // Improve vars passing. Use new method allow_undeclared_arg to allow arbitrary args for the template. Fix doVariableExpansion: use a ref. Fix pagename. Put away \b in regex.
224 // Revision 1.6 2007/01/03 21:24:06 rurban
225 // protect page in links. new doVariableExpansion() for CreatePage. preg_quote custom vars.
227 // Revision 1.5 2006/04/17 17:28:21 rurban
228 // honor getWikiPageLinks change linkto=>relation
230 // Revision 1.4 2005/09/11 13:30:22 rurban
233 // Revision 1.3 2005/09/10 20:43:19 rurban
234 // support <noinclude>
236 // Revision 1.2 2005/09/10 20:07:16 rurban
239 // Revision 1.1 2005/09/10 19:59:38 rurban
240 // Parametrized page inclusion ala mediawiki
248 // c-hanging-comment-ender-p: nil
249 // indent-tabs-mode: nil