簡體   English   中英

Silverlight異步單元測試

[英]Silverlight async unit testing

我遇到了Silverlight Unit Test Framework的一個奇怪問題。 每次執行的第一個方法都失敗了。 我用完全相同的代碼進行了第二次測試,然后通過。 第一次調用它的奇怪之處在於它實際上等待超時然后執行存儲庫調用(如果你關心的話,它下面是一個HTTP PUT)。 這是代碼 - 第一個代碼每次都失敗,第二個代碼每次都會失敗:

    [TestMethod]
    public void AuthShouldSucceed()
    {
        var autoResetEvent = new AutoResetEvent(false);

        _authRepository.Authenticate(_username, _password, response =>
        {
            Assert.IsTrue(response);
            autoResetEvent.Set();
        });
        if (!autoResetEvent.WaitOne(Constants.Timeout))
        {
            Assert.Fail("Test timed out.");
        } 
    }

    [TestMethod]
    public void AuthShouldSucceed2()
    {
        var autoResetEvent = new AutoResetEvent(false);

        _authRepository.Authenticate(_username, _password, response =>
        {
            Assert.IsTrue(response);
            autoResetEvent.Set();
        });
        if (!autoResetEvent.WaitOne(Constants.Timeout))
        {
            Assert.Fail("Test timed out.");
        } 
    }

編輯:我的最終解決方案是對Vladmir解決方案的修改:

    [TestMethod]
    [Asynchronous]
    public void AuthShouldSucceed()
    {
        var complete = false;
        var result = false;

        _authRepository.Authenticate(_username, _password, response =>
        {
            complete = true;
            result = response;
        });

        EnqueueConditional(() => complete);
        EnqueueCallback(() => Assert.IsTrue(result));
        EnqueueTestComplete();
    }

如果您正在使用Silverlight Unit Tests Framework,請嘗試下一步重寫您的測試:

    [TestMethod]
    [Asynchronous]
    public void AuthShouldSucceed()
    {
        var done = false;
        var authResult = false;
        _authRepository.Authenticate(_username, _password, response =>
        {
            var done = true;
            authResult = response;
        });

        EnqueueConditional(() => done);
        EnqueueCallback(() => Assert.IsTrue(authResult));
        EnqueueTestComplete();
    }

您的測試類應該派生自SilverlightTest類:

[TestClass]
public class MyTests: SilverlightTest

總結所有書面文字,你應該知道編寫Silverlight單元測試的幾個要點。


[Asynchronous]
測試方法的屬性表明您正在測試包含異步操作的部分,並希望將它們同步以用於測試目的。 Silverlight單元測試框架中的異步本身有點失真。 所有“入隊”指令都是“推遲發生這種情況”,這不是傳統編程異步意義所具有的意義。


EnqueueConditional
其他詞表示等到條件滿足。 這是異步測試中最重要的部分之一。 后條件變為合法所有EnqueueCallbacks ,直到下一個EnqueueConditional將被執行。

重要的提示:

EnqueueConditional重復調用在計時器/后台線程EnqueueConditional它的謂詞,每次檢查它是否返回true。

這就是為什么你應該避免在條件下使用繁重,復雜的邏輯。


EnqueueCallback
推遲代碼執行,直到它之前的EnqueueConditional滿足條件。 它將Actoin或一系列Actions排入Actoin


EnqueueDelay
在繼續之前排隊最小毫秒數/時間延遲。


EnqueueTestComplete
排隊調用TestComplete的動作,該動作表示在使用異步測試時測試已完成。

重要說明(來自文檔):

如果您使用自己的方法來完成,例如HtmlTimer或其他線程方法,則在使用超時測試超時 ,此調用可能會發生。 因此,要非常小心,因為您可以完成對下一個測試的調用。

您可以在TestMethod中使用Asynchronous關鍵字

[TestMethod]
[Asynchronous]
[Description("This test checks when NULL is passed")]

public void Testing()
{
 bool done = false;
 EnvViewModel test = new EnvViewModel ();
 .
 .

 test.AsyncCallBackCompleted += (() => done = true);

 EnqueueCallback(() => test.DataCommand.Execute(null));
 EnqueueConditional(() => done);
 EnqueueCallback(() => Assert.IsTrue(test.AADTDecisionModelList.Count == 0, 
                                             "The result does not have any data."));

 EnqueueTestComplete();
}

並使ViewModel中的委托用於每個正在測試的方法...

public delegate void AsynCallComplete();
public event AsynCallComplete AsyncCallBackCompleted;
public void InformCallbackCompleted()
{
     if (AsyncCallBackCompleted != null)
     {
          AsyncCallBackCompleted();
     }
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM