2016-02-05 129 views
0

我似乎无法模拟Mockito上的void方法。它给出了一个未完成的残片在这里检测到的错误。这是我的班级文件。使用Mockito嘲笑void方法

package com.twu.biblioteca; 

import java.io.InputStream; 
import java.io.PrintStream; 
import java.util.InputMismatchException; 
import java.util.Scanner; 

public class BibliotecaApp { 

public static class IntegerAsker { 
    private final Scanner scanner; 
    private final PrintStream out; 

    public IntegerAsker(InputStream in, PrintStream out) { 
     scanner = new Scanner(in); 
     this.out = out; 
    } 

    public int ask(String message) { 
     out.print(message); 
     return scanner.nextInt(); 
    } 
} 

public static int numberOfBooks = 0; 

public static class book{ 
    int serialNo; 
    String name; 
    String author; 
    int publication; 
    int checkoutstatus; 

    book(){ 
     serialNo = -1; 
     name = null; 
     author = null; 
     publication = -1; 
     checkoutstatus = -1; 
    } 

    book(int serialNo,String name, String author, int publication){ 
     this.serialNo = serialNo; 
     this.name = name; 
     this.author = author; 
     this.publication = publication; 
     this.checkoutstatus=checkoutstatus = 1; 
    } 
} 

public static int getBoundIntegerFromUser(IntegerAsker asker,String message,int lowerBound,int upperBound) { 
    int input; 
    try 
    { 
     input = asker.ask(message); 
     while(input>upperBound || input<lowerBound) 
      input = asker.ask("Select a valid option! "); 
      return input; 

    } 
    catch(InputMismatchException exception) 
    { 
     System.out.print("You have selected an invalid option! "); 
    } 
    return -1; 
} 

public static book[] booksList = new book[20]; 


public static String welcome(){ 
    IntegerAsker asker = new IntegerAsker(System.in,System.out); 
    return "**** Welcome Customer! We are glad to have you at Biblioteca! ****"; 

} 

public static void addBooks(){ 
    book newBook1 = new book(1,"Head First Java","Bert Bates",2014); 
    booksList[1] = newBook1; 
    numberOfBooks += 1; 

    book newBook2 = new book(2,"1000 IT Quizzes","Dheeraj Malhotra",2009); 
    booksList[2] = newBook2; 
    numberOfBooks += 1; 

    book newBook3 = new book(3,"100 Shell Programs in Unix","Shivani Jain",2009); 
    booksList[3] = newBook3; 
    numberOfBooks += 1; 

} 

public static void mainMenu(IntegerAsker asker){ 

    System.out.println("1 " + "List Books"); 
    System.out.println("2" + " Checkout a Book"); 
    System.out.println("3 " + "Quit"); 
    int n = getBoundIntegerFromUser(asker,"Enter your choice. ",1,3); 
    mainMenuaction(n,asker); 
} 

public static void mainMenuaction(int n,IntegerAsker asker){ 
    if(n==1){ 
     showBooks(); 
     mainMenu(asker); 
    } 
    else if(n==2){ 
     checkout(asker); 
    } 
    else if(n==3){ 
     return; 
    } 
} 

public static void showBooks(){ 
    for(int i=1;i<=numberOfBooks;i++){ 
     if(booksList[i].checkoutstatus!=0) 
     System.out.println(booksList[i].serialNo + ".\t" + booksList[i].name + "\t" + booksList[i].author + "\t" + booksList[i].publication); 
    } 
} 

public static void checkout(IntegerAsker asker){ 
    int Input = asker.ask("Enter the serial numebr of the book that you want to checkout"); 
    if(booksList[Input]!=null){ 
     if(booksList[Input].checkoutstatus!=0){ 
      booksList[Input].checkoutstatus=0; 
      System.out.println("Thank you! Enjoy the book"); 
     } 
     else{ 
      System.out.println("That book is not available."); 
     } 
    } 
    else{ 
     System.out.println("That book is not available."); 
    } 

    mainMenu(asker); 

} 


public static void main(String[] args) { 
    System.out.println(welcome()); 
    addBooks(); 
    IntegerAsker asker = new IntegerAsker(System.in,System.out); 
    mainMenu(asker); 
} 
} 

而且在这里不用我的测试文件 -

package com.twu.biblioteca; 


import org.mockito.Mockito; 
import org.mockito.Mockito.*; 
import org.junit.Test; 
import static org.junit.Assert.assertEquals; 
import static org.mockito.Mockito.*; 


public class ExampleTest { 

BibliotecaApp test = Mockito.mock(BibliotecaApp.class); 

@Test 
public void welcometest() { 
    assertEquals("**** Welcome Customer! We are glad to have you at Biblioteca! ****",test.welcome()); 
} 

@Test 
public void addBooksTest(){ 
    test.addBooks(); 

    assertEquals("Head First Java",test.booksList[1].name); 
    assertEquals("Dheeraj Malhotra",test.booksList[2].author); 
    assertEquals(2009,test.booksList[3].publication); 
} 

@Test 
public void getBoundIntegerFromUserTest(){ 
    BibliotecaApp.IntegerAsker asker = mock(BibliotecaApp.IntegerAsker.class); 
    when(asker.ask("Enter your choice. ")).thenReturn(99); 
    when(asker.ask("Select a valid option! ")).thenReturn(1); 

    BibliotecaApp.getBoundIntegerFromUser(asker,"Enter your choice. ",1,2); 

    verify(asker).ask("Select a valid option! "); 
} 

@Test 
public void mainMenuTest(){ 
    BibliotecaApp.IntegerAsker asker = mock(BibliotecaApp.IntegerAsker.class); 

    when(asker.ask("Enter your choice. ")).thenReturn(3); 
    test.mainMenu(asker); 

    verify(test).mainMenuaction(1,asker); 
} 

@Test 
public void checkoutTest(){ 
    BibliotecaApp.IntegerAsker asker = mock(BibliotecaApp.IntegerAsker.class); 
    BibliotecaApp test = new BibliotecaApp(); 
    BibliotecaApp mock = spy(test); 
    when(asker.ask("Enter the serial numebr of the book that you want to checkout")).thenReturn(2); 
    Mockito.doNothing().when(mock).mainMenu(asker); 

    test.addBooks(); 
    test.checkout(asker); 


    assertEquals(0,test.booksList[2].checkoutstatus); 
} 
} 

有人能说出什么我做错了吗?

+0

的Mockito.doNothing()是我给出的行错误!不好意思! – Ritabrata

+1

可能的重复[如何使模拟无效方法与mockito](http://stackoverflow.com/questions/2276271/how-to-make-mock-to-void-methods-with-mockito) –

+1

请考虑更新让测试类和测试类尽可能小的问题(一个静态方法,一个测试用例)。这会让问题更容易回答。 – avandeursen

回答

2
/* system */ public static void mainMenu(IntegerAsker asker){ ... } 
/* test */ Mockito.doNothing().when(mock).mainMenu(asker); 

你的问题是不是嘲讽void方法,它是关于嘲讽static方法,这可以的Mockito做不到。在幕后,Mockito正在创建一个覆盖你的模拟/侦探类的覆盖(BibliotecaApp)以覆盖每个方法,但由于static方法不能以相同方式覆盖,所以Mockito不能更改mainMenu的行为 - 即使只是检测你是否在存根中调用它,这就是为什么这会显示为“未完成的存根”。

mainMenu中删除static修饰符,您将完成该障碍。


附注:你也监视一个类,但保持原来的。这在Mockito中并不是一个好主意:间谍实际上创建了对象的副本,所以如果您依赖的是适用于间谍的行为,则必须调用间谍的测试方法。 (这是为了避免在测试中间谍的原因之一:使用间谍可以模糊测试你的系统的行为和测试的Mockito的行为之间的界线)

BibliotecaApp test = new BibliotecaApp(); 
BibliotecaApp mock = spy(test); 
when(asker.ask("...")).thenReturn(2); 
Mockito.doNothing().when(mock).mainMenu(asker); 

test.addBooks();   // should be: mock.addBooks() 
test.checkout(asker);  // should be: mock.checkout(asker)