[[TableOfContents]] 

= Objectives =

The CppUnit code base has grown into a monster and there are still many features that I would like to see added.

CppUnit2 is an attempt to propose a much cleaner implementation of the current features, and to follow good C++ practices.

The main objectives are:
 * use of smart-pointer for memory management
 * better support for custom test cases (repeat...) and parametrized test methods
 * flexible enough to allow sharing of a fixture across test cases (bad practice as it breaks test isolation, but may save a lot of time at execution if the setup is heavy).
 * better assertion support (equality testing, object conversion to string,...)
 * association of user data with test cases
 * thread support (passing assertion exceptions across threads, assertion...)
 * input-based test case support (read input data from external source, such as XML files...)
 * python binding

= Getting the sources =

CppUnit2 sources are finally available on CVS. You can obtain them as follows:
{{{
cvs -d:pserver:anonymous@cvs.sourceforge.net:/cvsroot/cppunit login
cvs -z3 -d:pserver:anonymous@cvs.sourceforge.net:/cvsroot/cppunit co cppunit2
}}}

= Compiler Requirements =

Four major requirements:
 * C++ exception
 * namespace support
 * enough template support to be able to implement /GenericFunctor
 * C++ style cast (easy to remove)
 * explicit keyword (easy to remove)

Compiler features that are '''not''' required:
 * function template overloading
 * template member support
 * run-time type information (rtti)
 * template partial specialization

Also, CppUnit2 should compile correctly on MSVC6/7.x and gcc 2.95, as those are probably the two most widely used compilers.

= Compatibility with CppUnit 1.x =

 CppUnit2 is implemented in a different namespace (Cpp``UT). This allows a compatibility layer to be created, as well as having both frameworks cohabiting. 

 It should be possible to build a compatibility layer for test fixtures, assertions, auto registration, hence preserving most of the written test code. Most of the remaining code written against other would like need to be ported (test listener, test registry, test runner, test context...).

= Build system =

 Experience with the autotools has shown that it is far from being perfect (AIX still doesn't support shared libraries), and that very few people actually know how to maintain and fix such build scripts. Also, the autotools don't work on Windows (managing builds on Windows with a total of about 8 configurations per project would be too much work).

 [Scons http://scons.sf.net] seems to be a good candidate for multiplatform builds. It should also be fairly easy for a user to 'hack' into the build script to adapt it to their compiler when not supported.

= Memory management =

 In CppUnit 1, it was difficult to know when passing a parameter what its expected life was and who was responsible to delete it.

 CppUnit2 solves this by using smart-pointer for dynamically allocated objects, and the following conventions:
  * pass by smart-pointer when the ownership of the parameter is transfered/shared.
  * pass by const reference indicates a 'pass by value', the parameter will be copied if needed.
  * pass by non const reference indicates that the ownership will not be assumed. The life-cycle requirement depends on the semantic of the function. In most case, if it is a constructor, then the reference is expected to be valid as long as the object being constructed. 

 The use of smart-pointer has greatly simplified the overall implementation (especially the TestFactoryRegistry).

 CppUnit2 comes with its own smart-pointer, which implements a subset of the generic smart-pointer that has been adopted by the standard C++ committee (neither weak pointer, nor checked_deleter are supported).

 A standard conformant implementation ([http://www.boost.org/libs/smart_ptr/smart_ptr.htm boost:shared_ptr]) can be used if CPPUT_USE_BOOST_SHARED_PTR is defined.

= Parametrized test method =
 In the implementation of the test case, the callback for setUp(), run() and tearDown() are provided through generic functors. Those functors can be bound to a struct functor, a C function or a C++ method. Parameters can also be bound by the functors so that when the call is made, specific values are passed as parameters.

= Test fixture sharing for test case methods / shared resources =
 When writing heavy functional test cases which have a time-consuming setUp()/tearDown() (often database related), you often want the setUp()/tearDown() step to be executed only once to run all the test cases to decrease the time required to run the test.

 The obvious drawback of this is that tests are not isolated from each other, which means that a test may pass because a test before it was run, or a test may fail because a previous test failed.

 This can easily be implemented by dynamically controlling the behavior of Fixture``Factory (should the last created fixture be returned, or should a new one be returned).

 * Open issue: how should the user specify that a shared fixture policy needs to be used?
 * Possible solutions: 
  * make this a 'property' of the fixture creation and have the Fixture``Factory look up those properties
  * provide specific methods on the Fixture``Factory and wrap them into macros for helper macro integration

 Notes: currently trying to approach this from a different angle. Shared test fixtures with single setUp/tearDown are complex to implement with some of the new features of the framework (such as multiple execution of a test case or execution of a few test cases of a test fixture). The rough idea is to dissociate the setUp/tearDown from the test fixture (let's call them ''resource'') and have the test framework properly handle those resources.

 After some thinking, the shared test fixture will be taken out. It's basically trying to achieve what the resource concept would do without materializing it. The idea of the resource concept is to have test cases depend on some resources. A resource is a simple C++ object with a setUp/tearDown, which can be retrieved using a key (likely a string identifier). A resource is shared among multiple objects and is initialized only once per test run.

 What's interesting about resources is that you have explicit resource dependency tracking and that, for example, in a concurrent test runner, you could prevent two tests using the same resource from running concurrently. This puts more complexity on the test driver side, but it provides much more flexiblity and make things easier to understand.

= Assertions =
   The goals when writing the new assertions facility were to:
  * make it easier to write custom assertions (specifically, being able to write complex assertions by reusing simple ones, support for default values in arguments)
  * decouple customization of conversion to string and equality comparison in equality assertions
  * provide more flexibility in customization of conversion to string and equality comparison
  * allow string types to be decorated with "..." so whitespace can be seen
  * provide string-specific assertions
  * provide some support for string types other than std::string.

  Two alternative designs were implemented and experimented with before electing the second one the winner.

  Here is how an assertion is written with CppUnit2:
{{{
# define CPPUT_ASSERT            \
   CPPUT_BEGIN_ASSERTION_MACRO() \
   ::CppUT::checkTrue

void checkTrue( bool shouldBeTrue, const Message &message )
{
   if ( shouldBeTrue )
      return;

   Message newMessage( message );
   newMessage.insertAt( 0, translate( "Assertion failed: expression did not evaluate to true." ) );
   fail( newMessage );
}
}}}

 The CPPUT_ASSERT macro first captures the location of the assertion (file, line...) with CPPUT_BEGIN_ASSERTION_MACRO() and then forwards the call to the function checkTrue() which implements the assertion. The final call to fail() will actually throw the assertion exception, using the location that was previously captured.

 This idiom supports overloading, default parameter values and templatized assertion functions, and conversion of macro parameters to strings (for insertion in messages) is still possible.

''Note: currently investigating the possibility of capturing the call stack in addition to the file and source line.''

 Here is a list of the assertions provided. The names should speak for themselves:
 * Basic assertions
  * CPPUT_ASSERT
  * CPPUT_ASSERT_EXPR( expression )
  * CPPUT_ASSERT_FALSE
  * CPPUT_ASSERT_EXPR_FALSE( expression )
  * CPPUT_ASSERT_EQUAL
  * CPPUT_ASSERT_NOT_EQUAL
  * CPPUT_ASSERT_THROW( expression, Exception``Type )
  * CPPUT_ASSERT_NO_THROW( expression )
  * CPPUT_ASSERT_ASSERTION_FAIL( assertion )
  * CPPUT_ASSERT_ASSERTION_PASS( assertion )
 * Assertions working with string
  * CPPUT_ASSERTSTR_START
  * CPPUT_ASSERTSTR_END
  * CPPUT_ASSERTSTR_CONTAIN
  * CPPUT_ASSERTSTR_EQUAL
 * Enumeration assertions
  * CPPUT_ASSERT_SEQUENCE_EQUAL
  * CPPUT_ASSERT_SET_EQUAL
  * CPPUT_ASSERT_STL_SEQUENCE_EQUAL
  * CPPUT_ASSERT_STL_SET_EQUAL

 The conversion of objects to strings, and test of two objects for equality services have been separated from the equality assertion implementation. As they are orthogonal concepts, they can now be customized separately.

 The new assertions working with strings introduced another service: conversion of a string type to an std::string. This allows the testing framework to work with unknown string type, as long as the user provides the required conversion functions. Those assertions will always convert their string arguments to std::strings before proceeding with the assertion test. This allows testing of two ''const char *'' pointers for equality as strings instead of pointers.

 The conversion of objects to strings will recognize string types and automatically escape and quote them. No more chasing non-printable characters on equality failure messages.

 Customization is done completely within headers and can therefore be done on a per-translation unit/application basis.

''Note: some regular-expression-based assertions would be useful.''
 
= Test descriptive data =
   Functional testing and environments that require extensive documentation often wish to associate data to test cases, such as a description for example.

   It would be desirable to work with other test case management projects and define a standard and shared xml test output. Applications to view the test results could be developed and managed separately from the test library. It would also allow the consistent management of multi-language systems. A system that has perl, Java, and C++ could have language-specific test frameworks, but share common test-reporting tools via the common xml test output.

  Also, data attached to test cases could be used for auditing existing tests, managing dependencies, concurrency...

  Being able to associate data with the result of a test case, whether successful or not, would be very useful. You could attach data such as time to run, some structured output of a failure (list of expected values/list of actual values...)

= Threaded test cases =

 Having a test case that spans multiple threads to check for thread-safety or interaction is a fairly common task. 

 This puts the following requirements over the framework:
 * thread-safety
 * test failure propagation from a thread spawned by a test case to the test framework

 == Thread-safety ==

 All components used in multiple threads must be thread-safe. (This mainly concerns assertions.)

 The checkpoint mecanism used by the assertions used a static variable. It was made thread-safe by the use of thread local storage. To achieve this, a minimal portable thread api is embedded in CppUnit2.

 The smart-pointer reference counter needs to be thread-safe.

 Care must be taken when manipulating std::strings across thread as they often use non-thread-safe reference counting.

 Notes: WIN32 implementations for this are done. pthread & MacOS implementations need to be done.  (Mac OS X uses pthread for its threading model)

 == Test failure propagation ==

 Assertions that occur in threads spawned by a test case need to be transfered to the main test framework thread and associated with the test case.

 This is achieved by reusing the Test``Failure``Guard``Chain components which capture test case uncaught exceptions and assertions. These components are reused to protect spawned thread main loop and 'memorize' failures. Those failures can then be dispatched in the main test framework thread.

== Test plug-in ==

 There are two main uses for plug-ins in cppunit:
 * writing unit tests in plug-ins
 * customizing/extending cppunit at run-time

 Unit test plug-ins are already handled by linking against a dll build of cppunit 2. The static registry is shared among users of the dll. A simple runner needed to be written though.

 Customization/extension should provide more flexibility than in cppunit 1. A very interesting goal to achieve would be to allow graphic test runner to be a simple 'extension', though this might be complex to achieve.

= Input-based test cases =
  
= Python binding =

Expose execution of unit tests, and other high-level functionnalities in python. If possible provide integration with python unit testing module.

 * Ease the development of new test runners (test plug-in runner...) and increase their reusability
 * Integration with python environment for unit testing

= Integration with test-driving environments =

 Study possiblity to integrate the test framework with:
 * [Cruise``Control http://cruisecontrol.sourceforge.net/]
 * [Cruise``Control.NET http://ccnet.thoughtworks.com/]
 * [QMTest http://www.codesourcery.com/qm/qmtest]
 * ?

= Architecture =

The test hierarchy:

attachment:uml_test.gif

Main changes compared to CppUnit 1.x include the use of the visitor pattern, a reference to the parent test in each test, and the use of generic functors in test case implementation.

 == Visitor pattern to distinguish between test case and test suite ==
   It simplifies implementation, and gives much more flexibility to explore the test hierarchy...

 == Each test references its parent ==
   * Helps provide useful reports on failure (the full test suite path can be easily reported). 
   * Does not depend on execution order to track which test suite the test belongs to. 
   * Avoid the ugly hack in the test fixture to prepend the method name with the fixture class name to report the suite the test belongs to.

 == Generic Functor in test case implementation ==
   * Test setUp/tearDown and run can be implemented in any form (functor, C function, member function)
   * Parameters can be bound to the generic functor implementing setUp/tearDown and run, thereby allowing simple test parametrization.
`
= To do =
 * build system
 * thread api for pthread (need to implement Thread``Id``Type)
 * thread api for Mac OS
 * thread guard (failure propagator for spawned thread in test case)
 * test plug-in
 * test listener plug-in
 * plug-in loader & manager
 * progress listener
 * result outputter (text, compiler, xml)
 * test plan (find test by pattern...)
 * test runner (mfc, qt, command line based)
 * input-based test case (likely to have an impact on the core design)
 * shared test fixture with single setUp/tearDown (likely to have an impact on the core design)

= Progress =
 * 2004/06/16:
  * enhanced assertenum.h to support convertion to string customization through functor.
  * idea: enhance class Message to carry a bag of properties, allowing structured result. Find a way to get this into success too (could be used to store elapsed time...). At the current time in cppunit 1, we must use a test listener and can only store results with the xml outputter.
 * 2004/02/08:
  * incorporated the portable dll loading api of cppunit 1
  * added header content descriptions to README.
TitleIndex  [[DraGona]]  [[DraGonb]] [[DraGonc]] [[DraGond]] [[DraGone]] [[DraGonf]] [[DraGong]] 

[[DraGonh]] [[DraGoni]] [[DraGonj]] [[DraGonk]] [[DraGonl]] [[DraGonm]] [[DraGonn]] [[DraGono]] 

[[DraGonp]] [[DraGonq]] [[DraGonr]] [[DraGons]] [[DraGont]] [[DraGonu]] [[DraGonv]] [[DraGonw]] 

[[DraGonx]] [[DraGony]] [[DraGonz]] [[DraGonaa]]

[http://www.51dragon.com 网站推广] 
[http://1.51dragon.com arm] 
[http://guangduanji.51dragon.com 光端机] 
[http://guangduanji.51dragon.com/shuzi.htm 数字光端机] 
[http://guangduanji.51dragon.com/shipin.htm 视频光端机] 
[http://guangduanji.51dragon.com/szsp.htm 数字视频光端机] 
[http://guangduanji.51dragon.com/jiankong.htm 监控视频光端机] 
[http://guangduanji.51dragon.com/guangbo.htm 广播级数字视频光端机] 
[http://guangduanji.51dragon.com/wangluo.htm 网络视频全套解决方案]
[http://1.51dragon.com arm]
[http://2.51dragon.com arm培训]
[http://3.51dragon.com 安防]
[http://3.51dragon.com/a.htm 安防器材]
[http://4.51dragon.com 笔记本]
[http://5.51dragon.com 笔记本电脑]
[http://6.51dragon.com 变速机]
[http://7.51dragon.com 标签]
[http://8.51dragon.com 标签打印机]
[http://9.51dragon.com 不孕不育]
[http://9.51dragon.com/a.htm 不孕不育治疗]
[http://10.51dragon.com 餐饮]
[http://10.51dragon.com/a.htm 餐饮管理]
[http://11.51dragon.com 叉车]
[http://12.51dragon.com 磁性材料]
[http://13.51dragon.com 刺绣]
[http://14.51dragon.com 仓储]
[http://15.51dragon.com 仓储设备]
[http://16.51dragon.com 充电器]
[http://16.51dragon.com/a.htm 手机充电器]
[http://17.51dragon.com 出国]
[http://18.51dragon.com 除湿机]
[http://18.51dragon.com/a.htm 工业除湿机]
[http://19.51dragon.com 创业]
[http://19.51dragon.com/a.htm 创业项目]
[http://20.51dragon.com 床上用品]
[http://20.51dragon.com/e.htm 家居用品]
[http://20.51dragon.com/a.htm 婴儿用品]
[http://20.51dragon.com/b.htm 情趣用品]
[http://20.51dragon.com/c.htm 宠物用品]
[http://20.51dragon.com/d.htm 儿童用品]
[http://21.51dragon.com 单片机] 
[http://22.51dragon.com 打印机] 
[http://23.51dragon.com 灯具] 
[http://24.51dragon.com 电源] 
[http://25.51dragon.com 开关电源] 
[http://26.51dragon.com ups电源] 
[http://27.51dragon.com 变频电源] 
[http://28.51dragon.com 稳压电源] 
[http://29.51dragon.com 电机] 
[http://30.51dragon.com 步进电机] 
[http://31.51dragon.com 微型电机] 
[http://32.51dragon.com 电梯] 
[http://33.51dragon.com 电子政务]
[http://34.51dragon.com 雕塑]
[http://35.51dragon.com 雕刻机]
[http://36.51dragon.com 激光雕刻机]
[http://36.51dragon.com/a.htm 电脑雕刻机]
[http://36.51dragon.com/b.htm 数控雕刻机]
[http://36.51dragon.com/c.htm 橡胶版雕刻机]
[http://36.51dragon.com/d.htm 木工雕刻机]
[http://37.51dragon.com 短信群发]
[http://38.51dragon.com 对讲机] 
[http://38.51dragon.com/a.htm 无线对讲机] 
[http://39.51dragon.com erp] 
[http://40.51dragon.com erp软件] 
[http://41.51dragon.com 耳机] 
[http://41.51dragon.com/a.htm 无线耳机] 
[http://42.51dragon.com 耳聋] 
[http://43.51dragon.com 阀] 
[http://44.51dragon.com 阀门] 
[http://44.51dragon.com/a.htm 球阀] 
[http://45.51dragon.com 法律咨询] 
[http://46.51dragon.com 翻译] 
[http://47.51dragon.com 翻译公司 ] 
[http://48.51dragon.com 北京翻译] 
[http://49.51dragon.com 纺织机械] 
[http://50.51dragon.com 服装] 
[http://51.51dragon.com 服务器] 
[http://52.51dragon.com gprs] 
[http://53.51dragon.com gps] 
[http://54.51dragon.com 车载gps] 
[http://55.51dragon.com 防盗GPS] 
[http://56.51dragon.com 干燥] 
[http://57.51dragon.com 干燥机] 
[http://58.51dragon.com 干燥设备] 
[http://59.51dragon.com 干洗] 
[http://60.51dragon.com 干洗设备] 
[http://61.51dragon.com 钢结构] 
[http://62.51dragon.com 钢铁] 
[http://63.51dragon.com 钢材] 
[http://64.51dragon.com 工控] 
[http://65.51dragon.com 工控机] 
[http://66.51dragon.com 公寓] 
[http://67.51dragon.com 管理咨询] 
[http://68.51dragon.com 管理培训] 
[http://69.51dragon.com 项目管理] 
[http://70.51dragon.com 管理顾问] 
[http://71.51dragon.com 光触媒] 
[http://72.51dragon.com 尖锐湿疣] 
[http://73.51dragon.com 广告] 
[http://74.51dragon.com 广告策划] 
[http://75.51dragon.com 广告设计] 
[http://76.51dragon.com 耗材] 
[http://77.51dragon.com 办公耗材] 
[http://78.51dragon.com 化工原料] 
[http://79.51dragon.com 化工设备] 
[http://80.51dragon.com 滑雪] 
[http://81.51dragon.com 滑雪场] 
[http://82.51dragon.com 化妆品] 
[http://83.51dragon.com 换热器] 
[http://83.51dragon.com/a.htm 板式换热器] 
[http://83.51dragon.com/b.htm 波纹管换热器] 
[http://83.51dragon.com/c.htm 螺旋板换热器] 
[http://83.51dragon.com/d.htm 列管换热器] 
[http://83.51dragon.com/e.htm 热管换热器] 
[http://83.51dragon.com/f.htm 舒瑞普板式换热器] 
[http://83.51dragon.com/g.htm 石墨换热器] 
[http://83.51dragon.com/h.htm 盘管换热器] 
[http://83.51dragon.com/i.htm 半导体换热器] 
[http://84.51dragon.com 婚庆] 
[http://85.51dragon.com 婚庆公司] 
[http://86.51dragon.com 货运] 
[http://87.51dragon.com 货运公司] 
[http://88.51dragon.com 货架] 
[http://89.51dragon.com 仓储货架] 
[http://89.51dragon.com/a.htm 物流仓储货架]
[http://89.51dragon.com/b.htm 立体仓储]
[http://89.51dragon.com/c.htm 移动货架]
[http://89.51dragon.com/d.htm 角钢货架]
[http://90.51dragon.com 集团电话] 
[http://90.51dragon.com/a.htm 集团电话交换机] 
[http://91.51dragon.com 机柜] 
[http://92.51dragon.com 机床] 
[http://93.51dragon.com 机箱] 
[http://94.51dragon.com 机票] 
[http://95.51dragon.com 打折机票] 
[http://96.51dragon.com 特价机票] 
[http://97.51dragon.com 国际机票] 
[http://98.51dragon.com 订机票] 
[http://99.51dragon.com 机票价格] 
[http://100.51dragon.com 飞机票] 
[http://101.51dragon.com 继电器] 
[http://102.51dragon.com 固态继电器] 
[http://102.51dragon.com/a.htm 时间继电器] 
[http://102.51dragon.com/b.htm 热继电器] 
[http://102.51dragon.com/c.htm 中间继电器] 
[http://102.51dragon.com/d.htm 小型继电器] 
[http://102.51dragon.com/e.htm 接地继电器] 
[http://102.51dragon.com/f.htm 汽车继电器] 
[http://102.51dragon.com/g.htm 交流继电器] 
[http://103.51dragon.com 加盟] 
[http://104.51dragon.com 加盟店] 
[http://105.51dragon.com 连锁加盟] 
[http://106.51dragon.com 家具] 
[http://107.51dragon.com 办公家具] 
[http://108.51dragon.com 驾校] 
[http://108.51dragon.com/a.htm 北京驾校] 
[http://109.51dragon.com 家政] 
[http://110.51dragon.com 家政服务] 
[http://111.51dragon.com 减肥] 
[http://112.51dragon.com 监控] 
[http://113.51dragon.com 闭路监控] 
[http://114.51dragon.com 远程监控] 
[http://115.51dragon.com 监控设备] 
[http://116.51dragon.com 交友] 
[http://117.51dragon.com 交换机] 
[http://118.51dragon.com 程控交换机] 
[http://119.51dragon.com 电话交换机] 
[http://120.51dragon.com 网络交换机] 
[http://121.51dragon.com 建材] 
[http://122.51dragon.com 新型建材] 
[http://123.51dragon.com 酒店] 
[http://124.51dragon.com 酒店预定] 
[http://125.51dragon.com 酒店预订] 
[http://126.51dragon.com KVM] 
[http://127.51dragon.com 切换器] 
[http://128.51dragon.com 矩阵切换器] 
[http://129.51dragon.com 考勤机] 
[http://130.51dragon.com 指纹] 
[http://131.51dragon.com 指纹考勤机] 
[http://132.51dragon.com 巡更] 
[http://132.51dragon.com/a.htm 电子巡更]
[http://133.51dragon.com 空压机] 
[http://133.51dragon.com/a.htm 螺杆式空压机] 
[http://133.51dragon.com/b.htm 阿特拉斯空压机] 
[http://133.51dragon.com/c.htm 活塞式空压机] 
[http://133.51dragon.com/d.htm 螺杆空压机] 
[http://133.51dragon.com/e.htm 空压机配件] 
[http://133.51dragon.com/f.htm 移动式空压机] 
[http://133.51dragon.com/g.htm 单螺杆空压机] 
[http://133.51dragon.com/h.htm 进口空压机] 
[http://134.51dragon.com 礼品] 
[http://135.51dragon.com 工艺品] 
[http://136.51dragon.com 纪念品] 
[http://137.51dragon.com 礼品公司] 
[http://138.51dragon.com 猎头] 
[http://139.51dragon.com 猎头公司] 
[http://140.51dragon.com 留学] 
[http://141.51dragon.com 法国留学] 
[http://142.51dragon.com 英国留学] 
[http://143.51dragon.com 德国留学] 
[http://144.51dragon.com 美国留学] 
[http://145.51dragon.com 出国留学] 
[http://146.51dragon.com 留学签证]
[http://147.51dragon.com 隆胸] 
[http://148.51dragon.com 路由器] 
[http://149.51dragon.com 旅行社] 
[http://150.51dragon.com 律师] 
[http://151.51dragon.com 律师事务所] 
[http://152.51dragon.com mba] 
[http://153.51dragon.com emba] 
[http://154.51dragon.com 美容] 
[http://155.51dragon.com 整形美容] 
[http://156.51dragon.com 门禁] 
[http://157.51dragon.com 一卡通] 
[http://158.51dragon.com 停车场] 
[http://159.51dragon.com 门禁系统] 
[http://159.51dragon.com/a.htm 指纹门禁] 
[http://159.51dragon.com/b.htm 门禁系统] 
[http://159.51dragon.com/c.htm 门禁考勤] 
[http://159.51dragon.com/e.htm 门禁管理系统] 
[http://159.51dragon.com/f.htm 门禁卡] 
[http://159.51dragon.com/g.htm 酒店门禁] 
[http://159.51dragon.com/h.htm 电子门禁] 
[http://159.51dragon.com/i.htm 门禁设备] 
[http://159.51dragon.com/j.htm 门禁软件] 
[http://160.51dragon.com 模具] 
[http://160.51dragon.com/a.htm 五金模具] 
[http://161.51dragon.com 塑料模具] 
[http://162.51dragon.com 排队机] 
[http://163.51dragon.com 票务] 
[http://164.51dragon.com 培训] 
[http://165.51dragon.com IT培训] 
[http://166.51dragon.com 计算机培训] 
[http://167.51dragon.com 软件培训] 
[http://168.51dragon.com 汽车] 
[http://169.51dragon.com 汽车美容] 
[http://170.51dragon.com 汽车配件] 
[http://171.51dragon.com 二手车] 
[http://172.51dragon.com 汽车养护] 
[http://173.51dragon.com 汽车租赁] 
[http://174.51dragon.com 起名] 
[http://175.51dragon.com 签证] 
[http://176.51dragon.com 求职] 
[http://177.51dragon.com 招聘] 
[http://178.51dragon.com 热水器] 
[http://178.51dragon.com/a.htm 太阳能热水器] 
[http://179.51dragon.com 人力资源] 
[http://179.51dragon.com/a.htm 人力资源管理] 
[http://180.51dragon.com 润滑油] 
[http://181.51dragon.com 商标] 
[http://182.51dragon.com 商标注册] 
[http://183.51dragon.com 首饰] 
[http://184.51dragon.com 设计] 
[http://185.51dragon.com 包装设计] 
[http://186.51dragon.com 平面设计] 
[http://187.51dragon.com 摄像机] 
[http://188.51dragon.com 数码摄像机] 
[http://189.51dragon.com 石材] 
[http://189.51dragon.com/a.htm 石材养护] 
[http://190.51dragon.com 视频会议] 
[http://191.51dragon.com 视频会议设备] 
[http://192.51dragon.com 视频会议系统] 
[http://193.51dragon.com 数据修复] 
[http://194.51dragon.com 水处理] 
[http://195.51dragon.com 水处理设备] 
[http://196.51dragon.com 水泵] 
[http://197.51dragon.com 真空泵] 
[http://197.51dragon.com/a.htm 电力真空泵] 
[http://198.51dragon.com 速记] 
[http://199.51dragon.com 速记培训] 
[http://200.51dragon.com 塑料]
[http://201.51dragon.com 塑料机械]
[http://202.51dragon.com 手表]
[http://202.51dragon.com/a.htm 瑞士手表]
[http://202.51dragon.com/b.htm 卡西欧手表]
[http://202.51dragon.com/c.htm 浪琴手表]
[http://202.51dragon.com/d.htm 手表报价]
[http://202.51dragon.com/e.htm 手表品牌]
[http://202.51dragon.com/f.htm 男士手表]
[http://202.51dragon.com/g.htm 女士手表]
[http://202.51dragon.com/h.htm 情侣手表]
[http://202.51dragon.com/i.htm 劳力士手表]
[http://202.51dragon.com/j.htm 时尚手表]
[http://203.51dragon.com 陶瓷]
[http://203.51dragon.com/a.htm 陶瓷雕塑]
[http://203.51dragon.com/b.htm 压电陶瓷]
[http://203.51dragon.com/c.htm 陶瓷制品]
[http://203.51dragon.com/e.htm 陶瓷膜]
[http://204.51dragon.com 条码]
[http://205.51dragon.com 条码打印机]
[http://206.51dragon.com 投影机]
[http://206.51dragon.com/a.htm 投影机维修]
[http://207.51dragon.com 大屏幕]
[http://208.51dragon.com 投资]
[http://209.51dragon.com 投资项目]
[http://210.51dragon.com 涂料]
[http://211.51dragon.com 团购]
[http://211.51dragon.com/a.htm 汽车团购]
[http://211.51dragon.com/b.htm 无忧团购]
[http://211.51dragon.com/c.htm 团购网]
[http://211.51dragon.com/d.htm 北京团购]
[http://211.51dragon.com/e.htm 建材团购]
[http://211.51dragon.com/f.htm 家具团购]
[http://211.51dragon.com/g.htm 年货团购]
[http://211.51dragon.com/h.htm 团购服务]
[http://211.51dragon.com/i.htm 服装团购]
[http://212.51dragon.com 托盘]
[http://213.51dragon.com VOD]
[http://214.51dragon.com VOIP]
[http://215.51dragon.com 挖掘机]
[http://215.51dragon.com/a.htm 二手挖掘机]
[http://215.51dragon.com/b.htm 挖掘机配件]
[http://215.51dragon.com/c.htm 网络挖掘机]
[http://215.51dragon.com/d.htm 挖掘机械]
[http://215.51dragon.com/e.htm 挖掘机修理]
[http://216.51dragon.com 物流]
[http://217.51dragon.com 玩具]
[http://217.51dragon.com/a.htm 儿童玩具]
[http://218.51dragon.com 鲜花]
[http://218.51dragon.com/a.htm 北京鲜花]
[http://219.51dragon.com 鲜花速递]
[http://219.51dragon.com/a.htm 北京鲜花速递]
[http://220.51dragon.com 显示器]
[http://221.51dragon.com/ 显示器维修]
[http://222.51dragon.com 小提琴]
[http://223.51dragon.com 小尾羊]
[http://224.51dragon.com 相机]
[http://224.51dragon.com/a.htm 帖纸相机]
[http://224.51dragon.com/b.htm 数码相机]
[http://225.51dragon.com 虚拟主机]
[http://225.51dragon.com/a.htm 北京虚拟主机]
[http://226.51dragon.com 空间租用]
[http://226.51dragon.com/a.htm 虚拟主机提供商]
[http://226.51dragon.com/b.htm 虚拟主机租用]
[http://226.51dragon.com/c.htm 域名虚拟主机]
[http://226.51dragon.com/d.htm 虚拟主机空间]
[http://227.51dragon.com 雅思]
[http://227.51dragon.com/a.htm 雅思考试]
[http://227.51dragon.com/b.htm 雅思报名]
[http://228.51dragon.com 液压]
[http://228.51dragon.com/a.htm 液压机]
[http://228.51dragon.com/b.htm 液压设备]
[http://228.51dragon.com/c.htm 液压件]
[http://229.51dragon.com 移民]
[http://229.51dragon.com/a.htm 加拿大移民]
[http://229.51dragon.com/b.htm 新加坡移民]
[http://230.51dragon.com 音响]
[http://231.51dragon.com 音箱]
[http://232.51dragon.com 印刷机械]
[http://233.51dragon.com 印刷设备]
[http://234.51dragon.com 印刷机]
[http://235.51dragon.com 英语培训]
[http://236.51dragon.com 外语培训]
[http://237.51dragon.com 法语培训]
[http://238.51dragon.com 饮水机]
[http://239.51dragon.com 元器件]
[http://240.51dragon.com 电子元器件]
[http://241.51dragon.com 油漆]
[http://242.51dragon.com 展览]
[http://243.51dragon.com 展览展示]
[http://244.51dragon.com 整形]
[http://245.51dragon.com 整形手术]
[http://246.51dragon.com 制药机械]
[http://247.51dragon.com 招商]
[http://248.51dragon.com 药品招商]
[http://249.51dragon.com 医药招商]
[http://250.51dragon.com 知识产权]
[http://251.51dragon.com 智能家居]
[http://252.51dragon.com 轴承]
[http://252.51dragon.com/a.htm 微型轴承]
[http://253.51dragon.com 珠宝]
[http://254.51dragon.com 注册公司]
[http://255.51dragon.com 公司注册]
[http://256.51dragon.com 装饰]
[http://257.51dragon.com 装饰设计]
[http://258.51dragon.com 装修]
[http://258.51dragon.com/a.htm 家庭装修]
[http://258.51dragon.com/b.htm 室内装修]
[http://258.51dragon.com/c.htm 家居装修]
[http://258.51dragon.com/d.htm 房屋装修]
[http://258.51dragon.com/e.htm 装饰装修]
[http://258.51dragon.com/f.htm 装修公司]
[http://258.51dragon.com/g.htm 装修设计]
[http://258.51dragon.com/h.htm 厨房装修]
[http://258.51dragon.com/i.htm 居室装修]
[http://258.51dragon.com/j.htm 住宅装修]
[http://258.51dragon.com/k.htm 住房装修]
[http://259.51dragon.com 租房]
[http://260.51dragon.com 北京租房]
[http://260.51dragon.com/a.htm 二手房]
[http://261.51dragon.com 旅游]
[http://262.51dragon.com 云南旅游]
[http://263.51dragon.com 海南旅游]
[http://264.51dragon.com 三亚] 
[http://265.51dragon.com 三亚旅游] 
[http://266.51dragon.com 四川旅游] 
[http://267.51dragon.com 张家界] 
[http://268.51dragon.com 张家界旅游] 
[http://269.51dragon.com 旅游景点] 
[http://270.51dragon.com 香港旅游] 
[http://271.51dragon.com 桂林旅游] 
[http://272.51dragon.com 桂林] 
[http://273.51dragon.com 猎头] 
[http://274.51dragon.com 猎头公司] 
[http://275.51dragon.com OA] 
[http://276.51dragon.com 办公自动化] 
[http://277.51dragon.com 九寨沟] 
[http://278.51dragon.com 九寨沟旅游] 
[http://279.51dragon.com 欧洲旅游] 
[http://280.51dragon.com 三峡] 
[http://281.51dragon.com 三峡旅游] 
[http://282.51dragon.com 调查] 
[http://283.51dragon.com 侦探] 
[http://284.51dragon.com 私人侦探] 
[http://285.51dragon.com 私家侦探] 
[http://286.51dragon.com 调查公司] 
[http://287.51dragon.com 市场调查] 
[http://288.51dragon.com 泵] 
[http://289.51dragon.com 水泵] 
[http://290.51dragon.com 真空泵] 
[http://291.51dragon.com mcse] 
[http://292.51dragon.com ccnp] 
[http://293.51dragon.com ccna] 
[http://294.51dragon.com 专利] 
[http://295.51dragon.com smt] 
[http://296.51dragon.com 房地产] 
[http://297.51dragon.com 橡胶] 
[http://298.51dragon.com 糖尿病] 
[http://299.51dragon.com 白癜风] 
[http://300.51dragon.com 氢氧化铝] 
[http://300.51dragon.com/a.htm 氢氧化镁] 
[http://300.51dragon.com/b.htm 水镁石] 
[http://300.51dragon.com/c.htm 萤石] 
[http://301.51dragon.com 制氮机] 
[http://302.51dragon.com 发电机] 
[http://303.51dragon.com 发电机组] 
[http://304.51dragon.com ibm笔记本]
[http://305.51dragon.com 索尼笔记本] 
[http://306.51dragon.com 流量计] 
[http://307.51dragon.com baidu竞价] 
[http://308.51dragon.com DELL笔记本] 
[http://309.51dragon.com 流媒体]
[http://310.51dragon.com 流媒体编码卡]
[http://311.51dragon.com 多屏卡]
[http://312.51dragon.com 视频墙]
[http://313.51dragon.com 切换台]
[http://314.51dragon.com 转换盒]
[http://315.51dragon.com 视频采集卡]
[http://316.51dragon.com 视频卡]
[http://317.51dragon.com 特技切换台]
[http://318.51dragon.com 数模转换器]
[http://319.51dragon.com 大屏幕控制器] 
[http://320.51dragon.com 包装机械]
[http://321.51dragon.com 包装机] 
[http://322.51dragon.com 液晶电视]
[http://323.51dragon.com 等离子电视]
[http://324.51dragon.com 液晶显示器]
[http://325.51dragon.com 等离子显示器]
[http://326.51dragon.com IBM显示器]
[http://327.51dragon.com IBM工作站]
[http://328.51dragon.com SONY显示器]
[http://329.51dragon.com 显示设备]
