如何在 golang 中模拟 request.Request

我正在使用github.com/aws/aws-sdk-go/aws/request获取预签名 URL,我需要将文件上传到 AWS 中的 s3 存储桶。我目前正在编写测试,为此我需要模拟func (r *Request) Presign(expire time.Duration)request.Request是一个结构,而不是一个接口,所以我不知道,我怎么能模拟它。



catspeake
浏览 156回答 3
3回答

精慕HU

这不是直接回答你的问题,但它可能会完全消除问题的基础。Go 中的一个巧妙之处在于,您可以使用接口轻松地隔离依赖项。如果您的代码,即您需要测试的部分,正在Presign间接使用,那么测试就很简单了。即创建一个界面type HigherLevelAws interface {    Upload(file string) error}并在您的代码中使用此接口以及Upload. 然后您可以使用例如https://godoc.org/github.com/stretchr/testify/mock轻松模拟它实际的实现看起来像这样type ActualAwsImpl struct {    aws *aws.Client}func (a *ActualAwsImpl) Upload(file string) error {    aws.Presign...}这允许您测试代码的业务部分,但当然,仍然会在ActualAwsImpl. 然而,这些未经测试的代码可以通过 aws sdk 本身的单元和集成测试来保证工作。无论哪种方式,在我的组织中,我们使用在 docker 中运行的假 aws 服务(例如https://github.com/gliffy/fake-s3)对此进行测试。

MMTTMM

我不得不模拟 S3 命令的请求。代码如下:req, result := r.s3.ListObjectsV2Request(&s3.ListObjectsV2Input{        Bucket: aws.String(configs.Settings.S3Bucket),    })    err := req.Send()Mock 函数必须返回一个请求对象func (m *mockS3ProviderClient) ListObjectsV2Request(input *s3.ListObjectsV2Input) (req *request.Request, output *s3.ListObjectsV2Output) {    err := input.Validate()    req = &request.Request{        HTTPRequest: &http.Request{},        Error:       err,    }    output = &s3.ListObjectsV2Output{        Contents: []*s3.Object{            {Key:aws.String("File1")},            {Key:aws.String("File2")},        },    }    return req, output}

慕容708150

您可以直接为该函数创建一个接口,如下所示:type presigner interface {    Presign(expire time.Duration) (string, error)}如果您在一个单独的函数中实现您的逻辑,该函数将 apresigner作为参数,如下所示(称为依赖注入):func Upload(p presigner, files string) error {    // ...    res, err := p.Presign(someduration)    if err != nil {        return err    }    // and so on}然后很容易在你的测试中模拟 - 只需实现presigner接口并让Presign函数返回你所期望的:type presignerMock struct {}func (p *presignerMock) Presign(d time.Duration) (string, error) {    return "yay", nil}要测试不同的场景,您可以向 中添加字段presignerMock并在您的实现中返回它们:type presignerMock {    res string    err error}func (p *presignerMock) Presign(d time.Duration) (string, error) {    return p.res, p.err}
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Go