Index: trunk/extensions/AuthorProtect/AuthorProtect.php |
— | — | @@ -1,12 +1,13 @@ |
2 | 2 | <?php |
3 | | -/* |
4 | | -* AuthorProtect extension by Ryan Schmidt |
5 | | -* See http://www.mediawiki.org/wiki/Extension:AuthorProtect for more details |
6 | | -*/ |
7 | 3 | |
8 | | -if(!defined('MEDIAWIKI')) { |
9 | | - echo("This file is an extension to MediaWiki and cannot be run externally"); |
10 | | - die(1); |
| 4 | +/** |
| 5 | + * AuthorProtect extension by Ryan Schmidt |
| 6 | + * See http://www.mediawiki.org/wiki/Extension:AuthorProtect for more details |
| 7 | + */ |
| 8 | + |
| 9 | +if( !defined( 'MEDIAWIKI' ) ) { |
| 10 | + echo "This file is an extension to MediaWiki and cannot be run externally\n"; |
| 11 | + die( 1 ); |
11 | 12 | } |
12 | 13 | |
13 | 14 | $wgExtensionCredits['other'][] = array( |
— | — | @@ -15,132 +16,178 @@ |
16 | 17 | 'author' => 'Ryan Schmidt', |
17 | 18 | 'url' => 'http://www.mediawiki.org/wiki/Extension:AuthorProtect', |
18 | 19 | 'version' => '1.2', |
19 | | - 'description' => 'Allows the author of a page to protect it from other users', |
| 20 | + 'description' => 'Allows the author of a page to protect it from other users', |
20 | 21 | 'descriptionmsg' => 'authorprotect-desc', |
21 | 22 | ); |
22 | 23 | |
23 | | -$wgAvailableRights[] = 'author'; //dynamically assigned to the author of a page, but can be set w/ GroupPermissions too |
| 24 | +$wgAvailableRights[] = 'author'; //dynamically assigned to the author of a page, but can be set w/ wgGroupPermissions too |
24 | 25 | $wgAvailableRights[] = 'authorprotect'; //users without this right cannot protect pages they author |
25 | | -$wgExtensionMessagesFiles['AuthorProtect'] = dirname(__FILE__) . '/AuthorProtect.i18n.php'; |
| 26 | +$wgExtensionMessagesFiles['AuthorProtect'] = dirname( __FILE__ ) . '/AuthorProtect.i18n.php'; |
26 | 27 | $wgGroupPermissions['sysop']['author'] = true; //sysops can edit every page despite author protection |
27 | 28 | $wgGroupPermissions['user']['authorprotect'] = true; //registered users can protect pages they author |
28 | 29 | $wgHooks['SkinTemplateContentActions'][] = 'efMakeContentAction'; |
29 | 30 | $wgHooks['UnknownAction'][] = 'efAuthorProtectForm'; |
30 | 31 | $wgHooks['userCan'][] = 'efAuthorProtectDelay'; |
| 32 | +$wgHooks['UserGetRights'][] = 'efAssignAuthor'; |
31 | 33 | $wgRestrictionLevels[] = 'author'; //so sysops, etc. using the normal protection interface can protect and unprotect it at the author level |
32 | 34 | |
33 | | -// FIXME: split off into one or more class files to reduce initial loading time |
34 | | -function efAuthorProtectDelay($title, &$user, $action, $result) { |
35 | | - $user->mRights = null; |
36 | | - $wgHooks['UserGetRights'][] = 'efAssignAuthor'; |
37 | | - $user->getRights(); //delay hook execution for compatibility w/ ConfirmAccount |
38 | | - $act = ( $action == '' || $action == 'view' ) ? 'edit' : $action; |
39 | | - if( userIsAuthor() && isAuthorProtected($title, $act) ) { |
40 | | - $result = true; |
41 | | - return false; |
| 35 | +//internal variables, do not modify |
| 36 | +$wgAuthorProtectDoProtect = false; |
| 37 | +$wgAuthorProtectDelayRun = true; |
| 38 | + |
| 39 | +/** |
| 40 | + * Extensions like ConfirmAccount do some weird stuff to $wgTitle during the UserGetRights hook |
| 41 | + * So this delays the hook's execution to a point where $wgTitle is set |
| 42 | + */ |
| 43 | +function efAuthorProtectDelay( $title, &$user, $action, $result ) { |
| 44 | + global $wgAuthorProtectDelayRun; |
| 45 | + if( $wgAuthorProtectDelayRun ) { |
| 46 | + $user->mRights = null; |
| 47 | + $user->getRights(); //delay hook execution for compatibility w/ ConfirmAccount |
| 48 | + $act = ( $action == '' || $action == 'view' ) ? 'edit' : $action; |
| 49 | + $wgAuthorProtectDelayRun = false; |
| 50 | + if( userIsAuthor() && isAuthorProtected( $title, $act ) ) { |
| 51 | + $result = true; |
| 52 | + return false; |
| 53 | + } |
42 | 54 | } |
43 | 55 | $result = null; |
44 | 56 | return true; |
45 | 57 | } |
46 | 58 | |
47 | | -function efAssignAuthor(&$user, &$aRights) { |
| 59 | +function efAssignAuthor( &$user, &$aRights ) { |
48 | 60 | //don't assign author to anons... messes up logging stuff. |
49 | 61 | //plus it's all user_id based so it is impossible to differentiate one anon from another |
50 | 62 | if( userIsAuthor() && $user->isLoggedIn() ) { |
51 | 63 | $aRights[] = 'author'; |
52 | | - $aRights = array_unique($aRights); |
| 64 | + $aRights = array_unique( $aRights ); |
53 | 65 | } |
| 66 | + //assign protect too if we need to |
| 67 | + global $wgAuthorProtectDoProtect; |
| 68 | + if( $wgAuthorProtectDoProtect ) { |
| 69 | + $aRights[] = 'protect'; |
| 70 | + $aRights = array_unique( $aRights ); |
| 71 | + } |
54 | 72 | return true; |
55 | 73 | } |
56 | 74 | |
57 | | -function efMakeContentAction(&$cactions) { |
| 75 | +function efAuthorProtectAssignProtect() { |
| 76 | + global $wgAuthorProtectDoProtect, $wgUser; |
| 77 | + $wgAuthorProtectDoProtect = true; |
| 78 | + $wgUser->mRights = null; |
| 79 | + $wgUser->getRights(); //re-trigger the above function to assign the protect right |
| 80 | + $wgAuthorProtectDoProtect = false; |
| 81 | +} |
| 82 | + |
| 83 | +function efAuthorProtectUnassignProtect() { |
| 84 | + global $wgUser; |
| 85 | + $wgUser->mRights = null; |
| 86 | + $wgUser->getRights(); |
| 87 | +} |
| 88 | + |
| 89 | +function efMakeContentAction( &$cactions ) { |
58 | 90 | global $wgUser, $wgRequest, $wgTitle; |
59 | | - if( userIsAuthor() && $wgUser->isAllowed('authorprotect') && !$wgUser->isAllowed('protect') ) { |
60 | | - $action = $wgRequest->getText('action'); |
| 91 | + if( userIsAuthor() && $wgUser->isAllowed( 'authorprotect' ) && !$wgUser->isAllowed( 'protect' ) ) { |
| 92 | + $action = $wgRequest->getText( 'action' ); |
61 | 93 | $cactions['authorprotect'] = array( |
62 | 94 | 'class' => $action == 'authorprotect' ? 'selected' : false, |
63 | | - 'text' => wfMsg(protectMessage($wgTitle)), |
64 | | - 'href' => $wgTitle->getLocalUrl('action=authorprotect'), |
| 95 | + 'text' => wfMsg( efAuthorProtectMessage( $wgTitle ) ), |
| 96 | + 'href' => $wgTitle->getLocalUrl( 'action=authorprotect' ), |
65 | 97 | ); |
66 | 98 | } |
67 | 99 | return true; |
68 | 100 | } |
69 | 101 | |
70 | | -function efAuthorProtectForm($action, &$article) { |
71 | | - global $wgTitle; |
72 | | - if($action == 'authorprotect') { |
73 | | - wfLoadExtensionMessages('AuthorProtect'); |
| 102 | +function efAuthorProtectForm( $action, &$article ) { |
| 103 | + global $wgTitle, $wgAuthorProtectDoProtect; |
| 104 | + if( $action == 'authorprotect' ) { |
| 105 | + wfLoadExtensionMessages( 'AuthorProtect' ); |
74 | 106 | global $wgOut, $wgUser, $wgRequest, $wgRestrictionTypes; |
75 | | - if($wgUser->isAllowed('authorprotect')) { |
76 | | - if(userIsAuthor()) { |
77 | | - $wgOut->setPageTitle(wfMsg('authorprotect')); |
| 107 | + if( $wgUser->isAllowed( 'authorprotect' ) ) { |
| 108 | + if( userIsAuthor() ) { |
| 109 | + $wgOut->setPageTitle( wfMsg( 'authorprotect' ) ); |
78 | 110 | if( !$wgRequest->wasPosted() ) { |
79 | | - $wgOut->addHTML(makeProtectForm()); |
| 111 | + $wgOut->addHTML( efAuthorProtectMakeProtectForm() ); |
80 | 112 | } else { |
81 | 113 | if( !$wgUser->matchEditToken( $wgRequest->getText('wpToken') ) ) { |
82 | | - $wgOut->setPageTitle(wfMsg('errorpagetitle')); |
83 | | - $wgOut->addWikiText(wfMsg('sessionfailure')); |
| 114 | + $wgOut->setPageTitle( wfMsg( 'errorpagetitle' ) ); |
| 115 | + $wgOut->addWikiText( wfMsg( 'sessionfailure' ) ); |
84 | 116 | return; |
85 | 117 | } |
86 | 118 | $restrictions = array(); |
| 119 | + $expiration = array(); |
| 120 | + $expiry = efAuthorProtectExpiry( $wgRequest->getText( 'wpExpiryTime' ) ); |
87 | 121 | foreach( $wgRestrictionTypes as $type ) { |
88 | | - $rest = $wgTitle->getRestrictions($type); |
| 122 | + $rest = $wgTitle->getRestrictions( $type ); |
89 | 123 | if( $rest !== array() ) { |
90 | | - if(!$wgUser->isAllowed($rest[0]) && !in_array('author', $rest) ) { |
| 124 | + if( !$wgUser->isAllowed( $rest[0] ) && !in_array( 'author', $rest ) ) { |
91 | 125 | $restrictions[$type] = $rest[0]; //don't let them lower the protection level |
92 | 126 | continue; |
93 | 127 | } |
94 | 128 | } |
95 | | - if( $wgRequest->getCheck("check-{$type}") ) { |
| 129 | + if( $wgRequest->getCheck( "check-{$type}" ) ) { |
96 | 130 | $restrictions[$type] = 'author'; |
| 131 | + $expiration[$type] = $expiry; |
97 | 132 | } else { |
98 | 133 | if( in_array( 'author', $rest ) ) { |
99 | 134 | $restrictions[$type] = ''; |
| 135 | + $expiration[$type] = $expiry; |
100 | 136 | } else { |
101 | | - $restrictions[$type] = $rest !== array() ? $rest[0] : ''; //we're not setting it |
| 137 | + $restrictions[$type] = ( $rest !== array() ) ? $rest[0] : ''; //we're not setting it |
| 138 | + $expiration[$type] = $expiry; |
102 | 139 | } |
103 | 140 | } |
104 | 141 | } |
105 | | - $success = doProtect( $restrictions, $wgRequest->getText('wpReason'), $wgRequest->getText('wpExpiryTime') ); |
106 | | - if($success) { |
107 | | - $wgOut->addWikiText(wfMsg('authorprotect-success')); |
| 142 | + $cascade = false; |
| 143 | + efAuthorProtectAssignProtect(); |
| 144 | + $str = var_export(array('restrictions' => $restrictions, 'reason' => $wgRequest->getText('wpReason'), 'cascade' => $cascade, 'expiry' => $expiration), true); |
| 145 | + wfDebugLog('authorprotect', $str); |
| 146 | + $success = $article->updateRestrictions( |
| 147 | + $restrictions, //array of restrictions |
| 148 | + $wgRequest->getText( 'wpReason' ), //reason |
| 149 | + $cascade, //cascading protection disabled, need to pass by reference |
| 150 | + $expiration //expiration |
| 151 | + ); |
| 152 | + efAuthorProtectUnassignProtect(); |
| 153 | + if( $success ) { |
| 154 | + $wgOut->addWikiText( wfMsg( 'authorprotect-success' ) ); |
108 | 155 | } else { |
109 | | - $wgOut->addWikiText(wfMsg('authorprotect-failure')); |
| 156 | + $wgOut->addWikiText( wfMsg( 'authorprotect-failure' ) ); |
110 | 157 | } |
111 | 158 | } |
112 | 159 | } else { |
113 | | - $wgOut->setPageTitle(wfMsg('errorpagetitle')); |
114 | | - $wgOut->addWikiText(wfMsg('authorprotect-notauthor')); |
| 160 | + $wgOut->setPageTitle( wfMsg('errorpagetitle') ); |
| 161 | + $wgOut->addWikiText( wfMsg('authorprotect-notauthor') ); |
115 | 162 | } |
116 | 163 | } else { |
117 | | - $wgOut->permissionRequired('authorprotect'); |
| 164 | + $wgOut->permissionRequired( 'authorprotect' ); |
118 | 165 | } |
119 | 166 | return false; //still continues hook processing, but doesn't throw an error message |
120 | 167 | } |
121 | 168 | return true; //unknown action, so state that the action doesn't exist |
122 | 169 | } |
123 | 170 | |
124 | | -function makeProtectForm() { |
| 171 | +function efAuthorProtectMakeProtectForm() { |
125 | 172 | global $wgRestrictionTypes, $wgTitle, $wgUser; |
126 | 173 | $token = $wgUser->editToken(); |
127 | | - $form = '<p>' . wfMsg('authorprotect-intro') . '</p>'; |
128 | | - $form .= Xml::openElement( 'form', array( 'method' => 'post', 'action' => $wgTitle->getLocalUrl('action=authorprotect') ) ); |
| 174 | + $form = Xml::openElement( 'p' ) . wfMsg( 'authorprotect-intro' ) . Xml::closeElement( 'p' ); |
| 175 | + $form .= Xml::openElement( 'form', array( 'method' => 'post', 'action' => $wgTitle->getLocalUrl( 'action=authorprotect' ) ) ); |
129 | 176 | foreach( $wgRestrictionTypes as $type ) { |
130 | | - $rest = $wgTitle->getRestrictions($type); |
| 177 | + $rest = $wgTitle->getRestrictions( $type ); |
131 | 178 | if( $rest !== array() ) { |
132 | | - if(!$wgUser->isAllowed($rest[0]) && !in_array('author', $rest) ) |
| 179 | + if( !$wgUser->isAllowed( $rest[0] ) && !in_array( 'author', $rest ) ) |
133 | 180 | continue; //it's protected at a level higher than them, so don't let them change it so they can now mess with stuff |
134 | 181 | } |
135 | 182 | $checked = in_array( 'author', $rest ); |
136 | 183 | $array = array( 'type' => 'checkbox', 'name' => 'check-' . $type, 'value' => $type ); |
137 | | - if($checked) |
| 184 | + if( $checked ) |
138 | 185 | $array = array_merge( $array, array( 'checked' => 'checked' ) ); |
139 | 186 | $form .= Xml::element( 'input', $array ); |
140 | | - $form .= ' ' . wfMsg('authorprotect-' . $type) . Xml::element( 'br' ); |
| 187 | + $form .= ' ' . wfMsg( 'authorprotect-' . $type ) . Xml::element( 'br' ); |
141 | 188 | } |
142 | | - $form .= Xml::element( 'br' ) . Xml::element( 'label', array( 'for' => 'wpExpiryTime' ), wfMsg('authorprotect-expiry') ) . ' '; |
| 189 | + $form .= Xml::element( 'br' ) . Xml::element( 'label', array( 'for' => 'wpExpiryTime' ), wfMsg( 'authorprotect-expiry' ) ) . ' '; |
143 | 190 | $form .= Xml::element( 'input', array( 'type' => 'text', 'name' => 'wpExpiryTime' ) ) . Xml::element( 'br' ); |
144 | | - $form .= Xml::element( 'br' ) . Xml::element( 'label', array( 'for' => 'wpReason' ), wfMsg('authorprotect-reason') ) . ' '; |
| 191 | + $form .= Xml::element( 'br' ) . Xml::element( 'label', array( 'for' => 'wpReason' ), wfMsg( 'authorprotect-reason' ) ) . ' '; |
145 | 192 | $form .= Xml::element( 'input', array( 'type' => 'text', 'name' => 'wpReason' ) ); |
146 | 193 | $form .= Xml::element( 'br' ) . Xml::element( 'input', array( 'type' => 'hidden', 'name' => 'wpToken', 'value' => $token ) ); |
147 | 194 | $form .= Xml::element( 'br' ) . Xml::element( 'input', array( 'type' => 'submit', 'name' => 'wpConfirm', 'value' => wfMsg( 'authorprotect-confirm' ) ) ); |
— | — | @@ -149,17 +196,16 @@ |
150 | 197 | } |
151 | 198 | |
152 | 199 | function userIsAuthor() { |
153 | | - global $wgTitle, $wgUser, $wgDBprefix; |
154 | | - if(!$wgTitle instanceOf Title) |
| 200 | + global $wgTitle, $wgUser; |
| 201 | + if( !$wgTitle instanceOf Title ) |
155 | 202 | return false; //quick hack to prevent the API from messing up. |
156 | 203 | $id = $wgTitle->getArticleId(); |
157 | | - $dbr = wfGetDB(DB_SLAVE); //grab the slave for reading |
158 | | - $res = $dbr->query( "SELECT `rev_user` FROM `{$wgDBprefix}revision` WHERE rev_page={$id} LIMIT 1", __METHOD__ ); |
159 | | - $row = $dbr->fetchRow($res); |
160 | | - return $wgUser->getID() == $row['rev_user']; |
| 204 | + $dbr = wfGetDB( DB_SLAVE ); //grab the slave for reading |
| 205 | + $aid = $dbr->selectField( 'revision', 'rev_user', array( 'rev_page' => $id ), __METHOD__ ); |
| 206 | + return $wgUser->getID() == $aid; |
161 | 207 | } |
162 | 208 | |
163 | | -function protectMessage($title) { |
| 209 | +function efAuthorProtectMessage( $title ) { |
164 | 210 | global $wgRestrictionTypes; |
165 | 211 | foreach( $wgRestrictionTypes as $type ) { |
166 | 212 | if( in_array( 'author', $title->getRestrictions( $type ) ) ) |
— | — | @@ -168,126 +214,25 @@ |
169 | 215 | return 'protect'; |
170 | 216 | } |
171 | 217 | |
172 | | -// do the protection, copied from Article.php's updateRestrictions then modified |
173 | | -// so that it isn't so picky about having the 'protect' right. |
174 | | -function doProtect( $limit = array(), $reason = '', &$expiry = '' ) { |
175 | | - global $wgUser, $wgRestrictionTypes, $wgContLang, $wgTitle; |
| 218 | +function isAuthorProtected($title, $action) { |
| 219 | + $rest = $title->getRestrictions($action); |
| 220 | + return in_array('author', $rest); |
| 221 | +} |
176 | 222 | |
177 | | - $id = $wgTitle->getArticleID(); |
178 | | - if( wfReadOnly() || $id == 0 ) { |
179 | | - return false; |
180 | | - } |
181 | | - |
182 | | - if ( strlen( $expiry ) == 0 ) { |
183 | | - $expiry = 'infinite'; |
184 | | - } |
185 | | - |
186 | | - if ( $expiry == 'infinite' || $expiry == 'indefinite' ) { |
187 | | - $expiry = Block::infinity(); |
| 223 | +//forked from ProtectionForm::getExpiry and modified to rewrite '' to infinity |
| 224 | +function efAuthorProtectExpiry( $value ) { |
| 225 | + if ( $value == 'infinite' || $value == 'indefinite' || $value == 'infinity' || $value == '' ) { |
| 226 | + $time = Block::infinity(); |
188 | 227 | } else { |
189 | | - # Convert GNU-style date, on error returns -1 for PHP <5.1 and false for PHP >=5.1 |
190 | | - $expiry = strtotime( $expiry ); |
| 228 | + $unix = strtotime( $value ); |
191 | 229 | |
192 | | - if ( $expiry < 0 || $expiry === false ) { |
193 | | - //invalid expiry, rewrite to infinity |
194 | | - $expiry = Block::infinity(); |
195 | | - } else { |
196 | | - // Fixme: non-qualified absolute times are not in users specified timezone |
197 | | - // and there isn't notice about it in the ui |
198 | | - $expiry = wfTimestamp( TS_MW, $expiry ); |
| 230 | + if ( !$unix || $unix === -1 ) { |
| 231 | + return false; |
199 | 232 | } |
200 | | - } |
201 | | - |
202 | | - // Take this opportunity to purge out expired restrictions |
203 | | - Title::purgeExpiredRestrictions(); |
204 | 233 | |
205 | | - # FIXME: Same limitations as described in ProtectionForm.php (line 37); |
206 | | - # we expect a single selection, but the schema allows otherwise. |
207 | | - $current = array(); |
208 | | - foreach( $wgRestrictionTypes as $action ) |
209 | | - $current[$action] = implode( '', $wgTitle->getRestrictions( $action ) ); |
210 | | - |
211 | | - $current = Article::flattenRestrictions( $current ); |
212 | | - $updated = Article::flattenRestrictions( $limit ); |
213 | | - $changed = ( $current != $updated ); |
214 | | - $changed = $changed || ($wgTitle->mRestrictionsExpiry != $expiry); |
215 | | - $protect = ( $updated != '' ); |
216 | | - |
217 | | - # If nothing's changed, do nothing |
218 | | - if( $changed ) { |
219 | | - global $wgGroupPermissions; |
220 | | - |
221 | | - $dbw = wfGetDB( DB_MASTER ); |
222 | | - |
223 | | - $encodedExpiry = Block::encodeExpiry($expiry, $dbw ); |
224 | | - |
225 | | - $expiry_description = ''; |
226 | | - if ( $encodedExpiry != 'infinity' ) { |
227 | | - $expiry_description = ' (' . wfMsgForContent( |
228 | | - 'protect-expiring', |
229 | | - $wgContLang->timeanddate( $expiry, false, false ), |
230 | | - $wgContLang->date( $expiry, false, false ), |
231 | | - $wgContLang->time( $expiry, false, false ) |
232 | | - ) . ')'; |
233 | | - } |
234 | | - |
235 | | - # Prepare a null revision to be added to the history |
236 | | - $modified = $current != '' && $protect; |
237 | | - if ( $protect ) { |
238 | | - $comment_type = $modified ? 'modifiedarticleprotection' : 'protectedarticle'; |
239 | | - } else { |
240 | | - $comment_type = 'unprotectedarticle'; |
241 | | - } |
242 | | - $comment = $wgContLang->ucfirst( wfMsgForContent( $comment_type, $wgTitle->getPrefixedText() ) ); |
243 | | - |
244 | | - if( $reason ) |
245 | | - $comment .= ": $reason"; |
246 | | - if( $protect ) |
247 | | - $comment .= " [$updated]"; |
248 | | - if ( $expiry_description && $protect ) |
249 | | - $comment .= "$expiry_description"; |
250 | | - |
251 | | - # Update restrictions table |
252 | | - foreach( $limit as $action => $restrictions ) { |
253 | | - if ($restrictions != '' ) { |
254 | | - $dbw->replace( 'page_restrictions', array(array('pr_page', 'pr_type')), |
255 | | - array( 'pr_page' => $id, 'pr_type' => $action |
256 | | - , 'pr_level' => $restrictions, 'pr_cascade' => 0 |
257 | | - , 'pr_expiry' => $encodedExpiry ), __METHOD__ ); |
258 | | - } else { |
259 | | - $dbw->delete( 'page_restrictions', array( 'pr_page' => $id, |
260 | | - 'pr_type' => $action ), __METHOD__ ); |
261 | | - } |
262 | | - } |
263 | | - |
264 | | - # Insert a null revision |
265 | | - $nullRevision = Revision::newNullRevision( $dbw, $id, $comment, true ); |
266 | | - $nullRevId = $nullRevision->insertOn( $dbw ); |
267 | | - |
268 | | - # Update page record |
269 | | - $dbw->update( 'page', |
270 | | - array( /* SET */ |
271 | | - 'page_touched' => $dbw->timestamp(), |
272 | | - 'page_restrictions' => '', |
273 | | - 'page_latest' => $nullRevId |
274 | | - ), array( /* WHERE */ |
275 | | - 'page_id' => $id |
276 | | - ), 'Article::protect' |
277 | | - ); |
278 | | - # Update the protection log |
279 | | - $log = new LogPage( 'protect' ); |
280 | | - |
281 | | - if( $protect ) { |
282 | | - $log->addEntry( $modified ? 'modify' : 'protect', $wgTitle, trim( $reason . " [$updated]$expiry_description" ) ); |
283 | | - } else { |
284 | | - $log->addEntry( 'unprotect', $wgTitle, $reason ); |
285 | | - } |
286 | | - } # End "changed" check |
287 | | - |
288 | | - return true; |
| 234 | + // Fixme: non-qualified absolute times are not in users specified timezone |
| 235 | + // and there isn't notice about it in the ui |
| 236 | + $time = wfTimestamp( TS_MW, $unix ); |
| 237 | + } |
| 238 | + return $time; |
289 | 239 | } |
290 | | - |
291 | | -function isAuthorProtected($title, $action) { |
292 | | - $rest = $title->getRestrictions($action); |
293 | | - return in_array('author', $rest); |
294 | | -} |