2010-06-17 31 views
7

Tôi đang phát triển một ngôn ngữ theo định hướng dòng dữ liệu theo định hướng cụ thể. Để đơn giản hóa, chúng ta hãy nhìn vào các hoạt động. Các hoạt động có một số tham số được đặt tên và có thể được yêu cầu tính kết quả của chúng bằng trạng thái hiện tại của chúng.Các chiến lược để kiểm tra mã phản ứng, không đồng bộ

Để quyết định khi nào Chiến dịch sẽ tạo ra kết quả, nó sẽ có Quyết định nhạy cảm với thông số nào có giá trị từ ai. Khi Quyết định này quyết định rằng nó được hoàn thành, nó phát ra một tín hiệu bằng cách sử dụng một Observer.

Trình điều khiển truy cập lắng nghe tín hiệu này và lần lượt gọi phương thức kết quả của hoạt động để ghép kênh với thông số của các thao tác khác.

Cho đến nay, thiết kế tốt, độc đáo được tách rời, có thể tổng hợp và tái sử dụng và tùy thuộc vào Máy quan sát cụ thể được sử dụng, không đồng bộ như bạn muốn.

Bây giờ, đây là vấn đề của tôi: Tôi sẽ yêu để bắt đầu mã hóa Kiểm tra thực tế đối với thiết kế này. Nhưng với Observer không đồng bộ ...

  • làm cách nào tôi biết rằng toàn bộ đường ống tín hiệu và thông số đã hoạt động?
  • Tôi có cần sử dụng thời gian chờ trong khi chờ tín hiệu để nói rằng nó đã được phát hành thành công hay không?
  • Làm thế nào tôi có thể, chính thức, chắc chắn rằng tín hiệu sẽ không được phát ra nếu tôi chỉ cần chờ đợi lâu hơn một chút (vấn đề ngăn chặn? ;-))
  • Và, làm thế nào tôi có thể chắc chắn rằng tín hiệu được phát ra bởi vì nó là tôi, người đã đặt tham số và không phải là một Hoạt động khác? Nó cũng có thể là thử nghiệm của tôi đến sớm và thấy một tín hiệu đã được phát ra cách trước khi thiết lập một tham số của tôi gây ra một quyết định phát ra nó.

Hiện tại, tôi đoán các trường hợp tầm thường rất dễ kiểm tra, nhưng ngay sau khi tôi muốn thử nghiệm phức tạp nhiều - nhiều - tình huống giữa các hoạt động tôi phải sử dụng để hy vọng rằng thiết kế Just Works (tm). ..

chỉnh sửa (1):

Hãy xem xét các tình huống sau:

Hãy tưởng tượng trường hợp một Operation A cung cấp một giá trị cho hoạt động B1, B2 và B3, từng có một On-mỗi- Đầu vào-Quyết định (một trong đó là hoàn thành bất cứ khi nào bất kỳ tham số được cập nhật). Sau đó, có B1 và ​​B2 và B3, mỗi cung cấp giá trị của chúng cho cùng một tham số của một hoạt động C (để tổng hợp các giá trị này thành một bảng tra cứu hoặc một số giá trị như vậy).

Các bước dự định là:

  1. Một tín hiệu rằng nó có một giá trị mới (nhờ Quyết định của nó)
  2. Một thời gian sau, Observer không đồng bộ công văn Signal để bất cứ điều gì đăng ký
  3. Ah , một Accessor đã đăng ký.Gọi lại của nó được gọi, mà lần lượt lấy kết quả của hoạt động và ghép nó vào các tham số của B1, B2 và B3
  4. B1, B2 và B3 thông báo quyết định của chúng, điều này tạo ra ba tín hiệu mới cho người quan sát
  5. một thời gian sau, Observer không đồng bộ công văn tín hiệu B1, sau đó B2, sau đó B3
  6. Mỗi kết quả tín hiệu trong một accessor lấy kết quả của B1 (2, 3) và thức ăn nó vào C

Vì vậy, tôi biết rằng trong trường hợp này tôi có thể thử ví dụ Quyết định cho C để xem liệu nó có thực sự được thông báo về những gì B1, B2 và B3 đã làm hay không. Câu hỏi là: khi tôi có an toàn để kiểm tra điều này không?

Chỉnh sửa (2): Mục tiêu của tôi dường như giống như kiểm tra đầu cuối, tức là tập hợp các phần khác nhau của DSL và xem kết quả có hoạt động theo cách tôi mong đợi hay không.

Chỉnh sửa (3): Hóa ra tôi đã overcomplicating điều :-)

+1

Tôi đã không đề cập đến nó trong trả lời của tôi dưới đây, nhưng không sử dụng tính giờ trong các bài kiểm tra đơn vị nếu bạn có thể giúp nó. Tôi gặp phải các vấn đề lớn, như được mô tả ở đây: http://stackoverflow.com/questions/2997653/orchestrating-cancellation-in-long-running-unit-test –

+0

Không chắc chắn nếu bạn thấy câu trả lời của tôi cho bình luận của bạn, dưới đây. Hoặc có lẽ bạn đã giải quyết được vấn đề? –

Trả lời

2

Bạn cần đảm bảo rằng tất cả các thành phần khác nhau của bạn được giao tiếp, và sau đó kiểm tra từng lớp cụ thể tại một thời điểm, chế nhạo hoàn toàn mọi thứ khác.

Lưu ý: Lời giải thích này giả định rằng bạn đang sử dụng nguyên tắc đảo ngược phụ thuộc cũng như thư viện nhạo báng (như Rhino Mocks).

Bạn trạng:

Để quyết định khi nào một hoạt động nên sản xuất Kết quả là, nó được một Quyết định đó là nhạy cảm mà thông số có một giá trị từ ai. Khi điều này Quyết định quyết định rằng nó được đáp ứng, nó phát ra Tín hiệu bằng Trình quan sát.

Trình điều khiển truy cập lắng nghe tín hiệu này và lần lượt gọi phương thức kết quả là hoạt động để ghép kênh này với thông số của các thao tác khác.

Điều này nói với tôi rằng bạn sẽ xây dựng một Chiến dịch có IDecision bị loại bỏ. Thử nghiệm đơn vị của bạn sau đó có thể phối hợp hành vi của IDecision theo cách như vậy để thực hiện tất cả các tình huống có thể xảy ra mà một Chiến dịch có thể phải giải quyết. Tương tự, các kiểm tra Accessor của bạn có một IDecision giả lập được thiết lập để hoạt động theo kiểu thời trang thực tế để bạn có thể kiểm tra đầy đủ lớp Accessor một cách cô lập. Nó cũng có thể có một IOperation giả lập, và bạn có thể kiểm tra rằng Accessor của bạn gọi các phương thức thích hợp trên (các) đối tượng giả để đáp ứng với các kích thích mong muốn.

Tóm tắt: Kiểm tra từng lớp học của bạn riêng biệt, sử dụng các đối tượng giả mạo cho tất cả các phần khác để dàn xếp các hành vi thích hợp.

+0

Bạn nhẹ nhàng lướt qua phần Observer không đồng bộ :-) Tôi đã thêm một ví dụ hy vọng có thể sử dụng cho câu hỏi của mình. Có thực sự là một vấn đề tôi cần phải giải quyết hay tôi làm quá nhiều thứ? – Arne

+0

Hãy để tôi trả lời bằng một câu hỏi sẽ giúp tôi hiểu rõ hơn về nơi bạn đến từ: bạn có cố gắng kiểm tra từng lớp riêng lẻ hay kiểm tra sự tích hợp của tất cả các lớp đang hoạt động cùng nhau không? –

+0

Sau này, tôi đoán vậy. Vấn đề tôi thấy là thử nghiệm cô lập dường như đảm bảo chức năng phù hợp khi mọi thứ được đặt lại với nhau. – Arne

1

Tôi đã không được sử dụng điều này, nhưng tôi nghe Framework phản ứng có thể được sử dụng để biến sự kiện thành báo cáo LINQ - mà sau đó có thể được sử dụng để cho phép kiểm tra đơn vị dễ dàng.

Đây là cách tôi tin đơn vị kiểm tra rất nhiều mã Silverlight - tác động đến khung công tác Phản ứng được phân phối với Silverlight Toolkit (System.Reactive.dll).

+0

Các nhân viên Rx đã tuyên bố rằng họ đang thử nghiệm khung của họ với PEX. http://research.microsoft.com/en-us/projects/pex/ – dtb

+0

Các dsl không sử dụng các sự kiện để giao tiếp giữa các hoạt động nhưng một cách tiếp cận được tách rời hơn bằng cách sử dụng mẫu Signal/Observer. Nhưng cảm ơn cho gợi ý, có lẽ có một số sức mạnh tổng hợp tôi có thể nhận được ra khỏi khuôn khổ RX. – Arne

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