ApiAggregateGroups.php

Go to the documentation of this file.
00001 <?php
00018 class ApiAggregateGroups extends ApiBase {
00019     protected static $right = 'translate-manage';
00020     protected static $salt = 'translate-manage';
00021 
00022     public function execute() {
00023         if ( !$this->getUser()->isAllowed( self::$right ) ) {
00024             $this->dieUsage( 'Permission denied', 'permissiondenied' );
00025         }
00026 
00027         $params = $this->extractRequestParams();
00028         $action = $params['do'];
00029         $output = array();
00030         if ( $action === 'associate' || $action === 'dissociate' ) {
00031             // Group is mandatory only for these two actions
00032             if ( !isset( $params['group'] ) ) {
00033                 $this->dieUsageMsg( array( 'missingparam', 'group' ) );
00034             }
00035             if ( !isset( $params['aggregategroup'] ) ) {
00036                 $this->dieUsageMsg( array( 'missingparam', 'aggregategroup' ) );
00037             }
00038             $aggregateGroup = $params['aggregategroup'];
00039             $subgroups = TranslateMetadata::getSubgroups( $aggregateGroup );
00040             if ( count( $subgroups ) === 0 ) {
00041                 // For newly created groups the subgroups value might be empty,
00042                 // but check that.
00043                 if ( TranslateMetadata::get( $aggregateGroup, 'name' ) === false ) {
00044                     $this->dieUsage( 'Invalid aggregate message group', 'invalidaggregategroup' );
00045                 }
00046                 $subgroups = array();
00047             }
00048 
00049             $subgroupId = $params['group'];
00050             $group = MessageGroups::getGroup( $subgroupId );
00051 
00052             // Add or remove from the list
00053             if ( $action === 'associate' ) {
00054                 if ( !$group instanceof WikiPageMessageGroup ) {
00055                     $this->dieUsage( 'Group does not exist or invalid', 'invalidgroup' );
00056                 }
00057 
00058                 $subgroups[] = $subgroupId;
00059                 $subgroups = array_unique( $subgroups );
00060             } elseif ( $action === 'dissociate' ) {
00061                 // Allow removal of non-existing groups
00062                 $subgroups = array_flip( $subgroups );
00063                 unset( $subgroups[$subgroupId] );
00064                 $subgroups = array_flip( $subgroups );
00065             }
00066 
00067             TranslateMetadata::setSubgroups( $aggregateGroup, $subgroups );
00068 
00069             $logParams = array(
00070                 'aggregategroup' => TranslateMetadata::get( $aggregateGroup, 'name' ),
00071                 'aggregategroup-id' => $aggregateGroup,
00072             );
00073 
00074             /* Note that to allow removing no longer existing groups from
00075              * aggregate message groups, the message group object $group
00076              * might not always be available. In this case we need to fake
00077              * some title. */
00078             $title = $group ?
00079                 $group->getTitle() :
00080                 Title::newFromText( "Special:Translate/$subgroupId" );
00081 
00082             $entry = new ManualLogEntry( 'pagetranslation', $action );
00083             $entry->setPerformer( $this->getUser() );
00084             $entry->setTarget( $title );
00085             // @todo
00086             // $entry->setComment( $comment );
00087             $entry->setParameters( $logParams );
00088 
00089             $logid = $entry->insert();
00090             $entry->publish( $logid );
00091         } elseif ( $action === 'remove' ) {
00092             if ( !isset( $params['aggregategroup'] ) ) {
00093                 $this->dieUsageMsg( array( 'missingparam', 'aggregategroup' ) );
00094             }
00095             TranslateMetadata::deleteGroup( $params['aggregategroup'] );
00096             // @todo Logging
00097 
00098         } elseif ( $action === 'add' ) {
00099             if ( !isset( $params['groupname'] ) ) {
00100                 $this->dieUsageMsg( array( 'missingparam', 'groupname' ) );
00101             }
00102             $name = trim( $params['groupname'] );
00103             if ( strlen( $name ) === 0 ) {
00104                 $this->dieUsage( 'Invalid aggregate message group name', 'invalidaggregategroupname' );
00105             }
00106 
00107             if ( !isset( $params['groupdescription'] ) ) {
00108                 $this->dieUsageMsg( array( 'missingparam', 'groupdescription' ) );
00109             }
00110             $desc = trim( $params['groupdescription'] );
00111 
00112             $aggregateGroupId = self::generateAggregateGroupId( $name );
00113             $exists = MessageGroups::getGroup( $aggregateGroupId );
00114             if ( $exists ) {
00115                 $this->dieUsage( 'Message group already exists', 'duplicateaggregategroup' );
00116             }
00117 
00118             TranslateMetadata::set( $aggregateGroupId, 'name', $name );
00119             TranslateMetadata::set( $aggregateGroupId, 'description', $desc );
00120             TranslateMetadata::setSubgroups( $aggregateGroupId, array() );
00121 
00122             // Once new aggregate group added, we need to show all the pages that can be added to that.
00123             $output['groups'] = self::getAllPages();
00124             $output['aggregategroupId'] = $aggregateGroupId;
00125             // @todo Logging
00126         }
00127 
00128         // If we got this far, nothing has failed
00129         $output['result'] = 'ok';
00130         $this->getResult()->addValue( null, $this->getModuleName(), $output );
00131         // Cache needs to be cleared after any changes to groups
00132         MessageGroups::clearCache();
00133         MessageIndexRebuildJob::newJob()->insert();
00134     }
00135 
00136     protected function generateAggregateGroupId( $aggregateGroupName, $prefix = "agg-" ) {
00137         // The database field has maximum limit of 200 bytes
00138         if ( strlen( $aggregateGroupName ) + strlen( $prefix ) >= 200 ) {
00139             return $prefix . substr( sha1( $aggregateGroupName ), 0, 5 );
00140         } else {
00141             $pattern = '/[\x00-\x1f\x23\x27\x2c\x2e\x3c\x3e\x5b\x5d\x7b\x7c\x7d\x7f\s]+/i';
00142             return $prefix . preg_replace( $pattern, '_', $aggregateGroupName );
00143         }
00144     }
00145 
00146     public function isWriteMode() {
00147         return true;
00148     }
00149 
00150     public function getTokenSalt() {
00151         return self::$salt;
00152     }
00153 
00154     public function needsToken() {
00155         return true;
00156     }
00157 
00158     public function getAllowedParams() {
00159         return array(
00160             'do' => array(
00161                 ApiBase::PARAM_TYPE => array( 'associate', 'dissociate', 'remove', 'add' ),
00162                 ApiBase::PARAM_REQUIRED => true,
00163             ),
00164             'aggregategroup' => array(
00165                 ApiBase::PARAM_TYPE => 'string',
00166             ),
00167             'group' => array(
00168                 // Not providing list of values, to allow dissociation of unknown groups
00169                 ApiBase::PARAM_TYPE => 'string',
00170             ),
00171             'groupname' => array(
00172                 ApiBase::PARAM_TYPE => 'string',
00173             ),
00174             'groupdescription' => array(
00175                 ApiBase::PARAM_TYPE => 'string',
00176             ),
00177             'token' => array(
00178                 ApiBase::PARAM_TYPE => 'string',
00179                 ApiBase::PARAM_REQUIRED => false,
00180             ),
00181         );
00182     }
00183 
00184     public function getParamDescription() {
00185         $action = TranslateUtils::getTokenAction( 'aggregategroups' );
00186 
00187         return array(
00188             'do' => 'What to do with aggregate message group',
00189             'group' => 'Message group id',
00190             'aggregategroup' => 'Aggregate message group id',
00191             'groupname' => 'Aggregate message group name',
00192             'groupdescription' => 'Aggregate message group description',
00193             'token' => "A token previously acquired with $action",
00194         );
00195     }
00196 
00197     public function getDescription() {
00198         return 'Manage aggregate message groups. You can add and remove aggregate message' .
00199             'groups and associate or dissociate message groups from them (one at a time).';
00200     }
00201 
00202     public function getPossibleErrors() {
00203         $right = self::$right;
00204 
00205         return array_merge( parent::getPossibleErrors(), array(
00206             array( 'code' => 'permissiondenied', 'info' => "You must have $right right" ),
00207         ) );
00208     }
00209 
00210     public function getExamples() {
00211         return array(
00212             "api.php?action=aggregategroups&do=associate&group=groupId&aggregategroup=aggregateGroupId",
00213         );
00214     }
00215 
00216     public function getVersion() {
00217         return __CLASS__ . ': ' . TRANSLATE_VERSION;
00218     }
00219 
00220     public static function getAllPages() {
00221         $groups = MessageGroups::getAllGroups();
00222         $pages = array();
00223         foreach ( $groups as $group ) {
00224             if ( $group instanceof WikiPageMessageGroup ) {
00225                 $pages[$group->getId()] = $group->getTitle()->getPrefixedText();
00226             }
00227         }
00228 
00229         return $pages;
00230     }
00231 
00232     public static function getToken() {
00233         $user = RequestContext::getMain()->getUser();
00234         if ( !$user->isAllowed( self::$right ) ) {
00235             return false;
00236         }
00237 
00238         return $user->getEditToken( self::$salt );
00239     }
00240 
00241     public static function injectTokenFunction( &$list ) {
00242         $list['aggregategroups'] = array( __CLASS__, 'getToken' );
00243 
00244         return true; // Hooks must return bool
00245     }
00246 
00247     public static function getRight() {
00248         return self::$right;
00249     }
00250 }
Generated on Tue Oct 29 00:00:23 2013 for MediaWiki Translate Extension by  doxygen 1.6.3