Extension:ProtectText/ProtectText.php

From MediaWiki.org

Jump to: navigation, search
<?php
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License along
# with this program; if not, write to the Free Software Foundation, Inc.,
# 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
# http://www.gnu.org/copyleft/gpl.html

/**
 * This is an extension that let you protect some part of a text. You just
 * have to be a member of a group with the 'protecttext' user right or
 * you have to be the sole contributor of the complete text.
 *
 * To protect a text, enclose it in a <protect> </protect> block.
 *
 * @addtogroup Extensions
 *
 * @author ThomasV <thomasv1@gmx.de>, John Erling Blad <john.erling.blad@jeb.no>
 * @copyright Copyright © 2006, ThomasV, John Erling Blad
 * @license http://www.gnu.org/copyleft/gpl.html GNU General Public License 2.0 or later
 */
 
if( !defined( 'MEDIAWIKI' ) ) {
    echo( "This file is an extension to the MediaWiki software and cannot be used standalone.\n" );
    die( 1 );
}
 
$wgExtensionCredits['other'][] = array(
	'name' => 'ProtectText',
	'version'=> '0.4',
	'author' => 'ThomasV, John Erling Blad',
	'description' => 'Allows authorised users, and sole contributors, to protect parts of a text',
	'url' => 'http://www.mediawiki.org/wiki/Extension:ProtectText'
);
 
$dir = dirname(__FILE__) . '/';
$wgExtensionMessagesFiles['ProtectText'] = $dir . 'ProtectText.i18n.php';
 
// Two new permissions
$wgGroupPermissions['*']['protectsolecontributor']  = true;
$wgGroupPermissions['sysop']['protecttext']         = true;
$wgGroupPermissions['bureaucrat']['protecttext']    = true;
$wgAvailableRights[] = 'protecttext';
 
$wgExtensionFunctions[] = 'wfProtectTextSetup';
 
// Register hooks
$wgHooks['ParserBeforeStrip'][] = 'wfStripProtectTags' ;
$wgHooks['EditFilter'][] = 'wfCheckProtectText' ;
 
/**
 * TODO: use some arrays in ./languages/ for proper l10n
 */
function wfProtectTextSetup() {
    wfLoadExtensionMessages( 'ProtectText' );
}
 
/**
 * @param &$parser The parser object
 * @param &$text The text being parsed
 * @param &$x Something not used
 */
function wfStripProtectTags ( &$parser , &$text, &$x ) { 
 
	$text = preg_replace(
		array('/<protect>(.*?)<\/protect>/si', '/(\n;?:*;?)§(.*?)\n/si', '/(\n;?:*;?)§(.*?)$/si', '/\{§(.*?)§\}/si'),
		array("$1", "$1$2\n", "$1$2", "$1"),
		$text);
	return true;
}
 
 
/**
 * @todo Document
 * @param $editpage
 * @param $textbox1
 * @param $section
 * @param $error
 */
function wfCheckProtectText ( $editpage, $textbox1, $section, $error )  {
 
	global $wgUser, $wgTitle, $wgOut, $wgVersion;
	$modifyProtect = false; 
 
	if ( !$wgUser->isAllowed( 'protecttext' ) ) {
		$text1 = $editpage->mArticle->getContent(true);
		$text2 = $textbox1 ;
 
		preg_match_all( "/<protect>(.*?)<\/protect>|\n;?:*;?§(.*?)\n|\{§(.*?)§\}/si", $text1, $list1, PREG_SET_ORDER );
		preg_match_all( "/<protect>(.*?)<\/protect>|\n;?:*;?§(.*?)\n|\{§(.*?)§\}/si", $text2, $list2, PREG_SET_ORDER );
		if( count($list1) < count($list2)) { 
			$error = '<p class="error">' . wfMsg( 'protecttext_remove') . '</p>'; 
			$modifyProtect = true; 
		}
		if( count($list1) > count($list2)) { 
			$error = '<p class="error">' . wfMsg( 'protecttext_add') . '</p>'; 
			$modifyProtect = true; 
		}
		else for ( $i=0 ; $i < count( $list1 ); $i++ ) {
			if( $list1[$i][0] != $list2[$i][0]) { 
				$error = '<p class="error">' . wfMsg( 'protecttext_modify' ) . '</p>';
				$modifyProtect = true; 
				break;
			}
		}
 
		if ( $modifyProtect && $wgUser->isAllowed( 'protectsolecontributor' ) ) {
			$conds['rev_page'] = $wgTitle->getArticleId();
			if( version_compare( $wgVersion, '1.11alpha', '>=' ) )
				$conds[] = 'rev_deleted & ' . Revision::DELETED_USER . ' = 0';
			$contributors = array();
			$dbr = wfGetDB( DB_SLAVE );
			$res = $dbr->select(
				'revision',
				array(
					'COUNT(*) AS count',
					'rev_user',
					'rev_user_text',
				),
				$conds,
				__METHOD__,
				array(
					'GROUP BY' => 'rev_user_text',
					'ORDER BY' => 'count DESC',
				)
			);
			if( $res && $dbr->numRows( $res ) > 0 )
				while( $row = $dbr->fetchObject( $res ) )
					$contributors[ $row->rev_user_text ] = array( $row->rev_user );
			$total = 0;
			foreach( $contributors as $username => $info ) {
				list( $id ) = $info;
				if ($wgUser->getID() != $id) {
					$total++;
					break;
				}
			}
			if (!$total)
				$error = null;
		}
	}
	return true;
}