if (!defined ('MEDIAWIKI')) {
echo 'This is a MediaWiki-Extension and not meant to be run standalone!';
exit (1);
}
$wgExtensionCredits['parserhook'] [] = array (
'name' => 'include_PHP',
'author' => 'Jannis Achstetter',
'url' => '
'description' => 'Allows you to include PHP-files that are executed and their output shown on the wiki-page',
'version' => 2,
'path' => __FILE__,
);
// We register our function "include_PHPParserHook" to the tag
// A filename of a file to be included must be given. For example:
//
// Files are searched in the "$IP/scripting"-folder and have the .php-extension.
// This extension must not be given with the file=-parameter; it is appended
//
// We parse the PHP in the "include_PHPParserHook"-function. The resulting text
// is not yet returned to the Wiki-page, only a marker is placed there. The
// output it stored in the array $markerList.
// In the "include_PHPParserAfterTidy"-function, the markers are replaced by
// the real output. This way, we can output HTML that is not touched by
// MediaWiki's parser.
$wgHooks['ParserAfterTidy'][] = 'include_PHPParserAfterTidy';
$wgHooks['ParserFirstCallInit'][] = 'include_PHPSetup';
function include_PHPSetup (&$parser) {
$parser->setHook( 'include_PHP', 'include_PHPParserHook' );
return true;
}
$markerList = array();
function include_PHPParserHook ($input, $argv, $parser) {
global $markerList;
// Disable page caching since the PHP-output is dynamic
//jamesqi 2011-5-7 $parser->disableCache();
// Sanity checking: allow execution only if the currently viewed Revision
// was created/edited by a user with the "scripting"-permission
$user = User::newFromName ($parser->getRevisionUser());
$user->load();
if (!$user->isAllowed ('scripting')) {
$output = 'include_PHP: The revision you are viewing was created by a user that does not have the permissions to include PHP code! I won\'t execute that!';
} else {
// No file-parameter has been given! Nothing to do for us :)
if (!array_key_exists("file", $argv)) {
$output = 'include_PHP: No script-file to be included given!';
} else {
// Check for evil directory traversal (alias "../")-attacks
// note the 3 "="-signs in the comparison!
if (!(strpos($argv['file'], '../') === FALSE)) {
$output = 'include_PHP: Possible directory-traversal attack! Why do you have "../" in the filename?';
} else {
// A file-parameter has been given! Check if it exists and is readable
if (!is_readable('scripting/'.$argv['file'].'.php')) {
$output = 'include_PHP: File to be included does not exist!';
} else {
// Actual parsing is done here!
// Use ob_start so things like phpinfo() put their output inside the wiki-page "body-text", not on top of it
ob_start();
include('scripting/'.$argv['file'].'.php');
$output = trim(ob_get_clean());
}
}
}
}
// Get a new marker, store the output there and
// insert it's name onto the (yet to be parsed) page
$markercount = count($markerList);
$marker = "xy-include_PHP-marker-".$markercount."-xy";
global $include_PHP_override_marker;
if ($include_PHP_override_marker) {
$markerList[$markercount] = $include_PHP_override_marker;
} else {
$markerList[$markercount] = $output;
}
return $marker;
}
// find markers in $text
// replace markers with actual output
function include_PHPParserAfterTidy ($parser, &$text) {
global $markerList;
// Disable page caching since the PHP-output is dynamic
//jamesqi2011-5-7 $parser->disableCache();
$keys = array();
$marker_count = count($markerList);
for ($i = 0; $i < $marker_count; $i++) {
$keys[] = 'xy-include_PHP-marker-'.$i.'-xy';
}
$text = str_replace($keys, $markerList, $text);
return true;
}
?>