• Share
  • Email
  • Embed
  • Like
  • Save
  • Private Content
Js 单元测试框架介绍
 

Js 单元测试框架介绍

on

  • 1,100 views

 

Statistics

Views

Total Views
1,100
Views on SlideShare
1,050
Embed Views
50

Actions

Likes
2
Downloads
4
Comments
0

2 Embeds 50

http://yafeilee.sinaapp.com 49
http://cache.baidu.com 1

Accessibility

Upload Details

Uploaded via as Adobe PDF

Usage Rights

© All Rights Reserved

Report content

Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
  • Full Name Full Name Comment goes here.
    Are you sure you want to
    Your message goes here
    Processing…
Post Comment
Edit your comment

    Js 单元测试框架介绍 Js 单元测试框架介绍 Presentation Transcript

    • 李亚飞 louie/185421
    • 1.Qunit2.Jasmine3.YUITest
    • Jörn Zaefferer : QUnit是一个JavaScript单元测试框架,主要用于在浏览器中运行单元测试。虽然这个项目从属于jQuery,但却不依赖于jQuery,也不依赖于浏览器DOM。因此你也可以在node.js或Rhino上使用。QUnit很容易学习,你只需在html页面中包含两个文件,不需要安装或者构建任何其他东西。最短的测试集只需要一个11行的html文件。特点:1.使用方便,界面美观2.支持异步3.手工加载4.对html文件有约束4.适合开发调试阶段使用
    • Davis Frank: Jasmine是一个 JavaScript测试框架,目的是将BDD风格引入JavaScript测试之中。至于区别嘛,我们的目标是BDD(相比标准的TDD),因此我们尽力帮助开发人员编写比一般xUnit框架表达性更强,组织更好的代码。此外我们还力图减少依赖,这样你可以在node.js上使用Jasmine,也可以在浏览器或移动程序中使用。特点:1.语法简洁,describe ,it2.Browsers,servers,phones,etc3.支持自定义Matchers4.beforeEach()、afterEach()、Single-spec After functions5.spies,mock6.异步,runs(),waits(),waitsFor()
    • YUI Test features:Rapid creation of test cases through simple syntax.Advanced failure detection for methods that throw errors.Grouping of related test cases using test suites.Mock objects for writing tests without external dependencies.Asynchronous tests for testing events and Ajax communication.DOM Event simulation in all A-grade browsers (through Event).
    • 引入测试框架 YUITest Standalone Library <script src="http://192.168.194.159/test/yuitest/yuitest.js"></script> YUI Test for YUI 3.x <script src="http://192.168.194.159/test/yui/build/yui/yui.js"></script> // Create a new YUI instance and populate it with the required modules. YUI().use(test, function (Y) { // Test is available and ready for use. Add implementation // code here. });
    • Using Test CasesYUITest Standalone Libraryvar testCase = new YUITest.TestCase({ name: "TestCase Name", //traditional test names testSomething : function () { //... }, testSomethingElse : function () { //... }});var testCase = new YUITest.TestCase({ name: "TestCase Name", //friendly test names "Something should happen here" : function () { //... }, "Something else should happen here" : function () { //... }});
    • Using Test CasesYUI Test for YUI 3.xvar testCase = new Y.Test.Case({ name: "TestCase Name", //traditional test names testSomething : function () { //... }, testSomethingElse : function () { //... }});var testCase = new Y.Test.Case({ name: "TestCase Name", //friendly test names "Something should happen here" : function () { //... }, "Something else should happen here" : function () { //... }});
    • setUp() and tearDown() var testCase = new YUITest.TestCase({ name: "TestCase Name", //--------------------------------------------- // Setup and tear down //--------------------------------------------- setUp : function () { this.data = { name : "Nicholas", age : 28 }; }, tearDown : function () { delete this.data; }, //--------------------------------------------- // Tests //--------------------------------------------- testName: function () { YUITest.Assert.areEqual("Nicholas", this.data.name, "Name should be Nicholas"); }, testAge: function () { YUITest.Assert.areEqual(28, this.data.age, "Age should be 28"); } });
    • init() and destroy() var testCase = new YUITest.TestCase({ name: "TestCase Name", //--------------------------------------------- // init and destroy //--------------------------------------------- init : function () { this.data = { name : "Nicholas", age : 28 }; }, destroy : function () { delete this.data; }, //--------------------------------------------- // Tests //--------------------------------------------- testName: function () { YUITest.Assert.areEqual("Nicholas", this.data.name, "Name should be Nicholas"); }, testAge: function () { YUITest.Assert.areEqual(28, this.data.age, "Age should be 28"); } });
    • Ignoring Tests var testCase = new YUITest.TestCase({ name: "TestCase Name", //--------------------------------------------- // Special instructions //--------------------------------------------- _should: { ignore: { testName: true //ignore this test } }, //--------------------------------------------- // Tests //--------------------------------------------- testName: function () { YUITest.Assert.areEqual("Nicholas", this.data.name, "Name should be Nicholas"); }, testAge: function () { YUITest.Assert.areEqual(28, this.data.age, "Age should be 28"); } });
    • Intentional Errors testGenericError : function() { YUITest.Assert.throwsError(Error, function() { throw new Error("Generic error"); }); }, testStringError : function() { YUITest.Assert.throwsError("Im a specific error message.", function() { throw new Error("Im a specific error message."); }); }, testObjectError : function() { YUITest.Assert.throwsError(new TypeError("Number expected."), function() { throw new TypeError("Number expected."); }); },
    • Assertions Equality Assertions Sameness Assertions Forced Failures areEqual() areNotSame() fail() areNotEqual() areSame() Special Value Assertions Data Type Assertions isFalse() isArray() isTrue() isBoolean() isNaN() isFunction() isNotNaN() isNumber() isNull() isObject() isNotNull() isString() isUndefined() isTypeOf() isNotUndefined()
    • ArrayAssert contains() containsItems() containsMatch() doesNotContain() doesNotContainItems() doesNotContainMatch() indexOf() isEmpty() isNotEmpty() itemsAreEqual() itemsAreEquivalent() itemsAreSame() lastIndexOf()
    • DateAssert datesAreEqual() timesAreEqual()
    • ObjectAssert hasKey() hasKeys() ownsKey() ownsKeys() ownsNoKeys() areEqual() inheritsKey() inheritsKeys() ownsOrInheritsKey() ownsOrInheritsKeys()
    • Mock Objects//code being testedfunction logToServer(message, xhr){ xhr.open("get", "/log.php?msg=" + encodeURIComponent(message), true); xhr.send(null);}//test case for testing the above functionvar testCase = new YUITest.TestCase({ name: "logToServer Tests", testPassingDataToXhr : function () { var mockXhr = YUITest.Mock(); //I expect the open() method to be called with the given arguments YUITest.Mock.expect(mockXhr, { method: "open", args: ["get", "/log.php?msg=hi", true] }); //I expect the send() method to be called with the given arguments YUITest.Mock.expect(mockXhr, { method: "send", args: [null] }); //now call the function logToServer("hi", mockXhr); //verify the expectations were met YUITest.Mock.verify(mockXhr); }});
    • Special Argument ValuesYUITest.Mock.Value.Any - any value is valid regardless of type.YUITest.Mock.Value.String - any string value is valid.YUITest.Mock.Value.Number - any number value is valid.YUITest.Mock.Value.Boolean - any Boolean value is valid.YUITest.Mock.Value.Object - any non-null object value is valid.YUITest.Mock.Value.Function - any function value is valid.YUITest.Mock.expect(mockXhr, { method: "open", args: [YUITest.Mock.Value.String, "/log.php?msg=hi“, YUITest.Mock.Value.Boolean]});
    • Property Expectationsvar testCase = new YUITest.TestCase({ name : "TestCase Name", testMock : function() { var mockMyObject = YUITest.Mock(); YUITest.Mock.expect(mockMyObject,{ method: "add", args: [1,2], returns: 3, property: "status", value: 404 }); var result = mockMyObject.add(1,2); mockMyObject.status = 100; Assert.areEqual(3,result,"1 + 2 = 3"); YUITest.Mock.verify(mockMyObject); }});
    • Asynchronous Testsvar testCase = new YUITest.TestCase({ name: "TestCase Name", setUp : function () { this.data = { name : "Nicholas", age : 29 }; }, tearDown : function () { delete this.data; }, testAsync: function () { YUITest.Assert.areEqual("Nicholas", this.data.name, "Name should be Nicholas"); //wait 1000 milliseconds and then run this function this.wait(function(){ YUITest.Assert.areEqual(29, this.data.age, "Age should be 29"); }, 1000); }});
    • Asynchronous Testsvar testCase = new YUITest.TestCase({ name: "TestCase Name", testAnimation : function (){ //animate width to 400px var myAnim = new Y.Anim({ node: #testDiv, to: {width: 400}, duration: 3}); var test = this; //assign oncomplete handler myAnim.on("end", function(){ //tell the TestRunner to resume test.resume(function(){ YUITest.Assert.areEqual(myAnim.get("node").get("offsetWidth"), 400, "Width of theDIV should be 400."); }); }); //start the animation myAnim.run(); //wait until something happens this.wait(3000); }});
    • Test Suites//create the test suitevar suite = new YUITest.TestSuite("TestSuite Name");//add test casessuite.add(new YUITest.TestCase({ //...}));suite.add(new YUITest.TestCase({ //...}));//add the second suite to the firstsuite.add(anotherSuite);//create a test suitevar suite = new YUITest.TestSuite({ name : "TestSuite Name", setUp : function () { //test-suite-level setup }, tearDown: function () { //test-suite-level teardown }});
    • Context Datavar testSuite = new YUITest.TestSuite({ name: "Test Suite Name", setUp: function(data){ data.topLevel = 1;}});testSuite.add(new YUITest.TestCase({ name: "First Test Case", init: function(data){ data.foo = "bar";}, testValueOfFoo : function (data) { YUITest.Assert.areEqual("bar", data.foo); //from init }, testValueOfTopLevel: function(data){ YUITest.Assert.areEqual(1, data.topLevel); //from test suite }});testSuite.add(new YUITest.TestCase({ name: "Second Test Case", testValueOfFoo : function (data) { YUITest.Assert.areEqual("bar", data.foo); //from init in First Test Case }, testValueOfTopLevel: function(data){ YUITest.Assert.areEqual(1, data.topLevel); //from test suite }});
    • Running Tests//add the test cases and suitesYUITest.TestRunner.add(testCase);YUITest.TestRunner.add(testSuite);//run all testsYUITest.TestRunner.run();YUITest.TestRunner.clear();
    • TestRunner EventsTest-Level EventsYUITest.TestRunner.TEST_PASS_EVENT - occurs when the test passes.YUITest.TestRunner.TEST_FAIL_EVENT - occurs when the test fails.YUITest.TestRunner.TEST_IGNORE_EVENT - occurs when a test is ignored.For each of these events, the event data object has three properties:type - indicates the type of event that occurred.testCase - the test case that is currently being run.testName - the name of the test that was just executed or ignored.
    • TestRunner EventsTestCase-Level EventsYUITest.TestRunner.TEST_CASE_BEGIN_EVENToccurs when the test case is next to be executed but before the first testis run.YUITest.TestRunner.TEST_CASE_COMPLETE_EVENToccurs when all tests in the test case have been executed or ignored.For these two events, the event data object has three properties:type - indicates the type of event that occurred.testCase - the test case that is currently being run.
    • TestRunner EventsTestSuite-Level EventsYUITest.TestRunner.TEST_SUITE_BEGIN_EVENToccurs when the test suite is next to be executed but before the firsttest is run.YUITest.TestRunner.TEST_SUITE_COMPLETE_EVENToccurs when all tests in all test cases in the test suite have beenexecuted or ignored.For these two events, the event data object has three properties:type - indicates the type of event that occurred.testSuite - the test suite that is currently being run.
    • TestRunner EventsTestRunner-Level EventsYUITest.TestRunner.BEGIN_EVENToccurs when testing is about to begin but before any tests are run.YUITest.TestRunner.COMPLETE_EVENToccurs when all tests in all test cases and test suites have been executed or ignored.Subscribing to Eventsfunction handleTestFail(data){ alert("Test named " + data.testName + " failed with message: " +data.error.message + ".");}var TestRunner = YUITest.TestRunner;TestRunner.subscribe(TestRunner.TEST_FAIL_EVENT, handleTestFail);TestRunner.run();
    • Viewing ResultsYUI({ logInclude: { TestRunner: true } }).use("console", function(Y){ //tests go here //initialize the console var yconsole = new Y.Console({ newestOnTop: false }); yconsole.render(#log); //run the tests YUITest.TestRunner.run();});
    • Viewing ResultsYUI({ useBrowserConsole: true }).use("test", function(Y){ //tests go here Y.Test.Runner.run();});
    • Viewing ResultsYUI({ useBrowserConsole: true }).use("test", function(Y){ //tests go here //get object of results var resultsObject = YUITest.TestRunner.getResult(); //get XML results var resultsXML = YUITest.TestRunner.getResult(YUITest.TestFormat.XML);});YUITest.TestFormat.XML - YUI Test XML (default)YUITest.TestFormat.JSON - JSONYUITest.TestFormat.JUnitXML - JUnit XMLYUITest.TestFormat.TAP - TAP
    • Code Coverage DataYUITest.TestRunner.getCoverage()YUITest.CoverageFormat.JSON - JSONYUITest.CoverageFormat.XdebugJSON - JSON formatted Xdebug
    • Test Reportingvar reporter = newYUITest.Reporter("http://www.yourserver.com/path/to/target",YUITest.TestFormat.JSON);reporter.report(results);results - the serialized results object.useragent - the user-agent string of the browser.timestamp - the date and time that the report was sent.reporter.addField("color", "blue");reporter.addField("message", "Hello world!");
    • Yeti: YUI’s Easy Testing InterfaceYeti is a command-line tool for launching JavaScript unit tests in abrowser and reporting the results without leaving your terminal. Yeti isdesigned to work with existing unmodified YUI-based tests.Yeti is designed to help you run tests before you commit. Itcompliments existing CI tools like Selenium and Hudson which run testspost-commit. Yeti is not a replacement for those tools.
    • More Infohttp://docs.jquery.com/Qunithttp://pivotal.github.com/jasmine/http://developer.yahoo.com/yui/http://yuilibrary.com/projects/yuitesthttp://yuilibrary.com/yui/docs/test/http://yuilibrary.com/theater/http://yuilibrary.com/projects/yeti/http://192.168.194.159/test/slide/yeti.html