为什么参数可以接受类型类的任何构造,但是其值不能有条件地构造?

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

我对Haskell还是相当陌生,尽管不是编程人员,并且我一直在使用req library执行HTTPS请求。

[为了保留一些通用性,将有两种类型的请求-一种是创建文档(通过HTTP POST),另一种是更新文档(通过HTTP PATCH,使用updateMask参数中的非空monoid) )。

我可以从updateMask == mempty是否推断出HTTP动词,但这不会编译,因为POSTPOST是不同的PATCH声明(尽管两者都可以作为PATCH的第一个参数有效) data的实例。

req

如果我将HttpMethodHttpMethod之一替换为getSaveEventRequestResponse :: Text -> Option Https -> Document -> IO IgnoreResponse getSaveEventRequestResponse authToken updateMask document = runReq defaultHttpConfig $ req (if updateMask == mempty then POST else PATCH) (https "test.example.com" /: "api" /: "projects" /: "myproject") (ReqBodyJson document) ignoreResponse $ oAuth2Bearer (encodeUtf8 authToken) <> updateMask 条件,则代码将正确编译。

有没有一种方法可以使编译器允许此条件响应,或者我必须复制此函数,一种使用if变体,另一种使用POST


Edit,以使任何尝试使用相同代码的人受益:

我使用的条件(PATCH)在这里实际上无效,但这与问题无关。问题在于是否将此条件替换为POSTPATCH


Edit 2关于链接的问题。虽然我现在已经获得了答案,但是看到它有多紧密的联系,这取决于已经考虑了部分应用程序。尽管原理相同,但是引入部分应用程序使Haskell的初学者很难将答案应用于此上下文。

haskell types typeclass haskell-req
1个回答
8
投票

可能的解决方法是使用

updateMask == mempty

这是因为

True

现在,False(if updateMask == mempty then req POST else req PATCH) other args here 相等,因为两者均定义为req :: (MonadHttp m, HttpMethod method, HttpBody body, HttpResponse response, HttpBodyAllowed (AllowsBody method) (ProvidesBody body)) => method -> Url scheme -> body -> Proxy response -> Option scheme -> m response 。因此,AllowsBody POSTAllowsBody PATCH可以共享一个公共类型:

'CanHaveBody

具有相同的类型,它们可以在相同的req POST的两个分支中使用。

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