2

我们在整个层次结构中使用@Before 来在测试执行之前将一些测试数据插入到数据库中。我想在 @Test 开始运行之前将所有数据提交到数据库。

一种方法是将数据作为此测试类的@Before 方法的最后一步提交。但是我们有数百个这样的类,并且不想进入并修改所有这些。

我玩过 ExternalResource @Rule 和 TestWatcher @Rule ......但在所有 @Before 发生后,他们没有办法参与进来。

我想我需要考虑构建一个自定义的 TestRunner 来做到这一点。

那是正确的轨道吗?

4

2 回答 2

0

你在找什么,对我来说似乎不一致。设置一些数据并提交它们是非常接近的操作,不应该属于不同的地方。相反,我宁愿将它们放入一个函数中,并在实际参数设置为您要插入的值的情况下调用它。或者使用 SQL 字符串作为实际参数。并从@Before 调用这个函数

如果你坚持,那么做是没有问题的。为您的 Junit 类创建后代类:

package ...;
import org.junit.Before;
public class NewAndBetterYourTest1 extends YourTest1 {
    @Override
    @Before
    public void setUp() {
        super.setUp(); // this is where you are setting everything.
        makeCommits();
    }
}

只是不要忘记启动这些新测试

于 2012-11-30T10:41:43.193 回答
0

虽然如果没有自定义 Runner,您无法完全满足您的要求,但您可以确保在@Before方法中创建的所有数据都使用规则提交:

public class LocalDatabase extends ExternalResource {
  private DataSource dataSource;

  @Override
  protected void before() {
    dataSource = createLocalDatabase();
  }

  @Override
  protected void after() {
    try {
      destoyLocalDatabase(dataSource);
    } finally {
      dataSource = null;
    }
  }

  public void run(Callback callback) {
    if (dataSource == null) {
      throw new IllegalStateException("No DataSource");
    }
    Collection con = null;
    try {
      con = ds.getConnection(DB_USERNAME, PASSWORD);
      callback.execute(con);
      con.commit();
    } finally {
      if (con != null) con.close();
    }
  }

您可以将其作为基类中的规则:

public DatabaseTest {
  @Rule
  public LocalDatabase final localDatabase = new LocalDatabase();
}

并且可以@Before在任何子类的方法中使用它

public UserDaoTest extends DatabaseTest {

  @Before
  public void populateInitialData() {
    localDatabase.run(new Callback() {
      @Override
      public void execute(Connection con) {
        ...
      }
    });
  }
  ...
}
于 2013-02-10T04:37:37.403 回答