2011-08-28 29 views
21

Có điều gì đó trong Scalatest sẽ cho phép tôi kiểm tra đầu ra theo tiêu chuẩn thông qua tuyên bố println không?Scalatest - cách kiểm tra println

Cho đến nay tôi chủ yếu sử dụng FunSuite with ShouldMatchers.

ví dụ: làm cách nào để chúng tôi kiểm tra đầu ra được in của

object Hi { 
    def hello() { 
    println("hello world") 
    } 
} 

Trả lời

24

Cách thông thường để kiểm tra báo cáo in trên bảng điều khiển là cấu trúc chương trình của bạn hơi khác để bạn có thể chặn các câu lệnh đó. Bạn có thể ví dụ như giới thiệu một Output đặc điểm:

trait Output { 
    def print(s: String) = Console.println(s) 
    } 

    class Hi extends Output { 
    def hello() = print("hello world") 
    } 

Và trong các thử nghiệm của bạn, bạn có thể xác định đặc điểm khác MockOutput thực sự chặn các cuộc gọi:

trait MockOutput extends Output { 
    var messages: Seq[String] = Seq() 

    override def print(s: String) = messages = messages :+ s 
    } 


    val hi = new Hi with MockOutput 
    hi.hello() 
    hi.messages should contain("hello world") 
+0

Bạn cần phải thêm 'override' vào MockOutput –

+0

Tôi thích giải pháp này rất nhiều, @Eric là có một cách để làm điều này mà không cần phải mở rộng' Output'. Tôi cảm thấy 'mở rộng' một đặc điểm, nơi mà đặc điểm đó là không cần thiết ngay từ đầu, là một hack. Nó sẽ có ý nghĩa nếu các đặc điểm đã được cần thiết và chúng tôi tạo ra một thử nghiệm impl. –

+3

Cách duy nhất để tránh mở rộng một đặc điểm là làm những gì mà Kevin hoặc Matthieu đang tư vấn. Điều đó đang được nói, tôi có triết lý xây dựng phần mềm của bạn để nó có thể kiểm tra được là một quyết định thiết kế tốt. Khi bạn theo đuổi ý nghĩ đó, bạn đi tất cả các cách để giới thiệu các đặc điểm cho * tất cả * các tương tác hệ thống IO/bên ngoài của bạn. – Eric

2

Bạn có thể thay thế nơi println ghi vào bằng cách sử dụng Console.setOut (PrintStream)

val stream = new java.io.ByteArrayOutputStream() 
Console.setOut(stream) 
println("Hello world") 
Console.err.println(stream.toByteArray) 
Console.err.println(stream.toString) 

Bạn rõ ràng có thể sử dụng bất kỳ loại luồng nào bạn muốn. Bạn có thể làm cùng một loại điều cho stderr và stdin với

Console.setErr(PrintStream) 
Console.setIn(PrintStream) 
+1

Lưu ý rằng 'Console. {setErr, setIn, setOut}' đã không được chấp nhận là 2.11.0 (~ 3 năm sau khi câu trả lời này được gửi). –

+0

Các phương pháp mới là Bảng điều khiển. {WithOut, withIn, withErr} – Zee

57

Nếu bạn chỉ muốn chuyển hướng điều khiển đầu ra cho một khoảng thời gian hạn chế, sử dụng withOutwithErr phương pháp xác định trên Console:

val stream = new java.io.ByteArrayOutputStream() 
Console.withOut(stream) { 
    //all printlns in this block will be redirected 
    println("Fly me to the moon, let me play among the stars") 
} 
+0

Điểm tốt, tôi quên mất điều đó. – Eric

+3

Đây là cách tốt hơn, không cần phải tái cơ cấu chương trình của bạn để kiểm tra. – incarnate

Các vấn đề liên quan