Java 使用mockobjects进行Junit测试
我正试图在测试失败的第一种情况下编写一些测试,而我知道我的代码可以工作:Java 使用mockobjects进行Junit测试,java,database,junit,mocking,easymock,Java,Database,Junit,Mocking,Easymock,我正试图在测试失败的第一种情况下编写一些测试,而我知道我的代码可以工作: import org.junit.*; import static org.junit.Assert.*; import java.sql.Connection; import java.sql.SQLException; public class TestGetConnection { @Test public void getConnection() throws SQLException{ Get
import org.junit.*;
import static org.junit.Assert.*;
import java.sql.Connection;
import java.sql.SQLException;
public class TestGetConnection {
@Test
public void getConnection() throws SQLException{
GetConnection getCon = new GetConnection();
Connection con = getCon.getConnection();
assertEquals("com.mysql.cj.jdbc.ConnectionImpl@3aa9e816",con.toString());
}
}
这是GetConnectionclass:
package BE.Intec.Daniel.BabySteps;
import java.sql.DriverManager;
import java.sql.SQLException;
import java.util.Scanner;
public class GetConnection {
private String url2 = "jdbc:mysql://";
private String url;
private String user;
private String timezone = "?useUnicode=true&use JDBCCompliantTimezoneShift=true&useLegacyDatetimeCode=false&serverTimezone=CET";
private String password;
private Scanner input = new Scanner(System.in);
public GetConnection() {
System.out.println("Geef het adres zonder http:// of www. van de database in aub.");
url2 += input.nextLine();
url = url2 + timezone;
System.out.println("Geef de username in aub.");
user = input.nextLine();
System.out.println("Geef het paswoord in aub.");
password = input.nextLine();
}
public String setUrl(String dbName) {
url2 += dbName;
return url = url2 + timezone;
}
public java.sql.Connection getConnection() throws SQLException {
return DriverManager.getConnection(url, user, password);
}
}
在第二个测试中,我首先使用mockobject来获取连接,但是在尝试创建数据库之前,before没有被超越
package BE.Intec.Daniel.BabySteps;
import static org.junit.Assert.*;
import java.sql.Connection;
import java.sql.SQLException;
import org.easymock.EasyMock;
import org.junit.Before;
import org.junit.Test;
public class TestCreateDatabase {
private Connection con;
@Before
public void init() throws SQLException{
GetConnection getcon = EasyMock.createMock(GetConnection.class);
con = getcon.getConnection();
}
@Test
public void createDatabase(){
CreateDataBase newDb = new CreateDataBase(con);
String result = newDb.createDataBase();
assertEquals("Uw databse werd succesvol gecreëerd",result);
}
}
以下是CreateDatabaseclass:
package BE.Intec.Daniel.BabySteps;
import java.sql.Connection;
import java.sql.SQLException;
import java.util.Scanner;
import com.mysql.cj.api.jdbc.Statement;
public class CreateDataBase {
private Connection con;
private java.sql.Statement stat;
private String databaseName;
public CreateDataBase(Connection con) {
this.con = con;
createDataBase();
}
public String createDataBase() {
Scanner in = new Scanner(System.in);
System.out.println("Hoe moet uw database noemen?");
databaseName = in.nextLine();
String succes = "";
try {
stat = con.createStatement();
String statement = "CREATE DATABASE IF NOT EXISTS " + databaseName;
stat.executeUpdate(statement);
succes ="Uw databse werd succesvol gecreëerd";
} catch (SQLException e) {
System.out.println("Er ging iets fout");
e.printStackTrace();
}
return succes;
}
public String getDatabaseName() {
return databaseName;
}
}
奇怪的想法为什么我的测试失败?
任何帮助都是非常必要的
不要介意我的英语,我是比利时人,所以不是本地人。第一次考试是技术考试。您需要检查驱动程序是否正确配置。
您应该将scanner.nextLine()返回的字符串值存根为要用于测试的值(url、用户名、密码)。
此外,您不应该选中com.mysql.cj.jdbc。ConnectionImpl@3aa9e816“在
assertEquals()
方法中。依赖对象类中的默认toString()
方法断言结果是一个坏主意,因为它在其表示中包含对象的哈希代码(@…
部分),这不是比较内容的正确方法。这就足够了:
Assert.assertTrue(con.toString().contains("com.mysql.cj.jdbc.ConnectionImpl"));
以下是更新的测试方法:
@Test
public void getConnection() throws SQLException {
String input = "urlToTest\nuser\nvalue";
InputStream in = new ByteArrayInputStream(input.getBytes());
System.setIn(in);
GetConnection getCon = new GetConnection();
Connection con = getCon.getConnection();
Assert.assertTrue(con.toString().contains("com.mysql.cj.jdbc.ConnectionImpl"));
}
对于第二个测试,您应该更喜欢Mockito而不是EasyMock,后者更易于使用、更有效、更灵活、更强大。
此外,使用的测试逻辑不正确。在这里,您模拟了
GetConnection
对象,但没有指定在上调用方法时模拟对象应执行的操作:
@Before
public void init() throws SQLException{
GetConnection getcon = EasyMock.createMock(GetConnection.class);
con = getcon.getConnection();
}
无论如何,在这方面嘲笑可能不是最好的选择。CreateDataBase
类执行数据库创建。如果您想测试它,您应该通过集成(即与真实数据库集成。为什么不使用内存中的数据库)而不是使用模拟来测试它。第一个测试是技术测试。您需要检查驱动程序是否正确配置。
您应该将scanner.nextLine()返回的字符串值存根为要用于测试的值(url、用户名、密码)。
此外,您不应该选中com.mysql.cj.jdbc。ConnectionImpl@3aa9e816“在
assertEquals()
方法中。依赖对象类中的默认toString()
方法断言结果是一个坏主意,因为它在其表示中包含对象的哈希代码(@…
部分),这不是比较内容的正确方法。这就足够了:
Assert.assertTrue(con.toString().contains("com.mysql.cj.jdbc.ConnectionImpl"));
以下是更新的测试方法:
@Test
public void getConnection() throws SQLException {
String input = "urlToTest\nuser\nvalue";
InputStream in = new ByteArrayInputStream(input.getBytes());
System.setIn(in);
GetConnection getCon = new GetConnection();
Connection con = getCon.getConnection();
Assert.assertTrue(con.toString().contains("com.mysql.cj.jdbc.ConnectionImpl"));
}
对于第二个测试,您应该更喜欢Mockito而不是EasyMock,后者更易于使用、更有效、更灵活、更强大。
此外,使用的测试逻辑不正确。在这里,您模拟了
GetConnection
对象,但没有指定在上调用方法时模拟对象应执行的操作:
@Before
public void init() throws SQLException{
GetConnection getcon = EasyMock.createMock(GetConnection.class);
con = getcon.getConnection();
}
无论如何,在这方面嘲笑可能不是最好的选择。CreateDataBase
类执行数据库创建。如果您想测试它,您应该通过集成(即与真实数据库集成。为什么不使用内存中的数据库)而不是使用模拟来测试它。谢谢David,这非常有帮助。我想说的是,这是一个学校作业,我们必须为一家公司编写一个管理行政的程序。Easymock是他们在课程中使用的示例,这就是我使用它的原因。我运行了我的代码,所以我知道数据库创建是可行的,但我必须为它编写一个测试。我们将努力争取95%的测试覆盖率,我总是发现很难为无效方法和第一次测试编写测试。为什么输入流?不会:@Test public void getConnection()抛出SQLException{getConnection getCon=new getConnection();Connection con=getCon.getConnection();Assert.assertTrue(con.toString().contains(“com.mysql.cj.jdbc.ConnectionImpl”);}够了吗?不客气。不幸的是,在学校,我们不总是学习的东西使用。。。回答您的问题:因为在
GetConnection()
构造函数中,您有Scanner
调用:input.nextLine()代码>。如果您不为输入模拟数据,输入和测试将永远等待输入。谢谢David,这非常有用。我想说的是,这是一个学校作业,我们必须为一家公司编写一个管理行政的程序。Easymock是他们在课程中使用的示例,这就是我使用它的原因。我运行了我的代码,所以我知道数据库创建是可行的,但我必须为它编写一个测试。我们将努力争取95%的测试覆盖率,我总是发现很难为无效方法和第一次测试编写测试。为什么输入流?不会:@Test public void getConnection()抛出SQLException{getConnection getCon=new getConnection();Connection con=getCon.getConnection();Assert.assertTrue(con.toString().contains(“com.mysql.cj.jdbc.ConnectionImpl”);}够了吗?不客气。不幸的是,在学校,我们不总是学习的东西使用。。。回答您的问题:因为在GetConnection()
构造函数中,您有Scanner
调用:input.nextLine()代码>。如果不为输入模拟数据,输入和测试将永远等待输入。