如何使用HSPEC测试是否执行了读取功能



我是Haskell的新手。

我写了以下代码,该代码将解析发送给脚本的参数;

module Billing.Options
  (
      GlobalOpts(..)
    , globalOptsParser
    , parseDb
  ) where
import Options.Applicative
import Options.Applicative.Simple
import Options.Applicative.Types
import System.FilePath.Posix
import Text.Regex.PCRE
-- ------------------------------------------------------------
data GlobalOpts = GlobalOpts
  {
    optDb          :: String,
    optSql         :: String
  } deriving Show
-- ------------------------------------------------------------
globalOptsParser :: Parser GlobalOpts
globalOptsParser = GlobalOpts
  <$> option (parseDb =<< readerAsk)
    (   long "db"
    <>  short 'd'
    <>  metavar "<DB name>"
    <>  help "dmt | report"
    )
  <*> option parseSql
    (   long "sql"
    <>  metavar "<SQL SELECT statement>"
    <>  help "sql select statement to use in order to generate JSON config file"
    )
-- ------------------------------------------------------------
matches :: String -> String -> Bool
matches = (=~)
-- ------------------------------------------------------------
parseDb :: String -> ReadM String
parseDb val = do
    if not (elem val ["dmt", "report"])
        then readerError $ "Unknown DB, '" ++ val ++ "'"
        else return val
-- ------------------------------------------------------------
parseSql :: ReadM String
parseSql = do
    val <- readerAsk
    if not (val `matches` "(?i)select .+ from .+")
        then readerError $ "Please provide a valid SQL SELECT statement"
        else return val
-- [EOF]

我想用HSPEC测试上面的" ParsedB"功能。我想确保指定未知数据库时将抛出"读取器"。因此,我想测试该功能调用 ParsedB"未知"产生一个"读取"呼叫,据我说一个例外。

我尝试了HSPEC应该插入功能,但它不起作用。似乎也不例外。ReaderRor的返回类型是" readm a"。在花了几天的时间阅读了《单调和读者》上,我仍然陷入困境(并且很困惑),不知道如何测试它以及是否有可能对其进行测试。当我搜索搜索时,找不到任何相关示例。

这是一些相关类型的信号:

parseDb :: String -> ReadM String
-- from Options.Applicative.Internal
runReadM :: MonadP m => ReadM a -> String -> m a
runP :: P a -> ParserPrefs -> (Either ParseError a, Context)

runReadMrunP的文档:(链接)

ParserPrefs只是一个简单的数据结构。

和这个类型:

 import Options.Applicative.Types
 import Options.Applicative.Internal
 parseDb :: String -> ReadM String
 parseDb val = do
     if not (elem val ["dmt", "report"])
         then readerError $ "Unknown DB, '" ++ val ++ "'"
         else return val
 foo :: (Either ParseError String, Context)     -- might be [Context] now
 foo =   runP (runReadM (parseDb "foo") "asd") opts
   where opts = ParserPrefs "suffix" False False False 80

评估fst foo返回:

*Main> fst foo
Left (ErrorMsg "Unknown DB, 'foo'")

update

这是如何测试 Parser,例如 globaloptsparser

import Options.Applicative.Common (runParser)
import Options.Applicative.Internal (runP)
bar = let mp = runParser AllowOpts globalOptsParser ["asd"]
          opts = ParserPrefs "suffix" False False False 80
      in fst $ runP mp opts

这里["asd"]是要测试的命令行参数。

检查ParserPrefs是您想要的 - 它们可以影响选项处理。

相关内容

  • 没有找到相关文章

最新更新