Gomock无法将类型map[string]*mockFoo用作map[string]foo。

huangapple go评论101阅读模式
英文:

Gomock cannot use type map[string]*mockFoo as map[string]foo

问题

我正在使用gomock,并且我有这段示例代码需要进行测试。

  1. type StructA struct {
  2. client map[string]Foo
  3. }
  4. type Foo interface {
  5. methodFoo() string
  6. }
  7. func (a *StructA) MethodA(name string) string {
  8. client := a.client[name]
  9. return client.methodFoo()
  10. }

在我的测试中,我已经为Foo生成了一个名为mockFoo的模拟对象。我使用mockgen v1.6.0生成了Foo接口的模拟对象。

我的测试代码如下:

  1. func Test_MethodA(t *testing.T) {
  2. type fields struct {
  3. client map[string]*mockFoo
  4. }
  5. tests := []struct {
  6. fields fields
  7. want string
  8. }{
  9. // 测试用例
  10. }
  11. for _, tt := range tests {
  12. t.Run(tt.name, func(t *testing.T) {
  13. a := &StructA{
  14. client: tt.fields.client // 这里有一个错误,提示不能将map[string]*mockFoo作为map[string]Foo类型使用
  15. }
  16. ...
  17. })
  18. }
  19. }

简而言之,map[string]*mockFoo不能作为类型map[string]Foo使用。

  1. var foo1 Foo
  2. var mockFoo1 *mockFoo
  3. foo1 = mockFoo1 // 没问题
  4. var fooMap map[string]Foo
  5. var mockFooMap map[string]*mockFoo
  6. fooMap = mockFooMap // 有问题

请问我在这里做错了什么,还是这是预期的行为?谢谢。

英文:

I am using gomock, and I have this piece of example code that I wish to test.

  1. type StructA struct {
  2. client map[string]Foo
  3. }
  4. type Foo interface {
  5. foo.methodFoo() string
  6. }
  7. func (a *structA) MethodA(name string) string {
  8. client := a.client[name]
  9. return client.methodFoo()
  10. }

In my test, i've generated a mock for foo, called mockFoo. Used mockgen v1.6.0 to generate the mock for interface foo.

I have the test code as:

  1. func Test_MethodA(t *testing.T) {
  2. type fields struct {
  3. client map[string]*mockFoo
  4. }
  5. tests := []struct {
  6. fields fields
  7. want string
  8. }
  9. {
  10. // test cases
  11. }
  12. for _, tt := range tests {
  13. t.Run(tt.name, func(t *testing.T) {
  14. a := &StructA {
  15. client: tt.fields.client //this has an error, saying that we cannot use map[string]*mockFoo as the type map[string]foo
  16. }
  17. ...
  18. })
  19. }
  20. }

TLDR is that map[string]*mockFoo cannot be used as the type map[string]Foo.

  1. var foo1 Foo
  2. var mockFoo1 *mockFoo
  3. foo1 = mockFoo1 // no problem
  4. var fooMap map[string]Foo
  5. var mockFooMap map[string]*mockFoo
  6. fooMap = mockFooMap // problematic

May I know if I'm doing anything wrong here or if this an expected behaviour? Thanks.

答案1

得分: 2

根据你的描述,Foo 是一个接口,*mockFoo 实现了 Foo 接口。因此,每当需要一个 Foo 时,你可以使用 *mockFoo

类型 map[string]Foo 和类型 map[string]*mockFoo 是不同的。它们都是具体类型(不是接口),所以不能互相替换。

不过,你可以使用 map[string]Foo,并将 *mockFoo 的值放入该映射中。根据你的代码,这似乎是你应该做的。声明映射为 map[string]Foo,并在其中使用 *mockFoo 的值。如果你需要将映射的值作为 *mockFoo 引用,你可以使用类型断言来获取 *mockFoo 的值,例如:

  1. fooMap := map[string]Foo{}
  2. fooMap["key"] = mockFoo1
  3. ...
  4. value := fooMap["key"].(*mockFoo)
英文:

Based on your description, Foo is an interface, and *mockFoo implements the Foo interface. Thus, whenever a Foo is required, you can used *mockFoo.

The type map[string]Foo is not the same as the type map[string]*mockFoo. Both are concrete types (they are not interfaces), so you cannot substitute one for the other.

You can, however, use map[string]Foo, and put *mockFoo values into that map, and as far as I can see from your code, that's what you should do. Declare the map as map[string]Foo, and use *mockFoo values in it. If you need to refer to the values of the map as *mockFoo, you can type-assert the map value to get the *mockFoo value, that is:

  1. fooMap=map[string]Foo{}
  2. fooMap["key"]=mockFoo1
  3. ...
  4. value:=foomap["key"].(*mockFoo)

huangapple
  • 本文由 发表于 2021年10月7日 11:57:58
  • 转载请务必保留本文链接:https://go.coder-hub.com/69475278.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定