首頁  >  文章  >  後端開發  >  在迭代測試結構時使用errors.As(),將第二個參數傳回給errors.As 不應該是*error

在迭代測試結構時使用errors.As(),將第二個參數傳回給errors.As 不應該是*error

PHPz
PHPz轉載
2024-02-15 14:06:07440瀏覽

在迭代测试结构时使用errors.As(),将第二个参数返回给errors.As 不应该是*error

php小編草莓在迭代測試結構時發現了一個錯誤。使用errors.As()時,將第二個參數傳回給errors.As時應該是一個指向error的指針,而不是一個error。這個錯誤可能會導致程式出現異常或不正確的行為。所以使用errors.As()時,務必注意參數的類型,確保傳遞的是一個指向error的指針,以免引發問題。這個問題可能會在迭代測試結構時出現,因此在使用errors.As()時要特別注意。

問題內容

我目前正在為一個套件編寫一些單元測試,其中函數可以傳回多種類型的錯誤。我將結構定義為:

tests := []struct {
    name   string
    data   string
    url    string
    status int
}

並且想使用 errors.as() 在我測試的錯誤中尋找 test.err 。我在測試中使用的範例結構如下:

{
    name:   "url not available",
    err:    &url.error{},
    data:   srvdata,
    url:    "a",
    status: http.statusok,
},

我想將 errors.as 用於實作錯誤介面的不同結構類型。因此,正如您在結構中看到的那樣,我將 err 定義為錯誤。可以看出,我使用 &url.error{} ,它應該實作錯誤介面。

t.run(test.name, func(t *testing.t) {
    data, err := i.getid(url)
    if err != nil {
        require.notnil(t, test.err)
        assert.true(t, errors.as(err, &test.err))
    } else {
        // ...
    }
})

但是,如上所述使用 errors.as 傳回

second argument to errors.As should not be *error

現在據我了解,errors.as() 接受 any 作為第二個參數,所以我很困惑為什麼不能使用 *error。

我還嘗試將測試結構中的 err 欄位更改為 interface{} ;然而,這樣做會使所有斷言通過,無論目標是否存在於錯誤中。

我找不到如何使用errors.as() 來實現以與上面類似的方式實現錯誤介面的不同類型的解決方案,所以現在我依靠使用contains() 來代替。想知道是否有人可以提供一些見解。

解決方法

指向錯誤類型的指標不滿足error 接口,這就是為什麼as 的第二個參數的類型為any。為了將您想要的類型直接儲存在 .err 欄位中,該欄位也必須是 any 類型。

但是,由於您已將此指標值包裝在介面中,因此您將需要使用類型斷言或反射來取得該值以供檢查:

var testErr any = new(*url.Error)
_, err := http.Get("http://error.error/")

if errors.As(err, testErr) {
    fmt.Println(reflect.ValueOf(testErr).Elem())
}

以上是在迭代測試結構時使用errors.As(),將第二個參數傳回給errors.As 不應該是*error的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文轉載於:stackoverflow.com。如有侵權,請聯絡admin@php.cn刪除