Как проводить модульное тестирование кода Javascript, взаимодействующего с элементами DOM

Предыстория:

Я пришел из Java, поэтому не слишком знаком с Javascript.

Мы планируем внедрить модульное тестирование JavaScript как в наш существующий (устаревший) код, так и в будущую работу. В основном мы являемся магазином Java (Spring, Weblogic и т. д.).

Мы рассматриваем варианты, обеспечивающие хорошую интеграцию с IDE (идея IntelliJ) и сонар, а также возможность запускать их как часть непрерывной интеграции.

JsTestDriver, похоже, отвечает всем требованиям.

Вопрос:

Большая часть нашего существующего кода javascript а) встроена в JSP и б) использует jQuery для непосредственного взаимодействия с элементами страницы.

Как нам протестировать функцию, которая сильно зависит от модели DOM.Вот несколько примеров кода функций, о которых я говорю:

function enableOccupationDetailsText (){
    $( "#fldOccupation" ).val("Unknown");
    $( "#fldOccupation_Details" ).attr("disabled", "");
    $( "#fldOccupation_Details" ).val("");
    $( "#fldOccupation_Details" ).focus();
}

или

jQuery(document).ready(function(){

    var oTable = $('#policies').dataTable( {
            "sDom" : 'frplitip',
                "bProcessing": true,
                "bServerSide": true,
                "sAjaxSource": "xxxx.do",
                "sPaginationType": "full_numbers",
                "aaSorting": [[ 1, "asc" ]],
                "oLanguage": {
                    "sProcessing":   "Processing...",
                    "sLengthMenu":   "Show _MENU_ policies",
                    "sZeroRecords":  "No matching policies found",
                    "sInfo":         "Showing _START_ to _END_ of _TOTAL_ policies",
                    "sInfoEmpty":    "Showing 0 to 0 of 0 policies",
                    "sInfoFiltered": "(filtered from _MAX_ total policies)",
                    "sInfoPostFix":  "",
                    "sSearch":       "Search:",
                    "sUrl":          "",
                    "oPaginate": {
                        "sFirst":    "First",
                        "sPrevious": "Previous",
                        "sNext":     "Next",
                        "sLast":     "Last"
                }
            },
                "fnRowCallback": function( nRow, aData, iDisplayIndex, iDisplayIndexFull ) {
                        $('td:eq(0)', nRow).html( "<a href='/ole/policy/general_details.do?policy_id="+aData[0]+"'>"+aData[0]+"</a>" );
                        return nRow;

                },

                "fnServerData" : function ( url, data, callback, settings ) {

                settings.jqXHR = $.ajax( {
                    "url": url,
                    "data": data,
                    "success": function (json) {
                        if (json.errorMessage != null) {
                            var an = settings.aanFeatures.r;
                            an[0].style.fontSize="18px";
                            an[0].style.backgroundColor="red";
                            an[0].style.height="70px";
                            an[0].innerHTML=json.errorMessage;
                            setTimeout('window.location="/xxxx"',1000);
                            //window.location="/xxxxx";
                        } else {
                            $(settings.oInstance).trigger('xhr', settings);
                            callback( json );
                        }
                    },
                    "dataType": "json",
                    "cache": false,
                    "error": function (xhr, error, thrown) {
                        if ( error == "parsererror" ) {
                            alert( "Unexpected error, please contact system administrator. Press OK to be redirected to home page." );
                            window.location="/xxxx";
                        }
                    }
                } );
                }

            } );
        $("#policies_filter :text").attr('id', 'fldKeywordSearch');
        $("#policies_length :input").attr('id', 'fldNumberOfRows');
        $("body").find("span > span").css("border","3px solid red");
        oTable.fnSetFilteringDelay(500);
        oTable.fnSearchHighlighting();
        $("#fldKeywordSearch").focus();

}
);

. В последнем случае мой подход заключается в том, что рассматриваемая функция слишком велика и должна быть разбита на более мелкие (единицы), чтобы она можно протестировать. Но все точки взаимодействия с DOM, jQuery, таблицами данных, ajax и т. д. усложняют рефакторинг вещей так, как мы это делаем в мире Java, чтобы сделать его более тестируемым.

Итак, мы будем очень признательны за любые предложения по приведенным выше примерам!

5
задан Ashkan Aryan 18 June 2012 в 11:21
поделиться