我还是Haskell的新手,我很难找到函数的正确类型签名 .
我有这个工作,相当直接的功能使用 http-conduit
和 authenticate-oauth
这是副作用,所以我不太关心返回值:
executeOAuthRequest oauth cred request =
withManager $ \manager -> do
signed <- signOAuth oauth cred request
http signed manager
我想指定正确的类型签名,但GHCi的输出对我来说非常可怕:
executeOAuthRequest
:: (monad-control-0.3.2.3:Control.Monad.Trans.Control.MonadBaseControl
IO m,
Control.Monad.Trans.Resource.Internal.MonadThrow m,
Control.Monad.Trans.Resource.Internal.MonadUnsafeIO m,
Control.Monad.IO.Class.MonadIO m) =>
OAuth
-> Credential
-> Request
-> m (Response (ResumableSource (ResourceT m) ByteString))
前三个参数( OAuth
, Credential
, Request
)对我有意义,但我不理解 m
的长前提条件,并想知道是否有必要像GHCi建议的那样指定完整的返回值 .
我不想仅仅提供正确的签名,而是想了解查找和减少正确签名背后的过程 .
1 回答
GHCi为您提供了最多态的签名,读取“任何类型
m
,它是Monad.Trans.Resource.Internal
模块中MonadThrow
类的实例,MonadIO
等” . 类型检查器有点结合你在executeOAuthRequest
中编写的那些多态函数类型引入的所有约束 .这是一个简单的例子:
可能是满足函数中所有约束的唯一类型是
IO
,或者可能有几个 . 通常的检查方法是阅读黑线鳕,或者做例如:因此,如果你只在
IO
中使用你的函数,你可以给它类型:或者您可以保留多态签名,例如,如果您在库中导出此函数并认为您的用户可能希望在不同的monad中使用它(甚至可能通过定义自己的新类型并使其成为
MonadIO
的实例,MonadThrow
等)