我正在使用smallcheck
进行第一部分实际工作,并且对如何使用Depth
参数有些困惑。在开始之前,请先说明一下我使用smallcheck
的目的。
在工作中,我们正在自己的内部数据库之前构建一个简单的Web服务。 Web服务执行一些查询,并以序列化为JSON的查询结果作为响应。目前,我正在做的保证是:给定一个表示查询结果的对象,该对象将产生预期的JSON。例如:
data Action
= Action { actionType :: !ActionType
, actionDescription :: !Text
, actionPerformedAt :: !UTCTime
, actionAgentName :: !Text
}
必须产生JSON,例如:
{
"type": "Booking",
"description": "Whatever",
"performedAt": "2012-01-04",
"agent": "Tom"
}
对于
smallcheck
来说,这看起来像是一项理想的任务,我将其表述为:testAction :: Tasty.TestTree
testAction = Tasty.testGroup "Action"
[ SmallCheck.testProperty "type" $
SmallCheck.over actions $ match $
Aeson.key "type" --> Aeson.toJSON . actionType
, SmallCheck.testProperty "dateActioned" $
SmallCheck.over actions $ match $
Aeson.key "dateActioned" --> expectedUTCTimeEncoding . actionPerformedAt
-- and so on
]
-- (-->) :: Eq a => lens-aeson traversal a -> (b -> a) -> b -> Bool
-- actions :: Monad m => SmallCheck.Series m Action
smallcheck
框架中默认的tasty
深度为5,这导致测试运行尚未完成。 smallcheck
具有changeDepth
和changeDepth1
函数,因此我可以将它们用作changeDepth (const 3)
以确保我的测试始终在合理的时间内运行。但是,这样做会让我不禁感到自己在某处错过了重点吗?例如,现在不可能仅通过更改命令行选项来运行测试来运行更长的测试,也许在一夜之间。另一方面,如果我使用changeDepth (- 2)
,仍然感觉好像我在假设测试的运行方式!也许最好假设全局测试深度为5,可以在n秒内运行,并且取决于每个属性是否根据需要调整深度?希望听到有关
smallcheck
的这一更实际方面的反馈。 最佳答案
尽管小支票的“穷尽性”(无论如何对于小情况而言)是一个吸引人的属性,但我还是建议在这种情况下进行快速支票。虽然JSON具有轻量级的结构,但从实际数据位的角度来看,它非常繁重。
测试时间也非常关键地取决于您如何在类型的Series实例中为smallcheck定义“大小”(深度)。如果您的类型有很多分支(许多构造函数),则测试数量将迅速增加。它是“深度”的指数,而指数的底数是与特定测试用例相关的Series实例中的分支数量。
换句话说,如果平均有2个构造函数,则要运行32个测试用例,而如果有20个,则更像是3200000。
但是,覆盖范围也会受到影响-如果您减少测试用例中的分支(使深度增加得更快),则在给定深度下覆盖范围会减少。使用quickcheck,您会损失一些“小的”测试用例,而倾向于对一些较大的示例进行采样,而这些示例是您使用smallcheck无法实现的。
关于haskell - 在smallcheck中应该控制多少个 `Depth`参数?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/20092191/