2014-06-04 19:47:05 +00:00
( function ( context , $ ) {
"use strict" ;
context . JK = context . JK || { } ;
context . JK . NetworkTest = function ( app ) {
var NETWORK _TEST _TYPES = {
2014-07-02 02:01:47 +00:00
RestPhase : 0 ,
PktTest100NormalLatency : 1 ,
PktTest200MediumLatency : 2 ,
PktTest400LowLatency : 3 ,
PktTestRateSweep : 4 ,
RcvOnly : 5
2014-06-04 19:47:05 +00:00
}
2015-08-24 21:18:31 +00:00
var STARTING _NUM _CLIENTS _AUDIO = 4 ;
var STARTING _NUM _CLIENTS _VIDEO = 2 ;
var AUDIO _PAYLOAD _SIZE = gon . global . ftue _network _test _packet _size ;
var VIDEO _PAYLOAD _SIZE = gon . global . ftue _network _test _packet _size _video ;
2014-06-04 19:47:05 +00:00
var MINIMUM _ACCEPTABLE _SESSION _SIZE = 2 ;
2014-08-13 17:51:40 +00:00
var RETRY _THRESHOLD = 2 ;
2014-06-04 19:47:05 +00:00
2014-06-25 21:54:31 +00:00
var gearUtils = context . JK . GearUtils ;
2014-06-04 19:47:05 +00:00
var rest = context . JK . Rest ( ) ;
var logger = context . JK . logger ;
var $step = null ;
var TEST _SUCCESS _CALLBACK = 'JK.HandleNetworkTestSuccess' ;
var TEST _TIMEOUT _CALLBACK = 'JK.HandleNetworkTestTimeout' ;
var $startNetworkTestBtn = null ;
2015-03-16 18:36:02 +00:00
var $foreverNetworkTestBtn = null ;
2014-06-04 19:47:05 +00:00
var $testResults = null ;
2015-08-24 21:18:31 +00:00
var $testScoreAudio = null ;
var $testScoreVideo = null ;
2014-06-04 19:47:05 +00:00
var $testText = null ;
2015-08-24 21:18:31 +00:00
var $inProgressText = null ;
var $audioResultText = null ;
var $videoResultText = null ;
2014-06-04 19:47:05 +00:00
var testedSuccessfully = false ;
var $scoringBar = null ;
var $goodMarker = null ;
var $goodLine = null ;
var $currentScore = null ;
2015-08-24 21:18:31 +00:00
var $scoredClientsAudio = null ;
var $scoredClientsVideo = null ;
2014-06-04 19:47:05 +00:00
var $subscore = null ;
2014-06-18 19:02:26 +00:00
var $watchVideo = null ;
2015-08-24 21:18:31 +00:00
var $container = null ;
2014-06-04 19:47:05 +00:00
var backendGuardTimeout = null ;
2014-07-02 02:01:47 +00:00
var primeGuardTimeout = null ;
var primeDeferred = null ;
2014-06-04 19:47:05 +00:00
var serverClientId = '' ;
2015-08-24 21:18:31 +00:00
var audioScoring = false ;
var videoScoring = false ;
var numClientToTestAudio = STARTING _NUM _CLIENTS _AUDIO ;
var numClientToTestVideo = STARTING _NUM _CLIENTS _VIDEO ;
var testSummary = { audioAttempts : [ ] , videoAttempts : [ ] , final : null }
2014-06-04 19:47:05 +00:00
var $self = $ ( this ) ;
var scoringZoneWidth = 100 ; //px
var inGearWizard = false ;
2014-06-18 19:02:26 +00:00
var operatingSystem = null ;
2014-08-14 22:24:46 +00:00
var PRIME _PUMP _TIME = 1 ;
2014-06-04 19:47:05 +00:00
2015-03-16 18:36:02 +00:00
var forever = false ;
2014-06-19 01:59:52 +00:00
// these try to make it such that we only pass a NetworkTest Pass/Failed one time in a new user flow
var trackedPass = false ;
var lastNetworkFailure = null ;
var bandwidthSamples = [ ] ;
2014-07-02 02:01:47 +00:00
var NETWORK _TEST _START = 'network_test.start' ;
var NETWORK _TEST _DONE = 'network_test.done' ;
var NETWORK _TEST _FAIL = 'network_test.fail' ;
var NETWORK _TEST _CANCEL = 'network_test.cancel' ;
2014-06-04 19:47:05 +00:00
2014-07-02 02:01:47 +00:00
function createSuccessCallbackName ( priming ) {
if ( priming ) {
if ( inGearWizard ) {
return TEST _SUCCESS _CALLBACK + 'ForPumpPrimingGW' ;
}
else {
return TEST _SUCCESS _CALLBACK + 'ForPumpPrimingDialog' ;
}
2014-06-04 19:47:05 +00:00
}
else {
2014-07-02 02:01:47 +00:00
if ( inGearWizard ) {
return TEST _SUCCESS _CALLBACK + 'ForGearWizard' ;
}
else {
return TEST _SUCCESS _CALLBACK + 'ForDialog' ;
}
2014-06-04 19:47:05 +00:00
}
}
2014-07-02 02:01:47 +00:00
function createTimeoutCallbackName ( priming ) {
if ( priming ) {
if ( inGearWizard ) {
return TEST _TIMEOUT _CALLBACK + 'ForPumpPrimingGW' ;
}
else {
return TEST _TIMEOUT _CALLBACK + 'ForPumpPrimingDialog' ;
}
2014-06-04 19:47:05 +00:00
}
else {
2014-07-02 02:01:47 +00:00
if ( inGearWizard ) {
return TEST _TIMEOUT _CALLBACK + 'ForGearWizard' ;
}
else {
return TEST _TIMEOUT _CALLBACK + 'ForDialog' ;
}
2014-06-04 19:47:05 +00:00
}
}
2014-06-19 01:59:52 +00:00
// this averages bandwidthSamples; this method is meant just for GA data
function avgBandwidth ( num _others ) {
2014-07-02 02:01:47 +00:00
if ( bandwidthSamples . length == 0 ) {
2014-06-19 01:59:52 +00:00
return 0 ;
}
else {
var total = 0 ;
2014-07-02 02:01:47 +00:00
context . _ . each ( bandwidthSamples , function ( sample ) {
2014-06-19 01:59:52 +00:00
total += ( sample * num _others * 400 * ( 100 + 28 ) ) ; // sample is a percentage of 400. So sample * 400 gives us how many packets/sec. 100 is payload; 28 is UDP+ETHERNET overhead, to give us bandwidth
} )
return total / bandwidthSamples . length ;
}
}
2014-06-04 19:47:05 +00:00
function reset ( ) {
2014-06-19 01:59:52 +00:00
trackedPass = false ;
lastNetworkFailure = null ;
resetTestState ( ) ;
}
function resetTestState ( ) {
2014-06-04 19:47:05 +00:00
serverClientId = '' ;
2015-08-24 21:18:31 +00:00
audioScoring = false ;
videoScoring = false ;
numClientToTestAudio = STARTING _NUM _CLIENTS _AUDIO ;
numClientToTestVideo = STARTING _NUM _CLIENTS _VIDEO ;
testSummary = { audioAttempts : [ ] , videoAttempts : [ ] } ;
2014-06-04 19:47:05 +00:00
configureStartButton ( ) ;
2015-08-24 21:18:31 +00:00
$scoredClientsAudio . empty ( ) ;
2014-06-04 19:47:05 +00:00
$testResults . removeClass ( 'good acceptable bad testing' ) ;
2015-08-24 21:18:31 +00:00
$testScoreAudio . removeClass ( 'good acceptable bad testing' ) ;
$testScoreVideo . removeClass ( 'good acceptable bad testing' ) ;
$scoredClientsAudio . text ( '-' )
$scoredClientsVideo . text ( '-' )
$inProgressText . empty ( ) ;
$audioResultText . empty ( ) ;
$audioResultText . hide ( ) ;
$videoResultText . empty ( ) ;
$videoResultText . hide ( ) ;
2014-06-04 19:47:05 +00:00
$subscore . empty ( ) ;
$currentScore . width ( 0 ) ;
2014-06-19 01:59:52 +00:00
bandwidthSamples = [ ] ;
2014-06-04 19:47:05 +00:00
}
2015-08-24 21:18:31 +00:00
function renderStartTestAudio ( ) {
2014-06-04 19:47:05 +00:00
configureStartButton ( ) ;
$testResults . addClass ( 'testing' ) ;
2015-08-24 21:18:31 +00:00
$testScoreAudio . addClass ( 'testing' ) ;
2014-06-04 19:47:05 +00:00
$goodLine . css ( 'left' , ( gon . ftue _packet _rate _treshold * 100 ) + '%' ) ;
$goodMarker . css ( 'left' , ( gon . ftue _packet _rate _treshold * 100 ) + '%' ) ;
}
2015-08-24 21:18:31 +00:00
function renderStartTestVideo ( ) {
configureStartButton ( ) ;
$testResults . addClass ( 'testing' ) ;
$testScoreVideo . addClass ( 'testing' ) ;
$goodLine . css ( 'left' , ( gon . ftue _packet _rate _treshold * 100 ) + '%' ) ;
$goodMarker . css ( 'left' , ( gon . ftue _packet _rate _treshold * 100 ) + '%' ) ;
}
function renderStopTestAudio ( score , text ) {
if ( ! score || score . length == 0 ) {
$scoredClientsAudio . html ( '0' ) ;
$inProgressText . html ( 'The audio test did not pass. Video is not tested in this case.<br><br>Please click <a rel="external" href="https://jamkazam.desk.com/customer/portal/articles/1716139-what-to-do-if-you-cannot-pass-the-network-test">HERE</a> for help information.' ) ;
}
else {
$scoredClientsAudio . html ( score ) ;
}
if ( text && text . length > 0 ) {
$audioResultText . text ( text ) ;
}
2014-06-04 19:47:05 +00:00
$testResults . removeClass ( 'testing' ) ;
2015-08-24 21:18:31 +00:00
$testScoreAudio . removeClass ( 'testing' ) ;
}
function renderStopTestVideo ( score , text ) {
logger . debug ( "renderStopTestVideo" , score , text )
// don't show the audio result text until the test is over (it looks confusing otherwise).
if ( $audioResultText . text ( ) && $audioResultText . text ( ) . length > 0 ) {
$audioResultText . show ( ) ;
}
$inProgressText . text ( 'Your router and Internet service will support:' )
if ( ! score || score . length == 0 ) {
$scoredClientsVideo . html ( '-' ) ;
}
else {
if ( score < 2 ) {
$scoredClientsVideo . html ( '0' )
$videoResultText . html ( 'No other players when in a video + audio session.' ) . show ( ) ;
$testScoreVideo . addClass ( 'acceptable' ) ;
}
else {
$scoredClientsVideo . html ( score ) ;
var summary = "Video + audio sessions with up to " + score + " players" ;
if ( text && text . length > 0 ) {
// presence of text means there was an error on the last test pass.
summary += '. Note that there was an error when testing for ' + ( score + 1 ) + 'players. Support code=' + text
}
$videoResultText . html ( summary ) . show ( ) ;
}
}
$testResults . removeClass ( 'testing' ) ;
$testScoreVideo . removeClass ( 'testing' ) ;
2014-06-04 19:47:05 +00:00
}
function postDiagnostic ( ) {
rest . createDiagnostic ( {
type : 'NETWORK_TEST_RESULT' ,
2014-07-02 02:01:47 +00:00
data : { client _type : context . JK . clientType ( ) , client _id : context . JK . JamServer . clientID , summary : testSummary }
2014-06-04 19:47:05 +00:00
} ) ;
}
function appendContextualStatement ( ) {
2014-07-02 02:01:47 +00:00
if ( inGearWizard ) {
2014-10-26 14:57:13 +00:00
return " You can skip this step for now."
2014-06-04 19:47:05 +00:00
}
else {
return '' ;
}
}
2014-06-19 01:59:52 +00:00
function getLastNetworkFailure ( ) {
return lastNetworkFailure ;
}
2014-10-06 21:44:30 +00:00
function haltScoring ( ) {
context . jamClient . SetLatencyTestBlocked ( true )
rest . updateNetworkTesting ( { client _id : app . clientId , is _network _testing : true } )
. fail ( function ( jqXHR ) {
if ( jqXHR . status == 404 ) {
// assume connection is missing
app . notifyAlert ( "Not Connected" , "You must be connected to the server to run the network test." )
}
else {
app . notifyServerError ( jqXHR , "Unable to tell server that we are beginning the network test" )
}
} )
}
function resumeScoring ( ) {
context . jamClient . SetLatencyTestBlocked ( false )
rest . updateNetworkTesting ( { client _id : app . clientId , is _network _testing : false } )
. fail ( function ( jqXHR ) {
if ( jqXHR . status == 404 ) {
// assume connection is missing
// do nothing in this case
}
else {
app . notifyServerError ( jqXHR , "Unable to tell server that we are ending the network test" )
}
} )
}
2014-06-19 01:59:52 +00:00
function storeLastNetworkFailure ( reason , data ) {
2014-07-02 02:01:47 +00:00
if ( ! trackedPass ) {
lastNetworkFailure = { reason : reason , data : data } ;
2014-06-19 01:59:52 +00:00
}
}
2015-08-24 21:18:31 +00:00
function testFinishedAudio ( ) {
var attempt = getCurrentAttemptAudio ( ) ;
2014-06-04 19:47:05 +00:00
2014-07-02 02:01:47 +00:00
if ( ! testSummary . final ) {
testSummary . final = { reason : attempt . reason } ;
2014-06-04 19:47:05 +00:00
}
var reason = testSummary . final . reason ;
var success = false ;
2014-07-02 02:01:47 +00:00
if ( reason == "success" ) {
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( attempt . num _clients , "Audio-only sessions with up to " + attempt . num _clients + " players" )
2014-06-04 19:47:05 +00:00
testedSuccessfully = true ;
2014-07-02 02:01:47 +00:00
if ( ! testSummary . final . num _clients ) {
2014-06-04 19:47:05 +00:00
testSummary . final . num _clients = attempt . num _clients ;
}
2014-06-19 01:59:52 +00:00
// context.jamClient.GetNetworkTestScore() == 0 is a rough approximation if the user has passed the FTUE before
2014-07-02 02:01:47 +00:00
if ( inGearWizard || context . jamClient . GetNetworkTestScore ( ) == 0 ) {
2014-06-19 01:59:52 +00:00
trackedPass = true ;
lastNetworkFailure = null ;
context . JK . GA . trackNetworkTest ( context . JK . detectOS ( ) , testSummary . final . num _clients ) ;
}
2014-06-04 19:47:05 +00:00
context . jamClient . SetNetworkTestScore ( attempt . num _clients ) ;
2014-07-02 02:01:47 +00:00
if ( testSummary . final . num _clients == 2 ) {
2015-08-24 21:18:31 +00:00
$testScoreAudio . addClass ( 'acceptable' ) ;
2014-06-04 19:47:05 +00:00
}
else {
2015-08-24 21:18:31 +00:00
$testScoreAudio . addClass ( 'good' ) ;
2014-06-04 19:47:05 +00:00
}
success = true ;
}
2014-07-02 02:01:47 +00:00
else if ( reason == "minimum_client_threshold" ) {
2014-06-04 19:47:05 +00:00
context . jamClient . SetNetworkTestScore ( 0 ) ;
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( '' , "We're sorry, but your router and Internet service will not effectively support JamKazam sessions. Please click the HELP button for more information." )
2014-06-19 01:59:52 +00:00
storeLastNetworkFailure ( context . JK . GA . NetworkTestFailReasons . bandwidth , avgBandwidth ( attempt . num _clients - 1 ) ) ;
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( reason == "unreachable" || reason == "no-transmit" ) {
2014-06-04 19:47:05 +00:00
context . jamClient . SetNetworkTestScore ( 0 ) ;
2014-10-08 19:24:51 +00:00
// https://jamkazam.atlassian.net/browse/VRFS-2323
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( '' , "We're sorry, but your router will not support JamKazam in its current configuration. Please click <a rel='external' href='https://jamkazam.desk.com/customer/portal/articles/1716139-what-to-do-if-you-cannot-pass-the-network-test'>HERE</a> for more information." ) ;
2014-06-19 01:59:52 +00:00
storeLastNetworkFailure ( context . JK . GA . NetworkTestFailReasons . stun , attempt . num _clients ) ;
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( reason == "internal_error" ) {
2014-06-04 19:47:05 +00:00
context . JK . alertSupportedNeeded ( "The JamKazam client software had an unexpected problem while scoring your Internet connection." ) ;
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( '' , '' ) ;
2014-06-19 01:59:52 +00:00
storeLastNetworkFailure ( context . JK . GA . NetworkTestFailReasons . jamerror ) ;
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( reason == "remote_peer_cant_test" ) {
2014-06-04 19:47:05 +00:00
context . JK . alertSupportedNeeded ( "The JamKazam service is experiencing technical difficulties." ) ;
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( '' , '' ) ;
2014-06-19 01:59:52 +00:00
storeLastNetworkFailure ( context . JK . GA . NetworkTestFailReasons . jamerror ) ;
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( reason == "server_comm_timeout" ) {
2014-06-25 21:54:31 +00:00
gearUtils . skipNetworkTest ( ) ;
2014-06-18 02:57:40 +00:00
context . JK . alertSupportedNeeded ( "Communication with the JamKazam network service has timed out." + appendContextualStatement ( ) ) ;
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( '' , '' ) ;
2014-06-19 01:59:52 +00:00
storeLastNetworkFailure ( context . JK . GA . NetworkTestFailReasons . jamerror ) ;
2014-06-18 02:57:40 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( reason == 'backend_gone' ) {
2014-06-04 19:47:05 +00:00
context . JK . alertSupportedNeeded ( "The JamKazam client is experiencing technical difficulties." ) ;
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( '' , '' ) ;
2014-06-19 01:59:52 +00:00
storeLastNetworkFailure ( context . JK . GA . NetworkTestFailReasons . jamerror ) ;
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( reason == "invalid_response" ) {
2014-06-25 21:54:31 +00:00
gearUtils . skipNetworkTest ( ) ;
2014-06-18 02:57:40 +00:00
context . JK . alertSupportedNeeded ( "The JamKazam client software had an unexpected problem while scoring your Internet connection.<br/><br/>Reason: " + attempt . backend _data . reason + '.' ) ;
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( '' , '' ) ;
2014-06-19 01:59:52 +00:00
storeLastNetworkFailure ( context . JK . GA . NetworkTestFailReasons . jamerror ) ;
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( reason == 'no_servers' ) {
2014-06-25 21:54:31 +00:00
gearUtils . skipNetworkTest ( ) ;
2014-09-16 20:22:35 +00:00
context . JK . Banner . showAlert ( "No network test servers are available." + appendContextualStatement ( ) ) ;
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( '' , '' ) ;
2014-06-04 19:47:05 +00:00
testedSuccessfully = true ;
2014-06-19 01:59:52 +00:00
storeLastNetworkFailure ( context . JK . GA . NetworkTestFailReasons . jamerror ) ;
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( reason == 'no_network' ) {
2014-06-04 19:47:05 +00:00
context . JK . Banner . showAlert ( "Please try again later. Your network appears down." ) ;
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( '' , '' ) ;
2014-06-19 01:59:52 +00:00
storeLastNetworkFailure ( context . JK . GA . NetworkTestFailReasons . noNetwork ) ;
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( reason == "rest_api_error" ) {
2014-06-25 21:54:31 +00:00
gearUtils . skipNetworkTest ( ) ;
2014-06-04 19:47:05 +00:00
context . JK . alertSupportedNeeded ( "Unable to acquire a network test server." + appendContextualStatement ( ) ) ;
testedSuccessfully = true ;
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( '' , '' ) ;
2014-06-19 01:59:52 +00:00
storeLastNetworkFailure ( context . JK . GA . NetworkTestFailReasons . jamerror ) ;
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( reason == "timeout" ) {
2014-06-25 21:54:31 +00:00
gearUtils . skipNetworkTest ( ) ;
2014-06-18 02:57:40 +00:00
context . JK . alertSupportedNeeded ( "Communication with the JamKazam network service timed out." + appendContextualStatement ( ) ) ;
2014-06-04 19:47:05 +00:00
testedSuccessfully = true ;
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( '' , '' ) ;
2014-06-19 01:59:52 +00:00
storeLastNetworkFailure ( context . JK . GA . NetworkTestFailReasons . jamerror ) ;
2014-06-04 19:47:05 +00:00
}
else {
2014-06-25 21:54:31 +00:00
gearUtils . skipNetworkTest ( ) ;
2014-06-04 19:47:05 +00:00
context . JK . alertSupportedNeeded ( "The JamKazam client software had a logic error while scoring your Internet connection." ) ;
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( '' , '' ) ;
2014-06-19 01:59:52 +00:00
storeLastNetworkFailure ( context . JK . GA . NetworkTestFailReasons . jamerror ) ;
2014-06-04 19:47:05 +00:00
}
2015-08-24 21:18:31 +00:00
numClientToTestAudio = STARTING _NUM _CLIENTS _AUDIO ;
audioScoring = false ;
2014-06-04 19:47:05 +00:00
postDiagnostic ( ) ;
2014-07-02 02:01:47 +00:00
if ( success ) {
2015-08-24 21:18:31 +00:00
2015-09-09 12:13:51 +00:00
if ( window . VideoStore . isVideoEnabled ( ) ) {
2015-09-09 01:30:47 +00:00
startVideoTest ( ) ;
}
else {
// don't test video if it's disabled
renderStopTestVideo ( null , null )
numClientToTestVideo = STARTING _NUM _CLIENTS _VIDEO ;
videoScoring = false ;
configureStartButton ( ) ;
2015-08-24 21:18:31 +00:00
2015-09-09 01:30:47 +00:00
$self . triggerHandler ( NETWORK _TEST _DONE )
2015-03-16 18:36:02 +00:00
}
2014-06-04 19:47:05 +00:00
}
else {
2015-08-24 21:18:31 +00:00
configureStartButton ( ) ;
2014-06-04 19:47:05 +00:00
$self . triggerHandler ( NETWORK _TEST _FAIL )
}
}
2015-08-24 21:18:31 +00:00
function testFinishedVideo ( ) {
var attempt = getCurrentAttemptVideo ( ) ;
if ( ! testSummary . video _final ) {
testSummary . video _final = { reason : attempt . reason , num _clients : attempt . num _clients } ;
}
if ( ! testSummary . video _final . num _clients ) {
testSummary . video _final . num _clients = attempt . num _clients ;
}
var reason = testSummary . video _final . reason ;
var success = false ;
logger . debug ( "testFinishedVideo" , testSummary )
if ( reason == "success" ) {
renderStopTestVideo ( attempt . num _clients , null )
//testedSuccessfully = true;
if ( ! testSummary . video _final . num _clients ) {
testSummary . video _final . num _clients = attempt . num _clients ;
}
// context.jamClient.GetNetworkTestScore() == 0 is a rough approximation if the user has passed the FTUE before
if ( inGearWizard || context . jamClient . GetVideoNetworkTestScore ( ) == 0 ) {
//trackedPass = true;
//lastNetworkFailure = null;
//context.JK.GA.trackNetworkTest(context.JK.detectOS(), testSummary.final.num_clients);
}
context . jamClient . SetVideoNetworkTestScore ( attempt . num _clients ) ;
if ( ! testSummary . video _final . num _clients ) {
$testScoreVideo . addClass ( 'acceptable' ) ;
}
else if ( testSummary . video _final . num _clients >= 2 ) {
$testScoreVideo . addClass ( 'good' ) ;
}
else {
$testScoreVideo . addClass ( 'acceptable' ) ;
}
success = true ;
}
else if ( reason == "minimum_client_threshold" ) {
context . jamClient . SetVideoNetworkTestScore ( testSummary . video _final . num _clients - 1 ) ;
renderStopTestVideo ( testSummary . video _final . num _clients - 1 , reason )
//storeLastNetworkFailure(context.JK.GA.NetworkTestFailReasons.bandwidth, avgBandwidth(attempt.num_clients - 1));
}
else if ( reason == "unreachable" || reason == "no-transmit" ) {
context . jamClient . SetVideoNetworkTestScore ( testSummary . video _final . num _clients - 1 ) ;
// https://jamkazam.atlassian.net/browse/VRFS-2323
renderStopTestVideo ( testSummary . video _final . num _clients - 1 , reason ) ;
// storeLastNetworkFailure(context.JK.GA.NetworkTestFailReasons.stun, attempt.num_clients);
}
else if ( reason == "internal_error" ) {
context . JK . alertSupportedNeeded ( "The JamKazam client software had an unexpected problem while scoring your Internet connection." ) ;
renderStopTestVideo ( testSummary . video _final . num _clients - 1 , reason ) ;
//storeLastNetworkFailure(context.JK.GA.NetworkTestFailReasons.jamerror);
}
else if ( reason == "remote_peer_cant_test" ) {
context . JK . alertSupportedNeeded ( "The JamKazam service is experiencing technical difficulties." ) ;
renderStopTestVideo ( testSummary . video _final . num _clients - 1 , reason ) ;
//storeLastNetworkFailure(context.JK.GA.NetworkTestFailReasons.jamerror);
}
else if ( reason == "server_comm_timeout" ) {
//gearUtils.skipNetworkTest();
context . JK . alertSupportedNeeded ( "Communication with the JamKazam network service has timed out." ) ;
renderStopTestVideo ( testSummary . video _final . num _clients - 1 , reason ) ;
//storeLastNetworkFailure(context.JK.GA.NetworkTestFailReasons.jamerror);
}
else if ( reason == 'backend_gone' ) {
context . JK . alertSupportedNeeded ( "The JamKazam client is experiencing technical difficulties." ) ;
renderStopTestVideo ( testSummary . video _final . num _clients - 1 , reason ) ;
//storeLastNetworkFailure(context.JK.GA.NetworkTestFailReasons.jamerror);
}
else if ( reason == "invalid_response" ) {
//gearUtils.skipNetworkTest();
context . JK . alertSupportedNeeded ( "The JamKazam client software had an unexpected problem while scoring your Internet connection.<br/><br/>Reason: " + attempt . backend _data . reason + '.' ) ;
renderStopTestVideo ( testSummary . video _final . num _clients - 1 , reason ) ;
//storeLastNetworkFailure(context.JK.GA.NetworkTestFailReasons.jamerror);
}
else if ( reason == 'no_servers' ) {
// gearUtils.skipNetworkTest();
context . JK . Banner . showAlert ( "No network test servers are available." ) ;
renderStopTestVideo ( null , reason ) ;
//testedSuccessfully = true;
//storeLastNetworkFailure(context.JK.GA.NetworkTestFailReasons.jamerror);
}
else if ( reason == 'no_network' ) {
context . JK . Banner . showAlert ( "Please try again later. Your network appears down." ) ;
renderStopTestVideo ( testSummary . video _final . num _clients - 1 , reason ) ;
//storeLastNetworkFailure(context.JK.GA.NetworkTestFailReasons.noNetwork);
}
else if ( reason == "rest_api_error" ) {
//gearUtils.skipNetworkTest();
context . JK . alertSupportedNeeded ( "Unable to acquire a network test server." ) ;
//testedSuccessfully = true;
renderStopTestVideo ( null , reason ) ;
//storeLastNetworkFailure(context.JK.GA.NetworkTestFailReasons.jamerror);
}
else if ( reason == "timeout" ) {
//gearUtils.skipNetworkTest();
context . JK . alertSupportedNeeded ( "Communication with the JamKazam network service timed out." ) ;
//testedSuccessfully = true;
renderStopTestVideo ( testSummary . video _final . num _clients - 1 , reason ) ;
//storeLastNetworkFailure(context.JK.GA.NetworkTestFailReasons.jamerror);
}
else {
//gearUtils.skipNetworkTest();
context . JK . alertSupportedNeeded ( "The JamKazam client software had a logic error while scoring your Internet connection." ) ;
renderStopTestVideo ( testSummary . video _final . num _clients - 1 , reason ) ;
//storeLastNetworkFailure(context.JK.GA.NetworkTestFailReasons.jamerror);
}
numClientToTestVideo = STARTING _NUM _CLIENTS _VIDEO ;
videoScoring = false ;
configureStartButton ( ) ;
postDiagnostic ( ) ;
$self . triggerHandler ( NETWORK _TEST _DONE )
}
function startVideoTest ( ) {
videoScoring = true ;
renderStartTestVideo ( ) ;
setTimeout ( attemptTestPassVideo , 500 ) ;
2014-06-04 19:47:05 +00:00
}
2015-08-24 21:18:31 +00:00
function getCurrentAttemptAudio ( ) {
return testSummary . audioAttempts [ testSummary . audioAttempts . length - 1 ] ;
}
function getCurrentAttemptVideo ( ) {
return testSummary . videoAttempts [ testSummary . videoAttempts . length - 1 ] ;
}
function isFirstAttemptAudio ( ) {
return testSummary . audioAttempts . length == 0 || testSummary . audioAttempts . length == 1 ;
}
function isFirstAttemptVideo ( ) {
return testSummary . videoAttempts . length == 0 || testSummary . videoAttempts . length == 1 ;
2014-08-13 17:51:40 +00:00
}
2014-08-19 01:41:44 +00:00
function hasGoneDown ( ) {
var goneDown = false ;
2015-08-24 21:18:31 +00:00
context . _ . each ( testSummary . audioAttempts , function ( attempt ) {
if ( attempt . num _clients == STARTING _NUM _CLIENTS _AUDIO - 1 ) {
2014-08-19 01:41:44 +00:00
goneDown = true
return false ;
}
} ) ;
return goneDown ;
}
2014-08-13 17:51:40 +00:00
// is this a retry attempt? If so, how many times now has it been.
// 0 = this is the 1st attempt
// > 0 indicates the number of retries.
function numRetryAttempts ( ) {
// starting at the end of the attempts array, see how many have the same session count, which is implicitely
// indicative of a retry
var i = 0 ;
var testSessionSize = null ;
var numSameSizeTests = 0 ;
2015-08-24 21:18:31 +00:00
for ( i = testSummary . audioAttempts . length - 1 ; i >= 0 ; i -- ) {
var attempt = testSummary . audioAttempts [ i ] ;
2014-08-13 17:51:40 +00:00
if ( testSessionSize === null ) {
// this is the 1st loop through. just recording the testSessionSize
testSessionSize = attempt . num _clients ;
}
else {
if ( testSessionSize == attempt . num _clients ) {
numSameSizeTests ++ ;
}
else {
break ; // different size session found, so we are digging back into non-retry territory. bail out
}
}
}
return numSameSizeTests ;
}
function hasTooManyRetries ( ) {
return numRetryAttempts ( ) >= RETRY _THRESHOLD ;
return false ;
}
2014-07-02 02:01:47 +00:00
function primeTimedOut ( ) {
logger . warn ( "backend never completed priming pump phase" ) ;
2015-08-24 21:18:31 +00:00
audioScoring = false ;
2014-07-02 02:01:47 +00:00
primeDeferred . reject ( ) ;
}
2014-06-04 19:47:05 +00:00
function backendTimedOut ( ) {
2015-08-24 21:18:31 +00:00
if ( audioScoring ) {
testSummary . final = { reason : 'backend_gone' }
testFinishedAudio ( ) ;
}
else {
testSummary . video _final = { reason : 'backend_gone' }
testFinishedVideo ( ) ;
}
2014-06-04 19:47:05 +00:00
}
function cancel ( ) {
2014-06-18 02:57:40 +00:00
2014-06-04 19:47:05 +00:00
}
2014-06-18 02:57:40 +00:00
2014-06-04 19:47:05 +00:00
function clearBackendGuard ( ) {
2014-07-02 02:01:47 +00:00
if ( backendGuardTimeout ) {
2014-06-04 19:47:05 +00:00
clearTimeout ( backendGuardTimeout ) ;
backendGuardTimeout = null ;
}
}
2014-08-31 20:02:49 +00:00
// we know we are attempting a pass if the backend or prime guard timeout is not null
function isAttemptingPass ( ) {
2014-09-01 01:35:51 +00:00
return backendGuardTimeout != null || primeGuardTimeout != null ;
2014-08-31 20:02:49 +00:00
}
2014-07-02 02:01:47 +00:00
function clearPrimeGuard ( ) {
if ( primeGuardTimeout ) {
clearTimeout ( primeGuardTimeout ) ;
primeGuardTimeout = null ;
}
}
function setPrimeGuard ( ) {
clearPrimeGuard ( ) ;
primeGuardTimeout = setTimeout ( function ( ) {
2014-08-31 20:02:49 +00:00
clearPrimeGuard ( ) ;
2014-07-02 02:01:47 +00:00
primeTimedOut ( )
2014-08-14 23:52:19 +00:00
} , ( PRIME _PUMP _TIME + 10 ) * 1000 ) ;
2014-07-02 02:01:47 +00:00
}
2014-06-18 02:57:40 +00:00
function setBackendGuard ( ) {
clearBackendGuard ( ) ;
2014-07-02 02:01:47 +00:00
backendGuardTimeout = setTimeout ( function ( ) {
2014-08-31 20:02:49 +00:00
clearBackendGuard ( ) ;
2014-07-02 02:01:47 +00:00
backendTimedOut ( )
2015-07-23 21:10:56 +00:00
} , ( gon . ftue _network _test _duration + 5 ) * 1000 ) ;
2014-06-18 02:57:40 +00:00
}
2015-08-24 21:18:31 +00:00
function attemptTestPassAudio ( ) {
2014-06-04 19:47:05 +00:00
var attempt = { } ;
2015-08-24 21:18:31 +00:00
attempt . payload _size = AUDIO _PAYLOAD _SIZE ;
2014-06-04 19:47:05 +00:00
attempt . duration = gon . ftue _network _test _duration ;
attempt . test _type = 'PktTest400LowLatency' ;
2015-08-24 21:18:31 +00:00
attempt . num _clients = numClientToTestAudio ;
2014-06-04 19:47:05 +00:00
attempt . server _client _id = serverClientId ;
attempt . received _progress = false ;
2015-08-24 21:18:31 +00:00
testSummary . audioAttempts . push ( attempt ) ;
$scoredClientsAudio . text ( numClientToTestAudio ) ;
2014-06-04 19:47:05 +00:00
//context.jamClient.StopNetworkTest('');
2015-08-24 21:18:31 +00:00
$inProgressText . html ( "Simulating the network traffic of a " + numClientToTestAudio + "-person <b>audio-only</b> session. Video will be tested next." ) ;
2014-06-04 19:47:05 +00:00
updateProgress ( 0 , false ) ;
2014-06-18 02:57:40 +00:00
setBackendGuard ( ) ;
2014-06-04 19:47:05 +00:00
2015-08-24 21:18:31 +00:00
audioScoring = true ;
logger . debug ( "network test attempt: " + numClientToTestAudio + "-person audio session, 400 packets/s, " + AUDIO _PAYLOAD _SIZE + " byte payload" )
2014-07-02 02:01:47 +00:00
context . jamClient . TestNetworkPktBwRate ( serverClientId , createSuccessCallbackName ( false ) , createTimeoutCallbackName ( false ) ,
2014-06-04 19:47:05 +00:00
NETWORK _TEST _TYPES . PktTest400LowLatency ,
gon . ftue _network _test _duration ,
2015-08-24 21:18:31 +00:00
numClientToTestAudio - 1 ,
AUDIO _PAYLOAD _SIZE , gon . global . ftue _network _test _backend _retries ) ;
2014-06-04 19:47:05 +00:00
}
2015-08-24 21:18:31 +00:00
function attemptTestPassVideo ( ) {
var attempt = { } ;
attempt . payload _size = VIDEO _PAYLOAD _SIZE ;
attempt . duration = gon . ftue _network _test _duration ;
attempt . test _type = 'PktTest400LowLatency' ;
attempt . num _clients = numClientToTestVideo ;
attempt . server _client _id = serverClientId ;
attempt . received _progress = false ;
testSummary . videoAttempts . push ( attempt ) ;
$scoredClientsVideo . text ( numClientToTestVideo ) ;
//context.jamClient.StopNetworkTest('');
$inProgressText . html ( "Simulating the network traffic of a " + numClientToTestVideo + "-person <b>video-enabled</b> session." ) ;
updateProgress ( 0 , false ) ;
setBackendGuard ( ) ;
logger . debug ( "network test attempt: " + numClientToTestVideo + "-person video session, 400 packets/s, " + VIDEO _PAYLOAD _SIZE + " byte payload" )
context . jamClient . TestNetworkPktBwRate ( serverClientId , createSuccessCallbackName ( false ) , createTimeoutCallbackName ( false ) ,
NETWORK _TEST _TYPES . PktTest400LowLatency ,
gon . ftue _network _test _duration ,
numClientToTestVideo - 1 ,
VIDEO _PAYLOAD _SIZE , gon . global . ftue _network _test _backend _retries ) ;
}
2014-07-02 02:01:47 +00:00
// you have to score a little to 'prime' the logic to know whether it's on wireless or not
function primePump ( ) {
2015-08-24 21:18:31 +00:00
audioScoring = true ;
2014-07-02 02:01:47 +00:00
primeDeferred = new $ . Deferred ( ) ;
2014-06-04 19:47:05 +00:00
2014-07-02 02:01:47 +00:00
setPrimeGuard ( ) ;
2014-06-04 19:47:05 +00:00
2014-07-02 02:01:47 +00:00
context . jamClient . TestNetworkPktBwRate ( serverClientId , createSuccessCallbackName ( true ) , createTimeoutCallbackName ( true ) ,
NETWORK _TEST _TYPES . PktTest400LowLatency ,
2014-08-14 22:24:46 +00:00
PRIME _PUMP _TIME ,
2014-07-02 02:01:47 +00:00
2 ,
2015-08-24 21:18:31 +00:00
AUDIO _PAYLOAD _SIZE , gon . global . ftue _network _test _backend _retries ) ;
2014-07-02 02:01:47 +00:00
return primeDeferred ;
}
2014-08-14 22:24:46 +00:00
function cancelTest ( ) {
2015-08-24 21:18:31 +00:00
audioScoring = false ;
2014-08-14 22:24:46 +00:00
configureStartButton ( ) ;
2015-08-24 21:18:31 +00:00
renderStopTestAudio ( ) ;
2014-08-14 22:24:46 +00:00
$self . triggerHandler ( NETWORK _TEST _CANCEL )
}
function postPumpRun ( ) {
2015-08-24 21:18:31 +00:00
// check if on Wifi 1st
2014-08-14 22:24:46 +00:00
var isWireless = context . jamClient . IsMyNetworkWireless ( ) ;
if ( isWireless == - 1 ) {
logger . warn ( "unable to determine if the user is on wireless or not for network test. skipping prompt." )
}
if ( isWireless == 1 ) {
context . JK . Banner . showAlert ( { buttons : [
{ name : 'CANCEL' , click : function ( ) {
cancelTest ( ) ;
} } ,
{ name : 'RUN NETWORK TEST ANYWAY' , click : function ( ) {
2015-08-24 21:18:31 +00:00
attemptTestPassAudio ( ) ;
2014-08-14 22:24:46 +00:00
;
} }
] ,
html : "<p>It appears that your computer is connected to your network using WiFi.</p>" +
"<p>We strongly advise against running the JamKazam application on a WiFi connection. " +
"We recommend using a wired Ethernet connection from your computer to your router. " +
"A WiFi connection is likely to cause significant issues in both latency and audio quality.</p>" } )
}
else {
2015-08-24 21:18:31 +00:00
attemptTestPassAudio ( ) ;
2014-08-14 22:24:46 +00:00
}
}
2014-10-06 21:44:30 +00:00
function pauseForRecentScoresTime ( ) {
var lastScoreTimes = context . jamClient . GetLastLatencyTestTimes ( )
console . log ( lastScoreTimes )
return 0 ;
var noPause = 0 ;
var longAgo = 1000000 ;
var initiated = lastScoreTimes . initiatied ;
var requested = lastScoreTimes . requested ;
if ( initiated === null || initiated === undefined ) {
logger . warn ( "lastScoreTimes.initiated is not set" ) ;
initiated = longAgo ;
}
if ( requested === null || requested === undefined ) {
logger . warn ( "lastScoreTimes.requested is not set" ) ;
requested = longAgo ;
}
if ( initiated == 0 ) {
logger . debug ( "lastScoreTimes.initiated is zero" ) ;
initiated = longAgo ;
}
if ( requested == 0 ) {
logger . debug ( "lastScoreTimes.requested is zero" ) ;
requested = longAgo ;
}
if ( initiated < 0 ) {
logger . debug ( "lastScoreTimes.initiated is less than zero" ) ;
initiated = longAgo ;
}
if ( requested < 0 ) {
logger . debug ( "lastScoreTimes.requested is less than zero" ) ;
requested = longAgo ;
}
var mostRecentValue = initiated < requested ? initiated : requested ;
if ( mostRecentValue > gon . globalftue _network _test _min _wait _since _last _score * 1000 ) {
return noPause ; // our last score was past our min wait; so no delay necessary
}
else {
// pause for the remainder of the min wait threshold
var remainder = gon . globalftue _network _test _min _wait _since _last _score * 1000 - mostRecentValue ;
if ( remainder > 1500 ) {
// we need to update the UI because this is a long time for a mystery pause
$startNetworkTestBtn . text ( 'SHORT QUIET PERIOD...' )
}
return remainder ;
}
}
2014-07-02 02:01:47 +00:00
function prepareNetworkTest ( ) {
2014-06-04 19:47:05 +00:00
2015-08-24 21:18:31 +00:00
if ( audioScoring || videoScoring ) return false ;
2014-10-06 21:44:30 +00:00
setTimeout ( function ( ) {
logger . info ( "starting network test" ) ;
resetTestState ( ) ;
2015-08-24 21:18:31 +00:00
audioScoring = true ;
2014-10-06 21:44:30 +00:00
$self . triggerHandler ( NETWORK _TEST _START ) ;
2015-08-24 21:18:31 +00:00
renderStartTestAudio ( ) ;
2014-10-06 21:44:30 +00:00
rest . getLatencyTester ( )
. done ( function ( response ) {
// ensure there are no tests ongoing
serverClientId = response . client _id ;
testSummary . serverClientId = serverClientId ;
logger . info ( "beginning network test against client_id: " + serverClientId ) ;
primePump ( )
. done ( function ( ) {
postPumpRun ( ) ;
} )
. fail ( function ( ) {
logger . debug ( "unable to determine user's network type. primePump failed." )
context . JK . Banner . showAlert ( {
title : 'Unable to Determine Network Type' ,
buttons : [
{ name : 'CANCEL' , click : function ( ) {
cancelTest ( ) ;
} } ,
{ name : 'RUN NETWORK TEST ANYWAY' , click : function ( ) {
2015-08-24 21:18:31 +00:00
attemptTestPassAudio ( ) ;
2014-10-06 21:44:30 +00:00
;
} }
] ,
html : "<p>We are unable to determine if your computer is connected to your network using WiFi.</p>" +
"<p>We strongly advise against running the JamKazam application on a WiFi connection. " +
"We recommend using a wired Ethernet connection from your computer to your router. " +
"A WiFi connection is likely to cause significant issues in both latency and audio quality.</p>" } )
} ) ;
} )
. fail ( function ( jqXHR ) {
if ( jqXHR . status == 404 ) {
// means there are no network testers available.
// we have to skip this part of the UI
testSummary . final = { reason : 'no_servers' }
2014-06-04 19:47:05 +00:00
}
else {
2014-10-06 21:44:30 +00:00
if ( context . JK . isNetworkError ( arguments ) ) {
testSummary . final = { reason : 'no_network' }
}
else {
testSummary . final = { reason : 'rest_api_error' }
}
2014-06-04 19:47:05 +00:00
}
2015-08-24 21:18:31 +00:00
testFinishedAudio ( ) ;
2014-10-06 21:44:30 +00:00
} )
} , pauseForRecentScoresTime ( ) )
2014-07-02 02:01:47 +00:00
2014-06-04 19:47:05 +00:00
return false ;
}
function updateProgress ( throughput , showSubscore ) {
2014-06-19 01:59:52 +00:00
2014-06-04 19:47:05 +00:00
var width = throughput * 100 ;
$currentScore . stop ( ) . data ( 'showSubscore' , showSubscore ) ;
2014-07-02 02:01:47 +00:00
if ( ! showSubscore ) {
2014-06-04 19:47:05 +00:00
$subscore . text ( '' ) ;
}
$currentScore . animate ( {
duration : 1000 ,
width : width + '%'
} , {
step : function ( now , fx ) {
2014-07-02 02:01:47 +00:00
if ( showSubscore ) {
2014-06-04 19:47:05 +00:00
var newWidth = ( 100 * parseFloat ( $currentScore . css ( 'width' ) ) / parseFloat ( $currentScore . parent ( ) . css ( 'width' ) ) ) ;
$subscore . text ( ( Math . round ( newWidth * 10 ) / 10 ) + '%' ) ;
}
}
} ) . css ( 'overflow' , 'visible' ) ;
;
}
2014-07-02 02:01:47 +00:00
function primePumpTimeout ( data ) {
2014-08-31 20:02:49 +00:00
if ( ! isAttemptingPass ( ) ) {
logger . error ( "primePumpTimeout: already completed the test pass. indicates backend sent > 1 final event" ) ;
return ;
}
2014-07-02 02:01:47 +00:00
clearPrimeGuard ( ) ;
2015-08-24 21:18:31 +00:00
audioScoring = false ;
2014-07-20 02:11:16 +00:00
logger . debug ( "the prime pump routine timed out" )
2014-07-02 02:01:47 +00:00
primeDeferred . reject ( ) ;
}
function primePumpComplete ( data ) {
2014-08-31 20:02:49 +00:00
if ( ! isAttemptingPass ( ) ) {
logger . error ( "primePumpComplete: already completed the test pass. indicates backend sent > 1 final event" ) ;
return ;
}
2014-07-02 02:01:47 +00:00
if ( data . progress === true ) {
// waiting...
logger . debug ( "pump prime progress report" ) ;
setPrimeGuard ( ) ;
}
else {
clearPrimeGuard ( ) ;
// we could check for errors, but it's confusing to do so. we just want to let the backend figure out if
// the interface is wireless, or not
setTimeout ( function ( ) {
logger . debug ( "pump primed" ) ;
2015-08-24 21:18:31 +00:00
audioScoring = false ;
2014-07-02 02:01:47 +00:00
primeDeferred . resolve ( ) ;
} , 500 ) ; // give backend room to breath for timing/race issues
}
}
2015-08-24 21:18:31 +00:00
function networkTestCompleteAudio ( data ) {
2014-08-31 20:02:49 +00:00
if ( ! isAttemptingPass ( ) ) {
logger . error ( "networkTestComplete: already completed the test pass. indicates backend sent > 1 final event" ) ;
return ;
}
2015-08-24 21:18:31 +00:00
var attempt = getCurrentAttemptAudio ( ) ;
2014-06-04 19:47:05 +00:00
function refineTest ( up ) {
2014-08-13 17:51:40 +00:00
if ( up === null ) {
2015-08-24 21:18:31 +00:00
logger . debug ( "retrying test at size: " + numClientToTestAudio ) ;
setTimeout ( attemptTestPassAudio , 500 ) ; // wait a second to avoid race conditions with client/server comm
2014-08-13 17:51:40 +00:00
}
else if ( up ) {
2015-08-24 21:18:31 +00:00
if ( numClientToTestAudio == gon . ftue _network _test _max _clients ) {
2014-06-04 19:47:05 +00:00
attempt . reason = "success" ;
2015-08-24 21:18:31 +00:00
testFinishedAudio ( ) ;
2014-06-04 19:47:05 +00:00
}
2014-08-19 01:41:44 +00:00
else if ( hasGoneDown ( ) ) {
// this means we've gone up before... so don't go back down (i.e., creating a loop)
attempt . reason = "success" ;
2015-08-24 21:18:31 +00:00
testSummary . final = { reason : 'success' , num _clients : numClientToTestAudio }
testFinishedAudio ( ) ;
2014-08-19 01:41:44 +00:00
}
2014-06-04 19:47:05 +00:00
else {
2015-08-24 21:18:31 +00:00
numClientToTestAudio ++ ;
logger . debug ( "increasing number of clients to " + numClientToTestAudio ) ;
setTimeout ( attemptTestPassAudio , 500 ) ; // wait a second to avoid race conditions with client/server comm
2014-06-04 19:47:05 +00:00
}
}
else {
// reduce numclients if we can
2015-08-24 21:18:31 +00:00
if ( numClientToTestAudio == MINIMUM _ACCEPTABLE _SESSION _SIZE ) {
2014-06-04 19:47:05 +00:00
// we are too low already. fail the user
attempt . reason = "minimum_client_threshold" ;
2015-08-24 21:18:31 +00:00
testFinishedAudio ( ) ;
2014-06-04 19:47:05 +00:00
}
2015-08-24 21:18:31 +00:00
else if ( numClientToTestAudio > STARTING _NUM _CLIENTS _AUDIO ) {
2014-06-04 19:47:05 +00:00
// this means we've gone up before... so don't go back down (i.e., creating a loop)
attempt . reason = "success" ;
2015-08-24 21:18:31 +00:00
testSummary . final = { reason : 'success' , num _clients : numClientToTestAudio - 1 }
testFinishedAudio ( ) ;
2014-06-04 19:47:05 +00:00
}
else {
2015-08-24 21:18:31 +00:00
numClientToTestAudio -- ;
logger . debug ( "reducing number of clients to " + numClientToTestAudio ) ;
setTimeout ( attemptTestPassAudio , 500 ) ; // wait a second to avoid race conditions with client/server comm
2014-06-04 19:47:05 +00:00
}
}
}
attempt . backend _data = data ;
2014-07-02 02:01:47 +00:00
if ( data . progress === true ) {
2014-06-04 19:47:05 +00:00
2014-06-18 02:57:40 +00:00
setBackendGuard ( ) ;
2014-06-04 19:47:05 +00:00
var animate = true ;
2014-07-02 02:01:47 +00:00
if ( data . downthroughput && data . upthroughput ) {
2014-06-04 19:47:05 +00:00
2014-07-02 02:01:47 +00:00
if ( data . downthroughput > 0 || data . upthroughput > 0 ) {
2014-06-04 19:47:05 +00:00
attempt . received _progress = true ;
animate = true ;
}
2014-07-02 02:01:47 +00:00
if ( attempt . received _progress ) {
2014-06-04 19:47:05 +00:00
// take the lower
2014-07-02 02:01:47 +00:00
var throughput = data . downthroughput < data . upthroughput ? data . downthroughput : data . upthroughput ;
2014-06-04 19:47:05 +00:00
2014-06-19 01:59:52 +00:00
bandwidthSamples . push ( data . upthroughput ) ;
2014-06-04 19:47:05 +00:00
updateProgress ( throughput , true ) ;
}
}
}
else {
2014-06-18 02:57:40 +00:00
clearBackendGuard ( ) ;
2014-08-06 21:52:40 +00:00
logger . debug ( "network test pass completed. data: " , data ) ;
2014-06-04 19:47:05 +00:00
2014-07-02 02:01:47 +00:00
if ( data . reason == "unreachable" ) {
2014-08-13 17:51:40 +00:00
logger . debug ( "network test: unreachable (STUN issue or similar)" )
2014-06-04 19:47:05 +00:00
attempt . reason = data . reason ;
2015-08-24 21:18:31 +00:00
testFinishedAudio ( ) ;
2014-06-16 03:32:56 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( data . reason == "no-transmit" ) {
2014-06-18 02:57:40 +00:00
logger . debug ( "network test: no-transmit (STUN issue or similar)" ) ;
attempt . reason = data . reason ;
2015-08-24 21:18:31 +00:00
testFinishedAudio ( ) ;
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( data . reason == "internal_error" ) {
2014-06-04 19:47:05 +00:00
// oops
logger . debug ( "network test: internal_error (client had a unexpected problem)" ) ;
attempt . reason = data . reason ;
2015-08-24 21:18:31 +00:00
testFinishedAudio ( ) ;
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( data . reason == "remote_peer_cant_test" ) {
2014-06-04 19:47:05 +00:00
// old client
logger . debug ( "network test: remote_peer_cant_test (old client)" )
attempt . reason = data . reason ;
2015-08-24 21:18:31 +00:00
testFinishedAudio ( ) ;
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
else if ( data . reason == "server_comm_timeout" ) {
2014-06-18 02:57:40 +00:00
logger . debug ( "network test: server_comm_timeout (communication with server problem)" )
attempt . reason = data . reason ;
2015-08-24 21:18:31 +00:00
testFinishedAudio ( ) ;
2014-06-18 02:57:40 +00:00
}
2014-06-04 19:47:05 +00:00
else {
2014-07-02 02:01:47 +00:00
if ( ! data . downthroughput || ! data . upthroughput ) {
2014-06-04 19:47:05 +00:00
// we have to assume this is bad. just not a reason we know about in code
logger . debug ( "network test: no test data (unknown issue? " + data . reason + ")" )
attempt . reason = "invalid_response" ;
2015-08-24 21:18:31 +00:00
testFinishedAudio ( ) ;
2014-06-04 19:47:05 +00:00
}
else {
// success... but we still have to verify if this data is within threshold
2014-07-02 02:01:47 +00:00
if ( data . downthroughput < gon . ftue _packet _rate _treshold ) {
2014-06-04 19:47:05 +00:00
logger . debug ( "network test: downthroughput too low. downthroughput: " + data . downthroughput + ", threshold: " + gon . ftue _packet _rate _treshold ) ;
refineTest ( false ) ;
}
2014-07-02 02:01:47 +00:00
else if ( data . upthroughput < gon . ftue _packet _rate _treshold ) {
2014-06-04 19:47:05 +00:00
logger . debug ( "network test: upthroughput too low. upthroughput: " + data . upthroughput + ", threshold: " + gon . ftue _packet _rate _treshold ) ;
refineTest ( false ) ;
}
else {
// true success. we can accept this score
logger . debug ( "network test: success" )
refineTest ( true ) ;
}
}
}
// VRFS-1742
// context.jamClient.StopNetworkTest(serverClientId);
}
}
2015-08-24 21:18:31 +00:00
function networkTestCompleteVideo ( data ) {
if ( ! isAttemptingPass ( ) ) {
logger . error ( "networkTestCompleteVideo: already completed the test pass. indicates backend sent > 1 final event" ) ;
return ;
}
var attempt = getCurrentAttemptVideo ( ) ;
function refineTest ( up ) {
if ( up === null ) {
logger . debug ( "retrying video test at size: " + numClientToTestVideo ) ;
setTimeout ( attemptTestPassVideo , 500 ) ; // wait a second to avoid race conditions with client/server comm
}
else if ( up ) {
if ( numClientToTestVideo == gon . ftue _network _test _max _clients ) {
attempt . reason = "success" ;
testFinishedVideo ( ) ;
}
else {
numClientToTestVideo ++ ;
logger . debug ( "increasing number of clients to " + numClientToTestVideo ) ;
setTimeout ( attemptTestPassVideo , 500 ) ; // wait a second to avoid race conditions with client/server comm
}
}
else {
attempt . reason = "success" ;
testSummary . video _final = { reason : 'success' , num _clients : numClientToTestVideo - 1 }
testFinishedVideo ( ) ;
}
}
attempt . backend _data = data ;
if ( data . progress === true ) {
setBackendGuard ( ) ;
var animate = true ;
if ( data . downthroughput && data . upthroughput ) {
if ( data . downthroughput > 0 || data . upthroughput > 0 ) {
attempt . received _progress = true ;
animate = true ;
}
if ( attempt . received _progress ) {
// take the lower
var throughput = data . downthroughput < data . upthroughput ? data . downthroughput : data . upthroughput ;
bandwidthSamples . push ( data . upthroughput ) ;
updateProgress ( throughput , true ) ;
}
}
}
else {
clearBackendGuard ( ) ;
logger . debug ( "network video test pass completed. data: " , data ) ;
if ( data . reason == "unreachable" ) {
logger . debug ( "video network test: unreachable (STUN issue or similar)" )
attempt . reason = data . reason ;
testFinishedVideo ( ) ;
}
else if ( data . reason == "no-transmit" ) {
logger . debug ( "video network test: no-transmit (STUN issue or similar)" ) ;
attempt . reason = data . reason ;
testFinishedVideo ( ) ;
}
else if ( data . reason == "internal_error" ) {
// oops
logger . debug ( "video network test: internal_error (client had a unexpected problem)" ) ;
attempt . reason = data . reason ;
testFinishedVideo ( ) ;
}
else if ( data . reason == "remote_peer_cant_test" ) {
// old client
logger . debug ( "video network test: remote_peer_cant_test (old client)" )
attempt . reason = data . reason ;
testFinishedVideo ( ) ;
}
else if ( data . reason == "server_comm_timeout" ) {
logger . debug ( "video network test: server_comm_timeout (communication with server problem)" )
attempt . reason = data . reason ;
testFinishedVideo ( ) ;
}
else {
if ( ! data . downthroughput || ! data . upthroughput ) {
// we have to assume this is bad. just not a reason we know about in code
logger . debug ( "video network test: no test data (unknown issue? " + data . reason + ")" )
attempt . reason = "invalid_response" ;
testFinishedVideo ( ) ;
}
else {
// success... but we still have to verify if this data is within threshold
if ( data . downthroughput < gon . ftue _packet _rate _treshold ) {
logger . debug ( "video network test: downthroughput too low. downthroughput: " + data . downthroughput + ", threshold: " + gon . ftue _packet _rate _treshold ) ;
refineTest ( false ) ;
}
else if ( data . upthroughput < gon . ftue _packet _rate _treshold ) {
logger . debug ( "video network test: upthroughput too low. upthroughput: " + data . upthroughput + ", threshold: " + gon . ftue _packet _rate _treshold ) ;
refineTest ( false ) ;
}
else {
// true success. we can accept this score
logger . debug ( "vido network test: success" )
refineTest ( true ) ;
}
}
}
}
}
function networkTestTimeoutAudio ( data ) {
2014-08-31 20:02:49 +00:00
if ( ! isAttemptingPass ( ) ) {
2015-08-24 21:18:31 +00:00
logger . error ( "networkTestTimeout: already completed the audio test pass. indicates backend sent > 1 final event" ) ;
2014-08-31 20:02:49 +00:00
return ;
}
2014-06-04 19:47:05 +00:00
clearBackendGuard ( ) ;
logger . warn ( "network timeout when testing latency test: " + data ) ;
2015-08-24 21:18:31 +00:00
var attempt = getCurrentAttemptAudio ( ) ;
2014-06-04 19:47:05 +00:00
attempt . reason = 'timeout' ;
attempt . backend _data = data ;
2015-08-24 21:18:31 +00:00
testFinishedAudio ( ) ;
}
function networkTestTimeoutVideo ( data ) {
if ( ! isAttemptingPass ( ) ) {
logger . error ( "networkTestTimeout: already completed the video test pass. indicates backend sent > 1 final event" ) ;
return ;
}
clearBackendGuard ( ) ;
logger . warn ( "network timeout when testing latency test: " + data ) ;
var attempt = getCurrentAttemptVideo ( ) ;
attempt . reason = 'timeout' ;
attempt . backend _data = data ;
testFinishedVideo ( ) ;
2014-06-04 19:47:05 +00:00
}
function hasScoredNetworkSuccessfully ( ) {
return testedSuccessfully ;
}
function configureStartButton ( ) {
2015-08-24 21:18:31 +00:00
if ( audioScoring || videoScoring ) {
2014-06-04 19:47:05 +00:00
$startNetworkTestBtn . text ( 'NETWORK TEST RUNNING...' ) . removeClass ( 'button-orange' ) . addClass ( 'button-grey' )
}
else {
$startNetworkTestBtn . text ( 'START NETWORK TEST' ) . removeClass ( 'button-grey' ) . addClass ( 'button-orange' ) ;
}
}
function initializeNextButtonState ( ) {
2015-08-24 21:18:31 +00:00
$dialog . setNextState ( hasScoredNetworkSuccessfully ( ) && ! audioScoring && ! videoScoring ) ;
2014-06-04 19:47:05 +00:00
}
function initializeBackButtonState ( ) {
2015-08-24 21:18:31 +00:00
$dialog . setBackState ( ! audioScoring && ! videoScoring ) ;
2014-06-04 19:47:05 +00:00
}
function beforeHide ( ) {
2014-06-18 02:57:40 +00:00
2014-06-04 19:47:05 +00:00
}
2014-06-18 19:02:26 +00:00
function initializeVideoWatchButton ( ) {
2014-07-02 02:01:47 +00:00
if ( operatingSystem == "Win32" ) {
2014-06-18 19:02:26 +00:00
$watchVideo . attr ( 'href' , 'https://www.youtube.com/watch?v=rhAdCVuwhBc' ) ;
}
else {
$watchVideo . attr ( 'href' , 'https://www.youtube.com/watch?v=0r1py0AYJ4Y' ) ;
}
}
2014-07-02 02:01:47 +00:00
2014-06-04 19:47:05 +00:00
function initialize ( _$step , _inGearWizard ) {
$step = _$step ;
inGearWizard = _inGearWizard ;
$startNetworkTestBtn = $step . find ( '.start-network-test' ) ;
2015-03-16 18:36:02 +00:00
$foreverNetworkTestBtn = $step . find ( '.forever-network-test' )
2014-06-04 19:47:05 +00:00
2016-04-13 17:05:04 +00:00
if ( $startNetworkTestBtn . length == 0 ) {
console . log ( 'no start network test button found in network-test. in gear wizard=' + inGearWizard )
return
//throw 'no start network test button found in network-test. in gear wizard=' + inGearWizard
}
2014-06-04 19:47:05 +00:00
$testResults = $step . find ( '.network-test-results' ) ;
2015-08-24 21:18:31 +00:00
$testScoreAudio = $step . find ( '.network-test-score-audio' ) ;
$scoredClientsAudio = $testScoreAudio . find ( '.scored-clients' ) ;
$testScoreVideo = $step . find ( '.network-test-score-video' ) ;
$scoredClientsVideo = $testScoreVideo . find ( '.scored-clients' ) ;
2014-06-04 19:47:05 +00:00
$testText = $step . find ( '.network-test-text' ) ;
2015-08-24 21:18:31 +00:00
$inProgressText = $step . find ( '.in-progress' )
$audioResultText = $step . find ( '.audio-result' )
$videoResultText = $step . find ( '.video-result' )
2014-06-04 19:47:05 +00:00
$scoringBar = $step . find ( '.scoring-bar' ) ;
$goodMarker = $step . find ( '.good-marker' ) ;
2014-07-02 02:01:47 +00:00
$goodLine = $step . find ( '.good-line' ) ;
2014-06-04 19:47:05 +00:00
$currentScore = $step . find ( '.current-score' ) ;
2015-08-24 21:18:31 +00:00
2014-06-04 19:47:05 +00:00
$subscore = $step . find ( '.subscore' ) ;
2014-06-18 19:02:26 +00:00
$watchVideo = $step . find ( '.watch-video' ) ;
2015-08-24 21:18:31 +00:00
$container = $step . find ( '.network-test' ) ;
if ( inGearWizard ) {
$container . attr ( 'data-mode' , 'gear-wizard' )
}
else {
$container . attr ( 'data-mode' , 'standalone' )
}
2014-07-02 02:01:47 +00:00
$startNetworkTestBtn . on ( 'click' , function ( ) {
2015-03-16 18:36:02 +00:00
forever = false ;
2014-07-02 02:01:47 +00:00
prepareNetworkTest ( ) ;
2015-08-24 21:18:31 +00:00
return false ;
2014-07-02 02:01:47 +00:00
} ) ;
2015-03-16 18:36:02 +00:00
if ( context . JK . currentUserAdmin ) {
$foreverNetworkTestBtn . on ( 'click' , function ( ) {
forever = true ;
prepareNetworkTest ( ) ;
2015-08-24 21:18:31 +00:00
return false ;
2015-03-16 18:36:02 +00:00
} ) . show ( ) ;
}
2014-06-18 19:02:26 +00:00
operatingSystem = context . JK . GetOSAsString ( ) ;
initializeVideoWatchButton ( ) ;
2014-06-04 19:47:05 +00:00
2014-07-02 02:01:47 +00:00
2014-06-04 19:47:05 +00:00
// if this network test is instantiated anywhere else than the gearWizard, or a dialog, then this will have to be expanded
2014-07-02 02:01:47 +00:00
if ( inGearWizard ) {
context . JK . HandleNetworkTestSuccessForPumpPrimingGW = function ( data ) {
primePumpComplete ( data )
} ;
context . JK . HandleNetworkTestTimeoutForPumpPrimingGW = function ( data ) {
primePumpTimeout ( data )
} ;
context . JK . HandleNetworkTestSuccessForGearWizard = function ( data ) {
2015-08-24 21:18:31 +00:00
if ( audioScoring ) {
networkTestCompleteAudio ( data ) ;
}
else if ( videoScoring ) {
networkTestCompleteVideo ( data ) ;
}
else {
logger . warn ( "unknown state in HandleNetworkTestSuccessForGearWizard" ) ;
}
2014-07-02 02:01:47 +00:00
} ; // pin to global for bridge callback
context . JK . HandleNetworkTestTimeoutForGearWizard = function ( data ) {
2015-08-24 21:18:31 +00:00
if ( audioScoring ) {
networkTestTimeoutAudio ( data ) ;
}
else if ( videoScoring ) {
networkTestTimeoutVideo ( data ) ;
}
2014-07-02 02:01:47 +00:00
} ; // pin to global for bridge callback
2014-06-04 19:47:05 +00:00
}
else {
2014-07-02 02:01:47 +00:00
context . JK . HandleNetworkTestSuccessForPumpPrimingDialog = function ( data ) {
primePumpComplete ( data )
} ;
context . JK . HandleNetworkTestTimeoutForPumpPrimingDialog = function ( data ) {
primePumpTimeout ( data )
} ;
context . JK . HandleNetworkTestSuccessForDialog = function ( data ) {
2015-08-24 21:18:31 +00:00
if ( audioScoring ) {
networkTestCompleteAudio ( data ) ;
}
else if ( videoScoring ) {
networkTestCompleteVideo ( data ) ;
}
else {
logger . warn ( "unknown state in HandleNetworkTestSuccessForDialog" ) ;
}
2014-07-02 02:01:47 +00:00
} ; // pin to global for bridge callback
context . JK . HandleNetworkTestTimeoutForDialog = function ( data ) {
2015-08-24 21:18:31 +00:00
if ( audioScoring ) {
networkTestTimeoutAudio ( data ) ;
}
else if ( videoScoring ) {
networkTestTimeoutVideo ( data ) ;
}
2014-07-02 02:01:47 +00:00
} ; // pin to global for bridge callback
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
2014-06-04 19:47:05 +00:00
}
2014-07-02 02:01:47 +00:00
this . isScoring = function ( ) {
2015-08-24 21:18:31 +00:00
return audioScoring || videoScoring ;
2014-07-02 02:01:47 +00:00
} ;
2014-06-04 19:47:05 +00:00
this . hasScoredNetworkSuccessfully = hasScoredNetworkSuccessfully ;
this . initialize = initialize ;
this . reset = reset ;
this . cancel = cancel ;
2014-06-19 01:59:52 +00:00
this . getLastNetworkFailure = getLastNetworkFailure ;
2014-10-06 21:44:30 +00:00
this . haltScoring = haltScoring ;
this . resumeScoring = resumeScoring ;
2014-06-04 19:47:05 +00:00
this . NETWORK _TEST _START = NETWORK _TEST _START ;
this . NETWORK _TEST _DONE = NETWORK _TEST _DONE ;
this . NETWORK _TEST _FAIL = NETWORK _TEST _FAIL ;
2014-07-02 02:01:47 +00:00
this . NETWORK _TEST _CANCEL = NETWORK _TEST _CANCEL ;
2014-06-04 19:47:05 +00:00
return this ;
}
} ) ( window , jQuery ) ;