我想测试可以从特定URL地址获取数据并将其作为String添加到ArrayList的方法。现在的代码:
public List<String> getListOfAirportsFromCsvAsAStrings(String urlAddress) {
BufferedReader reader = null;
try {
URL url = new URL(urlAddress);
HttpURLConnection connection = (HttpURLConnection) url.openConnection();
connection.setRequestMethod("GET");
reader = new BufferedReader(new InputStreamReader(connection.getInputStream()));
String line = null;
while ((line = reader.readLine()) != null) {
airportsAsAStringFromCsvFile.add(line);
}
} catch (Exception e) {
e.printStackTrace();
} finally {
if (reader != null) {
try {
reader.close();
} catch (IOException ioe) {
ioe.printStackTrace();
}
}
}
return airportsAsAStringFromCsvFile;
}
这种方法可以测试吗?
答案 0 :(得分:1)
原样,这种方法很难测试。显然,这不是以TDD方式完成的,正如标签所示。
不要在测试代码中创建HttpURLConnection。让调用者通过一个。这样你就可以在测试中轻松地模拟它并传递看起来像网络连接但不是真实的东西。保持外部依赖关系,如单元测试中的网络。在生产代码中,如果在一个地方创建连接,则可以轻松添加连接池或其他连接详细信息。
不要吞下异常。任何错误都会被忽视。几小时的调试乐趣。你甚至无法测试错误行为。
airportsAsAStringFromCsvFile
是成员变量吗?它可能应该是一个局部变量,你可以使你的函数静态。
您可能还想尝试使用资源。
至于TDD书籍,您可以尝试:
JUnit Recipes ---很老了,但可能还有一些好的指针
答案 1 :(得分:1)
这是不能正确测试单元的坏代码,单元测试是关于测试一些代码&#34; unit&#34;通常是隔离的类,如果这个代码需要其他类来工作,你需要使用模拟类而不是真正的实现。
在您的情况下,您应该将从网络中读取的代码与从网络中读取的代码分离。
public class Parser {
public List<String> getListOfAirportsFromCsvAsAStrings(InputStream inputCsvData) {
List<String> airportsAsAStringFromCsvFile = new ArrayList<>();
try (BufferedReader reader = new BufferedReader(new InputStreamReader(inputCsvData))) {
String line = null;
while ((line = reader.readLine()) != null) {
airportsAsAStringFromCsvFile.add(line);
}
} catch (IOException e) {
throw new RuntimeException(e);
}
return airportsAsAStringFromCsvFile;
}
}
我简化了你的代码(需要java 7或更高版本)。这是解析器的测试类:
import example.Parser;
import org.junit.Assert;
import org.junit.Test;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.util.Arrays;
import java.util.List;
public class ParserTest {
@Test
public void shouldReturnParsedTextFromInputFileStream() throws Exception {
String text = "row1\nrow2\nrow3";
InputStream inputFileStream = new ByteArrayInputStream(text.getBytes());
Parser parser = new Parser();
List<String> result = parser.getListOfAirportsFromCsvAsAStrings(inputFileStream);
List<String> expected = Arrays.asList("row1", "row2", "row3");
Assert.assertEquals(expected, result);
}
}
假设您的类路径中有 junit 库。 附:在我看来,这段代码仍然有异味,你需要更多重构你的代码。