+ public function testResetNotificationTimestamp_notWatchedPageForced() {
+ $user = $this->getMockNonAnonUserWithId( 1 );
+ $oldid = 22;
+ $title = $this->getMockTitle( 'SomeDbKey' );
+ $title->expects( $this->once() )
+ ->method( 'getNextRevisionID' )
+ ->with( $oldid )
+ ->will( $this->returnValue( 33 ) );
+
+ $mockDb = $this->getMockDb();
+ $mockDb->expects( $this->once() )
+ ->method( 'selectRow' )
+ ->with(
+ 'watchlist',
+ 'wl_notificationtimestamp',
+ [
+ 'wl_user' => 1,
+ 'wl_namespace' => 0,
+ 'wl_title' => 'SomeDbKey',
+ ]
+ )
+ ->will( $this->returnValue( false ) );
+
+ $mockCache = $this->getMockCache();
+ $mockDb->expects( $this->never() )
+ ->method( 'get' );
+ $mockDb->expects( $this->never() )
+ ->method( 'set' );
+ $mockDb->expects( $this->never() )
+ ->method( 'delete' );
+
+ $store = $this->newWatchedItemStore(
+ $this->getMockLoadBalancer( $mockDb ),
+ $mockCache
+ );
+
+ $callableCallCounter = 0;
+ $scopedOverride = $store->overrideDeferredUpdatesAddCallableUpdateCallback(
+ function( $callable ) use ( &$callableCallCounter, $title, $user ) {
+ $callableCallCounter++;
+ $this->verifyCallbackJob(
+ $callable,
+ $title,
+ $user->getId(),
+ function( $time ) {
+ return $time === null;
+ }
+ );
+ }
+ );
+
+ $this->assertTrue(
+ $store->resetNotificationTimestamp(
+ $user,
+ $title,
+ 'force',
+ $oldid
+ )
+ );
+ $this->assertEquals( 1, $callableCallCounter );
+
+ ScopedCallback::consume( $scopedOverride );
+ }
+
+ public function testResetNotificationTimestamp_futureNotificationTimestampForced() {
+ $user = $this->getMockNonAnonUserWithId( 1 );
+ $oldid = 22;
+ $title = $this->getMockTitle( 'SomeDbKey' );
+ $title->expects( $this->once() )
+ ->method( 'getNextRevisionID' )
+ ->with( $oldid )
+ ->will( $this->returnValue( 33 ) );
+
+ $mockDb = $this->getMockDb();
+ $mockDb->expects( $this->once() )
+ ->method( 'selectRow' )
+ ->with(
+ 'watchlist',
+ 'wl_notificationtimestamp',
+ [
+ 'wl_user' => 1,
+ 'wl_namespace' => 0,
+ 'wl_title' => 'SomeDbKey',
+ ]
+ )
+ ->will( $this->returnValue(
+ $this->getFakeRow( [ 'wl_notificationtimestamp' => '30151212010101' ] )
+ ) );
+
+ $mockCache = $this->getMockCache();
+ $mockDb->expects( $this->never() )
+ ->method( 'get' );
+ $mockDb->expects( $this->never() )
+ ->method( 'set' );
+ $mockDb->expects( $this->never() )
+ ->method( 'delete' );
+
+ $store = $this->newWatchedItemStore(
+ $this->getMockLoadBalancer( $mockDb ),
+ $mockCache
+ );
+
+ $addUpdateCallCounter = 0;
+ $scopedOverrideDeferred = $store->overrideDeferredUpdatesAddCallableUpdateCallback(
+ function( $callable ) use ( &$addUpdateCallCounter, $title, $user ) {
+ $addUpdateCallCounter++;
+ $this->verifyCallbackJob(
+ $callable,
+ $title,
+ $user->getId(),
+ function( $time ) {
+ return $time === '30151212010101';
+ }
+ );
+ }
+ );
+
+ $getTimestampCallCounter = 0;
+ $scopedOverrideRevision = $store->overrideRevisionGetTimestampFromIdCallback(
+ function( $titleParam, $oldidParam ) use ( &$getTimestampCallCounter, $title, $oldid ) {
+ $getTimestampCallCounter++;
+ $this->assertEquals( $title, $titleParam );
+ $this->assertEquals( $oldid, $oldidParam );
+ }
+ );
+
+ $this->assertTrue(
+ $store->resetNotificationTimestamp(
+ $user,
+ $title,
+ 'force',
+ $oldid
+ )
+ );
+ $this->assertEquals( 1, $addUpdateCallCounter );
+ $this->assertEquals( 1, $getTimestampCallCounter );
+
+ ScopedCallback::consume( $scopedOverrideDeferred );
+ ScopedCallback::consume( $scopedOverrideRevision );
+ }
+
+ public function testResetNotificationTimestamp_futureNotificationTimestampNotForced() {
+ $user = $this->getMockNonAnonUserWithId( 1 );
+ $oldid = 22;
+ $title = $this->getMockTitle( 'SomeDbKey' );
+ $title->expects( $this->once() )
+ ->method( 'getNextRevisionID' )
+ ->with( $oldid )
+ ->will( $this->returnValue( 33 ) );
+
+ $mockDb = $this->getMockDb();
+ $mockDb->expects( $this->once() )
+ ->method( 'selectRow' )
+ ->with(
+ 'watchlist',
+ 'wl_notificationtimestamp',
+ [
+ 'wl_user' => 1,
+ 'wl_namespace' => 0,
+ 'wl_title' => 'SomeDbKey',
+ ]
+ )
+ ->will( $this->returnValue(
+ $this->getFakeRow( [ 'wl_notificationtimestamp' => '30151212010101' ] )
+ ) );
+
+ $mockCache = $this->getMockCache();
+ $mockDb->expects( $this->never() )
+ ->method( 'get' );
+ $mockDb->expects( $this->never() )
+ ->method( 'set' );
+ $mockDb->expects( $this->never() )
+ ->method( 'delete' );
+
+ $store = $this->newWatchedItemStore(
+ $this->getMockLoadBalancer( $mockDb ),
+ $mockCache
+ );
+
+ $addUpdateCallCounter = 0;
+ $scopedOverrideDeferred = $store->overrideDeferredUpdatesAddCallableUpdateCallback(
+ function( $callable ) use ( &$addUpdateCallCounter, $title, $user ) {
+ $addUpdateCallCounter++;
+ $this->verifyCallbackJob(
+ $callable,
+ $title,
+ $user->getId(),
+ function( $time ) {
+ return $time === false;
+ }
+ );
+ }
+ );
+
+ $getTimestampCallCounter = 0;
+ $scopedOverrideRevision = $store->overrideRevisionGetTimestampFromIdCallback(
+ function( $titleParam, $oldidParam ) use ( &$getTimestampCallCounter, $title, $oldid ) {
+ $getTimestampCallCounter++;
+ $this->assertEquals( $title, $titleParam );
+ $this->assertEquals( $oldid, $oldidParam );
+ }
+ );
+
+ $this->assertTrue(
+ $store->resetNotificationTimestamp(
+ $user,
+ $title,
+ '',
+ $oldid
+ )
+ );
+ $this->assertEquals( 1, $addUpdateCallCounter );
+ $this->assertEquals( 1, $getTimestampCallCounter );
+
+ ScopedCallback::consume( $scopedOverrideDeferred );
+ ScopedCallback::consume( $scopedOverrideRevision );
+ }
+