首頁  >  文章  >  後端開發  >  Golang 單元測試的簡單錯誤問題

Golang 單元測試的簡單錯誤問題

WBOY
WBOY轉載
2024-02-13 20:51:16602瀏覽

Golang 单元测试的简单错误问题

Golang單元測試是保證程式碼品質和功能正確性的重要手段,但在實務中,我們常常會遇到一些簡單的錯誤問題。在本文中,php小編子墨將為大家介紹一些常見的錯誤問題,以及如何解決它們。透過學習這些問題的解決方法,相信大家在進行Golang單元測試時能夠更順利地進行,並提升程式碼的品質和可靠性。

問題內容

我在嘗試測試此函數時遇到問題,但內部有錯誤。以下是我的 responsejson 函數,它不回傳錯誤,但發送回應 json。

func responsejson(w http.responsewriter, code int, message string) {
    jsonstatus := struct {
        code int `json:"code"`
        message string `json:"message"`
    }{
        message: message,
        code: code,
    }

    bs, err := json.marshal(jsonstatus);

    if err != nil {
        log.println("error in marshal json in responsejson: ", err)
        str := "internal server error. please contact the system administrator."
        io.writestring(w, str);
        return 
    } else {
        io.writestring(w, string(bs));
        return
    }
    
}

以下是我的單元測試程式碼,它創建了一個模擬 responsewriter,它能夠成功測試編寫器回應 json 的情況,沒有錯誤。由於我沒有在 responsejson() 函數中傳回錯誤類型,因此如何在 test_responsejson 函數中測試它,如下所示?

func test_responsejson(t *testing.t) {
    responsejsontests := []struct {
        testname string
        code int
        message string
        expectedjsonresponse string
    } {
        {"successful login", http.statusok, "successfully logged in!", `{"code":200,"message":"successfully logged in!"}`},
        {"existing username", http.statusbadrequest, "username already exists. please try again.", `{"code":400,"message":"username already exists. please try again."}`},
    }

    for _, e := range responsejsontests {
        // creating a mock responsewriter
        w := httptest.newrecorder()

        responsejson(w, e.code, e.message)

        // read the response body as a string
        body, _ := io.readall(w.result().body)
        actual := string(body)

        expected := e.expectedjsonresponse
        if actual != expected {
            t.errorf("%s: expected %s but got %s", e.testname, e.expectedjsonresponse, actual)
        }
    }
}

此外,我還建立了一個函數,它為 log.println() 內建函數產生實際的日誌輸出。我知道 log.println() 函數是內建函數,它不太可能失敗。但是,我希望在單元測試中實現 100% 的覆蓋率。請幫忙!謝謝:)

func GenerateLogOutput(message string, errorMessage string) string {
    // Create a new bytes.Buffer to capture the log output
    var buf bytes.Buffer

    // Redirect log output to a different destination set as a buffer
    // By default, log message are written to the standard error stream os.Stderr
    log.SetOutput(&buf)

    // Generate an error
    err := errors.New(errorMessage)

    w := httptest.NewRecorder()

    // Calling the function
    InternalServerError(w, message, err)
    actualOutput := buf.String()

    return actualOutput
}

解決方法

簡單地說,我們可以為 responsejson 函數編寫一個測試案例,如下所示。

func Test_ResponseJson(t *testing.T) {
    tests := []struct {
        Code        int
        Message     string
        ExpectedStr string
    }{
        {
            Code:        1,
            Message:     "sample message",
            ExpectedStr: "{\"code\":1,\"message\":\"sample message\"}",
        },
    }
    for _, test := range tests {
        w := httptest.NewRecorder()

        ResponseJson(w, test.Code, test.Message)

        res := w.Result()
        data, err := ioutil.ReadAll(res.Body)
        res.Body.Close()

        actualStr := string(data)

        assert.Nil(t, err, "Invalid test data")
        assert.Equal(t, actualStr, test.ExpectedStr)
    }
}

我們無法從 bs 取得錯誤,err := json.marshal(jsonstatus)json.marshal 函數可以傳回兩種類型的錯誤。

  1. unsupportedtypeerror(例如:通道、複合值和函數值)
  2. unsupportedvalueerror(例如:循環資料結構)

我們無法解析值來產生上述錯誤之一。我們正在解析具有支援的值和支援的類型的結構。因此,我們無法編寫 100% 覆蓋率的測試。

以上是Golang 單元測試的簡單錯誤問題的詳細內容。更多資訊請關注PHP中文網其他相關文章!

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