Merge "Hide hiddencat catwatch changes in special changelists"
authorjenkins-bot <jenkins-bot@gerrit.wikimedia.org>
Tue, 19 Apr 2016 07:34:52 +0000 (07:34 +0000)
committerGerrit Code Review <gerrit@wikimedia.org>
Tue, 19 Apr 2016 07:34:52 +0000 (07:34 +0000)
includes/PageProps.php
includes/changes/RecentChange.php
includes/page/WikiCategoryPage.php
includes/page/WikiPage.php
includes/specials/SpecialRecentchanges.php
includes/specials/SpecialWatchlist.php
tests/phpunit/includes/changes/RecentChangeTest.php
tests/phpunit/includes/page/WikiCategoryPageTest.php [new file with mode: 0644]

index bc3e3f1..3654384 100644 (file)
@@ -33,6 +33,33 @@ class PageProps {
         */
        private static $instance;
 
+       /**
+        * Overrides the default instance of this class
+        * This is intended for use while testing and will fail if MW_PHPUNIT_TEST is not defined.
+        *
+        * If this method is used it MUST also be called with null after a test to ensure a new
+        * default instance is created next time getInstance is called.
+        *
+        * @since 1.27
+        *
+        * @param PageProps|null $store
+        *
+        * @return ScopedCallback to reset the overridden value
+        * @throws MWException
+        */
+       public static function overrideInstance( PageProps $store = null ) {
+               if ( !defined( 'MW_PHPUNIT_TEST' ) ) {
+                       throw new MWException(
+                               'Cannot override ' . __CLASS__ . 'default instance in operation.'
+                       );
+               }
+               $previousValue = self::$instance;
+               self::$instance = $store;
+               return new ScopedCallback( function() use ( $previousValue ) {
+                       self::$instance = $previousValue;
+               } );
+       }
+
        /**
         * @return PageProps
         */
index 3fe5f2f..159cfd9 100644 (file)
@@ -851,7 +851,9 @@ class RecentChange {
                        'rc_logid' => 0,
                        'rc_log_type' => null,
                        'rc_log_action' => '',
-                       'rc_params' => ''
+                       'rc_params' =>  serialize( [
+                               'hidden-cat' => WikiCategoryPage::factory( $categoryTitle )->isHidden()
+                       ] )
                ];
 
                $rc->mExtra = [
@@ -865,6 +867,19 @@ class RecentChange {
                return $rc;
        }
 
+       /**
+        * Get a parameter value
+        *
+        * @since 1.27
+        *
+        * @param string $name parameter name
+        * @return mixed
+        */
+       public function getParam( $name ) {
+               $params = $this->parseParams();
+               return isset( $params[$name] ) ? $params[$name] : null;
+       }
+
        /**
         * Initialises the members of this object from a mysql row object
         *
index d382001..6c93202 100644 (file)
@@ -47,4 +47,18 @@ class WikiCategoryPage extends WikiPage {
                }
                return false;
        }
+
+       /**
+        * Checks if a category is hidden.
+        *
+        * @since 1.27
+        *
+        * @return bool
+        */
+       public function isHidden() {
+               $pageId = $this->getTitle()->getArticleID();
+               $pageProps = PageProps::getInstance()->getProperties( $this->getTitle(), 'hiddencat' );
+
+               return isset( $pageProps[$pageId] ) ? true : false;
+       }
 }
index 82e66aa..06785b7 100644 (file)
@@ -94,7 +94,7 @@ class WikiPage implements Page, IDBAccessObject {
         * @param Title $title
         *
         * @throws MWException
-        * @return WikiPage Object of the appropriate type
+        * @return WikiPage|WikiCategoryPage|WikiFilePage
         */
        public static function factory( Title $title ) {
                $ns = $title->getNamespace();
index 8398989..b93fb4e 100644 (file)
@@ -324,12 +324,23 @@ class SpecialRecentChanges extends ChangesListSpecialPage {
                $list = ChangesList::newFromContext( $this->getContext() );
                $list->initChangesListRows( $rows );
 
+               $userShowHiddenCats = $this->getUser()->getBoolOption( 'showhiddencats' );
                $rclistOutput = $list->beginRecentChangesList();
                foreach ( $rows as $obj ) {
                        if ( $limit == 0 ) {
                                break;
                        }
                        $rc = RecentChange::newFromRow( $obj );
+
+                       # Skip CatWatch entries for hidden cats based on user preference
+                       if (
+                               $rc->getAttribute( 'rc_type' ) == RC_CATEGORIZE &&
+                               !$userShowHiddenCats &&
+                               $rc->getParam( 'hidden-cat' )
+                       ) {
+                               continue;
+                       }
+
                        $rc->counter = $counter++;
                        # Check if the page has been updated since the last visit
                        if ( $this->getConfig()->get( 'ShowUpdatedMarker' )
index 27e5829..15691f2 100644 (file)
@@ -369,10 +369,21 @@ class SpecialWatchlist extends ChangesListSpecialPage {
                }
 
                $s = $list->beginRecentChangesList();
+               $userShowHiddenCats = $this->getUser()->getBoolOption( 'showhiddencats' );
                $counter = 1;
                foreach ( $rows as $obj ) {
                        # Make RC entry
                        $rc = RecentChange::newFromRow( $obj );
+
+                       # Skip CatWatch entries for hidden cats based on user preference
+                       if (
+                               $rc->getAttribute( 'rc_type' ) == RC_CATEGORIZE &&
+                               !$userShowHiddenCats &&
+                               $rc->getParam( 'hidden-cat' )
+                       ) {
+                               continue;
+                       }
+
                        $rc->counter = $counter++;
 
                        if ( $this->getConfig()->get( 'ShowUpdatedMarker' ) ) {
index 4abe9ee..2efc802 100644 (file)
@@ -134,4 +134,51 @@ class RecentChangeTest extends MediaWikiTestCase {
                $this->assertEquals( $rcType, RecentChange::parseToRCType( $type ) );
        }
 
+       /**
+        * @return PHPUnit_Framework_MockObject_MockObject|PageProps
+        */
+       private function getMockPageProps() {
+               return $this->getMockBuilder( PageProps::class )
+                       ->disableOriginalConstructor()
+                       ->getMock();
+       }
+
+       public function provideCategoryContent() {
+               return [
+                       [ true ],
+                       [ false ],
+               ];
+       }
+
+       /**
+        * @dataProvider provideCategoryContent
+        * @covers RecentChange::newForCategorization
+        */
+       public function testHiddenCategoryChange( $isHidden ) {
+               $categoryTitle = Title::newFromText( 'CategoryPage', NS_CATEGORY );
+
+               $pageProps = $this->getMockPageProps();
+               $pageProps->expects( $this->once() )
+                       ->method( 'getProperties' )
+                       ->with( $categoryTitle, 'hiddencat' )
+                       ->will( $this->returnValue( $isHidden ? [ $categoryTitle->getArticleID() => '' ] : [ ] ) );
+
+               $scopedOverride = PageProps::overrideInstance( $pageProps );
+
+               $rc = RecentChange::newForCategorization(
+                       '0',
+                       $categoryTitle,
+                       $this->user,
+                       $this->user_comment,
+                       $this->title,
+                       $categoryTitle->getLatestRevID(),
+                       $categoryTitle->getLatestRevID(),
+                       '0',
+                       false
+               );
+
+               $this->assertEquals( $isHidden, $rc->getParam( 'hidden-cat' ) );
+
+               ScopedCallback::consume( $scopedOverride );
+       }
 }
diff --git a/tests/phpunit/includes/page/WikiCategoryPageTest.php b/tests/phpunit/includes/page/WikiCategoryPageTest.php
new file mode 100644 (file)
index 0000000..d6e1d9e
--- /dev/null
@@ -0,0 +1,61 @@
+<?php
+
+class WikiCategoryPageTest extends MediaWikiLangTestCase {
+
+       /**
+        * @return PHPUnit_Framework_MockObject_MockObject|PageProps
+        */
+       private function getMockPageProps() {
+               return $this->getMockBuilder( PageProps::class )
+                       ->disableOriginalConstructor()
+                       ->getMock();
+       }
+
+       /**
+        * @covers WikiCategoryPage::isHidden
+        */
+       public function testHiddenCategory_PropertyNotSet() {
+               $title = Title::makeTitle( NS_CATEGORY, 'CategoryPage' );
+               $categoryPage = WikiCategoryPage::factory( $title );
+
+               $pageProps = $this->getMockPageProps();
+               $pageProps->expects( $this->once() )
+                       ->method( 'getProperties' )
+                       ->with( $title, 'hiddencat' )
+                       ->will( $this->returnValue( [ ] ) );
+
+               $scopedOverride = PageProps::overrideInstance( $pageProps );
+
+               $this->assertFalse( $categoryPage->isHidden() );
+
+               ScopedCallback::consume( $scopedOverride );
+       }
+
+       public function provideCategoryContent() {
+               return [
+                       [ true ],
+                       [ false ],
+               ];
+       }
+
+       /**
+        * @dataProvider provideCategoryContent
+        * @covers WikiCategoryPage::isHidden
+        */
+       public function testHiddenCategory_PropertyIsSet( $isHidden ) {
+               $categoryTitle = Title::makeTitle( NS_CATEGORY, 'CategoryPage' );
+               $categoryPage = WikiCategoryPage::factory( $categoryTitle );
+
+               $pageProps = $this->getMockPageProps();
+               $pageProps->expects( $this->once() )
+                       ->method( 'getProperties' )
+                       ->with( $categoryTitle, 'hiddencat' )
+                       ->will( $this->returnValue( $isHidden ? [ $categoryTitle->getArticleID() => '' ] : [ ] ) );
+
+               $scopedOverride = PageProps::overrideInstance( $pageProps );
+
+               $this->assertEquals( $isHidden, $categoryPage->isHidden() );
+
+               ScopedCallback::consume( $scopedOverride );
+       }
+}