使用系统规则测试System.in和System.out
編寫單元測試是軟件開發的組成部分。 當您的被測類與操作系統交互時,您必須解決的一個問題是模擬其行為。 這可以通過使用模擬代替Java Runtime Environment(JRE)提供的實際對象來完成。 支持Java的模擬的庫是例如嘲笑或jMock 。
當您完全控制對象的實例化時,模擬對象是一件好事。 在處理標準輸入和標準輸出時,這有點棘手,但并非不可能,因為java.lang.System允許您替換標準InputStream和OutputStream 。
為了不必在每個測試用例前后都手動替換流,可以使用org.junit.rules.ExternalResource 。 此類提供了兩個方法before()和after() ,就像它們的名稱所暗示的那樣,在每個測試用例之前和之后調用。 這樣,您可以輕松地設置和清除一類中所有測試所需的資源。 或者,回到原始問題,替換java.lang.System的輸入和輸出流。
我上面所描述的完全由庫system-rules實現 。 要查看其工作原理,讓我們從一個簡單的示例開始:
public class CliExample {private Scanner scanner = new Scanner(System.in, "UTF-8");public static void main(String[] args) {CliExample cliExample = new CliExample();cliExample.run();}private void run() {try {int a = readInNumber();int b = readInNumber();int sum = a + b;System.out.println(sum);} catch (InputMismatchException e) {System.err.println("The input is not a valid integer.");} catch (IOException e) {System.err.println("An input/output error occurred: " + e.getMessage());}}private int readInNumber() throws IOException {System.out.println("Please enter a number:");String nextInput = scanner.next();try {return Integer.valueOf(nextInput);} catch(Exception e) {throw new InputMismatchException();}} }上面的代碼從標準輸入中讀取兩個整數,并打印出其總和。 如果用戶提供了無效的輸入,則程序應在錯誤流上輸出適當的消息。
在第一個測試用例中,我們要驗證程序是否正確地將兩個數字求和并打印出結果:
public class CliExampleTest {@Rulepublic final StandardErrorStreamLog stdErrLog = new StandardErrorStreamLog();@Rulepublic final StandardOutputStreamLog stdOutLog = new StandardOutputStreamLog();@Rulepublic final TextFromStandardInputStream systemInMock = emptyStandardInputStream();@Testpublic void testSuccessfulExecution() {systemInMock.provideText("2\n3\n");CliExample.main(new String[]{});assertThat(stdOutLog.getLog(), is("Please enter a number:\r\nPlease enter a number:\r\n5\r\n"));}... }為了模擬System.in我們利用系統規則的TextFromStandardInputStream 。 通過調用emptyStandardInputStream()用一個空的輸入流初始化實例變量。 在測試用例本身中,我們通過在適當的位置調用帶有換行符的provideText()來為應用程序提供信息。 然后,我們調用應用程序的main()方法。 最后,我們必須斷言該應用程序已將兩個輸入語句和結果寫入標準輸入。 后者是通過StandardOutputStreamLog實例完成的。 通過調用其方法getLog()我們可以檢索在當前測試用例中已寫入標準輸出的所有內容。
StandardErrorStreamLog可以類似地用于驗證寫入標準錯誤的內容:
@Test public void testInvalidInput() throws IOException {systemInMock.provideText("a\n");CliExample.main(new String[]{});assertThat(stdErrLog.getLog(), is("The input is not a valid integer.\r\n")); }除此之外, system-rules還提供了使用System.getProperty() , System.setProperty() , System.exit()和System.getSecurityManager() 。
結論 :通過系統規則測試,帶有單元測試的命令行應用程序比使用junit的規則本身更加簡單。 每個測試用例前后的所有樣板代碼都在一些易于使用的規則之內,用于更新系統環境。
PS:您可以在此處找到完整的資源。
翻譯自: https://www.javacodegeeks.com/2015/01/testing-system-in-and-system-out-with-system-rules.html
總結
以上是生活随笔為你收集整理的使用系统规则测试System.in和System.out的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 意大利人口和面积 关于意大利人口和面积介
- 下一篇: Windows上的Oracle Java