logo资料库

XUNIT测试模式-测试码重构.pdf

第1页 / 共948页
第2页 / 共948页
第3页 / 共948页
第4页 / 共948页
第5页 / 共948页
第6页 / 共948页
第7页 / 共948页
第8页 / 共948页
资料共948页,剩余部分请下载后查看
XUnit test patterns : refactoring test code
Contents
Visual Summary of the Pattern Language
Foreword
Preface
Acknowledgments
Introduction
Refactoring a Test
PART I. The Narratives
Chapter 1. A Brief Tour
About This Chapter
The Simplest Test Automation Strategy That Could Possibly Work
What’s Next?
Chapter 2. Test Smells
About This Chapter
An Introduction to Test Smells
A Catalog of Smells
What’s Next?
Chapter 3. Goals of Test Automation
About This Chapter
Why Test?
Goals of Test Automation
What’s Next?
Chapter 4. Philosophy of Test Automation
About This Chapter
Why Is Philosophy Important?
Some Philosophical Differences
When Philosophies Differ
My Philosophy
What’s Next?
Chapter 5. Principles of Test Automation
About This Chapter
The Principles
What’s Next?
Chapter 6. Test Automation Strategy
About This Chapter
What’s Strategic?
Which Kinds of Tests Should We Automate?
Which Tools Do We Use to Automate Which Tests?
Which Test Fixture Strategy Do We Use?
How Do We Ensure Testability?
What’s Next?
Chapter 7. xUnit Basics
About This Chapter
An Introduction to xUnit
Common Features
The Bare Minimum
Under the xUnit Covers
xUnit in the Procedural World
What’s Next?
Chapter 8. Transient Fixture Management
About This Chapter
Test Fixture Terminology
Building Fresh Fixtures
Tearing Down Transient Fresh Fixtures
What’s Next?
Chapter 9. Persistent Fixture Management
About This Chapter
Managing Persistent Fresh Fixtures
Managing Shared Fixtures
What’s Next?
Chapter 10. Result Verification
About This Chapter
Making Tests Self-Checking
State Verification
Verifying Behavior
Reducing Test Code Duplication
Avoiding Conditional Test Logic
Other Techniques
Where to Put Reusable Verification Logic?
What’s Next?
Chapter 11. Using Test Doubles
About This Chapter
What Are Indirect Inputs and Outputs?
Testing with Doubles
Other Uses of Test Doubles
Other Considerations
What’s Next?
Chapter 12. Organizing Our Tests
About This Chapter
Basic xUnit Mechanisms
Right-Sizing Test Methods
Test Methods and Testcase Classes
Test Naming Conventions
Organizing Test Suites
Test Code Reuse
Test File Organization
What’s Next?
Chapter 13. Testing with Databases
About This Chapter
Testing with Databases
Testing without Databases
Testing the Database
Testing with Databases (Again!)
What’s Next?
Chapter 14. A Roadmap to Effective Test Automation
About This Chapter
Test Automation Difficulty
Roadmap to Highly Maintainable Automated Tests
What’s Next?
PART II. The Test Smells
Chapter 15. Code Smells
Obscure Test
Conditional Test Logic
Hard-to-Test Code
Test Code Duplication
Test Logic in Production
Chapter 16. Behavior Smells
Assertion Roulette
Erratic Test
Fragile Test
Frequent Debugging
Manual Intervention
Slow Tests
Chapter 17. Project Smells
Buggy Tests
Developers Not Writing Tests
High Test Maintenance Cost
Production Bugs
PART III. The Patterns
Chapter 18. Test Strategy Patterns
Recorded Test
Scripted Test
Data-Driven Test
Test Automation Framework
Minimal Fixture
Standard Fixture
Fresh Fixture
Shared Fixture
Back Door Manipulation
Layer Test
Chapter 19. xUnit Basics Patterns
Test Method
Four-Phase Test
Assertion Method
Assertion Message
Testcase Class
Test Runner
Testcase Object
Test Suite Object
Test Discovery
Test Enumeration
Test Selection
Chapter 20. Fixture Setup Patterns
In-line Setup
Delegated Setup
Creation Method
Implicit Setup
Prebuilt Fixture
Lazy Setup
Suite Fixture Setup
Setup Decorator
Chained Tests
Chapter 21. Result Verification Patterns
State Verification
Behavior Verification
Custom Assertion
Delta Assertion
Guard Assertion
Unfinished Test Assertion
Chapter 22. Fixture Teardown Patterns
Garbage-Collected Teardown
Automated Teardown
In-line Teardown
Implicit Teardown
Chapter 23. Test Double Patterns
Test Double
Test Stub
Test Spy
Mock Object
Fake Object
Configurable Test Double
Hard-Coded Test Double
Test-Specific Subclass
Chapter 24. Test Organization Patterns
Named Test Suite
Test Utility Method
Parameterized Test
Testcase Class per Class
Testcase Class per Feature
Testcase Class per Fixture
Testcase Superclass
Test Helper
Chapter 25. Database Patterns
Database Sandbox
Stored Procedure Test
Table Truncation Teardown
Transaction Rollback Teardown
Chapter 26. Design-for-Testability Patterns
Dependency Injection
Dependency Lookup
Humble Object
Test Hook
Chapter 27. Value Patterns
Literal Value
Derived Value
Generated Value
Dummy Object
PART IV. Appendixes
Appendix A. Test Refactorings
Appendix B. xUnit Terminology
Appendix C. xUnit Family Members
Appendix D. Tools
Appendix E. Goals and Principles
Appendix F. Smells, Aliases, and Causes
Appendix G. Patterns, Aliases, and Variations
Glossary
A
B
C
D
E
F
G
H
I
L
M
N
O
P
R
S
T
U
V
References
Index
A
B
C
D
E
F
G
H
I
J
K
L
M
N
O
P
Q
R
S
T
U
V
W
X
List of Patterns Assertion Message (370): We include a descriptive string argument in each call to an Assertion Method. Assertion Method (362): We call a utility method to evaluate whether an expected outcome has been achieved. Automated Teardown (503): We keep track of all resources that are created in a test and automatically destroy/free them during teardown. Back Door Manipulation (327): We set up the test fi xture or verify the outcome by going through a back door (such as direct database access). Behavior Verifi cation (468): We capture the indirect outputs of the system under test (SUT) as they occur and compare them to the expected behavior. Chained Tests (454): We let the other tests in a test suite set up the test fi xture. Confi gurable Test Double (558): We confi gure a reusable Test Double with the values to be returned or verifi ed during the fi xture setup phase of a test. Creation Method (415): We set up the test fi xture by calling methods that hide the mechanics of building ready-to-use objects behind Intent-Revealing Names. Custom Assertion (474): We create a purpose-built Assertion Method that compares only those attributes of the object that defi ne test-specifi c equality. Data-Driven Test (288): We store all the information needed for each test in a data fi le and write an interpreter that reads the fi le and executes the tests. Database Sandbox (650): We provide a separate test database for each developer or tester. Delegated Setup (411): Each test creates its own Fresh Fixture by calling Creation Methods from within the Test Methods. Delta Assertion (485): We specify assertions based on differences between the pre- and post-exercise state of the SUT. Dependency Injection (678): The client provides the depended-on object to the SUT. Dependency Lookup (686): The SUT asks another object to return the depended-on object before it uses it. Derived Value (718): We use expressions to calculate values that can be derived from other values. Dummy Object (728): We pass an object that has no implementation as an argument of a method called on the SUT. Fake Object (551): We replace a component that the SUT depends on with a much lighter-weight implementation. Four-Phase Test (358): We structure each test with four distinct parts executed in sequence. Fresh Fixture (311): Each test constructs its own brand-new test fi xture for its own private use. Garbage-Collected Teardown (500): We let the garbage collection mechanism provided by the programming language clean up after our test. Generated Value (723): We generate a suitable value each time the test is run. Guard Assertion (490): We replace an if statement in a test with an assertion that fails the test if not satisfi ed. Hard-Coded Test Double (568): We build the Test Double by hard-coding the return values and/or expected calls. Humble Object (695): We extract the logic into a separate, easy-to-test component that is decoupled from its environment. Implicit Setup (424): We build the test fi xture common to several tests in the setUp method. Implicit Teardown (516): The Test Automation Framework calls our clean up logic in the tearDown method after every Test Method. In-line Setup (408): Each Test Method creates its own Fresh Fixture by calling the appropriate constructor methods to build exactly the test fi xture it requires. In-line Teardown (509): We include teardown logic at the end of the Test Method immediately after the result verifi cation. Layer Test (337): We can write separate tests for each layer of the layered architecture. Lazy Setup (435): We use Lazy Initialization of the fi xture to create it in the fi rst test that needs it. Literal Value (714): We use literal constants for object attributes and assertions. Minimal Fixture (302): We use the smallest and simplest fi xture possible for each test. Mock Object (544): We replace an object the SUT depends on with a test-specifi c object that verifi es it is being used correctly by the SUT.
Named Test Suite (592): We defi ne a test suite, suitably named, that contains a set of tests that we wish to be able to run as a group. Parameterized Test (607): We pass the information needed to do fi xture setup and result verifi cation to a utility method that implements the entire test life cycle. Prebuilt Fixture (429): We build the Shared Fixture separately from running the tests. Recorded Test (278): We automate tests by recording interactions with the application and playing them back using a test tool. Scripted Test (285): We automate the tests by writing test programs by hand. Setup Decorator (447): We wrap the test suite with a Decorator that sets up the shared test fi xture before running the tests and tears it down after all the tests are done. Shared Fixture (317): We reuse the same instance of the test fi xture across many tests. Standard Fixture (305): We reuse the same design of the test fi xture across many tests. State Verifi cation (462): We inspect the state of the SUT after it has been exercised and compare it to the expected state. Stored Procedure Test (654): We write Fully Automated Tests for each stored procedure. Suite Fixture Setup (441): We build/destroy the shared fi xture in special methods called by the Test Automation Framework before/after the fi rst/last Test Method is called. Table Truncation Teardown (661): We truncate the tables modifi ed during the test to tear down the fi xture. Test Automation Framework (298): We use a framework that provides all the mechanisms needed to run the test logic so the test writer needs to provide only the test-specifi c logic. Test Discovery (393): The Test Automation Framework discovers all the tests that belong to the test suite automatically. Test Double (522): We replace a component on which the SUT depends with a “test-specifi c equivalent.” Test Enumeration (399): The test automater manually writes the code that enumerates all tests that belong to the test suite. Test Helper (643): We defi ne a helper class to hold any Test Utility Methods we want to reuse in several tests. Test Hook (709): We modify the SUT to behave differently during the test. Test Method (348): We encode each test as a single Test Method on some class. Test Runner (377): We defi ne an application that instantiates a Test Suite Object and executes all the Testcase Objects it contains. Test Selection (403): The Test Automation Framework selects the Test Methods to be run at runtime based on attributes of the tests. Test Spy (538): We use a Test Double to capture the indirect output calls made to another component by the SUT for later verifi cation by the test. Test Stub (529): We replace a real object with a test-specifi c object that feeds the desired indirect inputs into the SUT. Test Suite Object (387): We defi ne a collection class that implements the standard test interface and use it to run a set of related Testcase Objects. Test Utility Method (599): We encapsulate the test logic we want to reuse behind a suitably named utility method. Test-Specifi c Subclass (579): We add methods that expose the state or behavior needed by the test to a subclass of the SUT. Testcase Class (373): We group a set of related Test Methods on a single Testcase Class. Testcase Class per Class (617): We put all the Test Methods for one SUT class onto a single Testcase Class. Testcase Class per Feature (624): We group the Test Methods onto Testcase Classes based on which testable feature of the SUT they exercise. Testcase Class per Fixture (631): We organize Test Methods into Testcase Classes based on commonality of the test fi xture. Testcase Object (382): We create a Command object for each test and call the run method when we wish to execute it. Testcase Superclass (638): We inherit reusable test-specifi c logic from an abstract Testcase Superclass. Transaction Rollback Teardown (668): We roll back the uncommitted test transaction as part of the teardown. Unfi nished Test Assertion (494): We ensure that incomplete tests fail by executing an assertion that is guaranteed to fail.
xUnit Test Patterns
xUnit Test Patterns Refactoring Test Code Gerard Meszaros Upper Saddle River, NJ • Boston • Indianapolis • San Francisco New York • Toronto • Montreal • London • Munich • Paris • Madrid Capetown • Sydney • Tokyo • Singapore • Mexico City
Many of the designations used by manufacturers and sellers to distinguish their products are claimed as trade- marks. Where those designations appear in this book, and the publisher was aware of a trademark claim, the designations have been printed with initial capital letters or in all capitals. The author and publisher have taken care in the preparation of this book, but make no expressed or implied war- ranty of any kind and assume no responsibility for errors or omissions. No liability is assumed for incidental or con- sequential damages in connection with or arising out of the use of the information or programs contained herein. The publisher offers excellent discounts on this book when ordered in quantity for bulk purchases or special sales, which may include electronic versions and/or custom covers and content particular to your business, training goals, marketing focus, and branding interests. For more information, please contact: U.S. Corporate and Government Sales (800) 382-3419 corpsales@pearsontechgroup.com For sales outside the United States please contact: International Sales international@pearsoned.com Library of Congress Cataloging-in-Publication Data Meszaros, Gerard. XUnit test patterns : refactoring test code / Gerard Meszaros. p. cm. Includes bibliographical references and index. ISBN-13: 978-0-13-149505-0 (hardback : alk. paper) ISBN-10: 0-13-149505-4 1. Software patterns. 2. Computer software—Testing. I. Title. QA76.76.P37M49 2007 005.1—dc22 2006103488 Copyright © 2007 Pearson Education, Inc. All rights reserved. Printed in the United States of America. This publication is protected by copyright, and per- mission must be obtained from the publisher prior to any prohibited reproduction, storage in a retrieval system, or transmission in any form or by any means, electronic, mechanical, photocopying, recording, or likewise. For information regarding permissions, write to: Pearson Education, Inc. Rights and Contracts Department 75 Arlington Street, Suite 300 Boston, MA 02116 Fax: (617) 848-7047 ISBN 13: 978-0-13-149505-0 ISBN 10: 0-13-149505-4 Text printed in the United States on recycled paper at Courier in Westford, Massachusetts. First printing, May 2007
This book is dedicated to the memory of Denis Clelland, who recruited me away from Nortel in 1995 to work at ClearStream Consulting and thereby gave me the opportunity to have the experiences that led to this book. Sadly, Denis passed away on April 27, 2006, while I was fi nalizing the second draft.
分享到:
收藏