测试高阶函数scala + Cats资源

问题描述 投票:0回答:1

我有一个问题。我将以下功能与Scala猫库一起使用。

 def process(
      client: Resource[IO, HttpClient] = HttpClientFactory.createClient()
  ): IO[Long] =
    client.use(httpClient => {
      for {
        files <- IO { getFiles() }
        placeMarkers <- IO { sendFile(client) }
      } yield placeMarkers
    })

现在,我想使用单元测试来测试此代码,并且我想模拟httpClient。我正在尝试类似的方法,但是它不起作用:

val resourceIOMock = mock[Resource[IO, HttpClient]]
val httpMock = mock[HttpClient]

doReturn(httpMock).when(resourceIOMock).use(any())

由于Mathcers any(),这不起作用。我真的不知道如何将模拟传递到那里,然后可以根据需要进行配置。从我看来,代码永远不会进入for循环。有人可以帮忙吗?Thx

scala unit-testing mockito scala-cats
1个回答
0
投票

为什么需要模拟Resource?您几乎可以做类似的事情:

// given
val client = mock[HttpClient]
val clientResource = Resource.make[IO, HttpClient](IO.pure(client))(_ => IO.unit)
doReturn(client).when(methodUsedInTest).use(...)

// when
val result = process(clientResource).runSync

// then
assert(...)

[如果您使用IO构建纯值,则当您拥有相当不错的工厂方法时,尤其是因为IO是数据,当为它们创建值时,它们就不会产生副作用,只有在以下情况下,它们才会产生副作用:您解释它(您不能对每个随机Java类都这么说)。

因此,模拟IO,资源,引用与模拟案例类或List / Option / Vector / Set / containers一般意义不大。如果将函数作为参数传递,则相同-为什么仅传递实现就进行模拟?资源只是一对acquirerelease函数。您可以比嘲笑它们更快地实现它们。

© www.soinside.com 2019 - 2024. All rights reserved.