Abort page restriction if no null revision can be created
authorMatthias Mullie <git@mullie.eu>
Fri, 21 Jun 2013 14:01:52 +0000 (16:01 +0200)
committerMatthias Mullie <git@mullie.eu>
Mon, 8 Jul 2013 16:23:05 +0000 (18:23 +0200)
In practice, this should not currently be happening: null revision can not be
created if no previous revision exists, which should not be the case where we
call the function in doUpdateRestrictions. However, since newNullRevision can
potentially return null (it's documented that way, perhaps some day in the
future, additional code paths can lead to null), we should check for it.

Also: after completing the restriction updates, the null revision is passed
along to a hook, which is documented[1] to get a Revision object. Right now,
in theory, this could be incorrect.

1: https://www.mediawiki.org/wiki/Manual:Hooks/NewRevisionFromEditComplete

Change-Id: I89b0be823d9933d557470005c390a9102f931684

includes/WikiPage.php
languages/messages/MessagesEn.php
languages/messages/MessagesQqq.php
maintenance/language/messages.inc

index 1a46b3e..d4734c9 100644 (file)
@@ -2362,24 +2362,6 @@ class WikiPage implements Page, IDBAccessObject {
                                $cascade = false;
                        }
 
-                       // Update restrictions table
-                       foreach ( $limit as $action => $restrictions ) {
-                               if ( $restrictions != '' ) {
-                                       $dbw->replace( 'page_restrictions', array( array( 'pr_page', 'pr_type' ) ),
-                                               array( 'pr_page' => $id,
-                                                       'pr_type' => $action,
-                                                       'pr_level' => $restrictions,
-                                                       'pr_cascade' => ( $cascade && $action == 'edit' ) ? 1 : 0,
-                                                       'pr_expiry' => $encodedExpiry[$action]
-                                               ),
-                                               __METHOD__
-                                       );
-                               } else {
-                                       $dbw->delete( 'page_restrictions', array( 'pr_page' => $id,
-                                               'pr_type' => $action ), __METHOD__ );
-                               }
-                       }
-
                        // Prepare a null revision to be added to the history
                        $editComment = $wgContLang->ucfirst(
                                wfMessage(
@@ -2401,8 +2383,30 @@ class WikiPage implements Page, IDBAccessObject {
                                )->inContentLanguage()->text();
                        }
 
-                       // Insert a null revision
                        $nullRevision = Revision::newNullRevision( $dbw, $id, $editComment, true );
+                       if ( $nullRevision === null ) {
+                               return Status::newFatal( 'no-null-revision', $this->mTitle->getPrefixedText() );
+                       }
+
+                       // Update restrictions table
+                       foreach ( $limit as $action => $restrictions ) {
+                               if ( $restrictions != '' ) {
+                                       $dbw->replace( 'page_restrictions', array( array( 'pr_page', 'pr_type' ) ),
+                                               array( 'pr_page' => $id,
+                                                       'pr_type' => $action,
+                                                       'pr_level' => $restrictions,
+                                                       'pr_cascade' => ( $cascade && $action == 'edit' ) ? 1 : 0,
+                                                       'pr_expiry' => $encodedExpiry[$action]
+                                               ),
+                                               __METHOD__
+                                       );
+                               } else {
+                                       $dbw->delete( 'page_restrictions', array( 'pr_page' => $id,
+                                               'pr_type' => $action ), __METHOD__ );
+                               }
+                       }
+
+                       // Insert a null revision
                        $nullRevId = $nullRevision->insertOn( $dbw );
 
                        $latest = $this->getLatest();
index 973c946..556d7dd 100644 (file)
@@ -1039,6 +1039,7 @@ It may have already been deleted by someone else.',
 'cannotdelete-title'            => 'Cannot delete page "$1"',
 'delete-hook-aborted'           => 'Deletion aborted by hook.
 It gave no explanation.',
+'no-null-revision'              => 'Could not create new null revision for page "$1"',
 'badtitle'                      => 'Bad title',
 'badtitletext'                  => 'The requested page title was invalid, empty, or an incorrectly linked inter-language or inter-wiki title.
 It may contain one or more characters that cannot be used in titles.',
index 7582c6c..8d9597f 100644 (file)
@@ -982,6 +982,7 @@ See also:
 'cannotdelete-title' => 'Title of error page when the user cannot delete a page. Parameters:
 * $1 - the page name',
 'delete-hook-aborted' => 'Error message shown when an extension hook prevents a page deletion, but does not provide an error message.',
+'no-null-revision' => 'Error message shown when no null revision could be created to reflect a protection level change.',
 'badtitle' => 'The page title when a user requested a page with invalid page name. The content will be {{msg-mw|badtitletext}}.',
 'badtitletext' => 'The message shown when a user requested a page with invalid page name. The page title will be {{msg-mw|badtitle}}.
 
index 2cb94cf..bc6219e 100644 (file)
@@ -403,6 +403,7 @@ $wgMessageStructure = array(
                'cannotdelete',
                'cannotdelete-title',
                'delete-hook-aborted',
+               'no-null-revision',
                'badtitle',
                'badtitletext',
                'perfcached',