2011-11-01 4 views
28

Tôi đang phát triển các thử nghiệm cho một ứng dụng. Có một phương thức có một mảng params làm tham số. Tôi đã thiết lập các phương pháp bằng cách sử dụng Moq nhưng khi tôi chạy thử nghiệm, giá trị trả về của phương thức là null, có nghĩa là nó không bị chế giễu.Phương pháp thiết lập với Params Array

Dưới đây là một mẫu mã:

public interface ITicketManager { 
    string GetFirstTicketInQueueIfMatches(params string[] ticketsToMatch); 
} 

public class TicketManager : ITicketManager { 
    private Queue<string> ticketQueue = new Queue<string>(); 

    public string GetFirstTicketInQueueIfMatches(params string[] ticketsToMatch) { 
     var firstQueuedTicket = ticketQueue.Peek(); 
     var firstQueuedTicketMatchesAnyOfRequested = ticketsToMatch.Any(t => t == firstQueuedTicket); 

     if(firstQueuedTicketMatchesAnyOfRequested) 
      return firstQueuedTicket; 

     return null; 
    } 
} 

Mã giả trông như thế này:

var mock = new Mock<ITicketManager>(); 

mock.Setup(m => m.GetFirstTicketInQueueIfMatches(It.IsAny<string>())) 
    .Returns(p => { 
    if(p.Contains("A")) 
      return "A"; 

    return null; 
}); 

Tại sao nó không bao giờ chạm phương pháp chế giễu?

Trả lời

50

Bạn đang cố gắng gọi một phương thức lấy một chuỗi, chứ không phải là một mảng. Hãy nhớ rằng đó là trình biên dịch C# xử lý phần params, chuyển đổi mã gọi mà chỉ định các giá trị riêng lẻ vào một cuộc gọi đi qua trong một mảng. Theo như phương pháp tự nó quan tâm, nó chỉ nhận được một mảng - và đó là những gì bạn đang chế giễu.

Trình biên dịch là thực chuyển mã của bạn vào:

mock.Setup(m => m.GetFirstTicketInQueueIfMatches 
         (new string[] { It.IsAny<string>() })) 

mà không phải là những gì bạn muốn.

Bạn nên sử dụng:

mock.Setup(m => m.GetFirstTicketInQueueIfMatches(It.IsAny<string[]>())) 

Nếu bạn cần phải xác minh rằng nó chỉ được cung cấp một giá trị duy nhất, bạn sẽ cần phải làm điều đó theo cách tương tự bạn sẽ cho một thông số không params.

Về cơ bản, params chỉ tạo sự khác biệt cho trình biên dịch C# - không phải là moq.

+0

@DiegoAC: Vâng, bạn đã có nó * có điều kiện * việc trở về của 'null' anyway. Bạn đã thử làm cho nó trở lại "Foo" thay vì nếu 'p' không chứa' "A" '? Bằng cách đó bạn ít nhất sẽ thấy nó được gọi ... –

+0

Câu trả lời tuyệt vời Jon. Cảm ơn. Thực ra tôi chỉ nhận được một chuỗi duy nhất. Giải thích về trình biên dịch rất hữu ích. –

9

Tôi tin rằng params string phải được kết hợp bởi It.IsAny<string[]>() hơn It.IsAny<string>()