mediawiki-extensions-Discus.../modules/dt.init.js

115 lines
3.9 KiB
JavaScript
Raw Normal View History

const controller = require( './controller.js' ),
url = new URL( location.href );
/**
* @class mw.dt
* @singleton
*/
mw.dt = {};
mw.dt.initState = {
firstLoad: true
};
// A/B test for logged out users:
if ( mw.user.isAnon() && mw.config.get( 'wgDiscussionToolsABTest' ) && mw.config.get( 'wgDiscussionToolsABTestBucket' ) ) {
const token = mw.cookie.get( 'DTABid', '', mw.user.generateRandomSessionId() );
mw.cookie.set( 'DTAB', mw.config.get( 'wgDiscussionToolsABTestBucket' ), { path: '/', expires: 90 * 86400, prefix: '' } );
mw.cookie.set( 'DTABid', token, { path: '/', expires: 90 * 86400, prefix: '' } );
}
if ( url.searchParams.get( 'dtrepliedto' ) ) {
// If we had to reload the page to highlight the new comment, extract that data from the URL and
// clean it up.
mw.dt.initState.repliedTo = url.searchParams.get( 'dtrepliedto' );
mw.dt.initState.tempUserCreated = url.searchParams.has( 'dttempusercreated' );
url.searchParams.delete( 'dtrepliedto' );
url.searchParams.delete( 'dttempusercreated' );
window.history.replaceState( {}, '', url );
}
/**
* Hook handler for `mw.hook( 'wikipage.content' )`.
*
* @param {jQuery} $container
*/
mw.dt.init = function ( $container ) {
function reallyInit( $node ) {
controller.init( $node, mw.dt.initState );
mw.dt.initState = {};
// TODO: This functionality could be provided by MediaWiki (T183720).
$( document.documentElement ).addClass( 'ext-discussiontools-init-ready' );
}
// Only (re)initialize if the hook is being fired on the page content not on e.g. a single image
// in a gallery slideshow, or a preview in our own reply tool
if ( $container.is( '#mw-content-text' ) || $container.find( '#mw-content-text' ).length ) {
// eslint-disable-next-line no-jquery/no-global-selector
reallyInit( $( '#mw-content-text' ) );
return;
}
// Otherwise, if node is detached, wait to see what it actually is
if ( !$container.closest( 'html' ).length ) {
setTimeout( () => {
if ( $container.closest( 'html' ).length ) {
mw.dt.init( $container );
}
} );
return;
}
// If it's a full page live preview, (re)initialize to support highlighting comments (T309423)
// FIXME This really should not depend on implementation details of 2 different live previews
// FIXME VisualEditor (2017WTE) preview can't be supported, because it messes with `id` attributes
const livePreviewSelectors = '#wikiPreview, .ext-WikiEditor-realtimepreview-preview';
if ( $container.parent().is( livePreviewSelectors ) ) {
reallyInit( $container );
return;
}
};
if ( url.searchParams.get( 'dtdebug' ) ) {
mw.loader.load( 'ext.discussionTools.debug' );
} else {
// Don't use an anonymous function, because ReplyWidget needs to be able to remove this handler
mw.hook( 'wikipage.content' ).add( mw.dt.init );
}
if ( mw.config.get( 'wgCanonicalSpecialPageName' ) === 'TopicSubscriptions' ) {
const topicSubscriptions = require( './topicsubscriptions.js' );
topicSubscriptions.initSpecialTopicSubscriptions();
}
if ( mw.config.get( 'wgAction' ) === 'history' ) {
const topicSubscriptions = require( './topicsubscriptions.js' );
topicSubscriptions.initNewTopicsSubscription();
}
// Clean up old localStorage entries that were erroneously set with no expiration (T339042).
// We are no longer using these keys since T329299.
// TODO: Remove this code after a few weeks.
mw.requestIdleCallback( () => {
try {
for ( const key in localStorage ) {
if ( key.startsWith( 'reply/' ) ) {
localStorage.removeItem( key );
localStorage.removeItem( '_EXPIRY_' + key );
}
}
} catch ( err ) {}
} );
module.exports = {
controller: controller,
Parser: require( './Parser.js' ),
Change CommentParser into a service Goal: ----- To have a method like CommentParser::parse(), which just takes a node to parse and a title and returns plain data, so that we don't need to keep track of the config to construct a CommentParser object (the required config like content language is provided by services) and we don't need to keep that object around after parsing. Changes: -------- CommentParser.php: * …is now a service. Constructor only takes services as arguments. The node and title are passed to a new parse() method. * parse() should return plain data, but I split this part to a separate patch for ease of review: I49bfe019aa460651447fd383f73eafa9d7180a92. * CommentParser still cheats and accesses global state in a few places, e.g. calling Title::makeTitleSafe or CommentUtils::getTitleFromUrl, so we can't turn its tests into true unit tests. This work is left for future commits. LanguageData.php: * …is now a service, instead of a static class. Parser.js: * …is not a real service, but it's changed to behave in a similar way. Constructor takes only the required config as argument, and node and title are instead passed to a new parse() method. CommentParserTest.php: parser.test.js: * Can be simplified, now that we don't need a useless node and title to test internal methods that don't use them. testUtils.js: * Can be simplified, now that we don't need to override internal ResourceLoader stuff just to change the parser config. Change-Id: Iadb7757debe000025e52770ca51ebcf24ca8ee66
2022-02-19 02:43:21 +00:00
parserData: require( './parser/data.json' ),
modifier: require( './modifier.js' ),
ThreadItem: require( './ThreadItem.js' ),
HeadingItem: require( './HeadingItem.js' ),
CommentItem: require( './CommentItem.js' ),
utils: require( './utils.js' ),
config: require( './config.json' )
};