From 0934e6b7043d8776bae1106dc7b70ae15a001878 Mon Sep 17 00:00:00 2001 From: David Haslip <103548776+davidhaslip@users.noreply.github.com> Date: Tue, 31 Dec 2024 21:23:49 -0800 Subject: [PATCH] Merge changes (#6) * (doc) Fix typo in comment * (tests) Run phpcs/phan via GitHub Actions * (1.43) Replace deprecated wfGetDB() * (1.43) Replace removed method User::getGroups() * (1.43) Replace nonexistent method ParserOutput::getRootText() * (1.43) Replace deprecated WikiPage::factory() * (1.43) Fix phan warning caused by incorrect type annotation * (1.43) Fix "undeclared class LinksUpdate" (class was renamed) * (phan) Fix "unused parameter" warnings * (1.43) Replace deprecated ContentHandler::getContentText() * (1.43) Replace deprecated ParserOutput::getText() * (1.43) Replace deprecated Status::getHTML() --------- Co-authored-by: Edward Chernenko --- .github/workflows/main.yml | 54 ++++++++++++++++++++++++++++++++++++++ .phan/config.php | 16 +++++++++++ composer.json | 7 ++--- extension.json | 2 +- src/AccessControlHooks.php | 52 ++++++++++++++++++++---------------- 5 files changed, 105 insertions(+), 26 deletions(-) create mode 100644 .github/workflows/main.yml create mode 100644 .phan/config.php diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml new file mode 100644 index 0000000..59b329c --- /dev/null +++ b/.github/workflows/main.yml @@ -0,0 +1,54 @@ +name: JSON linter + luacheck + +on: [push, pull_request, workflow_dispatch] + +env: + DBTYPE: mysql + DBUSER: root + +jobs: + # PHP linters: phpcs, parallel-lint, etc. + linter: + runs-on: ubuntu-22.04 + steps: + - uses: actions/checkout@v4 + - uses: shivammathur/setup-php@v2 + with: + php-version: '8.1' + tools: composer + - uses: actions/cache@v4 + with: + path: ~/.composer/cache + key: buildcache-linter + - run: sudo apt-get install -y composer && composer install + - run: composer test + + # Phan (PHP static analyzer) + phan: + runs-on: ubuntu-22.04 + env: + branch: REL1_43 + steps: + - uses: actions/checkout@v4 + - uses: shivammathur/setup-php@v2 + with: + php-version: '8.1' + extensions: ast + tools: composer + - uses: actions/cache@v4 + with: + path: | + ~/.composer/cache + buildcache + key: buildcache-phan + - uses: edwardspec/github-action-build-mediawiki@v1 + with: + branch: ${{ env.branch }} + noinstall: 1 + - name: Install dependencies + run: | + rsync -a --exclude buildcache --exclude mediawiki --exclude .git . mediawiki/extensions/AccessControl/ + cd mediawiki/extensions/AccessControl + composer install + - name: RUN -- phan + run: cd mediawiki/extensions/AccessControl && ./vendor/bin/phan --analyze-twice diff --git a/.phan/config.php b/.phan/config.php new file mode 100644 index 0000000..9ba6a8d --- /dev/null +++ b/.phan/config.php @@ -0,0 +1,16 @@ += 1.32.0" + "MediaWiki": ">= 1.43.0" }, "AutoloadClasses": { "AccessControlHooks": "src/AccessControlHooks.php" diff --git a/src/AccessControlHooks.php b/src/AccessControlHooks.php index 2af57c2..f7284b4 100644 --- a/src/AccessControlHooks.php +++ b/src/AccessControlHooks.php @@ -1,5 +1,7 @@ + * @phan-var array */ private static $cache = []; @@ -20,7 +22,7 @@ class AccessControlHooks { * @phan-var array * * Format: [ 'pageName1' => true, ... ] - * This is only used of $wgAccessControlAllowTextSnippetInSearchResultsForAll is true, + * This is only used if $wgAccessControlAllowTextSnippetInSearchResultsForAll is true, * which allows restricted pages to appear in search results. * * This array will contain the list of all restricted pages (which current user can't read) @@ -42,12 +44,11 @@ public static function accessControlExtension( Parser $parser ) { /** * Function called by accessControlExtension * @param string $input - * @param string[] $args + * @param string[] $args @phan-unused-param * @param Parser $parser - * @param PPFrame $frame * @return string */ - public static function doControlUserAccess( string $input, array $args, Parser $parser, PPFrame $frame ) { + public static function doControlUserAccess( string $input, array $args, Parser $parser ) { $parserOutput = $parser->getOutput(); $data = $parserOutput->getExtensionData( self::TAG_CONTENT_ARRAY ) ?: []; $inputArray = explode( ',', $input ); @@ -90,11 +91,12 @@ private static function canUserDoAction( User $user, ?array $tagContentArray, st return $return; } - if ( self::getConfigValue( 'AdminCanReadAll' ) && - in_array( 'sysop', $user->getGroups(), true ) - ) { - // Admin can read all - return $return; + if ( self::getConfigValue( 'AdminCanReadAll' ) ) { + $ugm = MediaWikiServices::getInstance()->getUserGroupManager(); + if ( in_array( 'sysop', $ugm->listAllGroups() ) ) { + // Admin can read all + return $return; + } } $userName = $user->isAnon() ? '*' : $user->getName(); @@ -165,12 +167,14 @@ public static function onOutputPageParserOutput( OutputPage $out, ParserOutput $ $status = self::canUserDoAction( $user, $tagContentArray, $actionName ); if ( !$status->getValue() ) { // User has no access - $parserOutput->setText( wfMessage( 'accesscontrol-info-box', $parserOutput->getRootText() )->parse() ); + $parserOutput->setRawText( + $out->msg( 'accesscontrol-info-box', $out->getTitle()->getRootText() )->parse() + ); } if ( !$status->isGood() ) { $text = $parserOutput->getRawText(); - $text = Html::rawElement( 'div', [ 'class' => 'error' ], $status->getHTML() ) . "\n$text"; - $parserOutput->setText( $text ); + $text = Html::rawElement( 'div', [ 'class' => 'error' ], $status->getMessage()->escaped() ) . "\n$text"; + $parserOutput->setRawText( $text ); } } @@ -299,11 +303,15 @@ private static function getUsersFromPages( string $group ): Status { if ( !$gt->exists() ) { return Status::newFatal( 'accesscontrol-group-does-not-exist', $gt->getFullText() ); } - // Article::fetchContent() is deprecated. - // Replaced by WikiPage::getContent() - $groupPage = WikiPage::factory( $gt ); - $allowedUsers = ContentHandler::getContentText( $groupPage->getContent() ); - $groupPage = null; + + $groupPage = MediaWikiServices::getInstance()->getWikiPageFactory()->newFromLinkTarget( $gt ); + $content = $groupPage->getContent(); + if ( !( $content instanceof TextContent ) ) { + // Non-text page, treat it as empty. + return Status::newGood( [] ); + } + + $allowedUsers = $content->getText(); $usersAccess = explode( "\n", $allowedUsers ); foreach ( $usersAccess as $userEntry ) { $userItem = trim( $userEntry ); @@ -394,9 +402,9 @@ public static function onGetUserPermissionsErrors( $title, $user, $action, &$res } /** - * @param SpecialSearch $searchPage + * @param SpecialSearch $searchPage @phan-unused-param * @param SearchResult $result - * @param string[] $terms + * @param string[] $terms @phan-unused-param * @param string &$link * @param string &$redirect * @param string &$section @@ -448,7 +456,7 @@ private static function getRestrictionForTitle( Title $title, User $user ) { return self::$cache[$pageId]; } - $dbr = wfGetDB( DB_REPLICA ); + $dbr = MediaWikiServices::getInstance()->getConnectionProvider()->getReplicaDatabase(); try { $row = $dbr->selectRow( self::TABLE, @@ -494,7 +502,7 @@ private static function updateRestrictionInDatabase( int $pageId, ?array $tagCon $tagContentArray = FormatJson::encode( $tagContentArray ); } - $db = wfGetDB( DB_MASTER ); + $db = MediaWikiServices::getInstance()->getConnectionProvider()->getPrimaryDatabase(); $index = [ self::C_PAGE => $pageId, ];