run-qunit.js 2.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172
  1. /**
  2. * Wait until the test condition is true or a timeout occurs. Useful for waiting
  3. * on a server response or for a ui change (fadeIn, etc.) to occur.
  4. *
  5. * @param testFx javascript condition that evaluates to a boolean,
  6. * it can be passed in as a string (e.g.: "1 == 1" or "$('#bar').is(':visible')" or
  7. * as a callback function.
  8. * @param onReady what to do when testFx condition is fulfilled,
  9. * it can be passed in as a string (e.g.: "1 == 1" or "$('#bar').is(':visible')" or
  10. * as a callback function.
  11. * @param timeOutMillis the max amount of time to wait. If not specified, 3 sec is used.
  12. */
  13. function waitFor(testFx, onReady, timeOutMillis) {
  14. var maxtimeOutMillis = timeOutMillis ? timeOutMillis : 3001, //< Default Max Timout is 3s
  15. start = new Date().getTime(),
  16. condition = false,
  17. interval = setInterval(function() {
  18. if ( (new Date().getTime() - start < maxtimeOutMillis) && !condition ) {
  19. // If not time-out yet and condition not yet fulfilled
  20. condition = (typeof(testFx) === "string" ? eval(testFx) : testFx()); //< defensive code
  21. } else {
  22. if(!condition) {
  23. // If condition still not fulfilled (timeout but condition is 'false')
  24. console.log("'waitFor()' timeout");
  25. phantom.exit(1);
  26. } else {
  27. // Condition fulfilled (timeout and/or condition is 'true')
  28. typeof(onReady) === "string" ? eval(onReady) : onReady(); //< Do what it's supposed to do once the condition is fulfilled
  29. clearInterval(interval); //< Stop this interval
  30. }
  31. }
  32. }, 100); //< repeat check every 250ms
  33. };
  34. if (phantom.args.length === 0 || phantom.args.length > 2) {
  35. console.log('Usage: run-qunit.js URL');
  36. phantom.exit();
  37. }
  38. var page = new WebPage();
  39. // Route "console.log()" calls from within the Page context to the main Phantom context (i.e. current "this")
  40. page.onConsoleMessage = function(msg) {
  41. console.log(msg);
  42. };
  43. page.open(phantom.args[0], function(status){
  44. if (status !== "success") {
  45. console.log("Unable to access network");
  46. phantom.exit();
  47. } else {
  48. waitFor(function(){
  49. return page.evaluate(function(){
  50. var el = document.getElementById('qunit-testresult');
  51. if (el && el.innerText.match('completed')) {
  52. return true;
  53. }
  54. return false;
  55. });
  56. }, function(){
  57. var failedNum = page.evaluate(function(){
  58. var el = document.getElementById('qunit-testresult');
  59. try {
  60. return el.getElementsByClassName('failed')[0].innerHTML;
  61. } catch (e) { }
  62. return 10000;
  63. });
  64. phantom.exit((parseInt(failedNum, 10) > 0) ? 1 : 0);
  65. });
  66. }
  67. });