<?php
/* This defines autoloading handler for whole MediaWiki framework */
+
+ini_set('unserialize_callback_func', '__autoload' );
+
function __autoload($className) {
global $wgAutoloadClasses;
'HistoryBlobCurStub' => 'includes/HistoryBlob.php',
'HTMLCacheUpdate' => 'includes/HTMLCacheUpdate.php',
'HTMLCacheUpdateJob' => 'includes/HTMLCacheUpdate.php',
+ 'Http' => 'includes/HttpFunctions.php',
'Image' => 'includes/Image.php',
'ThumbnailImage' => 'includes/Image.php',
'ImageGallery' => 'includes/ImageGallery.php',
'WikiError' => 'includes/WikiError.php',
'WikiErrorMsg' => 'includes/WikiError.php',
'WikiXmlError' => 'includes/WikiError.php',
+ 'Xml' => 'includes/Xml.php',
'ZhClient' => 'includes/ZhClient.php',
'memcached' => 'includes/memcached-client.php',
'UtfNormal' => 'includes/normal/UtfNormal.php'
} elseif ( isset( $wgAutoloadClasses[$className] ) ) {
$filename = $wgAutoloadClasses[$className];
} else {
- return;
+ # Try a different capitalisation
+ # The case can sometimes be wrong when unserializing PHP 4 objects
+ $filename = false;
+ $lowerClass = strtolower( $className );
+ foreach ( $localClasses as $class2 => $file2 ) {
+ if ( strtolower( $class2 ) == $lowerClass ) {
+ $filename = $file2;
+ }
+ }
+ if ( !$filename ) {
+ # Give up
+ return;
+ }
}
# Make an absolute path, this improves performance by avoiding some stat calls
* @package MediaWiki
*/
-/**
- * Depends on the CacheManager
- */
-require_once( 'CacheManager.php' );
-
/** See Database::makeList() */
define( 'LIST_COMMA', 0 );
define( 'LIST_AND', 1 );
*/
$wgSkinExtensionFunctions = array();
+/**
+ * List of valid skin names.
+ * The key should be the name in all lower case, the value should be a display name.
+ * The default skins will be added later, by Skin::getSkinNames(). Use
+ * Skin::getSkinNames() as an accessor if you wish to have access to the full list.
+ */
+$wgValidSkinNames = array();
/**
* Special page list.
}
}
+/**
+ * Aliases for modularized functions
+ */
+function wfGetHTTP( $url, $timeout = 'default' ) {
+ return Http::get( $url, $timeout );
+}
+function wfIsLocalURL( $url ) {
+ return Http::isLocalURL( $url );
+}
+
?>
<?php
-/**
- * Various HTTP related functions
- */
/**
- * Get the contents of a file by HTTP
- *
- * if $timeout is 'default', $wgHTTPTimeout is used
+ * Various HTTP related functions
*/
-function wfGetHTTP( $url, $timeout = 'default' ) {
- global $wgHTTPTimeout, $wgHTTPProxy, $wgVersion, $wgTitle;
+class Http {
+ /**
+ * Get the contents of a file by HTTP
+ *
+ * if $timeout is 'default', $wgHTTPTimeout is used
+ */
+ static function get( $url, $timeout = 'default' ) {
+ global $wgHTTPTimeout, $wgHTTPProxy, $wgVersion, $wgTitle;
- # Use curl if available
- if ( function_exists( 'curl_init' ) ) {
- $c = curl_init( $url );
- if ( wfIsLocalURL( $url ) ) {
- curl_setopt( $c, CURLOPT_PROXY, 'localhost:80' );
- } else if ($wgHTTPProxy) {
- curl_setopt($c, CURLOPT_PROXY, $wgHTTPProxy);
- }
+ # Use curl if available
+ if ( function_exists( 'curl_init' ) ) {
+ $c = curl_init( $url );
+ if ( wfIsLocalURL( $url ) ) {
+ curl_setopt( $c, CURLOPT_PROXY, 'localhost:80' );
+ } else if ($wgHTTPProxy) {
+ curl_setopt($c, CURLOPT_PROXY, $wgHTTPProxy);
+ }
- if ( $timeout == 'default' ) {
- $timeout = $wgHTTPTimeout;
- }
- curl_setopt( $c, CURLOPT_TIMEOUT, $timeout );
- curl_setopt( $c, CURLOPT_USERAGENT, "MediaWiki/$wgVersion" );
+ if ( $timeout == 'default' ) {
+ $timeout = $wgHTTPTimeout;
+ }
+ curl_setopt( $c, CURLOPT_TIMEOUT, $timeout );
+ curl_setopt( $c, CURLOPT_USERAGENT, "MediaWiki/$wgVersion" );
- # Set the referer to $wgTitle, even in command-line mode
- # This is useful for interwiki transclusion, where the foreign
- # server wants to know what the referring page is.
- # $_SERVER['REQUEST_URI'] gives a less reliable indication of the
- # referring page.
- if ( is_object( $wgTitle ) ) {
- curl_setopt( $c, CURLOPT_REFERER, $wgTitle->getFullURL() );
- }
+ # Set the referer to $wgTitle, even in command-line mode
+ # This is useful for interwiki transclusion, where the foreign
+ # server wants to know what the referring page is.
+ # $_SERVER['REQUEST_URI'] gives a less reliable indication of the
+ # referring page.
+ if ( is_object( $wgTitle ) ) {
+ curl_setopt( $c, CURLOPT_REFERER, $wgTitle->getFullURL() );
+ }
- ob_start();
- curl_exec( $c );
- $text = ob_get_contents();
- ob_end_clean();
+ ob_start();
+ curl_exec( $c );
+ $text = ob_get_contents();
+ ob_end_clean();
- # Don't return the text of error messages, return false on error
- if ( curl_getinfo( $c, CURLINFO_HTTP_CODE ) != 200 ) {
- $text = false;
+ # Don't return the text of error messages, return false on error
+ if ( curl_getinfo( $c, CURLINFO_HTTP_CODE ) != 200 ) {
+ $text = false;
+ }
+ curl_close( $c );
+ } else {
+ # Otherwise use file_get_contents, or its compatibility function from GlobalFunctions.php
+ # This may take 3 minutes to time out, and doesn't have local fetch capabilities
+ $url_fopen = ini_set( 'allow_url_fopen', 1 );
+ $text = file_get_contents( $url );
+ ini_set( 'allow_url_fopen', $url_fopen );
}
- curl_close( $c );
- } else {
- # Otherwise use file_get_contents, or its compatibility function from GlobalFunctions.php
- # This may take 3 minutes to time out, and doesn't have local fetch capabilities
- $url_fopen = ini_set( 'allow_url_fopen', 1 );
- $text = file_get_contents( $url );
- ini_set( 'allow_url_fopen', $url_fopen );
+ return $text;
}
- return $text;
-}
-/**
- * Check if the URL can be served by localhost
- */
-function wfIsLocalURL( $url ) {
- global $wgCommandLineMode, $wgConf;
- if ( $wgCommandLineMode ) {
- return false;
- }
+ /**
+ * Check if the URL can be served by localhost
+ */
+ static function isLocalURL( $url ) {
+ global $wgCommandLineMode, $wgConf;
+ if ( $wgCommandLineMode ) {
+ return false;
+ }
- // Extract host part
- $matches = array();
- if ( preg_match( '!^http://([\w.-]+)[/:].*$!', $url, $matches ) ) {
- $host = $matches[1];
- // Split up dotwise
- $domainParts = explode( '.', $host );
- // Check if this domain or any superdomain is listed in $wgConf as a local virtual host
- $domainParts = array_reverse( $domainParts );
- for ( $i = 0; $i < count( $domainParts ); $i++ ) {
- $domainPart = $domainParts[$i];
- if ( $i == 0 ) {
- $domain = $domainPart;
- } else {
- $domain = $domainPart . '.' . $domain;
- }
- if ( $wgConf->isLocalVHost( $domain ) ) {
- return true;
+ // Extract host part
+ $matches = array();
+ if ( preg_match( '!^http://([\w.-]+)[/:].*$!', $url, $matches ) ) {
+ $host = $matches[1];
+ // Split up dotwise
+ $domainParts = explode( '.', $host );
+ // Check if this domain or any superdomain is listed in $wgConf as a local virtual host
+ $domainParts = array_reverse( $domainParts );
+ for ( $i = 0; $i < count( $domainParts ); $i++ ) {
+ $domainPart = $domainParts[$i];
+ if ( $i == 0 ) {
+ $domain = $domainPart;
+ } else {
+ $domain = $domainPart . '.' . $domain;
+ }
+ if ( $wgConf->isLocalVHost( $domain ) ) {
+ return true;
+ }
}
}
+ return false;
}
- return false;
}
-
?>
} //class
-
-/**
- * Returns the image directory of an image
- * If the directory does not exist, it is created.
- * The result is an absolute path.
- *
- * This function is called from thumb.php before Setup.php is included
- *
- * @param $fname String: file name of the image file.
- * @public
- */
-function wfImageDir( $fname ) {
- global $wgUploadDirectory, $wgHashedUploadDirectory;
-
- if (!$wgHashedUploadDirectory) { return $wgUploadDirectory; }
-
- $hash = md5( $fname );
- $oldumask = umask(0);
- $dest = $wgUploadDirectory . '/' . $hash{0};
- if ( ! is_dir( $dest ) ) { mkdir( $dest, 0777 ); }
- $dest .= '/' . substr( $hash, 0, 2 );
- if ( ! is_dir( $dest ) ) { mkdir( $dest, 0777 ); }
-
- umask( $oldumask );
- return $dest;
-}
-
-/**
- * Returns the image directory of an image's thubnail
- * If the directory does not exist, it is created.
- * The result is an absolute path.
- *
- * This function is called from thumb.php before Setup.php is included
- *
- * @param $fname String: file name of the original image file
- * @param $shared Boolean: (optional) use the shared upload directory (default: 'false').
- * @public
- */
-function wfImageThumbDir( $fname, $shared = false ) {
- $base = wfImageArchiveDir( $fname, 'thumb', $shared );
- if ( Image::isHashed( $shared ) ) {
- $dir = "$base/$fname";
-
- if ( !is_dir( $base ) ) {
- $oldumask = umask(0);
- @mkdir( $base, 0777 );
- umask( $oldumask );
- }
-
- if ( ! is_dir( $dir ) ) {
- if ( is_file( $dir ) ) {
- // Old thumbnail in the way of directory creation, kill it
- unlink( $dir );
- }
- $oldumask = umask(0);
- @mkdir( $dir, 0777 );
- umask( $oldumask );
- }
- } else {
- $dir = $base;
- }
-
- return $dir;
-}
-
-/**
- * Old thumbnail directory, kept for conversion
- */
-function wfDeprecatedThumbDir( $thumbName , $subdir='thumb', $shared=false) {
- return wfImageArchiveDir( $thumbName, $subdir, $shared );
-}
-
-/**
- * Returns the image directory of an image's old version
- * If the directory does not exist, it is created.
- * The result is an absolute path.
- *
- * This function is called from thumb.php before Setup.php is included
- *
- * @param $fname String: file name of the thumbnail file, including file size prefix.
- * @param $subdir String: subdirectory of the image upload directory that should be used for storing the old version. Default is 'archive'.
- * @param $shared Boolean use the shared upload directory (only relevant for other functions which call this one). Default is 'false'.
- * @public
- */
-function wfImageArchiveDir( $fname , $subdir='archive', $shared=false ) {
- global $wgUploadDirectory, $wgHashedUploadDirectory;
- global $wgSharedUploadDirectory, $wgHashedSharedUploadDirectory;
- $dir = $shared ? $wgSharedUploadDirectory : $wgUploadDirectory;
- $hashdir = $shared ? $wgHashedSharedUploadDirectory : $wgHashedUploadDirectory;
- if (!$hashdir) { return $dir.'/'.$subdir; }
- $hash = md5( $fname );
- $oldumask = umask(0);
-
- # Suppress warning messages here; if the file itself can't
- # be written we'll worry about it then.
- wfSuppressWarnings();
-
- $archive = $dir.'/'.$subdir;
- if ( ! is_dir( $archive ) ) { mkdir( $archive, 0777 ); }
- $archive .= '/' . $hash{0};
- if ( ! is_dir( $archive ) ) { mkdir( $archive, 0777 ); }
- $archive .= '/' . substr( $hash, 0, 2 );
- if ( ! is_dir( $archive ) ) { mkdir( $archive, 0777 ); }
-
- wfRestoreWarnings();
- umask( $oldumask );
- return $archive;
-}
-
-
-/*
- * Return the hash path component of an image path (URL or filesystem),
- * e.g. "/3/3c/", or just "/" if hashing is not used.
- *
- * @param $dbkey The filesystem / database name of the file
- * @param $fromSharedDirectory Use the shared file repository? It may
- * use different hash settings from the local one.
- */
-function wfGetHashPath ( $dbkey, $fromSharedDirectory = false ) {
- if( Image::isHashed( $fromSharedDirectory ) ) {
- $hash = md5($dbkey);
- return '/' . $hash{0} . '/' . substr( $hash, 0, 2 ) . '/';
- } else {
- return '/';
- }
-}
-
-/**
- * Returns the image URL of an image's old version
- *
- * @param $name String: file name of the image file
- * @param $subdir String: (optional) subdirectory of the image upload directory that is used by the old version. Default is 'archive'
- * @public
- */
-function wfImageArchiveUrl( $name, $subdir='archive' ) {
- global $wgUploadPath, $wgHashedUploadDirectory;
-
- if ($wgHashedUploadDirectory) {
- $hash = md5( substr( $name, 15) );
- $url = $wgUploadPath.'/'.$subdir.'/' . $hash{0} . '/' .
- substr( $hash, 0, 2 ) . '/'.$name;
- } else {
- $url = $wgUploadPath.'/'.$subdir.'/'.$name;
- }
- return wfUrlencode($url);
-}
-
-/**
- * Return a rounded pixel equivalent for a labeled CSS/SVG length.
- * http://www.w3.org/TR/SVG11/coords.html#UnitIdentifiers
- *
- * @param $length String: CSS/SVG length.
- * @return Integer: length in pixels
- */
-function wfScaleSVGUnit( $length ) {
- static $unitLength = array(
- 'px' => 1.0,
- 'pt' => 1.25,
- 'pc' => 15.0,
- 'mm' => 3.543307,
- 'cm' => 35.43307,
- 'in' => 90.0,
- '' => 1.0, // "User units" pixels by default
- '%' => 2.0, // Fake it!
- );
- if( preg_match( '/^(\d+(?:\.\d+)?)(em|ex|px|pt|pc|cm|mm|in|%|)$/', $length, $matches ) ) {
- $length = floatval( $matches[1] );
- $unit = $matches[2];
- return round( $length * $unitLength[$unit] );
- } else {
- // Assume pixels
- return round( floatval( $length ) );
- }
-}
-
-/**
- * Compatible with PHP getimagesize()
- * @todo support gzipped SVGZ
- * @todo check XML more carefully
- * @todo sensible defaults
- *
- * @param $filename String: full name of the file (passed to php fopen()).
- * @return array
- */
-function wfGetSVGsize( $filename ) {
- $width = 256;
- $height = 256;
-
- // Read a chunk of the file
- $f = fopen( $filename, "rt" );
- if( !$f ) return false;
- $chunk = fread( $f, 4096 );
- fclose( $f );
-
- // Uber-crappy hack! Run through a real XML parser.
- if( !preg_match( '/<svg\s*([^>]*)\s*>/s', $chunk, $matches ) ) {
- return false;
- }
- $tag = $matches[1];
- if( preg_match( '/\bwidth\s*=\s*("[^"]+"|\'[^\']+\')/s', $tag, $matches ) ) {
- $width = wfScaleSVGUnit( trim( substr( $matches[1], 1, -1 ) ) );
- }
- if( preg_match( '/\bheight\s*=\s*("[^"]+"|\'[^\']+\')/s', $tag, $matches ) ) {
- $height = wfScaleSVGUnit( trim( substr( $matches[1], 1, -1 ) ) );
- }
-
- return array( $width, $height, 'SVG',
- "width=\"$width\" height=\"$height\"" );
-}
-
-/**
- * Determine if an image exists on the 'bad image list'.
- *
- * @param $name String: the image name to check
- * @return bool
- */
-function wfIsBadImage( $name ) {
- static $titleList = false;
-
- if( !$titleList ) {
- # Build the list now
- $titleList = array();
- $lines = explode( "\n", wfMsgForContent( 'bad_image_list' ) );
- foreach( $lines as $line ) {
- if( preg_match( '/^\*\s*\[\[:?(.*?)\]\]/i', $line, $matches ) ) {
- $title = Title::newFromText( $matches[1] );
- if( is_object( $title ) && $title->getNamespace() == NS_IMAGE )
- $titleList[ $title->getDBkey() ] = true;
- }
- }
- }
- return array_key_exists( $name, $titleList );
-}
-
-
-
/**
* Wrapper class for thumbnail images
* @package MediaWiki
}
-/**
- * Calculate the largest thumbnail width for a given original file size
- * such that the thumbnail's height is at most $maxHeight.
- * @param $boxWidth Integer Width of the thumbnail box.
- * @param $boxHeight Integer Height of the thumbnail box.
- * @param $maxHeight Integer Maximum height expected for the thumbnail.
- * @return Integer.
- */
-function wfFitBoxWidth( $boxWidth, $boxHeight, $maxHeight ) {
- $idealWidth = $boxWidth * $maxHeight / $boxHeight;
- $roundedUp = ceil( $idealWidth );
- if( round( $roundedUp * $boxHeight / $boxWidth ) > $maxHeight )
- return floor( $idealWidth );
- else
- return $roundedUp;
-}
-
?>
--- /dev/null
+<?php\r
+\r
+/**\r
+ * Returns the image directory of an image\r
+ * If the directory does not exist, it is created.\r
+ * The result is an absolute path.\r
+ *\r
+ * This function is called from thumb.php before Setup.php is included\r
+ *\r
+ * @param $fname String: file name of the image file.\r
+ * @public\r
+ */\r
+function wfImageDir( $fname ) {\r
+ global $wgUploadDirectory, $wgHashedUploadDirectory;\r
+\r
+ if (!$wgHashedUploadDirectory) { return $wgUploadDirectory; }\r
+\r
+ $hash = md5( $fname );\r
+ $oldumask = umask(0);\r
+ $dest = $wgUploadDirectory . '/' . $hash{0};\r
+ if ( ! is_dir( $dest ) ) { mkdir( $dest, 0777 ); }\r
+ $dest .= '/' . substr( $hash, 0, 2 );\r
+ if ( ! is_dir( $dest ) ) { mkdir( $dest, 0777 ); }\r
+\r
+ umask( $oldumask );\r
+ return $dest;\r
+}\r
+\r
+/**\r
+ * Returns the image directory of an image's thubnail\r
+ * If the directory does not exist, it is created.\r
+ * The result is an absolute path.\r
+ *\r
+ * This function is called from thumb.php before Setup.php is included\r
+ *\r
+ * @param $fname String: file name of the original image file\r
+ * @param $shared Boolean: (optional) use the shared upload directory (default: 'false').\r
+ * @public\r
+ */\r
+function wfImageThumbDir( $fname, $shared = false ) {\r
+ $base = wfImageArchiveDir( $fname, 'thumb', $shared );\r
+ if ( Image::isHashed( $shared ) ) {\r
+ $dir = "$base/$fname";\r
+\r
+ if ( !is_dir( $base ) ) {\r
+ $oldumask = umask(0);\r
+ @mkdir( $base, 0777 );\r
+ umask( $oldumask );\r
+ }\r
+\r
+ if ( ! is_dir( $dir ) ) {\r
+ if ( is_file( $dir ) ) {\r
+ // Old thumbnail in the way of directory creation, kill it\r
+ unlink( $dir );\r
+ }\r
+ $oldumask = umask(0);\r
+ @mkdir( $dir, 0777 );\r
+ umask( $oldumask );\r
+ }\r
+ } else {\r
+ $dir = $base;\r
+ }\r
+\r
+ return $dir;\r
+}\r
+\r
+/**\r
+ * Old thumbnail directory, kept for conversion\r
+ */\r
+function wfDeprecatedThumbDir( $thumbName , $subdir='thumb', $shared=false) {\r
+ return wfImageArchiveDir( $thumbName, $subdir, $shared );\r
+}\r
+\r
+/**\r
+ * Returns the image directory of an image's old version\r
+ * If the directory does not exist, it is created.\r
+ * The result is an absolute path.\r
+ *\r
+ * This function is called from thumb.php before Setup.php is included\r
+ *\r
+ * @param $fname String: file name of the thumbnail file, including file size prefix.\r
+ * @param $subdir String: subdirectory of the image upload directory that should be used for storing the old version. Default is 'archive'.\r
+ * @param $shared Boolean use the shared upload directory (only relevant for other functions which call this one). Default is 'false'.\r
+ * @public\r
+ */\r
+function wfImageArchiveDir( $fname , $subdir='archive', $shared=false ) {\r
+ global $wgUploadDirectory, $wgHashedUploadDirectory;\r
+ global $wgSharedUploadDirectory, $wgHashedSharedUploadDirectory;\r
+ $dir = $shared ? $wgSharedUploadDirectory : $wgUploadDirectory;\r
+ $hashdir = $shared ? $wgHashedSharedUploadDirectory : $wgHashedUploadDirectory;\r
+ if (!$hashdir) { return $dir.'/'.$subdir; }\r
+ $hash = md5( $fname );\r
+ $oldumask = umask(0);\r
+\r
+ # Suppress warning messages here; if the file itself can't\r
+ # be written we'll worry about it then.\r
+ wfSuppressWarnings();\r
+\r
+ $archive = $dir.'/'.$subdir;\r
+ if ( ! is_dir( $archive ) ) { mkdir( $archive, 0777 ); }\r
+ $archive .= '/' . $hash{0};\r
+ if ( ! is_dir( $archive ) ) { mkdir( $archive, 0777 ); }\r
+ $archive .= '/' . substr( $hash, 0, 2 );\r
+ if ( ! is_dir( $archive ) ) { mkdir( $archive, 0777 ); }\r
+\r
+ wfRestoreWarnings();\r
+ umask( $oldumask );\r
+ return $archive;\r
+}\r
+\r
+\r
+/*\r
+ * Return the hash path component of an image path (URL or filesystem),\r
+ * e.g. "/3/3c/", or just "/" if hashing is not used.\r
+ *\r
+ * @param $dbkey The filesystem / database name of the file\r
+ * @param $fromSharedDirectory Use the shared file repository? It may\r
+ * use different hash settings from the local one.\r
+ */\r
+function wfGetHashPath ( $dbkey, $fromSharedDirectory = false ) {\r
+ if( Image::isHashed( $fromSharedDirectory ) ) {\r
+ $hash = md5($dbkey);\r
+ return '/' . $hash{0} . '/' . substr( $hash, 0, 2 ) . '/';\r
+ } else {\r
+ return '/';\r
+ }\r
+}\r
+\r
+/**\r
+ * Returns the image URL of an image's old version\r
+ *\r
+ * @param $name String: file name of the image file\r
+ * @param $subdir String: (optional) subdirectory of the image upload directory that is used by the old version. Default is 'archive'\r
+ * @public\r
+ */\r
+function wfImageArchiveUrl( $name, $subdir='archive' ) {\r
+ global $wgUploadPath, $wgHashedUploadDirectory;\r
+\r
+ if ($wgHashedUploadDirectory) {\r
+ $hash = md5( substr( $name, 15) );\r
+ $url = $wgUploadPath.'/'.$subdir.'/' . $hash{0} . '/' .\r
+ substr( $hash, 0, 2 ) . '/'.$name;\r
+ } else {\r
+ $url = $wgUploadPath.'/'.$subdir.'/'.$name;\r
+ }\r
+ return wfUrlencode($url);\r
+}\r
+\r
+/**\r
+ * Return a rounded pixel equivalent for a labeled CSS/SVG length.\r
+ * http://www.w3.org/TR/SVG11/coords.html#UnitIdentifiers\r
+ *\r
+ * @param $length String: CSS/SVG length.\r
+ * @return Integer: length in pixels\r
+ */\r
+function wfScaleSVGUnit( $length ) {\r
+ static $unitLength = array(\r
+ 'px' => 1.0,\r
+ 'pt' => 1.25,\r
+ 'pc' => 15.0,\r
+ 'mm' => 3.543307,\r
+ 'cm' => 35.43307,\r
+ 'in' => 90.0,\r
+ '' => 1.0, // "User units" pixels by default\r
+ '%' => 2.0, // Fake it!\r
+ );\r
+ if( preg_match( '/^(\d+(?:\.\d+)?)(em|ex|px|pt|pc|cm|mm|in|%|)$/', $length, $matches ) ) {\r
+ $length = floatval( $matches[1] );\r
+ $unit = $matches[2];\r
+ return round( $length * $unitLength[$unit] );\r
+ } else {\r
+ // Assume pixels\r
+ return round( floatval( $length ) );\r
+ }\r
+}\r
+\r
+/**\r
+ * Compatible with PHP getimagesize()\r
+ * @todo support gzipped SVGZ\r
+ * @todo check XML more carefully\r
+ * @todo sensible defaults\r
+ *\r
+ * @param $filename String: full name of the file (passed to php fopen()).\r
+ * @return array\r
+ */\r
+function wfGetSVGsize( $filename ) {\r
+ $width = 256;\r
+ $height = 256;\r
+\r
+ // Read a chunk of the file\r
+ $f = fopen( $filename, "rt" );\r
+ if( !$f ) return false;\r
+ $chunk = fread( $f, 4096 );\r
+ fclose( $f );\r
+\r
+ // Uber-crappy hack! Run through a real XML parser.\r
+ if( !preg_match( '/<svg\s*([^>]*)\s*>/s', $chunk, $matches ) ) {\r
+ return false;\r
+ }\r
+ $tag = $matches[1];\r
+ if( preg_match( '/\bwidth\s*=\s*("[^"]+"|\'[^\']+\')/s', $tag, $matches ) ) {\r
+ $width = wfScaleSVGUnit( trim( substr( $matches[1], 1, -1 ) ) );\r
+ }\r
+ if( preg_match( '/\bheight\s*=\s*("[^"]+"|\'[^\']+\')/s', $tag, $matches ) ) {\r
+ $height = wfScaleSVGUnit( trim( substr( $matches[1], 1, -1 ) ) );\r
+ }\r
+\r
+ return array( $width, $height, 'SVG',\r
+ "width=\"$width\" height=\"$height\"" );\r
+}\r
+\r
+/**\r
+ * Determine if an image exists on the 'bad image list'.\r
+ *\r
+ * @param $name String: the image name to check\r
+ * @return bool\r
+ */\r
+function wfIsBadImage( $name ) {\r
+ static $titleList = false;\r
+ \r
+ if( !$titleList ) {\r
+ # Build the list now\r
+ $titleList = array();\r
+ $lines = explode( "\n", wfMsgForContent( 'bad_image_list' ) );\r
+ foreach( $lines as $line ) {\r
+ if( preg_match( '/^\*\s*\[\[:?(.*?)\]\]/i', $line, $matches ) ) {\r
+ $title = Title::newFromText( $matches[1] );\r
+ if( is_object( $title ) && $title->getNamespace() == NS_IMAGE )\r
+ $titleList[ $title->getDBkey() ] = true;\r
+ }\r
+ }\r
+ }\r
+ return array_key_exists( $name, $titleList );\r
+}\r
+\r
+/**\r
+ * Calculate the largest thumbnail width for a given original file size\r
+ * such that the thumbnail's height is at most $maxHeight.\r
+ * @param $boxWidth Integer Width of the thumbnail box.\r
+ * @param $boxHeight Integer Height of the thumbnail box.\r
+ * @param $maxHeight Integer Maximum height expected for the thumbnail.\r
+ * @return Integer.\r
+ */\r
+function wfFitBoxWidth( $boxWidth, $boxHeight, $maxHeight ) {\r
+ $idealWidth = $boxWidth * $maxHeight / $boxHeight;\r
+ $roundedUp = ceil( $idealWidth );\r
+ if( round( $roundedUp * $boxHeight / $boxWidth ) > $maxHeight )\r
+ return floor( $idealWidth );\r
+ else\r
+ return $roundedUp;\r
+}\r
+\r
+\r
+?>\r
var $mInitialised = false;
var $mDeferred = true;
- function initialise( &$memCached, $useDB, $expiry, $memcPrefix) {
+ function __construct( &$memCached, $useDB, $expiry, $memcPrefix) {
$fname = 'MessageCache::initialise';
wfProfileIn( $fname );
$this->mInitialised = true;
wfProfileIn( $fname.'-parseropt' );
- $this->mParserOptions = ParserOptions::newFromUser( $u=NULL );
+ $this->mParserOptions = new ParserOptions( $u=NULL );
wfProfileOut( $fname.'-parseropt' );
wfProfileIn( $fname.'-parser' );
$this->mParser = new Parser;
* @param string $lang The messages language, English by default
*/
function addMessages( $messages, $lang = 'en' ) {
+ wfProfileIn( __METHOD__ );
foreach ( $messages as $key => $value ) {
$this->addMessage( $key, $value, $lang );
}
+ wfProfileOut( __METHOD__ );
}
/**
* @subpackage Parser
*/
-/** */
-require_once( 'Sanitizer.php' );
-require_once( 'HttpFunctions.php' );
-
/**
* Update this version number when the ParserOutput format
* changes in an incompatible way, so the parser cache
}
}
- $text = wfGetHTTP($url);
+ $text = Http::get($url);
if (!$text)
return wfMsg('scarytranscludefailed', $url);
var $mTidy; # Ask for tidy cleanup
var $mInterfaceMessage; # Which lang to call for PLURAL and GRAMMAR
+ var $mUser; # Stored user object, just used to initialise the skin
+
function getUseTeX() { return $this->mUseTeX; }
function getUseDynamicDates() { return $this->mUseDynamicDates; }
function getInterwikiMagic() { return $this->mInterwikiMagic; }
function getAllowExternalImages() { return $this->mAllowExternalImages; }
function getAllowExternalImagesFrom() { return $this->mAllowExternalImagesFrom; }
- function &getSkin() { return $this->mSkin; }
function getDateFormat() { return $this->mDateFormat; }
function getEditSection() { return $this->mEditSection; }
function getNumberHeadings() { return $this->mNumberHeadings; }
function getTidy() { return $this->mTidy; }
function getInterfaceMessage() { return $this->mInterfaceMessage; }
+ function &getSkin() {
+ if ( !isset( $this->mSkin ) ) {
+ $this->mSkin = $this->mUser->getSkin();
+ }
+ return $this->mSkin;
+ }
+
function setUseTeX( $x ) { return wfSetVar( $this->mUseTeX, $x ); }
function setUseDynamicDates( $x ) { return wfSetVar( $this->mUseDynamicDates, $x ); }
function setInterwikiMagic( $x ) { return wfSetVar( $this->mInterwikiMagic, $x ); }
function setSkin( &$x ) { $this->mSkin =& $x; }
function setInterfaceMessage( $x ) { return wfSetVar( $this->mInterfaceMessage, $x); }
- function ParserOptions() {
- global $wgUser;
- $this->initialiseFromUser( $wgUser );
+ function ParserOptions( $user = null ) {
+ $this->initialiseFromUser( $user );
}
/**
* @static
*/
function newFromUser( &$user ) {
- $popts = new ParserOptions;
- $popts->initialiseFromUser( $user );
- return $popts;
+ return new ParserOptions( $user );
}
/** Get user options */
$fname = 'ParserOptions::initialiseFromUser';
wfProfileIn( $fname );
if ( !$userInput ) {
- $user = new User;
- $user->setLoaded( true );
+ global $wgUser;
+ if ( isset( $wgUser ) ) {
+ $user = $wgUser;
+ } else {
+ $user = new User;
+ $user->setLoaded( true );
+ }
} else {
$user =& $userInput;
}
+ $this->mUser = $user;
+
$this->mUseTeX = $wgUseTeX;
$this->mUseDynamicDates = $wgUseDynamicDates;
$this->mInterwikiMagic = $wgInterwikiMagic;
$this->mAllowExternalImages = $wgAllowExternalImages;
$this->mAllowExternalImagesFrom = $wgAllowExternalImagesFrom;
- wfProfileIn( $fname.'-skin' );
- $this->mSkin =& $user->getSkin();
- wfProfileOut( $fname.'-skin' );
+ $this->mSkin = null; # Deferred
$this->mDateFormat = $user->getOption( 'date' );
$this->mEditSection = true;
$this->mNumberHeadings = $user->getOption( 'numberheadings' );
require_once( "$IP/includes/Hooks.php" );
require_once( "$IP/includes/Namespace.php" );
require_once( "$IP/includes/User.php" );
-require_once( "$IP/includes/Skin.php" );
require_once( "$IP/includes/OutputPage.php" );
require_once( "$IP/includes/MagicWord.php" );
-require_once( "$IP/includes/Block.php" );
require_once( "$IP/includes/MessageCache.php" );
require_once( "$IP/includes/Parser.php" );
require_once( "$IP/includes/LoadBalancer.php" );
-require_once( "$IP/includes/HistoryBlob.php" );
require_once( "$IP/includes/ProxyTools.php" );
require_once( "$IP/includes/ObjectCache.php" );
+require_once( "$IP/includes/ImageFunctions.php" );
if ( $wgUseDynamicDates ) {
require_once( "$IP/includes/DateFormatter.php" );
wfProfileOut( $fname.'-language2' );
wfProfileIn( $fname.'-MessageCache' );
-$wgMessageCache = new MessageCache;
-$wgMessageCache->initialise( $parserMemc, $wgUseDatabaseMessages, $wgMsgCacheExpiry, $wgDBname);
+$wgMessageCache = new MessageCache( $parserMemc, $wgUseDatabaseMessages, $wgMsgCacheExpiry, $wgDBname);
wfProfileOut( $fname.'-MessageCache' );
$wgPostCommitUpdateList = array();
$wgMagicWords = array();
-$wgMwRedir =& MagicWord::get( MAG_REDIRECT );
if ( $wgUseXMLparser ) {
require_once( 'ParserXML.php' );
*/
# See skin.txt
-require_once( 'Linker.php' );
-require_once( 'Image.php' );
-
-# Get a list of available skins
-# Build using the regular expression '^(.*).php$'
-# Array keys are all lower case, array value keep the case used by filename
-#
-
-$skinDir = dir( $wgStyleDirectory );
-
-# while code from www.php.net
-while (false !== ($file = $skinDir->read())) {
- // Skip non-PHP files, hidden files, and '.dep' includes
- if(preg_match('/^([^.]*)\.php$/',$file, $matches)) {
- $aSkin = $matches[1];
- $wgValidSkinNames[strtolower($aSkin)] = $aSkin;
- }
-}
-$skinDir->close();
-unset($matches);
/**
* The main skin class that provide methods and properties for all other skins.
* @return array of strings
* @static
*/
- function getSkinNames() {
+ function &getSkinNames() {
global $wgValidSkinNames;
+ static $skinsInitialised = false;
+ if ( !$skinsInitialised ) {
+ # Get a list of available skins
+ # Build using the regular expression '^(.*).php$'
+ # Array keys are all lower case, array value keep the case used by filename
+ #
+ wfProfileIn( __METHOD__ . '-init' );
+ global $wgStyleDirectory;
+ $skinDir = dir( $wgStyleDirectory );
+
+ # while code from www.php.net
+ while (false !== ($file = $skinDir->read())) {
+ // Skip non-PHP files, hidden files, and '.dep' includes
+ if(preg_match('/^([^.]*)\.php$/',$file, $matches)) {
+ $aSkin = $matches[1];
+ $wgValidSkinNames[strtolower($aSkin)] = $aSkin;
+ }
+ }
+ $skinDir->close();
+ $skinsInitialised = true;
+ wfProfileOut( __METHOD__ . '-init' );
+ }
return $wgValidSkinNames;
}
global $wgSpecialPages;
global $wgDisableCounters, $wgDisableInternalSearch, $wgEmailAuthentication;
- #throw new MWException( __METHOD__ );
-
if ( self::$mListInitialised ) {
return;
}
* @access private
*/
function mainPrefsForm( $status , $message = '' ) {
- global $wgUser, $wgOut, $wgLang, $wgContLang, $wgValidSkinNames;
+ global $wgUser, $wgOut, $wgLang, $wgContLang;
global $wgAllowRealName, $wgImageLimits, $wgThumbLimits;
global $wgDisableLangConversion;
global $wgEnotifWatchlist, $wgEnotifUserTalk,$wgEnotifMinorEdits;
$wgOut->addHTML( "<fieldset>\n<legend>\n" . wfMsg('skin') . "</legend>\n" );
$mptitle = Title::newMainPage();
$previewtext = wfMsg('skinpreview');
- # Only show members of $wgValidSkinNames rather than
+ # Only show members of Skin::getSkinNames() rather than
# $skinNames (skins is all skin names from Language.php)
- foreach ($wgValidSkinNames as $skinkey => $skinname ) {
+ $validSkinNames = Skin::getSkinNames();
+ foreach ($validSkinNames as $skinkey => $skinname ) {
if ( in_array( $skinkey, $wgSkipSkins ) ) {
continue;
}
* @access public
*/
function newFromRedirect( $text ) {
- global $wgMwRedir;
+ $mwRedir = MagicWord::get( MAG_REDIRECT );
$rt = NULL;
- if ( $wgMwRedir->matchStart( $text ) ) {
+ if ( $mwRedir->matchStart( $text ) ) {
if ( preg_match( '/\[{2}(.*?)(?:\||\]{2})/', $text, $m ) ) {
# categories are escaped using : for example one can enter:
# #REDIRECT [[:Category:Music]]. Need to remove it.
* Check that the corresponding skin exists
*/
function isValidCssJsSubpage() {
- global $wgValidSkinNames;
- return( $this->isCssJsSubpage() && array_key_exists( $this->getSkinFromCssJsSubpage(), $wgValidSkinNames ) );
+ if ( $this->isCssJsSubpage() ) {
+ $skinNames = Skin::getSkinNames();
+ return array_key_exists( $this->getSkinFromCssJsSubpage(), $skinNames );
+ } else {
+ return false;
+ }
}
/**
* Trim down a .css or .js subpage title to get the corresponding skin name
* @private
*/
function moveOverExistingRedirect( &$nt, $reason = '' ) {
- global $wgUseSquid, $wgMwRedir;
+ global $wgUseSquid;
$fname = 'Title::moveOverExistingRedirect';
$comment = wfMsgForContent( '1movedto2', $this->getPrefixedText(), $nt->getPrefixedText() );
$linkCache->clearLink( $nt->getPrefixedDBkey() );
# Recreate the redirect, this time in the other direction.
- $redirectText = $wgMwRedir->getSynonym( 0 ) . ' [[' . $nt->getPrefixedText() . "]]\n";
+ $mwRedir = MagicWord::get( MAG_REDIRECT );
+ $redirectText = $mwRedir->getSynonym( 0 ) . ' [[' . $nt->getPrefixedText() . "]]\n";
$redirectArticle = new Article( $this );
$newid = $redirectArticle->insertOn( $dbw );
$redirectRevision = new Revision( array(
*/
function moveToNewTitle( &$nt, $reason = '' ) {
global $wgUseSquid;
- global $wgMwRedir;
$fname = 'MovePageForm::moveToNewTitle';
$comment = wfMsgForContent( '1movedto2', $this->getPrefixedText(), $nt->getPrefixedText() );
if ( $reason ) {
$linkCache->clearLink( $nt->getPrefixedDBkey() );
# Insert redirect
- $redirectText = $wgMwRedir->getSynonym( 0 ) . ' [[' . $nt->getPrefixedText() . "]]\n";
+ $mwRedir = MagicWord::get( MAG_REDIRECT );
+ $redirectText = $mwRedir->getSynonym( 0 ) . ' [[' . $nt->getPrefixedText() . "]]\n";
$redirectArticle = new Article( $this );
$newid = $redirectArticle->insertOn( $dbw );
$redirectRevision = new Revision( array(
--- /dev/null
+<?php\r
+\r
+/**\r
+ * Module of static functions for generating XML\r
+ */\r
+\r
+class Xml {\r
+ /**\r
+ * Format an XML element with given attributes and, optionally, text content.\r
+ * Element and attribute names are assumed to be ready for literal inclusion.\r
+ * Strings are assumed to not contain XML-illegal characters; special\r
+ * characters (<, >, &) are escaped but illegals are not touched.\r
+ *\r
+ * @param $element String:\r
+ * @param $attribs Array: Name=>value pairs. Values will be escaped.\r
+ * @param $contents String: NULL to make an open tag only; '' for a contentless closed tag (default)\r
+ * @return string\r
+ */\r
+ function element( $element, $attribs = null, $contents = '') {\r
+ $out = '<' . $element;\r
+ if( !is_null( $attribs ) ) {\r
+ foreach( $attribs as $name => $val ) {\r
+ $out .= ' ' . $name . '="' . htmlspecialchars( $val ) . '"';\r
+ }\r
+ }\r
+ if( is_null( $contents ) ) {\r
+ $out .= '>';\r
+ } else {\r
+ if( $contents === '' ) {\r
+ $out .= ' />';\r
+ } else {\r
+ $out .= '>' . htmlspecialchars( $contents ) . "</$element>";\r
+ }\r
+ }\r
+ return $out;\r
+ }\r
+\r
+ /**\r
+ * Format an XML element as with self::element(), but run text through the\r
+ * UtfNormal::cleanUp() validator first to ensure that no invalid UTF-8\r
+ * is passed.\r
+ *\r
+ * @param $element String:\r
+ * @param $attribs Array: Name=>value pairs. Values will be escaped.\r
+ * @param $contents String: NULL to make an open tag only; '' for a contentless closed tag (default)\r
+ * @return string\r
+ */\r
+ function elementClean( $element, $attribs = array(), $contents = '') {\r
+ if( $attribs ) {\r
+ $attribs = array_map( array( 'UtfNormal', 'cleanUp' ), $attribs );\r
+ }\r
+ if( $contents ) {\r
+ $contents = UtfNormal::cleanUp( $contents );\r
+ }\r
+ return self::element( $element, $attribs, $contents );\r
+ }\r
+\r
+ // Shortcuts\r
+ function openElement( $element, $attribs = null ) { return self::element( $element, $attribs, null ); }\r
+ function closeElement( $element ) { return "</$element>"; }\r
+\r
+ /**\r
+ * Create a namespace selector\r
+ *\r
+ * @param $selected Mixed: the namespace which should be selected, default ''\r
+ * @param $allnamespaces String: value of a special item denoting all namespaces. Null to not include (default)\r
+ * @param $includehidden Bool: include hidden namespaces?\r
+ * @return String: Html string containing the namespace selector\r
+ */\r
+ function &namespaceSelector($selected = '', $allnamespaces = null, $includehidden=false) {\r
+ global $wgContLang;\r
+ if( $selected !== '' ) {\r
+ if( is_null( $selected ) ) {\r
+ // No namespace selected; let exact match work without hitting Main\r
+ $selected = '';\r
+ } else {\r
+ // Let input be numeric strings without breaking the empty match.\r
+ $selected = intval( $selected );\r
+ }\r
+ }\r
+ $s = "<select id='namespace' name='namespace' class='namespaceselector'>\n\t";\r
+ $arr = $wgContLang->getFormattedNamespaces();\r
+ if( !is_null($allnamespaces) ) {\r
+ $arr = array($allnamespaces => wfMsg('namespacesall')) + $arr;\r
+ }\r
+ foreach ($arr as $index => $name) {\r
+ if ($index < NS_MAIN) continue;\r
+\r
+ $name = $index !== 0 ? $name : wfMsg('blanknamespace');\r
+\r
+ if ($index === $selected) {\r
+ $s .= self::element("option",\r
+ array("value" => $index, "selected" => "selected"),\r
+ $name);\r
+ } else {\r
+ $s .= self::element("option", array("value" => $index), $name);\r
+ }\r
+ }\r
+ $s .= "\n</select>\n";\r
+ return $s;\r
+ }\r
+\r
+ function span( $text, $class, $attribs=array() ) {\r
+ return self::element( 'span', array( 'class' => $class ) + $attribs, $text );\r
+ }\r
+\r
+ /**\r
+ * Convenience function to build an HTML text input field\r
+ * @return string HTML\r
+ */\r
+ function input( $name, $size=false, $value=false, $attribs=array() ) {\r
+ return self::element( 'input', array(\r
+ 'name' => $name,\r
+ 'size' => $size,\r
+ 'value' => $value ) + $attribs );\r
+ }\r
+\r
+ /**\r
+ * Internal function for use in checkboxes and radio buttons and such.\r
+ * @return array\r
+ */\r
+ function attrib( $name, $present = true ) {\r
+ return $present ? array( $name => $name ) : array();\r
+ }\r
+\r
+ /**\r
+ * Convenience function to build an HTML checkbox\r
+ * @return string HTML\r
+ */\r
+ function check( $name, $checked=false, $attribs=array() ) {\r
+ return self::element( 'input', array(\r
+ 'name' => $name,\r
+ 'type' => 'checkbox',\r
+ 'value' => 1 ) + self::attrib( 'checked', $checked ) + $attribs );\r
+ }\r
+\r
+ /**\r
+ * Convenience function to build an HTML radio button\r
+ * @return string HTML\r
+ */\r
+ function radio( $name, $value, $checked=false, $attribs=array() ) {\r
+ return self::element( 'input', array(\r
+ 'name' => $name,\r
+ 'type' => 'radio',\r
+ 'value' => $value ) + self::attrib( 'checked', $checked ) + $attribs );\r
+ }\r
+\r
+ /**\r
+ * Convenience function to build an HTML form label\r
+ * @return string HTML\r
+ */\r
+ function label( $label, $id ) {\r
+ return self::element( 'label', array( 'for' => $id ), $label );\r
+ }\r
+\r
+ /**\r
+ * Convenience function to build an HTML text input field with a label\r
+ * @return string HTML\r
+ */\r
+ function inputLabel( $label, $name, $id, $size=false, $value=false, $attribs=array() ) {\r
+ return Xml::label( $label, $id ) .\r
+ ' ' .\r
+ self::input( $name, $size, $value, array( 'id' => $id ) + $attribs );\r
+ }\r
+\r
+ /**\r
+ * Convenience function to build an HTML checkbox with a label\r
+ * @return string HTML\r
+ */\r
+ function checkLabel( $label, $name, $id, $checked=false, $attribs=array() ) {\r
+ return self::check( $name, $checked, array( 'id' => $id ) + $attribs ) .\r
+ ' ' .\r
+ self::label( $label, $id );\r
+ }\r
+\r
+ /**\r
+ * Convenience function to build an HTML radio button with a label\r
+ * @return string HTML\r
+ */\r
+ function radioLabel( $label, $name, $value, $id, $checked=false, $attribs=array() ) {\r
+ return self::radio( $name, $value, $checked, array( 'id' => $id ) + $attribs ) .\r
+ ' ' .\r
+ self::label( $label, $id );\r
+ }\r
+\r
+ /**\r
+ * Convenience function to build an HTML submit button\r
+ * @param $value String: label text for the button\r
+ * @param $attribs Array: optional custom attributes\r
+ * @return string HTML\r
+ */\r
+ function submitButton( $value, $attribs=array() ) {\r
+ return self::element( 'input', array( 'type' => 'submit', 'value' => $value ) + $attribs );\r
+ }\r
+\r
+ /**\r
+ * Convenience function to build an HTML hidden form field.\r
+ * @todo Document $name parameter.\r
+ * @param $name FIXME\r
+ * @param $value String: label text for the button\r
+ * @param $attribs Array: optional custom attributes\r
+ * @return string HTML\r
+ */\r
+ function hidden( $name, $value, $attribs=array() ) {\r
+ return self::element( 'input', array(\r
+ 'name' => $name,\r
+ 'type' => 'hidden',\r
+ 'value' => $value ) + $attribs );\r
+ }\r
+\r
+ /**\r
+ * Returns an escaped string suitable for inclusion in a string literal\r
+ * for JavaScript source code.\r
+ * Illegal control characters are assumed not to be present.\r
+ *\r
+ * @param string $string\r
+ * @return string\r
+ */\r
+ function escapeJsString( $string ) {\r
+ // See ECMA 262 section 7.8.4 for string literal format\r
+ $pairs = array(\r
+ "\\" => "\\\\",\r
+ "\"" => "\\\"",\r
+ '\'' => '\\\'',\r
+ "\n" => "\\n",\r
+ "\r" => "\\r",\r
+\r
+ # To avoid closing the element or CDATA section\r
+ "<" => "\\x3c",\r
+ ">" => "\\x3e",\r
+ );\r
+ return strtr( $string, $pairs );\r
+ }\r
+\r
+ /**\r
+ * Check if a string is well-formed XML.\r
+ * Must include the surrounding tag.\r
+ *\r
+ * @param $text String: string to test.\r
+ * @return bool\r
+ *\r
+ * @todo Error position reporting return\r
+ */\r
+ function isWellFormed( $text ) {\r
+ $parser = xml_parser_create( "UTF-8" );\r
+\r
+ # case folding violates XML standard, turn it off\r
+ xml_parser_set_option( $parser, XML_OPTION_CASE_FOLDING, false );\r
+\r
+ if( !xml_parse( $parser, $text, true ) ) {\r
+ $err = xml_error_string( xml_get_error_code( $parser ) );\r
+ $position = xml_get_current_byte_index( $parser );\r
+ //$fragment = $this->extractFragment( $html, $position );\r
+ //$this->mXmlError = "$err at byte $position:\n$fragment";\r
+ xml_parser_free( $parser );\r
+ return false;\r
+ }\r
+ xml_parser_free( $parser );\r
+ return true;\r
+ }\r
+\r
+ /**\r
+ * Check if a string is a well-formed XML fragment.\r
+ * Wraps fragment in an \<html\> bit and doctype, so it can be a fragment\r
+ * and can use HTML named entities.\r
+ *\r
+ * @param $text String:\r
+ * @return bool\r
+ */\r
+ function isWellFormedXmlFragment( $text ) {\r
+ $html =\r
+ Sanitizer::hackDocType() .\r
+ '<html>' .\r
+ $text .\r
+ '</html>';\r
+ return Xml::isWellFormedXml( $html );\r
+ }\r
+}\r
+?>\r
<?php
/**
- * Format an XML element with given attributes and, optionally, text content.
- * Element and attribute names are assumed to be ready for literal inclusion.
- * Strings are assumed to not contain XML-illegal characters; special
- * characters (<, >, &) are escaped but illegals are not touched.
- *
- * @param $element String:
- * @param $attribs Array: Name=>value pairs. Values will be escaped.
- * @param $contents String: NULL to make an open tag only; '' for a contentless closed tag (default)
- * @return string
+ * Aliases for functions in the Xml module
*/
-function wfElement( $element, $attribs = null, $contents = '') {
- $out = '<' . $element;
- if( !is_null( $attribs ) ) {
- foreach( $attribs as $name => $val ) {
- $out .= ' ' . $name . '="' . htmlspecialchars( $val ) . '"';
- }
- }
- if( is_null( $contents ) ) {
- $out .= '>';
- } else {
- if( $contents === '' ) {
- $out .= ' />';
- } else {
- $out .= '>' . htmlspecialchars( $contents ) . "</$element>";
- }
- }
- return $out;
+function wfElement( $element, $attribs = null, $contents = '') {
+ return Xml::element( $element, $attribs, $contents );
}
-
-/**
- * Format an XML element as with wfElement(), but run text through the
- * UtfNormal::cleanUp() validator first to ensure that no invalid UTF-8
- * is passed.
- *
- * @param $element String:
- * @param $attribs Array: Name=>value pairs. Values will be escaped.
- * @param $contents String: NULL to make an open tag only; '' for a contentless closed tag (default)
- * @return string
- */
function wfElementClean( $element, $attribs = array(), $contents = '') {
- if( $attribs ) {
- $attribs = array_map( array( 'UtfNormal', 'cleanUp' ), $attribs );
- }
- if( $contents ) {
- $contents = UtfNormal::cleanUp( $contents );
- }
- return wfElement( $element, $attribs, $contents );
+ return Xml::elementClean( $element, $attribs, $contents );
+}
+function wfOpenElement( $element, $attribs = null ) {
+ return Xml::openElement( $element, $attribs );
+}
+function wfCloseElement( $element ) {
+ return "</$element>";
}
-
-// Shortcuts
-function wfOpenElement( $element, $attribs = null ) { return wfElement( $element, $attribs, null ); }
-function wfCloseElement( $element ) { return "</$element>"; }
-
-/**
- * Create a namespace selector
- *
- * @param $selected Mixed: the namespace which should be selected, default ''
- * @param $allnamespaces String: value of a special item denoting all namespaces. Null to not include (default)
- * @param $includehidden Bool: include hidden namespaces?
- * @return String: Html string containing the namespace selector
- */
function &HTMLnamespaceselector($selected = '', $allnamespaces = null, $includehidden=false) {
- global $wgContLang;
- if( $selected !== '' ) {
- if( is_null( $selected ) ) {
- // No namespace selected; let exact match work without hitting Main
- $selected = '';
- } else {
- // Let input be numeric strings without breaking the empty match.
- $selected = intval( $selected );
- }
- }
- $s = "<select id='namespace' name='namespace' class='namespaceselector'>\n\t";
- $arr = $wgContLang->getFormattedNamespaces();
- if( !is_null($allnamespaces) ) {
- $arr = array($allnamespaces => wfMsg('namespacesall')) + $arr;
- }
- foreach ($arr as $index => $name) {
- if ($index < NS_MAIN) continue;
-
- $name = $index !== 0 ? $name : wfMsg('blanknamespace');
-
- if ($index === $selected) {
- $s .= wfElement("option",
- array("value" => $index, "selected" => "selected"),
- $name);
- } else {
- $s .= wfElement("option", array("value" => $index), $name);
- }
- }
- $s .= "\n</select>\n";
- return $s;
+ return Xml::namespaceSelector( $selected = '', $allnamespaces = null, $includehidden=false );
}
-
function wfSpan( $text, $class, $attribs=array() ) {
- return wfElement( 'span', array( 'class' => $class ) + $attribs, $text );
+ return Xml::span( $text, $class, $attribs );
}
-
-/**
- * Convenience function to build an HTML text input field
- * @return string HTML
- */
function wfInput( $name, $size=false, $value=false, $attribs=array() ) {
- return wfElement( 'input', array(
- 'name' => $name,
- 'size' => $size,
- 'value' => $value ) + $attribs );
+ return Xml::input( $name, $size, $value, $attribs );
}
-
-/**
- * Internal function for use in checkboxes and radio buttons and such.
- * @return array
- */
function wfAttrib( $name, $present = true ) {
- return $present ? array( $name => $name ) : array();
+ return Xml::attrib( $name, $present );
}
-
-/**
- * Convenience function to build an HTML checkbox
- * @return string HTML
- */
function wfCheck( $name, $checked=false, $attribs=array() ) {
- return wfElement( 'input', array(
- 'name' => $name,
- 'type' => 'checkbox',
- 'value' => 1 ) + wfAttrib( 'checked', $checked ) + $attribs );
+ return Xml::check( $name, $checked, $attribs );
}
-
-/**
- * Convenience function to build an HTML radio button
- * @return string HTML
- */
function wfRadio( $name, $value, $checked=false, $attribs=array() ) {
- return wfElement( 'input', array(
- 'name' => $name,
- 'type' => 'radio',
- 'value' => $value ) + wfAttrib( 'checked', $checked ) + $attribs );
+ return Xml::radio( $name, $value, $checked, $attribs );
}
-
-/**
- * Convenience function to build an HTML form label
- * @return string HTML
- */
function wfLabel( $label, $id ) {
- return wfElement( 'label', array( 'for' => $id ), $label );
+ return Xml::label( $label, $id );
}
-
-/**
- * Convenience function to build an HTML text input field with a label
- * @return string HTML
- */
function wfInputLabel( $label, $name, $id, $size=false, $value=false, $attribs=array() ) {
- return wfLabel( $label, $id ) .
- ' ' .
- wfInput( $name, $size, $value, array( 'id' => $id ) + $attribs );
+ return Xml::inputLabel( $label, $name, $id, $size, $value, $attribs );
}
-
-/**
- * Convenience function to build an HTML checkbox with a label
- * @return string HTML
- */
function wfCheckLabel( $label, $name, $id, $checked=false, $attribs=array() ) {
- return wfCheck( $name, $checked, array( 'id' => $id ) + $attribs ) .
- ' ' .
- wfLabel( $label, $id );
+ return Xml::checkLabel( $label, $name, $id, $checked, $attribs );
}
-
-/**
- * Convenience function to build an HTML radio button with a label
- * @return string HTML
- */
function wfRadioLabel( $label, $name, $value, $id, $checked=false, $attribs=array() ) {
- return wfRadio( $name, $value, $checked, array( 'id' => $id ) + $attribs ) .
- ' ' .
- wfLabel( $label, $id );
+ return Xml::radioLabel( $label, $name, $value, $id, $checked, $attribs );
}
-
-/**
- * Convenience function to build an HTML submit button
- * @param $value String: label text for the button
- * @param $attribs Array: optional custom attributes
- * @return string HTML
- */
function wfSubmitButton( $value, $attribs=array() ) {
- return wfElement( 'input', array( 'type' => 'submit', 'value' => $value ) + $attribs );
+ return Xml::submitButton( $value, $attribs );
}
-
-/**
- * Convenience function to build an HTML hidden form field.
- * @todo Document $name parameter.
- * @param $name FIXME
- * @param $value String: label text for the button
- * @param $attribs Array: optional custom attributes
- * @return string HTML
- */
function wfHidden( $name, $value, $attribs=array() ) {
- return wfElement( 'input', array(
- 'name' => $name,
- 'type' => 'hidden',
- 'value' => $value ) + $attribs );
+ return Xml::hidden( $name, $value, $attribs );
}
-
-/**
- * Returns an escaped string suitable for inclusion in a string literal
- * for JavaScript source code.
- * Illegal control characters are assumed not to be present.
- *
- * @param string $string
- * @return string
- */
function wfEscapeJsString( $string ) {
- // See ECMA 262 section 7.8.4 for string literal format
- $pairs = array(
- "\\" => "\\\\",
- "\"" => "\\\"",
- '\'' => '\\\'',
- "\n" => "\\n",
- "\r" => "\\r",
-
- # To avoid closing the element or CDATA section
- "<" => "\\x3c",
- ">" => "\\x3e",
- );
- return strtr( $string, $pairs );
+ return Xml::escapeJsString( $string );
}
-
-/**
- * Check if a string is well-formed XML.
- * Must include the surrounding tag.
- *
- * @param $text String: string to test.
- * @return bool
- *
- * @todo Error position reporting return
- */
function wfIsWellFormedXml( $text ) {
- $parser = xml_parser_create( "UTF-8" );
-
- # case folding violates XML standard, turn it off
- xml_parser_set_option( $parser, XML_OPTION_CASE_FOLDING, false );
-
- if( !xml_parse( $parser, $text, true ) ) {
- $err = xml_error_string( xml_get_error_code( $parser ) );
- $position = xml_get_current_byte_index( $parser );
- //$fragment = $this->extractFragment( $html, $position );
- //$this->mXmlError = "$err at byte $position:\n$fragment";
- xml_parser_free( $parser );
- return false;
- }
- xml_parser_free( $parser );
- return true;
+ return Xml::isWellFormed( $text );
}
-
-/**
- * Check if a string is a well-formed XML fragment.
- * Wraps fragment in an \<html\> bit and doctype, so it can be a fragment
- * and can use HTML named entities.
- *
- * @param $text String:
- * @return bool
- */
function wfIsWellFormedXmlFragment( $text ) {
- $html =
- Sanitizer::hackDocType() .
- '<html>' .
- $text .
- '</html>';
- return wfIsWellFormedXml( $html );
+ return Xml::isWellFormedXmlFragment( $text );
}
$GLOBALS['wgContLang'] = $langObj;
$GLOBALS['wgLoadBalancer']->loadMasterPos();
- $GLOBALS['wgMessageCache']->initialise( new BagOStuff(), false, 0, $GLOBALS['wgDBname'] );
+ $GLOBALS['wgMessageCache'] = new MessageCache( new BagOStuff(), false, 0, $GLOBALS['wgDBname'] );
$this->setupDatabase();
global $wgUser;