我创建了一个Get函数,用于从postgres数据库获取练习.我写了模拟测试,但我从 struct 中得到了这个错误,我如何修复它呢?

我使用了处理程序 struct ,它有*Gorm.DB struct .

错误:

不能将moockDB(*MockDB类型的变量)用作 struct 文本中的*Gorm.DB值

// router
package exercises

import (
    "github.com/gin-gonic/gin"
    "gorm.io/gorm"
)

type Handlers struct {
    DB *gorm.DB
}

func RegisterRoutes(router *gin.Engine, db *gorm.DB) {
    h := &Handlers{
        DB: db,
    }

    routes := router.Group("/exercises")
    routes.POST("/", h.AddExercise)
    routes.GET("/", h.GetExercises)
    routes.GET("/:id", h.GetExercise)
    routes.PUT("/:id", h.UpdateExercise)
    routes.DELETE("/:id", h.DeleteExercise)
}

// test
package exercises

import (
    "net/http"
    "net/http/httptest"
    "testing"

    "github.com/gin-gonic/gin"
    "github.com/kayraberktuncer/sports-planner/pkg/common/models"
    "github.com/stretchr/testify/mock"
    "gorm.io/gorm"
)

type MockDB struct {
    mock.Mock
}

func (m *MockDB) Find(value interface{}) *gorm.DB {
    args := m.Called(value)
    return args.Get(0).(*gorm.DB)
}

func (m *MockDB) Error() error {
    args := m.Called()
    return args.Error(0)
}

func TestGetExercises(t *testing.T) {
    // Setup mock DB
    mockDB := new(MockDB)
    mockDB.On("Find", &[]models.Exercise{}).Return(mockDB).Once()

    // Setup Gin router
    router := gin.New()
    router.GET("/", func(c *gin.Context) {
        handlers := &Handlers{DB: mockDB} // error
        handlers.GetExercises(c)
    })

    // Perform request
    w := httptest.NewRecorder()
    req, _ := http.NewRequest("GET", "/", nil)
    router.ServeHTTP(w, req)

    // Assert response
    if w.Code != http.StatusOK {
        t.Errorf("Expected status code %d, got %d", http.StatusOK, w.Code)
    }

    // Assert mock DB was called correctly
    mockDB.AssertExpectations(t)
}

我想用我的处理程序 struct 进行模拟测试

推荐答案

MockDB和GORM的DB是两个不同的 struct ,不能互换使用.如果它们实现相同的接口,则可以在相同的位置使用它们.例如:

// router
package exercises

import (
    "github.com/gin-gonic/gin"
    "gorm.io/gorm"
)

// this interface will be implemented by gorm.DB struct
type Store interface {
    Create(value interface{}) *gorm.DB
    First(out interface{}, where ...interface{}) *gorm.DB
    Model(value interface{}) *gorm.DB
    Delete(value interface{}, where ...interface{}) *gorm.DB
    Find(out interface{}, where ...interface{}) *gorm.DB
    DB() *sql.DB
    Raw(sql string, values ...interface{}) *gorm.DB
    Exec(sql string, values ...interface{}) *gorm.DB
    Where(query interface{}, args ...interface{}) *gorm.DB
    //other method signatures
}

type Handlers struct {
    DB Store
}

func RegisterRoutes(router *gin.Engine, db Store) {
    h := &Handlers{
        DB: db,
    }

    routes := router.Group("/exercises")
    routes.POST("/", h.AddExercise)
    routes.GET("/", h.GetExercises)
    routes.GET("/:id", h.GetExercise)
    routes.PUT("/:id", h.UpdateExercise)
    routes.DELETE("/:id", h.DeleteExercise)
}

现在,您可以在代码中将*gorm.DB传递给RegisterRoutes函数.对于测试,如果您的MockDB struct 实现了来自Store接口的所有方法,则可以使用它.

Go相关问答推荐

如何存储来自异步Goroutine的返回值列表?

按键值排序字符串- Golang

go中跨域自定义验证的问题

Golang telegram 机器人

使用Go和Operator SDK通过API调用设置Kubernetes Pods的安装步骤

一个Go module可以和之前的非module模块发布在同一个路径下吗?

Kubo,来自 IpfsNode.Bootstrap 的无效内存地址或零指针取消引用

xml.Unmarshal 不支持的类型 struct

自定义 Fyne 自适应网格布局

Go 中如何调用测试函数?

有没有办法约束(通用)类型参数?

Gorm 预加载给出了模糊的列错误

如何在切片增长时自动将切片的新元素添加到函数参数

从 Makefile 运行时权限被拒绝

GqlGen - 在字段解析器中访问查询输入参数

Golang grpc go.mod 问题

如何在gorm中处理多个查询

Golang:每个键具有多个值的映射

golangci-lint 的 GitHub 操作失败,无法加载 fmt

Go:为一组单个结果实现 ManyDecode