diff --git a/resources/js/ext.uls.displaysettings.js b/resources/js/ext.uls.displaysettings.js index 79caa42c..ba69311e 100644 --- a/resources/js/ext.uls.displaysettings.js +++ b/resources/js/ext.uls.displaysettings.js @@ -159,6 +159,19 @@ new mw.Api().parse( $.i18n( 'ext-uls-display-settings-anon-log-in-cta' ) ) .done( function ( parsedCta ) { $loginCta.html( parsedCta ); + // Because browsers navigate away when clicking a link, + // we are are overriding the normal click behavior to + // allow the event be logged first - currently there is no + // local queue for events. The timeout is there to make sure + // the user gets to the new page even if event logging is slow + // or fails. + $loginCta.find( 'a' ).click( function ( event ) { + event.preventDefault(); + mw.uls.logEvent( { action: 'login-click' }, 500 ) + .always( function () { + window.location.href = event.target.href; + } ); + } ); } ); return; diff --git a/resources/js/ext.uls.init.js b/resources/js/ext.uls.init.js index 47579b86..ad11d55b 100644 --- a/resources/js/ext.uls.init.js +++ b/resources/js/ext.uls.init.js @@ -158,13 +158,32 @@ * and ensures the correct schema is loaded. * * @param {Object} data Event action and optional fields + * @param {int} [timeout] Fail the request if it is not completed within + * the specified timeout. Can be use for example to log actions that + * cause the browser to navigate to other pages. + * @return {jQuery.Promise} jQuery Promise object for the logging call * @since 2013.07 * @see https://meta.wikimedia.org/wiki/Schema:UniversalLanguageSelector */ - mw.uls.logEvent = function ( event ) { + mw.uls.logEvent = function ( event, timeout ) { + // We need to create our own deferred for two reasons: + // - logEvent might not be executed immediately + // - we cannot reject a promise returned by it + // So we proxy the original promises status updates + // and register our timeout if requested (for links). + var deferred = $.Deferred(); + logEventQueue.add( function () { - mw.eventLog.logEvent( 'UniversalLanguageSelector', event ); + mw.eventLog.logEvent( 'UniversalLanguageSelector', event ) + .done( deferred.resolve ) + .fail( deferred.reject ); } ); + + if ( timeout !== undefined ) { + window.setTimeout( deferred.reject, timeout ); + } + + return deferred.promise(); }; /**