summaryrefslogtreecommitdiff
path: root/Data/GraphQL/Error.hs
diff options
context:
space:
mode:
Diffstat (limited to 'Data/GraphQL/Error.hs')
-rw-r--r--Data/GraphQL/Error.hs76
1 files changed, 38 insertions, 38 deletions
diff --git a/Data/GraphQL/Error.hs b/Data/GraphQL/Error.hs
index b19047b..08d1622 100644
--- a/Data/GraphQL/Error.hs
+++ b/Data/GraphQL/Error.hs
@@ -1,57 +1,57 @@
{-# LANGUAGE OverloadedStrings #-}
-{-# LANGUAGE TupleSections #-}
-module Data.GraphQL.Error (
- parseError,
- CollectErrsT,
- addErr,
- addErrMsg,
- runCollectErrs,
- joinErrs,
- errWrap
+module Data.GraphQL.Error
+ ( parseError
+ , CollectErrsT
+ , addErr
+ , addErrMsg
+ , runCollectErrs
+ , runAppendErrs
) where
import qualified Data.Aeson as Aeson
import Data.Text (Text, pack)
-
-import Control.Arrow ((&&&))
+import Control.Monad.Trans.Class (lift)
+import Control.Monad.Trans.State ( StateT
+ , modify
+ , runStateT
+ )
-- | Wraps a parse error into a list of errors.
parseError :: Applicative f => String -> f Aeson.Value
parseError s =
pure $ Aeson.object [("errors", Aeson.toJSON [makeErrorMsg $ pack s])]
--- | A wrapper for an 'Applicative' to pass error messages around.
-type CollectErrsT f a = f (a,[Aeson.Value])
-
--- | Takes a (wrapped) list (foldable functor) of values and errors,
--- joins the values into a list and concatenates the errors.
-joinErrs
- :: (Functor m, Functor f, Foldable f)
- => m (f (a,[Aeson.Value])) -> CollectErrsT m (f a)
-joinErrs = fmap $ fmap fst &&& concatMap snd
-
--- | Wraps the given 'Applicative' to handle errors
-errWrap :: Functor f => f a -> f (a, [Aeson.Value])
-errWrap = fmap (, [])
+-- | A wrapper to pass error messages around.
+type CollectErrsT m = StateT [Aeson.Value] m
-- | Adds an error to the list of errors.
-addErr :: Functor f => Aeson.Value -> CollectErrsT f a -> CollectErrsT f a
-addErr v = (fmap . fmap) (v :)
+addErr :: Monad m => Aeson.Value -> CollectErrsT m ()
+addErr v = modify (v :)
makeErrorMsg :: Text -> Aeson.Value
-makeErrorMsg s = Aeson.object [("message",Aeson.toJSON s)]
+makeErrorMsg s = Aeson.object [("message", Aeson.toJSON s)]
-- | Convenience function for just wrapping an error message.
-addErrMsg :: Functor f => Text -> CollectErrsT f a -> CollectErrsT f a
+addErrMsg :: Monad m => Text -> CollectErrsT m ()
addErrMsg = addErr . makeErrorMsg
--- | Runs the given query, but collects the errors into an error
--- list which is then sent back with the data.
-runCollectErrs :: Functor f => CollectErrsT f Aeson.Value -> f Aeson.Value
-runCollectErrs = fmap finalD
- where
- finalD (dat,errs) =
- Aeson.object
- $ if null errs
- then [("data",dat)]
- else [("data",dat),("errors",Aeson.toJSON $ reverse errs)]
+-- | Appends the given list of errors to the current list of errors.
+appendErrs :: Monad m => [Aeson.Value] -> CollectErrsT m ()
+appendErrs errs = modify (errs ++)
+
+-- | Runs the given query computation, but collects the errors into an error
+-- list, which is then sent back with the data.
+runCollectErrs :: Monad m => CollectErrsT m Aeson.Value -> m Aeson.Value
+runCollectErrs res = do
+ (dat, errs) <- runStateT res []
+ if null errs
+ then return $ Aeson.object [("data", dat)]
+ else return $ Aeson.object [("data", dat), ("errors", Aeson.toJSON $ reverse errs)]
+
+-- | Runs the given computation, collecting the errors and appending them
+-- to the previous list of errors.
+runAppendErrs :: Monad m => CollectErrsT m a -> CollectErrsT m a
+runAppendErrs f = do
+ (v, errs) <- lift $ runStateT f []
+ appendErrs errs
+ return v