{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE RecordWildCards #-}
module Main (main) where
import Data.Char (isDigit)
import Data.Maybe (fromMaybe)
import Data.Monoid ((<>))
import Data.Text (Text)
import qualified Data.Text as T
import qualified JsonSpec
import qualified MainSpec
import Options.Applicative
import qualified PaymentsSpec
import qualified StickersSpec
import System.Environment (lookupEnv, withArgs)
import Test.Hspec
import qualified Text.PrettyPrint.ANSI.Leijen as PP
import qualified UpdatesSpec
import Web.Telegram.API.Bot
-- | Command line options for test suite
data Options = Options
{
opt_integration :: Bool -- ^ Run integration tests
, opt_chatId :: Maybe String -- ^ Id of a chat or of your bot
, opt_botName :: Maybe String -- ^ Bot name
, opt_hSpecOpts :: Maybe [String] -- ^ Command line options to pass to hSpec
}
options :: Parser Options
options = Options
<$> switch
( long "integration"
<> help "Run integration tests" )
<*> optional ( strOption
( long "chatid"
<> short 'c'
<> metavar "CHAT_ID"
<> help "Chat Id" ))
<*> optional ( strOption
( long "botname"
<> short 'b'
<> metavar "BOT_NAME"
<> help "Bot Name" ))
<*> optional ( some ( argument str
( metavar "HSPEC_ARGS"
<> help "Hspec arguments")))
main :: IO ()
main = do
tokenEnv <- lookupEnv "BOT_TOKEN"
paymentTokenEnv <- lookupEnv "PAYMENT_TOKEN"
Options{..} <- execParser opts
let integration = opt_integration
token = (\x -> Token ("bot" <> T.pack x)) <$> tokenEnv
paymentToken = T.pack <$> paymentTokenEnv
chatId = readChatId <$> opt_chatId
botName = T.pack <$> opt_botName
hspecArgs = fromMaybe [] opt_hSpecOpts
withArgs hspecArgs $ hspec (runSpec' integration token chatId botName paymentToken)
where opts = info (helper <*> options)
( fullDesc
<> progDescDoc description)
runSpec' :: Bool -> Maybe Token -> Maybe ChatId -> Maybe Text -> Maybe Text -> SpecWith ()
runSpec' integration token chatId botName paymentToken = do
describe "Unit tests" $
describe "Json tests" JsonSpec.spec
if integration then runIntegrationSpec token chatId botName paymentToken
else describe "Integration tests" $ it "skipping..." $
pendingWith "Use --integration switch to run integration tests"
runIntegrationSpec :: Maybe Token -> Maybe ChatId -> Maybe Text -> Maybe Text -> SpecWith ()
runIntegrationSpec (Just token) (Just chatId) (Just botName) (Just paymentToken) = do
describe "Main integration tests" $ MainSpec.spec token chatId botName
describe "Payments integration tests" $ PaymentsSpec.spec token chatId botName paymentToken
describe "Updates API spec" $ UpdatesSpec.spec token botName
describe "Stickers API spec" $ StickersSpec.spec token chatId botName
--describe "Inline integration tests" $ InlineSpec.spec token chatId botName
runIntegrationSpec _ _ _ _ = describe "Integration tests" $
fail "Missing required arguments for integration tests. Run stack test --test-arguments \"--help\" for more info"
description :: Maybe PP.Doc
description = Just $
(PP.text "Run the haskell-telegram-api tests")
PP.<$> ((PP.text "Running with stack: ") PP.<> (PP.text "stack test --test-arguments=\"--integration -c 1235122 -b MyTeleBot -- -m send\""))
PP.<$> ((PP.red . PP.text $ "WARNING: ") PP.<> (PP.text "the HSPEC_ARGS are optional but if present MUST be at the end and seperated from the other options with a -- "))
readChatId :: String -> ChatId
readChatId s@('@':_) = ChatChannel $ T.pack s
readChatId s | all isDigit s = ChatId (read s)
readChatId _ = error "ChatId must be either Integer or String in form '@channel'"