mirror of
https://gerrit.wikimedia.org/r/mediawiki/extensions/MultimediaViewer
synced 2024-11-13 18:06:57 +00:00
Replace all direct localStorage interaction by mw.storage
Meanwhile I also updated a few places where a non-string was passed to/expected from localStorage - this could’ve led to inconsistencies because localStorage stringifies everything. And I also removed CP.canSetMediaViewerEnabledOnClick, which was no longer used anywhere except for a test case. Bug: T137777 Change-Id: I21ad4ba15ca751bb03e5e2c523d09a45c0444ccf
This commit is contained in:
parent
8d07d09085
commit
3e5ad4c83a
|
@ -106,6 +106,7 @@
|
|||
"mediawiki.Title",
|
||||
"mediawiki.Uri",
|
||||
"mediawiki.jqueryMsg",
|
||||
"mediawiki.storage",
|
||||
"oojs",
|
||||
"jquery.fullscreen",
|
||||
"jquery.hidpi",
|
||||
|
@ -344,6 +345,7 @@
|
|||
"mediawiki.ui.icon",
|
||||
"mediawiki.Title",
|
||||
"mediawiki.user",
|
||||
"mediawiki.storage",
|
||||
"mmv.head",
|
||||
"oojs"
|
||||
],
|
||||
|
@ -369,7 +371,8 @@
|
|||
"mmv/mmv.head.js"
|
||||
],
|
||||
"dependencies": [
|
||||
"mediawiki.user"
|
||||
"mediawiki.user",
|
||||
"mediawiki.storage"
|
||||
],
|
||||
"position": "top"
|
||||
}
|
||||
|
|
|
@ -26,7 +26,7 @@
|
|||
* @param {mw.Map} mwConfig
|
||||
* @param {Object} mwUser
|
||||
* @param {mw.Api} api
|
||||
* @param {Object} localStorage
|
||||
* @param {mw.storage} localStorage
|
||||
*/
|
||||
function Config( viewerConfig, mwConfig, mwUser, api, localStorage ) {
|
||||
/**
|
||||
|
@ -55,7 +55,7 @@
|
|||
|
||||
/**
|
||||
* The localStorage object, for dependency injection
|
||||
* @type {Object}
|
||||
* @type {mw.storage}
|
||||
*/
|
||||
this.localStorage = localStorage;
|
||||
}
|
||||
|
@ -66,21 +66,24 @@
|
|||
*
|
||||
* @param {string} key
|
||||
* @param {*} [fallback] value to return when key is not set or localStorage is not supported
|
||||
* @return {*} stored value or fallback or null if neither exists
|
||||
* @return {string|null} stored value or fallback or null if neither exists
|
||||
*/
|
||||
CP.getFromLocalStorage = function ( key, fallback ) {
|
||||
var value = null;
|
||||
if ( this.localStorage ) {
|
||||
try {
|
||||
value = this.localStorage.getItem( key );
|
||||
} catch ( e ) {
|
||||
mw.log( 'Failed to fetch item ' + key + ' from localStorage', e );
|
||||
}
|
||||
var value = this.localStorage.get( key );
|
||||
|
||||
// localStorage will only store strings; if values `null`, `false` or
|
||||
// `0` are set, they'll come out as `"null"`, `"false"` or `"0"`, so we
|
||||
// can be certain that an actual null is a failure to locate the item,
|
||||
// and false is an issue with localStorage itself
|
||||
if ( value !== null && value !== false ) {
|
||||
return value;
|
||||
}
|
||||
if ( value === null && fallback !== undefined ) {
|
||||
value = fallback;
|
||||
|
||||
if ( value === null ) {
|
||||
mw.log( 'Failed to fetch item ' + key + ' from localStorage' );
|
||||
}
|
||||
return value;
|
||||
|
||||
return fallback !== undefined ? fallback : null;
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -91,14 +94,7 @@
|
|||
* @return {boolean} whether storing the item was successful
|
||||
*/
|
||||
CP.setInLocalStorage = function ( key, value ) {
|
||||
var success = false;
|
||||
if ( this.localStorage ) {
|
||||
try {
|
||||
this.localStorage.setItem( key, value );
|
||||
success = true;
|
||||
} catch ( e ) {}
|
||||
}
|
||||
return success;
|
||||
return this.localStorage.set( key, value );
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -108,15 +104,15 @@
|
|||
* @return {boolean} whether storing the item was successful
|
||||
*/
|
||||
CP.removeFromLocalStorage = function ( key ) {
|
||||
if ( this.localStorage ) {
|
||||
try {
|
||||
this.localStorage.removeItem( key );
|
||||
return true;
|
||||
} catch ( e ) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true; // since we never even stored the value, this is considered a success
|
||||
this.localStorage.remove( key );
|
||||
|
||||
// mw.storage.remove catches all exceptions and returns false if any
|
||||
// occur, so we can't distinguish between actual issues, and
|
||||
// localStorage not being supported - however, localStorage.removeItem
|
||||
// is not documented to throw any errors, so nothing to worry about;
|
||||
// when localStorage is not supported, we'll consider removal successful
|
||||
// (it can't have been there in the first place)
|
||||
return true;
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -143,7 +139,7 @@
|
|||
// IMPORTANT: mmv.head.js uses the same logic but does not use this class to be lightweight. Make sure to keep it in sync.
|
||||
return this.mwConfig.get( 'wgMediaViewer' ) && // global opt-out switch, can be set in user JS
|
||||
this.mwConfig.get( 'wgMediaViewerOnClick' ) && // thumbnail opt-out, can be set in preferences
|
||||
( !this.mwUser.isAnon() || this.getFromLocalStorage( 'wgMediaViewerOnClick', 1 ) === 1 ); // thumbnail opt-out for anons
|
||||
( !this.mwUser.isAnon() || this.getFromLocalStorage( 'wgMediaViewerOnClick', '1' ) === '1' ); // thumbnail opt-out for anons
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -198,15 +194,6 @@
|
|||
} );
|
||||
};
|
||||
|
||||
/**
|
||||
* Returns true if #setMediaViewerEnabledOnClick() is supported.
|
||||
*
|
||||
* @return {boolean}
|
||||
*/
|
||||
CP.canSetMediaViewerEnabledOnClick = function () {
|
||||
return !this.mwUser.isAnon() || !!this.localStorage;
|
||||
};
|
||||
|
||||
/**
|
||||
* True if info about enable/disable status should be displayed (mingle #719).
|
||||
*
|
||||
|
|
|
@ -25,12 +25,6 @@
|
|||
* @class mw.mmv.MultimediaViewerBootstrap
|
||||
*/
|
||||
function MultimediaViewerBootstrap() {
|
||||
var localStorage = false;
|
||||
|
||||
try {
|
||||
localStorage = window.localStorage || false;
|
||||
} catch ( e ) { }
|
||||
|
||||
// Exposed for tests
|
||||
this.hoverWaitDuration = 200;
|
||||
|
||||
|
@ -42,7 +36,7 @@
|
|||
mw.config,
|
||||
mw.user,
|
||||
new mw.Api(),
|
||||
localStorage
|
||||
mw.storage
|
||||
);
|
||||
|
||||
this.validExtensions = this.config.extensions();
|
||||
|
|
|
@ -25,15 +25,11 @@
|
|||
|
||||
// If the user disabled MediaViewer in his preferences, we do not set up click handling.
|
||||
// This is loaded before user JS so we cannot check wgMediaViewer.
|
||||
try {
|
||||
if (
|
||||
mw.config.get( 'wgMediaViewerOnClick' ) !== true ||
|
||||
mw.user.isAnon() && window.localStorage && localStorage.getItem( 'wgMediaViewerOnClick' ) === false
|
||||
) {
|
||||
return;
|
||||
}
|
||||
} catch ( e ) { // localStorage.getItem can throw exceptions
|
||||
mw.log( 'Could not check value of wgMediaViewerOnClick in localStorage' );
|
||||
if (
|
||||
mw.config.get( 'wgMediaViewerOnClick' ) !== true ||
|
||||
mw.user.isAnon() && mw.storage.get( 'wgMediaViewerOnClick', '1' ) !== '1'
|
||||
) {
|
||||
return;
|
||||
}
|
||||
|
||||
$document.on( 'click.mmv-head', 'a.image', function ( e ) {
|
||||
|
|
|
@ -26,10 +26,7 @@
|
|||
* @constructor
|
||||
*/
|
||||
function LightboxInterface() {
|
||||
this.localStorage = false;
|
||||
try {
|
||||
this.localStorage = window.localStorage || false;
|
||||
} catch ( e ) {}
|
||||
this.localStorage = mw.storage;
|
||||
|
||||
/** @property {mw.mmv.Config} config - */
|
||||
this.config = new mw.mmv.Config(
|
||||
|
|
|
@ -29,7 +29,7 @@
|
|||
* @param {jQuery} $aboveFold The brighter headline of the metadata panel (.mw-mmv-above-fold).
|
||||
* Called "aboveFold" for historical reasons, but actually a part of the next sibling of the element
|
||||
* is also above the fold (bottom of the screen).
|
||||
* @param {Object} localStorage the localStorage object, for dependency injection
|
||||
* @param {mw.storage} localStorage the localStorage object, for dependency injection
|
||||
* @param {mw.mmv.Config} config A configuration object.
|
||||
*/
|
||||
function MetadataPanel( $container, $aboveFold, localStorage, config ) {
|
||||
|
@ -185,7 +185,7 @@
|
|||
/**
|
||||
* Initializes the header, which contains the title, credit, and license elements.
|
||||
*
|
||||
* @param {Object} localStorage the localStorage object, for dependency injection
|
||||
* @param {mw.storage} localStorage the localStorage object, for dependency injection
|
||||
*/
|
||||
MPP.initializeHeader = function ( localStorage ) {
|
||||
this.progressBar = new mw.mmv.ui.ProgressBar( this.$aboveFold );
|
||||
|
|
|
@ -26,14 +26,14 @@
|
|||
* @constructor
|
||||
* @param {jQuery} $container The container for the panel (.mw-mmv-post-image).
|
||||
* @param {jQuery} $aboveFold The control bar element (.mw-mmv-above-fold).
|
||||
* @param {Object} localStorage the localStorage object, for dependency injection
|
||||
* @param {mw.storage} localStorage the localStorage object, for dependency injection
|
||||
*/
|
||||
function MetadataPanelScroller( $container, $aboveFold, localStorage ) {
|
||||
mw.mmv.ui.Element.call( this, $container );
|
||||
|
||||
this.$aboveFold = $aboveFold;
|
||||
|
||||
/** @property {Object} localStorage the window.localStorage object */
|
||||
/** @property {mw.storage} localStorage */
|
||||
this.localStorage = localStorage;
|
||||
|
||||
/** @property {boolean} panelWasOpen state flag which will be used to detect open <-> closed transitions */
|
||||
|
@ -72,13 +72,9 @@
|
|||
} ) );
|
||||
|
||||
this.$container.on( 'mmv-metadata-open', function () {
|
||||
if ( !panel.hasOpenedMetadata && panel.localStorage ) {
|
||||
if ( !panel.hasOpenedMetadata && panel.localStorage.store ) {
|
||||
panel.hasOpenedMetadata = true;
|
||||
try {
|
||||
panel.localStorage.setItem( 'mmv.hasOpenedMetadata', true );
|
||||
} catch ( e ) {
|
||||
// localStorage is full or disabled
|
||||
}
|
||||
panel.localStorage.set( 'mmv.hasOpenedMetadata', '1' );
|
||||
}
|
||||
} );
|
||||
|
||||
|
@ -141,9 +137,16 @@
|
|||
};
|
||||
|
||||
MPSP.initialize = function () {
|
||||
try {
|
||||
this.hasOpenedMetadata = !this.localStorage || this.localStorage.getItem( 'mmv.hasOpenedMetadata' );
|
||||
} catch ( e ) { // localStorage.getItem can throw exceptions
|
||||
var value = this.localStorage.get( 'mmv.hasOpenedMetadata' );
|
||||
|
||||
// localStorage will only store strings; if values `null`, `false` or
|
||||
// `0` are set, they'll come out as `"null"`, `"false"` or `"0"`, so we
|
||||
// can be certain that an actual null is a failure to locate the item,
|
||||
// and false is an issue with localStorage itself
|
||||
if ( value !== false ) {
|
||||
this.hasOpenedMetadata = value !== null;
|
||||
} else {
|
||||
// if there was an issue with localStorage, treat it as opened
|
||||
this.hasOpenedMetadata = true;
|
||||
}
|
||||
};
|
||||
|
|
|
@ -26,25 +26,25 @@
|
|||
QUnit.test( 'Localstorage get', 8, function ( assert ) {
|
||||
var localStorage, config;
|
||||
|
||||
localStorage = undefined; // no browser support
|
||||
localStorage = mw.mmv.testHelpers.getUnsupportedLocalStorage(); // no browser support
|
||||
config = new mw.mmv.Config( {}, {}, {}, {}, localStorage );
|
||||
assert.strictEqual( config.getFromLocalStorage( 'foo' ), null, 'Returns null when not supported' );
|
||||
assert.strictEqual( config.getFromLocalStorage( 'foo', 'bar' ), 'bar', 'Returns fallback when not supported' );
|
||||
|
||||
localStorage = null; // browser supports it but disabled
|
||||
localStorage = mw.mmv.testHelpers.getDisabledLocalStorage(); // browser supports it but disabled
|
||||
config = new mw.mmv.Config( {}, {}, {}, {}, localStorage );
|
||||
assert.strictEqual( config.getFromLocalStorage( 'foo' ), null, 'Returns null when disabled' );
|
||||
assert.strictEqual( config.getFromLocalStorage( 'foo', 'bar' ), 'bar', 'Returns fallback when disabled' );
|
||||
|
||||
localStorage = { getItem: this.sandbox.stub() };
|
||||
localStorage = mw.mmv.testHelpers.createLocalStorage( { getItem: this.sandbox.stub() } );
|
||||
config = new mw.mmv.Config( {}, {}, {}, {}, localStorage );
|
||||
|
||||
localStorage.getItem.withArgs( 'foo' ).returns( null );
|
||||
localStorage.store.getItem.withArgs( 'foo' ).returns( null );
|
||||
assert.strictEqual( config.getFromLocalStorage( 'foo' ), null, 'Returns null when key not set' );
|
||||
assert.strictEqual( config.getFromLocalStorage( 'foo', 'bar' ), 'bar', 'Returns fallback when key not set' );
|
||||
|
||||
localStorage.getItem.reset();
|
||||
localStorage.getItem.withArgs( 'foo' ).returns( 'boom' );
|
||||
localStorage.store.getItem.reset();
|
||||
localStorage.store.getItem.withArgs( 'foo' ).returns( 'boom' );
|
||||
assert.strictEqual( config.getFromLocalStorage( 'foo' ), 'boom', 'Returns correct value' );
|
||||
assert.strictEqual( config.getFromLocalStorage( 'foo', 'bar' ), 'boom', 'Returns correct value ignoring fallback' );
|
||||
} );
|
||||
|
@ -52,45 +52,41 @@
|
|||
QUnit.test( 'Localstorage set', 4, function ( assert ) {
|
||||
var localStorage, config;
|
||||
|
||||
localStorage = undefined; // no browser support
|
||||
localStorage = mw.mmv.testHelpers.getUnsupportedLocalStorage(); // no browser support
|
||||
config = new mw.mmv.Config( {}, {}, {}, {}, localStorage );
|
||||
assert.strictEqual( config.setInLocalStorage( 'foo', 'bar' ), false, 'Returns false when not supported' );
|
||||
|
||||
localStorage = null; // browser supports it but disabled
|
||||
localStorage = mw.mmv.testHelpers.getDisabledLocalStorage(); // browser supports it but disabled
|
||||
config = new mw.mmv.Config( {}, {}, {}, {}, localStorage );
|
||||
assert.strictEqual( config.setInLocalStorage( 'foo', 'bar' ), false, 'Returns false when disabled' );
|
||||
|
||||
localStorage = { setItem: this.sandbox.stub() };
|
||||
localStorage = mw.mmv.testHelpers.createLocalStorage( { setItem: this.sandbox.stub() } );
|
||||
config = new mw.mmv.Config( {}, {}, {}, {}, localStorage );
|
||||
|
||||
assert.strictEqual( config.setInLocalStorage( 'foo', 'bar' ), true, 'Returns true when works' );
|
||||
|
||||
localStorage.setItem.throwsException( 'localStorage full!' );
|
||||
localStorage.store.setItem.throwsException( 'localStorage full!' );
|
||||
assert.strictEqual( config.setInLocalStorage( 'foo', 'bar' ), false, 'Returns false on error' );
|
||||
} );
|
||||
|
||||
QUnit.test( 'Localstorage remove', 4, function ( assert ) {
|
||||
QUnit.test( 'Localstorage remove', 3, function ( assert ) {
|
||||
var localStorage, config;
|
||||
|
||||
localStorage = undefined; // no browser support
|
||||
localStorage = mw.mmv.testHelpers.getUnsupportedLocalStorage(); // no browser support
|
||||
config = new mw.mmv.Config( {}, {}, {}, {}, localStorage );
|
||||
assert.strictEqual( config.removeFromLocalStorage( 'foo' ), true, 'Returns true when not supported' );
|
||||
|
||||
localStorage = null; // browser supports it but disabled
|
||||
localStorage = mw.mmv.testHelpers.getDisabledLocalStorage(); // browser supports it but disabled
|
||||
config = new mw.mmv.Config( {}, {}, {}, {}, localStorage );
|
||||
assert.strictEqual( config.removeFromLocalStorage( 'foo' ), true, 'Returns true when disabled' );
|
||||
|
||||
localStorage = { removeItem: this.sandbox.stub() };
|
||||
localStorage = mw.mmv.testHelpers.createLocalStorage( { removeItem: this.sandbox.stub() } );
|
||||
config = new mw.mmv.Config( {}, {}, {}, {}, localStorage );
|
||||
|
||||
assert.strictEqual( config.removeFromLocalStorage( 'foo' ), true, 'Returns true when works' );
|
||||
|
||||
localStorage.removeItem.throwsException( 'cannot write localStorage!' );
|
||||
assert.strictEqual( config.removeFromLocalStorage( 'foo' ), false, 'Returns false on error' );
|
||||
} );
|
||||
|
||||
QUnit.test( 'isMediaViewerEnabledOnClick', 7, function ( assert ) {
|
||||
var localStorage = { getItem: this.sandbox.stub() },
|
||||
var localStorage = mw.mmv.testHelpers.createLocalStorage( { getItem: this.sandbox.stub() } ),
|
||||
mwConfig = { get: this.sandbox.stub() },
|
||||
mwUser = { isAnon: this.sandbox.stub() },
|
||||
config = new mw.mmv.Config( {}, mwConfig, mwUser, {}, localStorage );
|
||||
|
@ -123,18 +119,22 @@
|
|||
mwUser.isAnon.returns( true );
|
||||
mwConfig.get.withArgs( 'wgMediaViewer' ).returns( true );
|
||||
mwConfig.get.withArgs( 'wgMediaViewerOnClick' ).returns( true );
|
||||
localStorage.getItem.withArgs( 'wgMediaViewerOnClick' ).returns( null );
|
||||
localStorage.store.getItem.withArgs( 'wgMediaViewerOnClick' ).returns( null );
|
||||
assert.strictEqual( config.isMediaViewerEnabledOnClick(), true, 'Returns true for anon with standard settings' );
|
||||
|
||||
mwUser.isAnon.returns( true );
|
||||
mwConfig.get.withArgs( 'wgMediaViewer' ).returns( true );
|
||||
mwConfig.get.withArgs( 'wgMediaViewerOnClick' ).returns( true );
|
||||
localStorage.getItem.withArgs( 'wgMediaViewerOnClick' ).returns( '0' );
|
||||
localStorage.store.getItem.withArgs( 'wgMediaViewerOnClick' ).returns( '0' );
|
||||
assert.strictEqual( config.isMediaViewerEnabledOnClick(), false, 'Returns true for anon opted out via localSettings' );
|
||||
} );
|
||||
|
||||
QUnit.test( 'setMediaViewerEnabledOnClick sanity check', 3, function ( assert ) {
|
||||
var localStorage = { getItem: this.sandbox.stub(), setItem: this.sandbox.stub(), removeItem: this.sandbox.stub() },
|
||||
var localStorage = mw.mmv.testHelpers.createLocalStorage( {
|
||||
getItem: this.sandbox.stub(),
|
||||
setItem: this.sandbox.stub(),
|
||||
removeItem: this.sandbox.stub()
|
||||
} ),
|
||||
mwUser = { isAnon: this.sandbox.stub() },
|
||||
mwConfig = new mw.Map(),
|
||||
api = { postWithToken: this.sandbox.stub().returns( $.Deferred().resolve() ) },
|
||||
|
@ -148,31 +148,11 @@
|
|||
|
||||
mwUser.isAnon.returns( true );
|
||||
config.setMediaViewerEnabledOnClick( false );
|
||||
assert.ok( localStorage.setItem.called, 'For anons, opt-out is set in localStorage' );
|
||||
assert.ok( localStorage.store.setItem.called, 'For anons, opt-out is set in localStorage' );
|
||||
|
||||
mwUser.isAnon.returns( true );
|
||||
config.setMediaViewerEnabledOnClick( true );
|
||||
assert.ok( localStorage.removeItem.called, 'For anons, opt-in means clearing localStorage' );
|
||||
} );
|
||||
|
||||
QUnit.test( 'canSetMediaViewerEnabledOnClick', 4, function ( assert ) {
|
||||
var mwUser = { isAnon: this.sandbox.stub() },
|
||||
config = new mw.mmv.Config( {}, {}, mwUser, {}, {} );
|
||||
|
||||
mwUser.isAnon.returns( false );
|
||||
assert.strictEqual( config.canSetMediaViewerEnabledOnClick(), true, 'Logged-in users can always disable' );
|
||||
|
||||
mwUser.isAnon.returns( true );
|
||||
config = new mw.mmv.Config( {}, {}, mwUser, {}, {} );
|
||||
assert.strictEqual( config.canSetMediaViewerEnabledOnClick(), true, 'Anons can disable when they have localStorage support' );
|
||||
|
||||
mwUser.isAnon.returns( true );
|
||||
config = new mw.mmv.Config( {}, {}, mwUser, {}, null );
|
||||
assert.strictEqual( config.canSetMediaViewerEnabledOnClick(), false, 'Anons cannot disable when they have no localStorage support' );
|
||||
|
||||
mwUser.isAnon.returns( true );
|
||||
config = new mw.mmv.Config( {}, {}, mwUser, {}, undefined );
|
||||
assert.strictEqual( config.canSetMediaViewerEnabledOnClick(), false, 'Anons cannot disable when disabled localStorage' );
|
||||
assert.ok( localStorage.store.removeItem.called, 'For anons, opt-in means clearing localStorage' );
|
||||
} );
|
||||
|
||||
QUnit.test( 'shouldShowStatusInfo', 12, function ( assert ) {
|
||||
|
|
|
@ -29,21 +29,57 @@
|
|||
return ex;
|
||||
};
|
||||
|
||||
/**
|
||||
* Creates an mw.storage-like object.
|
||||
*
|
||||
* @param {Object} storage localStorage stub with getItem, setItem, removeItem methods
|
||||
* @return {mw.storage} Local storage-like object
|
||||
*/
|
||||
MTH.createLocalStorage = function ( storage ) {
|
||||
return new ( Object.getPrototypeOf( mw.storage ) ).constructor( storage );
|
||||
};
|
||||
|
||||
/**
|
||||
* Returns an mw.storage that mimicks lack of localStorage support.
|
||||
*
|
||||
* @return {mw.storage} Local storage-like object
|
||||
*/
|
||||
MTH.getUnsupportedLocalStorage = function () {
|
||||
return this.createLocalStorage( undefined );
|
||||
};
|
||||
|
||||
/**
|
||||
* Returns an mw.storage that mimicks localStorage being disabled in browser.
|
||||
*
|
||||
* @return {mw.storage} Local storage-like object
|
||||
*/
|
||||
MTH.getDisabledLocalStorage = function () {
|
||||
var e = function () {
|
||||
throw new Error( 'Error' );
|
||||
};
|
||||
|
||||
return this.createLocalStorage( {
|
||||
getItem: e,
|
||||
setItem: e,
|
||||
removeItem: e
|
||||
} );
|
||||
};
|
||||
|
||||
/**
|
||||
* Returns a fake local storage which is not saved between reloads.
|
||||
*
|
||||
* @param {Object} [initialData]
|
||||
* @return {Object} Local storage-like object
|
||||
* @return {mw.storage} Local storage-like object
|
||||
*/
|
||||
MTH.getFakeLocalStorage = function ( initialData ) {
|
||||
var bag = new mw.Map();
|
||||
bag.set( initialData );
|
||||
|
||||
return {
|
||||
return this.createLocalStorage( {
|
||||
getItem: function ( key ) { return bag.get( key ); },
|
||||
setItem: function ( key, value ) { bag.set( key, value ); },
|
||||
removeItem: function ( key ) { bag.set( key, null ); }
|
||||
};
|
||||
} );
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
|
@ -18,7 +18,7 @@
|
|||
QUnit.test( 'The panel is emptied properly when necessary', thingsShouldBeEmptied.length + thingsShouldHaveEmptyClass.length, function ( assert ) {
|
||||
var i,
|
||||
$qf = $( '#qunit-fixture' ),
|
||||
panel = new mw.mmv.ui.MetadataPanel( $qf, $( '<div>' ).appendTo( $qf ), window.localStorage, new mw.mmv.Config( {}, mw.config, mw.user, new mw.Api(), window.localStorage ) );
|
||||
panel = new mw.mmv.ui.MetadataPanel( $qf, $( '<div>' ).appendTo( $qf ), mw.storage, new mw.mmv.Config( {}, mw.config, mw.user, new mw.Api(), mw.storage ) );
|
||||
|
||||
panel.empty();
|
||||
|
||||
|
@ -33,7 +33,7 @@
|
|||
|
||||
QUnit.test( 'Setting location information works as expected', 6, function ( assert ) {
|
||||
var $qf = $( '#qunit-fixture' ),
|
||||
panel = new mw.mmv.ui.MetadataPanel( $qf, $( '<div>' ).appendTo( $qf ), window.localStorage, new mw.mmv.Config( {}, mw.config, mw.user, new mw.Api(), window.localStorage ) ),
|
||||
panel = new mw.mmv.ui.MetadataPanel( $qf, $( '<div>' ).appendTo( $qf ), mw.storage, new mw.mmv.Config( {}, mw.config, mw.user, new mw.Api(), mw.storage ) ),
|
||||
fileName = 'Foobar.jpg',
|
||||
latitude = 12.3456789,
|
||||
longitude = 98.7654321,
|
||||
|
@ -98,7 +98,7 @@
|
|||
QUnit.test( 'Setting image information works as expected', 17, function ( assert ) {
|
||||
var creditPopupText,
|
||||
$qf = $( '#qunit-fixture' ),
|
||||
panel = new mw.mmv.ui.MetadataPanel( $qf, $( '<div>' ).appendTo( $qf ), window.localStorage, new mw.mmv.Config( {}, mw.config, mw.user, new mw.Api(), window.localStorage ) ),
|
||||
panel = new mw.mmv.ui.MetadataPanel( $qf, $( '<div>' ).appendTo( $qf ), mw.storage, new mw.mmv.Config( {}, mw.config, mw.user, new mw.Api(), mw.storage ) ),
|
||||
title = 'Foo bar',
|
||||
image = {
|
||||
filePageTitle: mw.Title.newFromText( 'File:' + title + '.jpg' )
|
||||
|
@ -170,7 +170,7 @@
|
|||
|
||||
QUnit.test( 'Setting permission information works as expected', 1, function ( assert ) {
|
||||
var $qf = $( '#qunit-fixture' ),
|
||||
panel = new mw.mmv.ui.MetadataPanel( $qf, $( '<div>' ).appendTo( $qf ), window.localStorage, new mw.mmv.Config( {}, mw.config, mw.user, new mw.Api(), window.localStorage ) );
|
||||
panel = new mw.mmv.ui.MetadataPanel( $qf, $( '<div>' ).appendTo( $qf ), mw.storage, new mw.mmv.Config( {}, mw.config, mw.user, new mw.Api(), mw.storage ) );
|
||||
|
||||
panel.setLicense( null, 'http://example.com' ); // make sure license is visible as it contains the permission
|
||||
panel.setPermission( 'Look at me, I am a permission!' );
|
||||
|
@ -179,7 +179,7 @@
|
|||
|
||||
QUnit.test( 'Date formatting', 1, function ( assert ) {
|
||||
var $qf = $( '#qunit-fixture' ),
|
||||
panel = new mw.mmv.ui.MetadataPanel( $qf, $( '<div>' ).appendTo( $qf ), window.localStorage, new mw.mmv.Config( {}, mw.config, mw.user, new mw.Api(), window.localStorage ) ),
|
||||
panel = new mw.mmv.ui.MetadataPanel( $qf, $( '<div>' ).appendTo( $qf ), mw.storage, new mw.mmv.Config( {}, mw.config, mw.user, new mw.Api(), mw.storage ) ),
|
||||
date1 = 'Garbage',
|
||||
promise = panel.formatDate( date1 );
|
||||
|
||||
|
@ -198,7 +198,7 @@
|
|||
this.sandbox.stub( mw.user, 'isAnon' );
|
||||
mw.config.set( 'wgMediaViewerIsInBeta', false );
|
||||
// eslint-disable-next-line no-new
|
||||
new mw.mmv.ui.MetadataPanel( $qf.empty(), $( '<div>' ).appendTo( $qf ), window.localStorage, new mw.mmv.Config( {}, mw.config, mw.user, new mw.Api(), window.localStorage ) );
|
||||
new mw.mmv.ui.MetadataPanel( $qf.empty(), $( '<div>' ).appendTo( $qf ), mw.storage, new mw.mmv.Config( {}, mw.config, mw.user, new mw.Api(), mw.storage ) );
|
||||
|
||||
assert.strictEqual( $qf.find( '.mw-mmv-about-link' ).length, 1, 'About link is created.' );
|
||||
assert.strictEqual( $qf.find( '.mw-mmv-discuss-link' ).length, 1, 'Discuss link is created.' );
|
||||
|
|
|
@ -24,7 +24,8 @@
|
|||
|
||||
QUnit.test( 'empty()', 1, function ( assert ) {
|
||||
var $qf = $( '#qunit-fixture' ),
|
||||
scroller = new mw.mmv.ui.MetadataPanelScroller( $qf, $( '<div>' ).appendTo( $qf ) );
|
||||
localStorage = mw.mmv.testHelpers.getFakeLocalStorage(),
|
||||
scroller = new mw.mmv.ui.MetadataPanelScroller( $qf, $( '<div>' ).appendTo( $qf ), localStorage );
|
||||
|
||||
scroller.empty();
|
||||
assert.ok( !scroller.$container.hasClass( 'invite' ), 'We successfully reset the invite' );
|
||||
|
@ -32,12 +33,13 @@
|
|||
|
||||
QUnit.test( 'Metadata div is only animated once', 5, function ( assert ) {
|
||||
var $qf = $( '#qunit-fixture' ),
|
||||
displayCount,
|
||||
scroller = new mw.mmv.ui.MetadataPanelScroller( $qf, $( '<div>' ).appendTo( $qf ), {
|
||||
displayCount = null, // pretend it doesn't exist at first
|
||||
localStorage = mw.mmv.testHelpers.createLocalStorage( {
|
||||
// We simulate localStorage to avoid test side-effects
|
||||
getItem: function () { return displayCount; },
|
||||
setItem: function ( _, val ) { displayCount = val; }
|
||||
} );
|
||||
} ),
|
||||
scroller = new mw.mmv.ui.MetadataPanelScroller( $qf, $( '<div>' ).appendTo( $qf ), localStorage );
|
||||
|
||||
scroller.attach();
|
||||
|
||||
|
@ -69,7 +71,8 @@
|
|||
|
||||
QUnit.test( 'No localStorage', 1, function ( assert ) {
|
||||
var $qf = $( '#qunit-fixture' ),
|
||||
scroller = new mw.mmv.ui.MetadataPanelScroller( $qf, $( '<div>' ).appendTo( $qf ) );
|
||||
localStorage = mw.mmv.testHelpers.getUnsupportedLocalStorage(),
|
||||
scroller = new mw.mmv.ui.MetadataPanelScroller( $qf, $( '<div>' ).appendTo( $qf ), localStorage );
|
||||
|
||||
this.sandbox.stub( $, 'scrollTo', function () { return { scrollTop: function () { return 10; } }; } );
|
||||
|
||||
|
@ -80,7 +83,10 @@
|
|||
|
||||
QUnit.test( 'localStorage is full', 2, function ( assert ) {
|
||||
var $qf = $( '#qunit-fixture' ),
|
||||
localStorage = { getItem: $.noop, setItem: this.sandbox.stub().throwsException( 'I am full' ) },
|
||||
localStorage = mw.mmv.testHelpers.createLocalStorage( {
|
||||
getItem: this.sandbox.stub().returns( null ),
|
||||
setItem: this.sandbox.stub().throwsException( 'I am full' )
|
||||
} ),
|
||||
scroller = new mw.mmv.ui.MetadataPanelScroller( $qf, $( '<div>' ).appendTo( $qf ), localStorage );
|
||||
|
||||
this.sandbox.stub( $, 'scrollTo', function () {
|
||||
|
@ -99,7 +105,7 @@
|
|||
|
||||
scroller.scroll();
|
||||
|
||||
assert.ok( localStorage.setItem.calledOnce, 'localStorage only written once' );
|
||||
assert.ok( localStorage.store.setItem.calledOnce, 'localStorage only written once' );
|
||||
|
||||
scroller.unattach();
|
||||
} );
|
||||
|
@ -153,13 +159,16 @@
|
|||
var $qf = $( '#qunit-fixture' ),
|
||||
$container = $( '<div>' ).css( 'height', 100 ).appendTo( $qf ),
|
||||
$aboveFold = $( '<div>' ).css( 'height', 50 ).appendTo( $container ),
|
||||
fakeLocalStorage = { getItem: $.noop, setItem: $.noop },
|
||||
fakeLocalStorage = mw.mmv.testHelpers.createLocalStorage( {
|
||||
getItem: this.sandbox.stub().returns( null ),
|
||||
setItem: $.noop
|
||||
} ),
|
||||
scroller = new mw.mmv.ui.MetadataPanelScroller( $container, $aboveFold, fakeLocalStorage ),
|
||||
keydown = $.Event( 'keydown' );
|
||||
|
||||
stubScrollFunctions( this.sandbox, scroller );
|
||||
|
||||
this.sandbox.stub( fakeLocalStorage, 'setItem' );
|
||||
this.sandbox.stub( fakeLocalStorage.store, 'setItem' );
|
||||
|
||||
// First phase of the test: up and down arrows
|
||||
|
||||
|
@ -169,13 +178,13 @@
|
|||
|
||||
assert.strictEqual( $.scrollTo().scrollTop(), 0, 'scrollTo scrollTop should be set to 0' );
|
||||
|
||||
assert.ok( !fakeLocalStorage.setItem.called, 'The metadata hasn\'t been open yet, no entry in localStorage' );
|
||||
assert.ok( !fakeLocalStorage.store.setItem.called, 'The metadata hasn\'t been open yet, no entry in localStorage' );
|
||||
|
||||
keydown.which = 38; // Up arrow
|
||||
scroller.keydown( keydown );
|
||||
this.clock.tick( scroller.toggleScrollDuration );
|
||||
|
||||
assert.ok( fakeLocalStorage.setItem.calledWithExactly( 'mmv.hasOpenedMetadata', true ), 'localStorage knows that the metadata has been open' );
|
||||
assert.ok( fakeLocalStorage.store.setItem.calledWithExactly( 'mmv.hasOpenedMetadata', '1' ), 'localStorage knows that the metadata has been open' );
|
||||
|
||||
keydown.which = 40; // Down arrow
|
||||
scroller.keydown( keydown );
|
||||
|
@ -211,7 +220,8 @@
|
|||
var $qf = $( '#qunit-fixture' ),
|
||||
$container = $( '<div>' ).css( 'height', 100 ).appendTo( $qf ),
|
||||
$aboveFold = $( '<div>' ).css( 'height', 50 ).appendTo( $container ),
|
||||
scroller = new mw.mmv.ui.MetadataPanelScroller( $container, $aboveFold ),
|
||||
localStorage = mw.mmv.testHelpers.getFakeLocalStorage(),
|
||||
scroller = new mw.mmv.ui.MetadataPanelScroller( $container, $aboveFold, localStorage ),
|
||||
keydown = $.Event( 'keydown' );
|
||||
|
||||
stubScrollFunctions( this.sandbox, scroller );
|
||||
|
|
Loading…
Reference in a new issue