module Freckle.App.Bugsnag.HttpException
  ( httpExceptionBeforeNotify

    -- * Re-exports
  , HttpException
  ) where

import Freckle.App.Prelude

import Data.Bugsnag (Exception (..))
import qualified Data.ByteString.Char8 as BS8
import Freckle.App.Exception.Types (AnnotatedException)
import qualified Freckle.App.Exception.Types as Annotated
import Network.Bugsnag
  ( BeforeNotify
  , setGroupingHash
  , updateEventFromOriginalException
  , updateExceptions
  )
import Network.HTTP.Client (HttpException (..), host, method)

httpExceptionBeforeNotify :: BeforeNotify
httpExceptionBeforeNotify :: BeforeNotify
httpExceptionBeforeNotify =
  forall e. Exception e => (e -> BeforeNotify) -> BeforeNotify
updateEventFromOriginalException @(AnnotatedException HttpException)
    (HttpException -> BeforeNotify
asHttpException (HttpException -> BeforeNotify)
-> (AnnotatedException HttpException -> HttpException)
-> AnnotatedException HttpException
-> BeforeNotify
forall b c a. (b -> c) -> (a -> b) -> a -> c
. AnnotatedException HttpException -> HttpException
forall exception. AnnotatedException exception -> exception
Annotated.exception)

asHttpException :: HttpException -> BeforeNotify
asHttpException :: HttpException -> BeforeNotify
asHttpException (HttpExceptionRequest Request
req HttpExceptionContent
content) =
  Text -> BeforeNotify
setGroupingHash (ByteString -> Text
decodeUtf8 (ByteString -> Text) -> ByteString -> Text
forall a b. (a -> b) -> a -> b
$ Request -> ByteString
host Request
req) BeforeNotify -> BeforeNotify -> BeforeNotify
forall a. Semigroup a => a -> a -> a
<> BeforeNotify
update
 where
  update :: BeforeNotify
update = (Exception -> Exception) -> BeforeNotify
updateExceptions ((Exception -> Exception) -> BeforeNotify)
-> (Exception -> Exception) -> BeforeNotify
forall a b. (a -> b) -> a -> b
$ \Exception
ex ->
    Exception
ex
      { exception_errorClass :: Text
exception_errorClass = Text
"HttpExceptionRequest"
      , exception_message :: Maybe Text
exception_message =
          Text -> Maybe Text
forall a. a -> Maybe a
Just
            (Text -> Maybe Text)
-> (ByteString -> Text) -> ByteString -> Maybe Text
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ByteString -> Text
decodeUtf8
            (ByteString -> Maybe Text) -> ByteString -> Maybe Text
forall a b. (a -> b) -> a -> b
$ Request -> ByteString
method Request
req
              ByteString -> ByteString -> ByteString
forall a. Semigroup a => a -> a -> a
<> ByteString
" request to "
              ByteString -> ByteString -> ByteString
forall a. Semigroup a => a -> a -> a
<> Request -> ByteString
host Request
req
              ByteString -> ByteString -> ByteString
forall a. Semigroup a => a -> a -> a
<> ByteString
" failed: "
              ByteString -> ByteString -> ByteString
forall a. Semigroup a => a -> a -> a
<> String -> ByteString
BS8.pack (HttpExceptionContent -> String
forall a. Show a => a -> String
show HttpExceptionContent
content)
      }
asHttpException (InvalidUrlException String
url String
msg) = (Exception -> Exception) -> BeforeNotify
updateExceptions ((Exception -> Exception) -> BeforeNotify)
-> (Exception -> Exception) -> BeforeNotify
forall a b. (a -> b) -> a -> b
$ \Exception
ex ->
  Exception
ex
    { exception_errorClass :: Text
exception_errorClass = Text
"InvalidUrlException"
    , exception_message :: Maybe Text
exception_message = Text -> Maybe Text
forall a. a -> Maybe a
Just (Text -> Maybe Text) -> Text -> Maybe Text
forall a b. (a -> b) -> a -> b
$ String -> Text
pack (String -> Text) -> String -> Text
forall a b. (a -> b) -> a -> b
$ String
url String -> String -> String
forall a. Semigroup a => a -> a -> a
<> String
" is invalid: " String -> String -> String
forall a. Semigroup a => a -> a -> a
<> String
msg
    }