Search code examples
jquerymockingqunitsinon

Issue Mocking Function Invoked by Event with QUnit and Sinon


My goal is to mock the runProcedure function and check that it was called after the user clicks. However, the test continues to fail even though it can clearly be seen that the runProcedure function is called once the user clicks the page and if the miniWindowShowing variable is false, which it is when the page loads. Can anyone explain how to use QUnit with sinon to accomplish this goal? Below is the code I am working with.

QUnit HTML Page

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
  <title>Function Testing</title>
  <link rel="stylesheet" href="http://code.jquery.com/qunit/qunit-1.12.0.css">
</head>
<body>
  <div id="qunit"></div>
  <div id="qunit-fixture"></div>
  <script src="http://code.jquery.com/qunit/qunit-1.12.0.js"></script>
  <script src="http://code.jquery.com/jquery-1.7.2.min.js"></script>
  <script src="http://code.jquery.com/ui/1.10.1/jquery-ui.js"></script>
  <script type="text/javascript" src="http://sinonjs.org/releases/sinon-1.7.3.js"></script>
  <script type="text/javascript" src="http://sinonjs.org/releases/sinon-qunit-0.8.0.js"></script>

  <script type="text/javascript" src="Function Source.js"></script>
  <script type="text/javascript" src="TestSuite.js"></script>
  <script>
    test( "Test Click Calls Function", testClickCallsFunction);
  </script>
</body>
</html>

JavaScript Test File

// Test that when user clicks on the page, a function is called
function testClickCallsFunction(){

    var event = $.Event("click");   
    var funcSpy = sinon.spy(runProcedure);
    $(document).trigger(event);

    ok(funcSpy.called);
}

JavaScript Functions to Test

var miniWindowShowing = false;

$(document).ready(function () {

    $(this).click(function (e) {
        //Ignore input events if the mini window is showing
        if(!miniWindowShowing)
        {
            runProcedure();         
        }
    });

})

function runProcedure() {

}

Solution

  • There is a minor issue with your way creating the spy. sinon.spy(runProcedure) creates a new spy with the passed function, but it don't replace the original function with that spy. So when you call runProcedure its still the original function. To overwrite the function with the spy you have to use this syntax: sinon.spy(window, 'runProcedure'), which will replace the function runProcedure in the global namespace with the spy.