我正在尝试使用Crypto.Gpgme来检查pgp签名。我有几个函数:
parseData signedData = do
res <- liftIO $ verifyPlain' "gpghome" (DBL.toStrict signedData) ""
case res of
Left err -> return $ Left $ errorString err
Right ((err, _, fg):xs, msg) -> case errorString err of
"Success" -> return $ Right (fg, msg)
_ -> return $ Left $ errorString err
parseRequest d = do
parsed <- parseData d
case parsed of
Left err -> throw $ UnknownError err
Right (fg, msg) -> return (fg, msg)这样,在Web.Scotty中,我就可以使用(fg, msg) <- parseRequest =<< body来获取签名密钥和签名消息的指纹(我使用指纹进行身份验证,而消息是实际的请求)。
这段代码不能工作,它会分段。我发现了一些有用的东西:
parseData signedData ctx = do
res <- verifyPlain ctx (DBL.toStrict signedData) ""
case res of
Left err -> return $ Left $ errorString err
Right ((err, _, fg):xs, msg) -> case errorString err of
"Success" -> return $ Right (fg, msg)
_ -> return $ Left $ errorString err
parseRequest d = do
parsed <- liftIO $ withCtx "gpghome" "C" OpenPGP $ parseData d
case parsed of
Left err -> throw $ UnknownError err
Right (fg, msg) -> return (fg, msg)所以这很好,我猜errorString访问Ctx是出于某种原因,不管是什么。现在我的实际问题是,这些代码只能运行一次。如果我尝试检查同一查询两次,第一次可以很好地工作,第二次给UnknownError "No public key",所以看起来parseRequest得到了一个没有充分理由的左。
我猜是库中有一个bug,它一定不能在请求之间正确地释放一些东西。我试着在我的main中分配一个ctx,并在所有地方使用那个ctx,但同样的错误。如果是我,你知道我做错了什么吗?如果是库,你知道如何修复或解决这个问题吗?
谢谢
发布于 2018-02-22 16:25:55
刚刚弄清楚这个问题,我在代码中的其他地方有一个setCurrentDirectory,路径变得无效。我猜Ctx必须存储gpghome的路径,而使用SetCurrentDirectory基本上会使Ctx无效。
verifyPlain仍然存在一个引起段错误的bug,但我会在github的问题上看看这个问题。
https://stackoverflow.com/questions/48908274
复制相似问题