2012-01-31 21 views
8

Tôi đang viết bài kiểm tra đơn vị sử dụng Spock cho groovy-2.0 và sử dụng gradle để chạy. Nếu tôi viết sau khi vượt qua bài kiểm tra.Kiểm tra đơn vị Groovy2.0 với Spock: setup()

import spock.lang.Specification 

class MyTest extends Specification { 

    def "test if myMethod returns true"() {  
    expect: 
     Result == true; 
    where: 
     Result = new DSLValidator().myMethod() 

    } 
} 

myMethod() là một phương pháp đơn giản trong lớp DSLValidator, đơn giản trả về đúng.

Nhưng nếu tôi viết một hàm setup() và tạo ra các đối tượng trong setup(), thử nghiệm của tôi thất bại: Gradel nói: FAILED: java.lang.NullPointerException: Không thể gọi phương thức myMethod() trên đối tượng null

Sau đây là giao diện của thiết lập(),

import spock.lang.Specification 

class MyTest extends Specification { 

    def obj 

    def setup(){ 
    obj = new DSLValidator() 
    } 

    def "test if myMethod returns true"() {  
    expect: 
     Result == true; 
    where: 
     Result = obj.myMethod() 

    } 
}  

Ai đó có thể trợ giúp?

Dưới đây là giải pháp tôi đã đến vấn đề:

import spock.lang.Specification 

class DSLValidatorTest extends Specification { 

    def validator 

    def setup() { 
    validator = new DSLValidator() 
    } 


    def "test if DSL is valid"() { 

     expect: 
     true == validator.isValid() 
    } 
} 

Trả lời

20

Trong Spock đối tượng được lưu trữ vào instance fields không được chia sẻ giữa các phương pháp tính năng. Thay vào đó, mọi phương thức tính năng đều có đối tượng riêng của nó.

Nếu bạn cần chia sẻ đối tượng giữa các phương pháp tính năng, khai báo trường @Shared.

class MyTest extends Specification { 
    @Shared obj = new DSLValidator() 

    def "test if myMethod returns true"() {  
     expect: 
      Result == true 
     where: 
      Result = obj.myMethod() 
    } 
} 

class MyTest extends Specification { 
    @Shared obj 

    def setupSpec() { 
     obj = new DSLValidator() 
    } 

    def "test if myMethod returns true"() {  
     expect: 
      Result == true 
     where: 
      Result = obj.myMethod() 
    } 
} 

Có 2 phương pháp cố định cho việc thiết lập môi trường:

def setup() {}   // run before every feature method 
def setupSpec() {}  // run before the first feature method 

Tôi không hiểu tại sao ví dụ thứ hai với setupSpec() công trình và không thành công với setup() bởi vì trong documentation nói cách khác:

Lưu ý: Các phương thức setupSpec() và cleanupSpec() có thể không tham chiếu đến các trường thể hiện .

+0

Lạ ... Tài liệu Spock thực sự có thể làm với làm rõ về điều này ... Tôi sẽ không nói rằng obj đang được chia sẻ giữa các phương pháp tính năng, nhưng đang được thiết lập trước mỗi vật cố được gọi ... –

+5

Bạn không hiểu điều gì? Một @Shared field _is_ được chia sẻ giữa các phương thức tính năng và phải được thiết lập với một trình khởi tạo trường hoặc phương thức 'setupSpec'. 'setup' không phải là một lựa chọn tốt ở đây bởi vì nó được gọi sau khi khối' where' được đánh giá. –

+0

Cảm ơn bạn đã làm rõ –