@@ -22,6 +22,7 @@ module Aws.Core
2222, HeaderException (.. )
2323, FormException (.. )
2424, NoCredentialsException (.. )
25+ , throwStatusCodeException
2526 -- ** Response deconstruction helpers
2627, readHex2
2728 -- *** XML
@@ -111,8 +112,10 @@ import qualified Data.ByteString.UTF8 as BU
111112import Data.Char
112113import Data.Conduit (($$+-) )
113114import qualified Data.Conduit as C
115+ #if MIN_VERSION_http_conduit(2,2,0)
116+ import qualified Data.Conduit.Binary as CB
117+ #endif
114118import qualified Data.Conduit.List as CL
115- import Data.Default (def )
116119import Data.IORef
117120import Data.List
118121import qualified Data.Map as M
@@ -130,14 +133,13 @@ import qualified Network.HTTP.Types as HTTP
130133import System.Directory
131134import System.Environment
132135import System.FilePath ((</>) )
133- #if MIN_VERSION_time(1,5,0)
134- import Data.Time.Format
135- #else
136+ #if !MIN_VERSION_time(1,5,0)
136137import System.Locale
137138#endif
138139import qualified Text.XML as XML
139140import qualified Text.XML.Cursor as Cu
140141import Text.XML.Cursor hiding (force , forceM )
142+ import Prelude
141143-------------------------------------------------------------------------------
142144
143145-- | Types that can be logged (textually).
@@ -201,14 +203,15 @@ class Monoid (ResponseMetadata resp) => ResponseConsumer req resp where
201203 -- metadata type for each AWS service.
202204 type ResponseMetadata resp
203205
204- -- | Response parser. Takes the corresponding request, an 'IORef'
205- -- for metadata, and HTTP response data.
206- responseConsumer :: req -> IORef (ResponseMetadata resp ) -> HTTPResponseConsumer resp
206+ -- | Response parser. Takes the corresponding AWS request, the derived
207+ -- @http-client@ request (for error reporting), an 'IORef' for metadata, and
208+ -- HTTP response data.
209+ responseConsumer :: HTTP. Request -> req -> IORef (ResponseMetadata resp ) -> HTTPResponseConsumer resp
207210
208211-- | Does not parse response. For debugging.
209212instance ResponseConsumer r (HTTP. Response L. ByteString ) where
210213 type ResponseMetadata (HTTP. Response L. ByteString ) = ()
211- responseConsumer _ _ resp = do
214+ responseConsumer _ _ _ resp = do
212215 bss <- HTTP. responseBody resp $$+- CL. consume
213216 return resp
214217 { HTTP. responseBody = L. fromChunks bss
@@ -317,8 +320,8 @@ loadCredentialsFromEnv = liftIO $ do
317320 Traversable. sequence $ makeCredentials' <$> keyID <*> secret
318321
319322loadCredentialsFromInstanceMetadata :: MonadIO io => io (Maybe Credentials )
320- loadCredentialsFromInstanceMetadata = liftIO $ HTTP. withManager $ \ mgr ->
321- do
323+ loadCredentialsFromInstanceMetadata = do
324+ mgr <- liftIO $ HTTP. newManager HTTP. tlsManagerSettings
322325 -- check if the path is routable
323326 avail <- liftIO $ hostAvailable " 169.254.169.254"
324327 if not avail
@@ -462,7 +465,7 @@ queryToHttpRequest :: SignedQuery -> IO (HTTP.Request (C.ResourceT IO))
462465#endif
463466queryToHttpRequest SignedQuery {.. } = do
464467 mauth <- maybe (return Nothing ) (Just <$> ) sqAuthorization
465- return $ def {
468+ return $ HTTP. defaultRequest {
466469 HTTP. method = httpMethod sqMethod
467470 , HTTP. secure = case sqProtocol of
468471 HTTP -> False
@@ -494,7 +497,11 @@ queryToHttpRequest SignedQuery{..} = do
494497 _ -> HTTP. RequestBodyBuilder 0 mempty
495498
496499 , HTTP. decompress = HTTP. alwaysDecompress
497- , HTTP. checkStatus = \ _ _ _ -> Nothing
500+ #if MIN_VERSION_http_conduit(2,2,0)
501+ , HTTP. checkResponse = \ _ _ -> return ()
502+ #else
503+ , HTTP. checkStatus = \ _ _ _-> Nothing
504+ #endif
498505
499506 , HTTP. redirectCount = 10
500507 }
@@ -792,6 +799,24 @@ newtype NoCredentialsException = NoCredentialsException { noCredentialsErrorMess
792799
793800instance E. Exception NoCredentialsException
794801
802+ -- | A helper to throw an 'HTTP.StatusCodeException'.
803+ throwStatusCodeException :: HTTP. Request
804+ -> HTTP. Response (C. ResumableSource (ResourceT IO ) ByteString )
805+ -> ResourceT IO a
806+ #if MIN_VERSION_http_conduit(2,2,0)
807+ throwStatusCodeException req resp = do
808+ let resp' = fmap (const () ) resp
809+ -- only take first 10kB of error response
810+ body <- HTTP. responseBody resp C. $$+- CB. take (10 * 1024 )
811+ let sce = HTTP. StatusCodeException resp' (L. toStrict body)
812+ throwM $ HTTP. HttpExceptionRequest req sce
813+ #else
814+ throwStatusCodeException _req resp = do
815+ let cookies = HTTP. responseCookieJar resp
816+ headers = HTTP. responseHeaders resp
817+ status = HTTP. responseStatus resp
818+ throwM $ HTTP. StatusCodeException status headers cookies
819+ #endif
795820
796821-- | A specific element (case-insensitive, ignoring namespace - sadly necessary), extracting only the textual contents.
797822elContent :: T. Text -> Cursor -> [T. Text ]
0 commit comments