How to test a function which has a setTimeout with jasmine?

后端 未结 4 1555
失恋的感觉
失恋的感觉 2020-12-02 22:00

I need to write a test for a function that has a setTimeout() call inside, but i can\'t find how i should do.

This is the function

// Di         


        
4条回答
  •  有刺的猬
    2020-12-02 22:49

    I've never done any testing with jasmine, but I think I understand your problem. I would restructure the code a little to allow for you to wrap the function being called in a proxy function like this:

    Modify your code that is being test to extract the setTimeout code into another function:

    Original Code:

    // Disables all submit buttons after a submit button is pressed. 
    var block_all_submit_and_ajax = function( el ) { 
        // Clone the clicked button, we need to know what button has been clicked so that we can react accordingly 
        var $clone = $( el ).clone(); 
        // Change the type to hidden 
        $clone.attr( 'type', 'hidden' ); 
        // Put the hidden button in the DOM 
        $( el ).after( $clone ); 
        // Disable all submit button. I use setTimeout otherwise this doesn't work in chrome. 
        setTimeout(function() { 
            $( '#facebook input[type=submit]' ).prop( 'disabled', true ); 
        }, 10); 
        // unbind all click handler from ajax 
        $( '#facebook a.btn' ).unbind( "click" ); 
        // Disable all AJAX buttons. 
        $( '#facebook a.btn' ).click( function( e ) { 
            e.preventDefault(); 
            e.stopImmediatePropagation(); 
        } ); 
    };
    

    Modified Code:

    // Disables all submit buttons after a submit button is pressed. 
    var block_all_submit_and_ajax = function( el ) { 
        // Clone the clicked button, we need to know what button has been clicked so that we can react accordingly 
        var $clone = $( el ).clone(); 
        // Change the type to hidden 
        $clone.attr( 'type', 'hidden' ); 
        // Put the hidden button in the DOM 
        $( el ).after( $clone ); 
        // Disable all submit button. I use setTimeout otherwise this doesn't work in chrome. 
        setTimeout(disableSubmitButtons, 10); 
        // unbind all click handler from ajax 
        $( '#facebook a.btn' ).unbind( "click" ); 
        // Disable all AJAX buttons. 
        $( '#facebook a.btn' ).click( function( e ) { 
            e.preventDefault(); 
            e.stopImmediatePropagation(); 
        } ); 
    };
    
    var utilityFunctions =
    {
      disableSubmitButtons : function()
      {
        $( '#facebook input[type=submit]' ).prop( 'disabled', true ); 
    
      }
    }
    

    Next I would modify the testing code like this:

    it( "Disable all submit buttons", function() { 
        // Get a button 
        var $button = $( '#ai1ec_subscribe_users' ); 
    
        var originalFunction = utilityFunctions.disableSubmitButtons;
        utilityFunctions.disableSubmitButtons = function()
        {
            // call the original code, and follow it up with the test
            originalFunction();
    
            // check that all submit are disabled 
            $( '#facebook input[type=submit]' ).each( function( i, el ) { 
                console.log( 'f' ); 
                expect( el ).toHaveProp( 'disabled', true ); 
            }); 
    
            // set things back the way they were
            utilityFunctions.disableSubmitButtons = originalFunction;
        }
    
        // Call the function 
        utility_functions.block_all_submit_and_ajax( $button.get(0) ); 
    }); 
    

提交回复
热议问题