packages feed

amazonka-core 0.3.6 → 1.0.0

raw patch · 72 files changed

+4097/−3637 lines, 72 filesdep +QuickCheckdep +cryptonitedep +exceptionsdep −base16-bytestringdep −base64-bytestringdep −cryptohashdep ~aesondep ~attoparsecdep ~bytestringPVP ok

version bump matches the API change (PVP)

Dependencies added: QuickCheck, cryptonite, exceptions, memory, quickcheck-unicode, tasty-quickcheck, xml-types

Dependencies removed: base16-bytestring, base64-bytestring, cryptohash, data-default-class, mmorph, vector

Dependency ranges changed: aeson, attoparsec, bytestring, case-insensitive, conduit, http-client, http-types, lens, time

API changes (from Hackage documentation)

- Network.AWS.Data: (.!=) :: Parser (Maybe a) -> a -> Parser a
- Network.AWS.Data: (.!@) :: Either String (Maybe a) -> a -> Either String a
- Network.AWS.Data: (.:) :: FromJSON a => Object -> Text -> Parser a
- Network.AWS.Data: (.:>) :: FromJSON a => Object -> Text -> Either String a
- Network.AWS.Data: (.:?) :: FromJSON a => Object -> Text -> Parser (Maybe a)
- Network.AWS.Data: (.:?>) :: FromJSON a => Object -> Text -> Either String (Maybe a)
- Network.AWS.Data: (.=) :: ToJSON a => Text -> a -> Pair
- Network.AWS.Data: (.@) :: FromXML a => [Node] -> Text -> Either String a
- Network.AWS.Data: (.@?) :: FromXML a => [Node] -> Text -> Either String (Maybe a)
- Network.AWS.Data: (=:) :: ToHeader a => HeaderName -> a -> [Header]
- Network.AWS.Data: (=?) :: ToQuery a => ByteString -> a -> Query
- Network.AWS.Data: (=@) :: ToXML a => Name -> a -> Node
- Network.AWS.Data: (~:) :: FromText a => ResponseHeaders -> HeaderName -> Either String a
- Network.AWS.Data: (~::) :: ResponseHeaders -> CI Text -> Either String (Map (CI Text) Text)
- Network.AWS.Data: (~:?) :: FromText a => ResponseHeaders -> HeaderName -> Either String (Maybe a)
- Network.AWS.Data: AWSFormat :: Format
- Network.AWS.Data: Base64 :: ByteString -> Base64
- Network.AWS.Data: BasicFormat :: Format
- Network.AWS.Data: EMap :: HashMap k v -> EMap k v
- Network.AWS.Data: ISO8601Format :: Format
- Network.AWS.Data: List :: [a] -> List a
- Network.AWS.Data: List1 :: NonEmpty a -> List1 a
- Network.AWS.Data: Map :: HashMap k v -> Map k v
- Network.AWS.Data: Nat :: Natural -> Nat
- Network.AWS.Data: POSIXFormat :: Format
- Network.AWS.Data: RFC822Format :: Format
- Network.AWS.Data: RqBody :: Digest SHA256 -> RequestBody -> RqBody
- Network.AWS.Data: RsBody :: (ResumableSource (ResourceT IO) ByteString) -> RsBody
- Network.AWS.Data: Sensitive :: a -> Sensitive a
- Network.AWS.Data: Time :: UTCTime -> Time a
- Network.AWS.Data: _EMap :: (Coercible a b, Coercible b a) => Iso' (EMap e i j k a) (HashMap k b)
- Network.AWS.Data: _List :: (Coercible a b, Coercible b a) => Iso' (List e a) [b]
- Network.AWS.Data: _List1 :: (Coercible a b, Coercible b a) => Iso' (List1 e a) (NonEmpty b)
- Network.AWS.Data: _Map :: (Coercible a b, Coercible b a) => Iso' (Map k a) (HashMap k b)
- Network.AWS.Data: _Nat :: Iso' Nat Natural
- Network.AWS.Data: _RsBody :: Iso' RsBody (ResumableSource (ResourceT IO) ByteString)
- Network.AWS.Data: _Sensitive :: Iso' (Sensitive a) a
- Network.AWS.Data: _Time :: Iso' (Time a) UTCTime
- Network.AWS.Data: _bdyBody :: RqBody -> RequestBody
- Network.AWS.Data: _bdyHash :: RqBody -> Digest SHA256
- Network.AWS.Data: bdyBody :: Lens' RqBody RequestBody
- Network.AWS.Data: bdyHash :: Lens' RqBody (Digest SHA256)
- Network.AWS.Data: bodyHash :: RqBody -> ByteString
- Network.AWS.Data: build :: ToBuilder a => a -> Builder
- Network.AWS.Data: buildBS :: ToBuilder a => a -> LazyByteString
- Network.AWS.Data: childNodes :: Text -> Node -> Maybe [Node]
- Network.AWS.Data: class FromJSON a
- Network.AWS.Data: class FromText a
- Network.AWS.Data: class FromXML a
- Network.AWS.Data: class ToBody a where toBody = const (RqBody (hash "") (RequestBodyLBS mempty))
- Network.AWS.Data: class ToBuilder a where build = build . toBS
- Network.AWS.Data: class ToByteString a where toBS = encodeUtf8 . toText
- Network.AWS.Data: class ToHeader a where toHeader k = toHeader k . toText
- Network.AWS.Data: class ToHeaders a where toHeaders = const mempty
- Network.AWS.Data: class ToJSON a
- Network.AWS.Data: class ToPath a where toPath = const mempty
- Network.AWS.Data: class ToQuery a where toQuery = toQuery . toText
- Network.AWS.Data: class ToText a
- Network.AWS.Data: class ToXML a where toXML = maybeToList . fmap NodeElement . toXMLRoot
- Network.AWS.Data: class ToXMLRoot a
- Network.AWS.Data: collapsePath :: ByteString -> ByteString
- Network.AWS.Data: connectBody :: MonadResource m => RsBody -> Sink ByteString m a -> m a
- Network.AWS.Data: data Format
- Network.AWS.Data: data Query
- Network.AWS.Data: data RqBody
- Network.AWS.Data: data RsBody
- Network.AWS.Data: data Time :: Format -> *
- Network.AWS.Data: data UTCTime :: *
- Network.AWS.Data: decodeXML :: LazyByteString -> Either String [Node]
- Network.AWS.Data: defaultTimeLocale :: TimeLocale
- Network.AWS.Data: desensitise :: Sensitive a -> a
- Network.AWS.Data: eitherDecode' :: FromJSON a => ByteString -> Either String a
- Network.AWS.Data: element :: Name -> [Node] -> Element
- Network.AWS.Data: encodeXML :: ToXMLRoot a => a -> LazyByteString
- Network.AWS.Data: extractRoot :: Text -> [Node] -> Maybe Element
- Network.AWS.Data: findElement :: Text -> [Node] -> Either String [Node]
- Network.AWS.Data: fromEMap :: EMap k v -> HashMap k v
- Network.AWS.Data: fromList1 :: List1 e a -> List e a
- Network.AWS.Data: fromMap :: Map k v -> HashMap k v
- Network.AWS.Data: fromText :: FromText a => Text -> Either String a
- Network.AWS.Data: hAMZAlgorithm :: HeaderName
- Network.AWS.Data: hAMZAuth :: HeaderName
- Network.AWS.Data: hAMZContentSHA256 :: HeaderName
- Network.AWS.Data: hAMZCredential :: HeaderName
- Network.AWS.Data: hAMZDate :: HeaderName
- Network.AWS.Data: hAMZExpires :: HeaderName
- Network.AWS.Data: hAMZSignedHeaders :: HeaderName
- Network.AWS.Data: hAMZTarget :: HeaderName
- Network.AWS.Data: hAMZToken :: HeaderName
- Network.AWS.Data: hHost :: HeaderName
- Network.AWS.Data: hMetaPrefix :: HeaderName
- Network.AWS.Data: hdr :: HeaderName -> ByteString -> [Header] -> [Header]
- Network.AWS.Data: hdrs :: [Header] -> [Header] -> [Header]
- Network.AWS.Data: isStreaming :: RqBody -> Bool
- Network.AWS.Data: iso8601DateFormat :: Maybe String -> String
- Network.AWS.Data: list :: List a -> [a]
- Network.AWS.Data: list1 :: List1 a -> NonEmpty a
- Network.AWS.Data: localName :: Node -> Maybe Text
- Network.AWS.Data: matchCI :: Text -> a -> Parser a
- Network.AWS.Data: namespaced :: Text -> Text -> [Node] -> Maybe Element
- Network.AWS.Data: newtype Base64
- Network.AWS.Data: newtype EMap (e :: Symbol) (i :: Symbol) (j :: Symbol) k v
- Network.AWS.Data: newtype List (e :: Symbol) a
- Network.AWS.Data: newtype List1 (e :: Symbol) a
- Network.AWS.Data: newtype Map k v
- Network.AWS.Data: newtype Nat
- Network.AWS.Data: newtype Sensitive a
- Network.AWS.Data: nodes :: Name -> [Node] -> [Node]
- Network.AWS.Data: object :: [Pair] -> Value
- Network.AWS.Data: pair :: ToQuery a => ByteString -> a -> Query -> Query
- Network.AWS.Data: parseJSON :: FromJSON a => Value -> Parser a
- Network.AWS.Data: parseJSONText :: FromText a => String -> Value -> Parser a
- Network.AWS.Data: parseTime :: ParseTime t => TimeLocale -> String -> String -> Maybe t
- Network.AWS.Data: parseXML :: FromXML a => [Node] -> Either String a
- Network.AWS.Data: parseXMLText :: FromText a => String -> [Node] -> Either String a
- Network.AWS.Data: parser :: FromText a => Parser a
- Network.AWS.Data: renderQuery :: Query -> ByteString
- Network.AWS.Data: showBS :: ToByteString a => a -> String
- Network.AWS.Data: showText :: ToText a => a -> String
- Network.AWS.Data: stripBS :: ByteString -> ByteString
- Network.AWS.Data: takeLowerText :: Parser Text
- Network.AWS.Data: toBS :: ToByteString a => a -> ByteString
- Network.AWS.Data: toBody :: ToBody a => a -> RqBody
- Network.AWS.Data: toHeader :: ToHeader a => HeaderName -> a -> [Header]
- Network.AWS.Data: toHeaderText :: ToText a => HeaderName -> a -> [Header]
- Network.AWS.Data: toHeaders :: ToHeaders a => a -> [Header]
- Network.AWS.Data: toJSON :: ToJSON a => a -> Value
- Network.AWS.Data: toJSONText :: ToText a => a -> Value
- Network.AWS.Data: toList1 :: List e a -> Either String (List1 e a)
- Network.AWS.Data: toPath :: ToPath a => a -> Text
- Network.AWS.Data: toQuery :: ToQuery a => a -> Query
- Network.AWS.Data: toQueryList :: (IsList a, ToQuery (Item a)) => ByteString -> a -> Query
- Network.AWS.Data: toText :: ToText a => a -> Text
- Network.AWS.Data: toXML :: ToXML a => a -> [Node]
- Network.AWS.Data: toXMLRoot :: ToXMLRoot a => a -> Maybe Element
- Network.AWS.Data: toXMLText :: ToText a => a -> [Node]
- Network.AWS.Data: type AWSTime = Time AWSFormat
- Network.AWS.Data: type BasicTime = Time BasicFormat
- Network.AWS.Data: type ISO8601 = Time ISO8601Format
- Network.AWS.Data: type LazyByteString = ByteString
- Network.AWS.Data: type Object = HashMap Text Value
- Network.AWS.Data: type POSIX = Time POSIXFormat
- Network.AWS.Data: type RFC822 = Time RFC822Format
- Network.AWS.Data: unBase64 :: Base64 -> ByteString
- Network.AWS.Data: unNat :: Nat -> Natural
- Network.AWS.Data: unsafeToXML :: (Show a, ToXML a) => a -> Node
- Network.AWS.Data: valuesOf :: Traversal' Query (Maybe ByteString)
- Network.AWS.Data: withContent :: String -> [Node] -> Either String (Maybe Text)
- Network.AWS.Data: withElement :: Text -> ([Node] -> Either String a) -> [Node] -> Either String a
- Network.AWS.Data: withObject :: String -> (Object -> Parser a) -> Value -> Parser a
- Network.AWS.Error: ErrorCode :: Text -> ErrorCode
- Network.AWS.Error: Errors :: [ServiceError a] -> ServiceError a
- Network.AWS.Error: HttpError :: HttpException -> ServiceError a
- Network.AWS.Error: Receiver :: ErrorType
- Network.AWS.Error: Sender :: ErrorType
- Network.AWS.Error: SerializerError :: Abbrev -> String -> ServiceError a
- Network.AWS.Error: ServiceError :: Abbrev -> Status -> a -> ServiceError a
- Network.AWS.Error: awsError :: AWSError a => a -> ServiceError String
- Network.AWS.Error: awsErrorCode :: AWSErrorCode a => a -> Maybe ErrorCode
- Network.AWS.Error: class AWSError a
- Network.AWS.Error: class AWSErrorCode a
- Network.AWS.Error: data ErrorType
- Network.AWS.Error: data JSONError
- Network.AWS.Error: data RESTError
- Network.AWS.Error: data ServiceError a
- Network.AWS.Error: instance AWSErrorCode JSONError
- Network.AWS.Error: instance AWSErrorCode RESTError
- Network.AWS.Error: instance Constructor C1_0ErrorCode
- Network.AWS.Error: instance Constructor C1_0ErrorType
- Network.AWS.Error: instance Constructor C1_0JSONError
- Network.AWS.Error: instance Constructor C1_0RESTError
- Network.AWS.Error: instance Constructor C1_1ErrorType
- Network.AWS.Error: instance Datatype D1ErrorCode
- Network.AWS.Error: instance Datatype D1ErrorType
- Network.AWS.Error: instance Datatype D1JSONError
- Network.AWS.Error: instance Datatype D1RESTError
- Network.AWS.Error: instance Enum ErrorType
- Network.AWS.Error: instance Eq ErrorCode
- Network.AWS.Error: instance Eq ErrorType
- Network.AWS.Error: instance Eq JSONError
- Network.AWS.Error: instance Eq RESTError
- Network.AWS.Error: instance FromJSON ErrorCode
- Network.AWS.Error: instance FromJSON JSONError
- Network.AWS.Error: instance FromText ErrorType
- Network.AWS.Error: instance FromXML ErrorCode
- Network.AWS.Error: instance FromXML ErrorType
- Network.AWS.Error: instance FromXML RESTError
- Network.AWS.Error: instance Generic ErrorCode
- Network.AWS.Error: instance Generic ErrorType
- Network.AWS.Error: instance Generic JSONError
- Network.AWS.Error: instance Generic RESTError
- Network.AWS.Error: instance IsString ErrorCode
- Network.AWS.Error: instance Ord ErrorCode
- Network.AWS.Error: instance Ord ErrorType
- Network.AWS.Error: instance Selector S1_0_0JSONError
- Network.AWS.Error: instance Selector S1_0_0RESTError
- Network.AWS.Error: instance Selector S1_0_1JSONError
- Network.AWS.Error: instance Selector S1_0_1RESTError
- Network.AWS.Error: instance Selector S1_0_2JSONError
- Network.AWS.Error: instance Selector S1_0_2RESTError
- Network.AWS.Error: instance Selector S1_0_3RESTError
- Network.AWS.Error: instance Show ErrorCode
- Network.AWS.Error: instance Show ErrorType
- Network.AWS.Error: instance Show JSONError
- Network.AWS.Error: instance Show RESTError
- Network.AWS.Error: instance Show a => AWSError (ServiceError a)
- Network.AWS.Error: jsonCode :: Lens' JSONError (Maybe ErrorCode)
- Network.AWS.Error: jsonError :: FromJSON (Er a) => (Status -> Bool) -> Service a -> Status -> Maybe (ByteString -> ServiceError (Er a))
- Network.AWS.Error: jsonMessage :: Lens' JSONError Text
- Network.AWS.Error: jsonType :: Lens' JSONError (Maybe Text)
- Network.AWS.Error: newtype ErrorCode
- Network.AWS.Error: restCode :: Lens' RESTError (Maybe ErrorCode)
- Network.AWS.Error: restError :: FromXML (Er a) => (Status -> Bool) -> Service a -> Status -> Maybe (ByteString -> ServiceError (Er a))
- Network.AWS.Error: restMessage :: Lens' RESTError Text
- Network.AWS.Error: restRequestId :: Lens' RESTError Text
- Network.AWS.Error: restType :: Lens' RESTError (Maybe ErrorType)
- Network.AWS.Pagination: choice :: Alternative f => (a -> f b) -> (a -> f b) -> a -> f b
- Network.AWS.Pagination: index :: ToText c => Getter a [b] -> Getter b c -> Getter a (Maybe Text)
- Network.AWS.Pagination: instance AWSMore (HashMap k v)
- Network.AWS.Pagination: instance AWSMore (Maybe Bool)
- Network.AWS.Pagination: instance AWSMore (Maybe Text)
- Network.AWS.Pagination: instance AWSMore Bool
- Network.AWS.Pagination: instance AWSMore [a]
- Network.AWS.Pagination: more :: AWSMore a => a -> Bool
- Network.AWS.Pagination: stop :: AWSMore a => a -> Bool
- Network.AWS.Prelude: (:|) :: a -> [a] -> NonEmpty a
- Network.AWS.Prelude: CONNECT :: StdMethod
- Network.AWS.Prelude: DELETE :: StdMethod
- Network.AWS.Prelude: Empty :: Empty
- Network.AWS.Prelude: Errors :: [ServiceError a] -> ServiceError a
- Network.AWS.Prelude: Exponential :: !Double -> !Int -> !Int -> (Status -> Er a -> Bool) -> Retry a
- Network.AWS.Prelude: GET :: StdMethod
- Network.AWS.Prelude: HEAD :: StdMethod
- Network.AWS.Prelude: HttpError :: HttpException -> ServiceError a
- Network.AWS.Prelude: OPTIONS :: StdMethod
- Network.AWS.Prelude: PATCH :: StdMethod
- Network.AWS.Prelude: POST :: StdMethod
- Network.AWS.Prelude: PUT :: StdMethod
- Network.AWS.Prelude: SerializerError :: Abbrev -> String -> ServiceError a
- Network.AWS.Prelude: Service :: !Text -> !ByteString -> !ByteString -> Maybe ByteString -> Maybe ByteString -> (Status -> Maybe (LazyByteString -> ServiceError (Er a))) -> Retry a -> Service a
- Network.AWS.Prelude: ServiceError :: Abbrev -> Status -> a -> ServiceError a
- Network.AWS.Prelude: Status :: Int -> ByteString -> Status
- Network.AWS.Prelude: TRACE :: StdMethod
- Network.AWS.Prelude: _retryAttempts :: Retry a -> !Int
- Network.AWS.Prelude: _retryBase :: Retry a -> !Double
- Network.AWS.Prelude: _retryCheck :: Retry a -> Status -> Er a -> Bool
- Network.AWS.Prelude: _retryGrowth :: Retry a -> !Int
- Network.AWS.Prelude: _svcAbbrev :: Service a -> !Text
- Network.AWS.Prelude: _svcHandle :: Service a -> Status -> Maybe (LazyByteString -> ServiceError (Er a))
- Network.AWS.Prelude: _svcJSONVersion :: Service a -> Maybe ByteString
- Network.AWS.Prelude: _svcPrefix :: Service a -> !ByteString
- Network.AWS.Prelude: _svcRetry :: Service a -> Retry a
- Network.AWS.Prelude: _svcTargetPrefix :: Service a -> Maybe ByteString
- Network.AWS.Prelude: _svcVersion :: Service a -> !ByteString
- Network.AWS.Prelude: awsError :: AWSError a => a -> ServiceError String
- Network.AWS.Prelude: awsErrorCode :: AWSErrorCode a => a -> Maybe ErrorCode
- Network.AWS.Prelude: class AWSError a
- Network.AWS.Prelude: class AWSErrorCode a
- Network.AWS.Prelude: class AWSRequest a => AWSPager a
- Network.AWS.Prelude: class (AWSService (Sv a), AWSSigner (Sg (Sv a))) => AWSRequest a where type family Sv a :: * type family Rs a :: *
- Network.AWS.Prelude: class (AWSSigner (Sg a), Show (Er a)) => AWSService a where type family Sg a :: * type family Er a :: *
- Network.AWS.Prelude: class (Typeable * e, Show e) => Exception e
- Network.AWS.Prelude: class Generic a
- Network.AWS.Prelude: class IsString a
- Network.AWS.Prelude: class Semigroup a
- Network.AWS.Prelude: data ByteString :: *
- Network.AWS.Prelude: data CI s :: * -> *
- Network.AWS.Prelude: data Empty
- Network.AWS.Prelude: data HashMap k v :: * -> * -> *
- Network.AWS.Prelude: data HttpException :: *
- Network.AWS.Prelude: data JSONError
- Network.AWS.Prelude: data Natural :: *
- Network.AWS.Prelude: data NonEmpty a :: * -> *
- Network.AWS.Prelude: data RESTError
- Network.AWS.Prelude: data RequestBody :: *
- Network.AWS.Prelude: data Retry a
- Network.AWS.Prelude: data Service a
- Network.AWS.Prelude: data ServiceError a
- Network.AWS.Prelude: data Status :: *
- Network.AWS.Prelude: data StdMethod :: *
- Network.AWS.Prelude: data Text :: *
- Network.AWS.Prelude: fromString :: IsString a => String -> a
- Network.AWS.Prelude: jsonError :: FromJSON (Er a) => (Status -> Bool) -> Service a -> Status -> Maybe (ByteString -> ServiceError (Er a))
- Network.AWS.Prelude: page :: AWSPager a => a -> Rs a -> Maybe a
- Network.AWS.Prelude: request :: AWSRequest a => a -> Request a
- Network.AWS.Prelude: response :: (AWSRequest a, MonadResource m) => Logger -> Request a -> Either HttpException ClientResponse -> m (Response' a)
- Network.AWS.Prelude: restError :: FromXML (Er a) => (Status -> Bool) -> Service a -> Status -> Maybe (ByteString -> ServiceError (Er a))
- Network.AWS.Prelude: service :: AWSService a => Service a
- Network.AWS.Prelude: statusCode :: Status -> Int
- Network.AWS.Prelude: statusMessage :: Status -> ByteString
- Network.AWS.Prelude: statusSuccess :: Status -> Bool
- Network.AWS.Prelude: type ClientRequest = Request
- Network.AWS.Prelude: type ClientResponse = Response ResponseBody
- Network.AWS.Prelude: type Response a = Either (ServiceError (Er (Sv a))) (Rs a)
- Network.AWS.Request.JSON: post :: (AWSService (Sv a), ToQuery a, ToPath a, ToHeaders a, ToJSON a) => Action -> a -> Request a
- Network.AWS.Request.Query: post :: (AWSService (Sv a), ToQuery a, ToPath a, ToHeaders a) => Action -> a -> Request a
- Network.AWS.Request.RestJSON: delete :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
- Network.AWS.Request.RestJSON: get :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
- Network.AWS.Request.RestJSON: post :: (AWSService (Sv a), ToQuery a, ToPath a, ToHeaders a, ToJSON a) => a -> Request a
- Network.AWS.Request.RestJSON: put :: (AWSService (Sv a), ToQuery a, ToPath a, ToHeaders a, ToJSON a) => a -> Request a
- Network.AWS.Request.RestJSON: stream :: (AWSService (Sv a), ToPath a, ToQuery a, ToHeaders a, ToBody a) => StdMethod -> a -> Request a
- Network.AWS.Request.RestXML: delete :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
- Network.AWS.Request.RestXML: get :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
- Network.AWS.Request.RestXML: head :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
- Network.AWS.Request.RestXML: post :: (ToPath a, ToQuery a, ToHeaders a, ToXMLRoot a) => a -> Request a
- Network.AWS.Request.RestXML: put :: (ToPath a, ToQuery a, ToHeaders a, ToXMLRoot a) => a -> Request a
- Network.AWS.Request.S3: delete :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
- Network.AWS.Request.S3: get :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
- Network.AWS.Request.S3: head :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
- Network.AWS.Request.S3: post :: (ToPath a, ToQuery a, ToHeaders a, ToXMLRoot a) => a -> Request a
- Network.AWS.Request.S3: put :: (ToPath a, ToQuery a, ToHeaders a, ToXMLRoot a) => a -> Request a
- Network.AWS.Request.S3: stream :: (ToPath a, ToQuery a, ToHeaders a, ToBody a) => StdMethod -> a -> Request a
- Network.AWS.Response: bodyResponse :: (MonadResource m, AWSService (Sv a)) => (ResponseHeaders -> Int -> ResponseBody -> Either String (Rs a)) -> Logger -> Request a -> Either HttpException ClientResponse -> m (Response' a)
- Network.AWS.Response: headerResponse :: (MonadResource m, AWSService (Sv a)) => (ResponseHeaders -> Either String (Rs a)) -> Logger -> Request a -> Either HttpException ClientResponse -> m (Response' a)
- Network.AWS.Response: jsonHeaderResponse :: (MonadResource m, AWSService (Sv a)) => (ResponseHeaders -> Int -> Object -> Either String (Rs a)) -> Logger -> Request a -> Either HttpException ClientResponse -> m (Response' a)
- Network.AWS.Response: jsonResponse :: (MonadResource m, AWSService (Sv a), FromJSON (Rs a)) => Logger -> Request a -> Either HttpException ClientResponse -> m (Response' a)
- Network.AWS.Response: nullResponse :: (MonadResource m, AWSService (Sv a)) => Rs a -> Logger -> Request a -> Either HttpException ClientResponse -> m (Response' a)
- Network.AWS.Response: xmlHeaderResponse :: (MonadResource m, AWSService (Sv a)) => (ResponseHeaders -> [Node] -> Either String (Rs a)) -> Logger -> Request a -> Either HttpException ClientResponse -> m (Response' a)
- Network.AWS.Response: xmlResponse :: (MonadResource m, AWSService (Sv a), FromXML (Rs a)) => Logger -> Request a -> Either HttpException ClientResponse -> m (Response' a)
- Network.AWS.Signing: data V2
- Network.AWS.Signing: data V4
- Network.AWS.Signing: presign :: (MonadIO m, AWSRequest a, AWSPresigner (Sg (Sv a))) => Auth -> Region -> Request a -> UTCTime -> Integer -> m (Signed a (Sg (Sv a)))
- Network.AWS.Signing: sign :: (MonadIO m, AWSRequest a, AWSSigner (Sg (Sv a))) => Auth -> Region -> Request a -> UTCTime -> m (Signed a (Sg (Sv a)))
- Network.AWS.Types: Action :: Text -> Action
- Network.AWS.Types: Empty :: Empty
- Network.AWS.Types: Errors :: [ServiceError a] -> ServiceError a
- Network.AWS.Types: HttpError :: HttpException -> ServiceError a
- Network.AWS.Types: SecurityToken :: ByteString -> SecurityToken
- Network.AWS.Types: SerializerError :: Abbrev -> String -> ServiceError a
- Network.AWS.Types: _Errors :: Prism' (ServiceError a_avh9) [ServiceError a_avh9]
- Network.AWS.Types: _HttpError :: Prism' (ServiceError a_avh9) HttpException
- Network.AWS.Types: _SerializerError :: Prism' (ServiceError a_avh9) (Abbrev, String)
- Network.AWS.Types: _svcHandle :: Service a -> Status -> Maybe (LazyByteString -> ServiceError (Er a))
- Network.AWS.Types: _svcJSONVersion :: Service a -> Maybe ByteString
- Network.AWS.Types: _svcTargetPrefix :: Service a -> Maybe ByteString
- Network.AWS.Types: class AWSRequest a => AWSPager a
- Network.AWS.Types: data Empty
- Network.AWS.Types: endpoint :: Service a -> Region -> Endpoint
- Network.AWS.Types: instance (Show a, Typeable a) => Exception (ServiceError a)
- Network.AWS.Types: instance Default (Request a)
- Network.AWS.Types: instance Default Region
- Network.AWS.Types: instance Eq Action
- Network.AWS.Types: instance Eq Empty
- Network.AWS.Types: instance Eq SecurityToken
- Network.AWS.Types: instance IsString Action
- Network.AWS.Types: instance IsString SecurityToken
- Network.AWS.Types: instance Monoid (ServiceError a)
- Network.AWS.Types: instance Ord Action
- Network.AWS.Types: instance Show Action
- Network.AWS.Types: instance Show Empty
- Network.AWS.Types: instance Show a => Show (ServiceError a)
- Network.AWS.Types: instance ToBuilder (Request a)
- Network.AWS.Types: instance ToBuilder AccessKey
- Network.AWS.Types: instance ToBuilder Auth
- Network.AWS.Types: instance ToBuilder AuthEnv
- Network.AWS.Types: instance ToBuilder Region
- Network.AWS.Types: instance ToByteString Action
- Network.AWS.Types: instance ToByteString SecurityToken
- Network.AWS.Types: instance ToJSON Empty
- Network.AWS.Types: instance ToText Action
- Network.AWS.Types: instance ToText SecurityToken
- Network.AWS.Types: newtype Action
- Network.AWS.Types: newtype SecurityToken
- Network.AWS.Types: page :: AWSPager a => a -> Rs a -> Maybe a
- Network.AWS.Types: type Abbrev = Text
- Network.AWS.Types: type Response' a = Either (ServiceError (Er (Sv a))) (Status, Rs a)
- Network.AWS.Waiters: AcceptFailure :: Accept
- Network.AWS.Waiters: AcceptRetry :: Accept
- Network.AWS.Waiters: AcceptSuccess :: Accept
- Network.AWS.Waiters: Wait :: !ByteString -> !Int -> !Int -> [Acceptor a] -> Wait a
- Network.AWS.Waiters: _waitAcceptors :: Wait a -> [Acceptor a]
- Network.AWS.Waiters: _waitAttempts :: Wait a -> !Int
- Network.AWS.Waiters: _waitDelay :: Wait a -> !Int
- Network.AWS.Waiters: _waitName :: Wait a -> !ByteString
- Network.AWS.Waiters: accept :: Wait a -> Acceptor a
- Network.AWS.Waiters: data Accept
- Network.AWS.Waiters: data Wait a
- Network.AWS.Waiters: instance Eq Accept
- Network.AWS.Waiters: instance Show Accept
- Network.AWS.Waiters: instance ToBuilder Accept
- Network.AWS.Waiters: matchAll :: Eq b => b -> Accept -> Fold (Rs a) b -> Acceptor a
- Network.AWS.Waiters: matchAny :: Eq b => b -> Accept -> Fold (Rs a) b -> Acceptor a
- Network.AWS.Waiters: matchError :: AWSErrorCode (Er (Sv a)) => ErrorCode -> Accept -> Acceptor a
- Network.AWS.Waiters: matchStatus :: Int -> Accept -> Acceptor a
- Network.AWS.Waiters: nonEmpty :: Fold a Text -> Fold a Bool
- Network.AWS.Waiters: type Acceptor a = Request a -> Response' a -> Maybe Accept
+ Network.AWS.Compat.Locale: defaultTimeLocale :: TimeLocale
+ Network.AWS.Compat.Locale: iso8601DateFormat :: Maybe String -> String
+ Network.AWS.Compat.Time: parseTime :: ParseTime t => TimeLocale -> String -> String -> Maybe t
+ Network.AWS.Data.Base64: Base64 :: ByteString -> Base64
+ Network.AWS.Data.Base64: _Base64 :: Iso' Base64 ByteString
+ Network.AWS.Data.Base64: instance Constructor C1_0Base64
+ Network.AWS.Data.Base64: instance Data Base64
+ Network.AWS.Data.Base64: instance Datatype D1Base64
+ Network.AWS.Data.Base64: instance Eq Base64
+ Network.AWS.Data.Base64: instance FromJSON Base64
+ Network.AWS.Data.Base64: instance FromText Base64
+ Network.AWS.Data.Base64: instance FromXML Base64
+ Network.AWS.Data.Base64: instance Generic Base64
+ Network.AWS.Data.Base64: instance Ord Base64
+ Network.AWS.Data.Base64: instance Read Base64
+ Network.AWS.Data.Base64: instance Selector S1_0_0Base64
+ Network.AWS.Data.Base64: instance Show Base64
+ Network.AWS.Data.Base64: instance ToByteString Base64
+ Network.AWS.Data.Base64: instance ToJSON Base64
+ Network.AWS.Data.Base64: instance ToQuery Base64
+ Network.AWS.Data.Base64: instance ToText Base64
+ Network.AWS.Data.Base64: instance ToXML Base64
+ Network.AWS.Data.Base64: instance Typeable Base64
+ Network.AWS.Data.Base64: newtype Base64
+ Network.AWS.Data.Base64: unBase64 :: Base64 -> ByteString
+ Network.AWS.Data.Body: RqBody :: Digest SHA256 -> RequestBody -> RqBody
+ Network.AWS.Data.Body: RsBody :: ResumableSource (ResourceT IO) ByteString -> RsBody
+ Network.AWS.Data.Body: bodyCalculateMD5 :: RqBody -> Maybe (Digest MD5)
+ Network.AWS.Data.Body: bodyRequest :: RqBody -> RequestBody
+ Network.AWS.Data.Body: bodyResponse :: RsBody -> ResumableSource (ResourceT IO) ByteString
+ Network.AWS.Data.Body: bodySHA256 :: RqBody -> Digest SHA256
+ Network.AWS.Data.Body: bodyStream :: RqBody -> Bool
+ Network.AWS.Data.Body: class ToBody a
+ Network.AWS.Data.Body: data RqBody
+ Network.AWS.Data.Body: instance IsString RqBody
+ Network.AWS.Data.Body: instance Show RqBody
+ Network.AWS.Data.Body: instance Show RsBody
+ Network.AWS.Data.Body: instance ToBody ByteString
+ Network.AWS.Data.Body: instance ToBody Element
+ Network.AWS.Data.Body: instance ToBody QueryString
+ Network.AWS.Data.Body: instance ToBody RqBody
+ Network.AWS.Data.Body: instance ToBody Text
+ Network.AWS.Data.Body: instance ToBody Value
+ Network.AWS.Data.Body: newtype RsBody
+ Network.AWS.Data.Body: toBody :: ToBody a => a -> RqBody
+ Network.AWS.Data.ByteString: class ToByteString a where toBS = encodeUtf8 . toText
+ Network.AWS.Data.ByteString: data ByteString :: *
+ Network.AWS.Data.ByteString: instance ToByteString Builder
+ Network.AWS.Data.ByteString: instance ToByteString ByteString
+ Network.AWS.Data.ByteString: instance ToByteString Double
+ Network.AWS.Data.ByteString: instance ToByteString Int
+ Network.AWS.Data.ByteString: instance ToByteString Integer
+ Network.AWS.Data.ByteString: instance ToByteString LazyByteString
+ Network.AWS.Data.ByteString: instance ToByteString Natural
+ Network.AWS.Data.ByteString: instance ToByteString StdMethod
+ Network.AWS.Data.ByteString: instance ToByteString String
+ Network.AWS.Data.ByteString: instance ToByteString Text
+ Network.AWS.Data.ByteString: instance ToByteString UTCTime
+ Network.AWS.Data.ByteString: instance ToByteString a => ToByteString (CI a)
+ Network.AWS.Data.ByteString: showBS :: ToByteString a => a -> String
+ Network.AWS.Data.ByteString: stripBS :: ByteString -> ByteString
+ Network.AWS.Data.ByteString: toBS :: ToByteString a => a -> ByteString
+ Network.AWS.Data.ByteString: type LazyByteString = ByteString
+ Network.AWS.Data.Crypto: Base16 :: Base
+ Network.AWS.Data.Crypto: Base32 :: Base
+ Network.AWS.Data.Crypto: Base64 :: Base
+ Network.AWS.Data.Crypto: MD5 :: MD5
+ Network.AWS.Data.Crypto: SHA256 :: SHA256
+ Network.AWS.Data.Crypto: class HashAlgorithm a
+ Network.AWS.Data.Crypto: data Base :: *
+ Network.AWS.Data.Crypto: data Digest a :: * -> *
+ Network.AWS.Data.Crypto: data HMAC a :: * -> *
+ Network.AWS.Data.Crypto: data MD5 :: *
+ Network.AWS.Data.Crypto: data SHA256 :: *
+ Network.AWS.Data.Crypto: digestToBS :: ByteArrayAccess a => a -> ByteString
+ Network.AWS.Data.Crypto: digestToBase :: ByteArrayAccess a => Base -> a -> ByteString
+ Network.AWS.Data.Crypto: hash :: (ByteArrayAccess ba, HashAlgorithm a) => ba -> Digest a
+ Network.AWS.Data.Crypto: hashFinalize :: HashAlgorithm a => Context a -> Digest a
+ Network.AWS.Data.Crypto: hashInit :: HashAlgorithm a => Context a
+ Network.AWS.Data.Crypto: hashMD5 :: ByteArrayAccess a => a -> Digest MD5
+ Network.AWS.Data.Crypto: hashSHA256 :: ByteArrayAccess a => a -> Digest SHA256
+ Network.AWS.Data.Crypto: hashUpdate :: (ByteArrayAccess ba, HashAlgorithm a) => Context a -> ba -> Context a
+ Network.AWS.Data.Crypto: hashlazy :: HashAlgorithm a => ByteString -> Digest a
+ Network.AWS.Data.Crypto: hmacSHA256 :: (ByteArrayAccess a, ByteArray b) => a -> b -> HMAC SHA256
+ Network.AWS.Data.Headers: (.#) :: FromText a => ResponseHeaders -> HeaderName -> Either String a
+ Network.AWS.Data.Headers: (.#?) :: FromText a => ResponseHeaders -> HeaderName -> Either String (Maybe a)
+ Network.AWS.Data.Headers: (=#) :: ToHeader a => HeaderName -> a -> [Header]
+ Network.AWS.Data.Headers: class ToHeader a where toHeader k = toHeader k . toText
+ Network.AWS.Data.Headers: class ToHeaders a where toHeaders = const mempty
+ Network.AWS.Data.Headers: hAMZAlgorithm :: HeaderName
+ Network.AWS.Data.Headers: hAMZContentSHA256 :: HeaderName
+ Network.AWS.Data.Headers: hAMZCredential :: HeaderName
+ Network.AWS.Data.Headers: hAMZDate :: HeaderName
+ Network.AWS.Data.Headers: hAMZExpires :: HeaderName
+ Network.AWS.Data.Headers: hAMZNAuth :: HeaderName
+ Network.AWS.Data.Headers: hAMZNErrorType :: HeaderName
+ Network.AWS.Data.Headers: hAMZNRequestId :: HeaderName
+ Network.AWS.Data.Headers: hAMZRequestId :: HeaderName
+ Network.AWS.Data.Headers: hAMZSignedHeaders :: HeaderName
+ Network.AWS.Data.Headers: hAMZTarget :: HeaderName
+ Network.AWS.Data.Headers: hAMZToken :: HeaderName
+ Network.AWS.Data.Headers: hHost :: HeaderName
+ Network.AWS.Data.Headers: hMetaPrefix :: HeaderName
+ Network.AWS.Data.Headers: hdr :: HeaderName -> ByteString -> [Header] -> [Header]
+ Network.AWS.Data.Headers: instance ToHeader ByteString
+ Network.AWS.Data.Headers: instance ToHeader Text
+ Network.AWS.Data.Headers: instance ToText a => ToHeader (Maybe a)
+ Network.AWS.Data.Headers: toHeader :: ToHeader a => HeaderName -> a -> [Header]
+ Network.AWS.Data.Headers: toHeaders :: ToHeaders a => a -> [Header]
+ Network.AWS.Data.Headers: type Header = (HeaderName, ByteString)
+ Network.AWS.Data.Headers: type HeaderName = CI ByteString
+ Network.AWS.Data.JSON: (.!=) :: Parser (Maybe a) -> a -> Parser a
+ Network.AWS.Data.JSON: (.:) :: FromJSON a => Object -> Text -> Parser a
+ Network.AWS.Data.JSON: (.:>) :: FromJSON a => Object -> Text -> Either String a
+ Network.AWS.Data.JSON: (.:?) :: FromJSON a => Object -> Text -> Parser (Maybe a)
+ Network.AWS.Data.JSON: (.=) :: ToJSON a => Text -> a -> Pair
+ Network.AWS.Data.JSON: (.?>) :: FromJSON a => Object -> Text -> Either String (Maybe a)
+ Network.AWS.Data.JSON: Object :: SrictNotUnpackedObject -> Value
+ Network.AWS.Data.JSON: class FromJSON a
+ Network.AWS.Data.JSON: class ToJSON a
+ Network.AWS.Data.JSON: data Value :: *
+ Network.AWS.Data.JSON: eitherDecode' :: FromJSON a => ByteString -> Either String a
+ Network.AWS.Data.JSON: eitherParseJSON :: FromJSON a => Object -> Either String a
+ Network.AWS.Data.JSON: object :: [Pair] -> Value
+ Network.AWS.Data.JSON: parseJSON :: FromJSON a => Value -> Parser a
+ Network.AWS.Data.JSON: parseJSONText :: FromText a => String -> Value -> Parser a
+ Network.AWS.Data.JSON: toJSON :: ToJSON a => a -> Value
+ Network.AWS.Data.JSON: toJSONText :: ToText a => a -> Value
+ Network.AWS.Data.JSON: withObject :: String -> (Object -> Parser a) -> Value -> Parser a
+ Network.AWS.Data.List1: List1 :: NonEmpty a -> List1 a
+ Network.AWS.Data.List1: _List1 :: (Coercible a b, Coercible b a) => Iso' (List1 a) (NonEmpty b)
+ Network.AWS.Data.List1: instance Applicative List1
+ Network.AWS.Data.List1: instance Constructor C1_0List1
+ Network.AWS.Data.List1: instance Data a => Data (List1 a)
+ Network.AWS.Data.List1: instance Datatype D1List1
+ Network.AWS.Data.List1: instance Eq a => Eq (List1 a)
+ Network.AWS.Data.List1: instance Foldable List1
+ Network.AWS.Data.List1: instance FromJSON a => FromJSON (List1 a)
+ Network.AWS.Data.List1: instance Functor List1
+ Network.AWS.Data.List1: instance Generic (List1 a)
+ Network.AWS.Data.List1: instance IsList (List1 a)
+ Network.AWS.Data.List1: instance Monad List1
+ Network.AWS.Data.List1: instance Ord a => Ord (List1 a)
+ Network.AWS.Data.List1: instance Read a => Read (List1 a)
+ Network.AWS.Data.List1: instance Selector S1_0_0List1
+ Network.AWS.Data.List1: instance Semigroup (List1 a)
+ Network.AWS.Data.List1: instance Show a => Show (List1 a)
+ Network.AWS.Data.List1: instance ToJSON a => ToJSON (List1 a)
+ Network.AWS.Data.List1: instance Traversable List1
+ Network.AWS.Data.List1: instance Typeable List1
+ Network.AWS.Data.List1: newtype List1 a
+ Network.AWS.Data.List1: parseXMLList1 :: FromXML a => Text -> [Node] -> Either String (List1 a)
+ Network.AWS.Data.List1: toNonEmpty :: List1 a -> NonEmpty a
+ Network.AWS.Data.Log: build :: ToLog a => a -> Builder
+ Network.AWS.Data.Log: buildLines :: [Builder] -> Builder
+ Network.AWS.Data.Log: class ToLog a
+ Network.AWS.Data.Log: instance ToLog (Response a)
+ Network.AWS.Data.Log: instance ToLog Bool
+ Network.AWS.Data.Log: instance ToLog Builder
+ Network.AWS.Data.Log: instance ToLog ByteString
+ Network.AWS.Data.Log: instance ToLog Char
+ Network.AWS.Data.Log: instance ToLog Double
+ Network.AWS.Data.Log: instance ToLog EscapedPath
+ Network.AWS.Data.Log: instance ToLog Float
+ Network.AWS.Data.Log: instance ToLog HttpException
+ Network.AWS.Data.Log: instance ToLog HttpVersion
+ Network.AWS.Data.Log: instance ToLog Int
+ Network.AWS.Data.Log: instance ToLog Int16
+ Network.AWS.Data.Log: instance ToLog Int32
+ Network.AWS.Data.Log: instance ToLog Int64
+ Network.AWS.Data.Log: instance ToLog Int8
+ Network.AWS.Data.Log: instance ToLog Integer
+ Network.AWS.Data.Log: instance ToLog QueryString
+ Network.AWS.Data.Log: instance ToLog Request
+ Network.AWS.Data.Log: instance ToLog RequestBody
+ Network.AWS.Data.Log: instance ToLog Status
+ Network.AWS.Data.Log: instance ToLog StdMethod
+ Network.AWS.Data.Log: instance ToLog Text
+ Network.AWS.Data.Log: instance ToLog UTCTime
+ Network.AWS.Data.Log: instance ToLog Word
+ Network.AWS.Data.Log: instance ToLog Word16
+ Network.AWS.Data.Log: instance ToLog Word32
+ Network.AWS.Data.Log: instance ToLog Word64
+ Network.AWS.Data.Log: instance ToLog Word8
+ Network.AWS.Data.Log: instance ToLog [Char]
+ Network.AWS.Data.Log: instance ToLog [Header]
+ Network.AWS.Data.Log: instance ToLog a => ToLog (CI a)
+ Network.AWS.Data.Log: instance ToLog a => ToLog (Maybe a)
+ Network.AWS.Data.Map: Map :: HashMap k v -> Map k v
+ Network.AWS.Data.Map: _Map :: (Coercible a b, Coercible b a) => Iso' (Map k a) (HashMap k b)
+ Network.AWS.Data.Map: instance (Eq k, Data k, Data v, Hashable k) => Data (Map k v)
+ Network.AWS.Data.Map: instance (Eq k, Eq v) => Eq (Map k v)
+ Network.AWS.Data.Map: instance (Eq k, Hashable k) => Monoid (Map k v)
+ Network.AWS.Data.Map: instance (Eq k, Hashable k) => Semigroup (Map k v)
+ Network.AWS.Data.Map: instance (Eq k, Hashable k, FromText k, FromJSON v) => FromJSON (Map k v)
+ Network.AWS.Data.Map: instance (Eq k, Hashable k, ToByteString k, ToText v) => ToHeader (Map k v)
+ Network.AWS.Data.Map: instance (Eq k, Hashable k, ToText k, ToJSON v) => ToJSON (Map k v)
+ Network.AWS.Data.Map: instance (Eq k, Read k, Read v, Hashable k) => Read (Map k v)
+ Network.AWS.Data.Map: instance (Hashable k, Eq k) => IsList (Map k v)
+ Network.AWS.Data.Map: instance (Show k, Show v) => Show (Map k v)
+ Network.AWS.Data.Map: instance Constructor C1_0Map
+ Network.AWS.Data.Map: instance Datatype D1Map
+ Network.AWS.Data.Map: instance Foldable (Map k)
+ Network.AWS.Data.Map: instance Functor (Map k)
+ Network.AWS.Data.Map: instance Generic (Map k v)
+ Network.AWS.Data.Map: instance Selector S1_0_0Map
+ Network.AWS.Data.Map: instance Traversable (Map k)
+ Network.AWS.Data.Map: instance Typeable Map
+ Network.AWS.Data.Map: newtype Map k v
+ Network.AWS.Data.Map: parseHeadersMap :: FromText a => ByteString -> ResponseHeaders -> Either String (Map Text a)
+ Network.AWS.Data.Map: parseXMLMap :: (Eq k, Hashable k, FromText k, FromXML v) => Text -> Text -> Text -> [Node] -> Either String (Map k v)
+ Network.AWS.Data.Map: toMap :: Map k v -> HashMap k v
+ Network.AWS.Data.Map: toQueryMap :: (Hashable k, Eq k, ToQuery k, ToQuery v) => ByteString -> ByteString -> ByteString -> Map k v -> QueryString
+ Network.AWS.Data.Numeric: Nat :: Natural -> Nat
+ Network.AWS.Data.Numeric: _Nat :: Iso' Nat Natural
+ Network.AWS.Data.Numeric: instance Constructor C1_0Nat
+ Network.AWS.Data.Numeric: instance Data Nat
+ Network.AWS.Data.Numeric: instance Datatype D1Nat
+ Network.AWS.Data.Numeric: instance Enum Nat
+ Network.AWS.Data.Numeric: instance Eq Nat
+ Network.AWS.Data.Numeric: instance FromJSON Nat
+ Network.AWS.Data.Numeric: instance FromText Nat
+ Network.AWS.Data.Numeric: instance FromXML Nat
+ Network.AWS.Data.Numeric: instance Generic Nat
+ Network.AWS.Data.Numeric: instance Integral Nat
+ Network.AWS.Data.Numeric: instance Num Nat
+ Network.AWS.Data.Numeric: instance Ord Nat
+ Network.AWS.Data.Numeric: instance Read Nat
+ Network.AWS.Data.Numeric: instance Real Nat
+ Network.AWS.Data.Numeric: instance Selector S1_0_0Nat
+ Network.AWS.Data.Numeric: instance Show Nat
+ Network.AWS.Data.Numeric: instance ToByteString Nat
+ Network.AWS.Data.Numeric: instance ToJSON Nat
+ Network.AWS.Data.Numeric: instance ToQuery Nat
+ Network.AWS.Data.Numeric: instance ToText Nat
+ Network.AWS.Data.Numeric: instance ToXML Nat
+ Network.AWS.Data.Numeric: instance Typeable Nat
+ Network.AWS.Data.Numeric: newtype Nat
+ Network.AWS.Data.Numeric: unNat :: Nat -> Natural
+ Network.AWS.Data.Path: class ToPath a
+ Network.AWS.Data.Path: collapsePath :: Path a -> Path a
+ Network.AWS.Data.Path: escapePath :: Path a -> EscapedPath
+ Network.AWS.Data.Path: instance Eq (Path a)
+ Network.AWS.Data.Path: instance Eq Encoding
+ Network.AWS.Data.Path: instance Monoid RawPath
+ Network.AWS.Data.Path: instance Show (Path a)
+ Network.AWS.Data.Path: instance Show Encoding
+ Network.AWS.Data.Path: instance ToByteString EscapedPath
+ Network.AWS.Data.Path: instance ToPath ByteString
+ Network.AWS.Data.Path: instance ToPath Text
+ Network.AWS.Data.Path: rawPath :: ToPath a => a -> Path NoEncoding
+ Network.AWS.Data.Path: toPath :: ToPath a => a -> ByteString
+ Network.AWS.Data.Path: type EscapedPath = Path Percent
+ Network.AWS.Data.Path: type RawPath = Path NoEncoding
+ Network.AWS.Data.Query: (=:) :: ToQuery a => ByteString -> a -> QueryString
+ Network.AWS.Data.Query: QList :: [QueryString] -> QueryString
+ Network.AWS.Data.Query: QPair :: ByteString -> QueryString -> QueryString
+ Network.AWS.Data.Query: QValue :: (Maybe ByteString) -> QueryString
+ Network.AWS.Data.Query: class ToQuery a where toQuery = toQuery . toText
+ Network.AWS.Data.Query: data QueryString
+ Network.AWS.Data.Query: instance (ToByteString k, ToQuery v) => ToQuery (k, v)
+ Network.AWS.Data.Query: instance Data QueryString
+ Network.AWS.Data.Query: instance Eq QueryString
+ Network.AWS.Data.Query: instance IsString QueryString
+ Network.AWS.Data.Query: instance Monoid QueryString
+ Network.AWS.Data.Query: instance Show QueryString
+ Network.AWS.Data.Query: instance ToByteString QueryString
+ Network.AWS.Data.Query: instance ToQuery Bool
+ Network.AWS.Data.Query: instance ToQuery ByteString
+ Network.AWS.Data.Query: instance ToQuery Char
+ Network.AWS.Data.Query: instance ToQuery Double
+ Network.AWS.Data.Query: instance ToQuery Int
+ Network.AWS.Data.Query: instance ToQuery Integer
+ Network.AWS.Data.Query: instance ToQuery Natural
+ Network.AWS.Data.Query: instance ToQuery QueryString
+ Network.AWS.Data.Query: instance ToQuery Text
+ Network.AWS.Data.Query: instance ToQuery a => ToQuery (Maybe a)
+ Network.AWS.Data.Query: instance Typeable QueryString
+ Network.AWS.Data.Query: pair :: ToQuery a => ByteString -> a -> QueryString -> QueryString
+ Network.AWS.Data.Query: toQuery :: ToQuery a => a -> QueryString
+ Network.AWS.Data.Query: toQueryList :: (IsList a, ToQuery (Item a)) => ByteString -> a -> QueryString
+ Network.AWS.Data.Sensitive: Sensitive :: a -> Sensitive a
+ Network.AWS.Data.Sensitive: _Sensitive :: Iso' (Sensitive a) a
+ Network.AWS.Data.Sensitive: desensitise :: Sensitive a -> a
+ Network.AWS.Data.Sensitive: instance Constructor C1_0Sensitive
+ Network.AWS.Data.Sensitive: instance Data a => Data (Sensitive a)
+ Network.AWS.Data.Sensitive: instance Datatype D1Sensitive
+ Network.AWS.Data.Sensitive: instance Eq a => Eq (Sensitive a)
+ Network.AWS.Data.Sensitive: instance FromJSON a => FromJSON (Sensitive a)
+ Network.AWS.Data.Sensitive: instance FromText a => FromText (Sensitive a)
+ Network.AWS.Data.Sensitive: instance FromXML a => FromXML (Sensitive a)
+ Network.AWS.Data.Sensitive: instance Generic (Sensitive a)
+ Network.AWS.Data.Sensitive: instance IsString a => IsString (Sensitive a)
+ Network.AWS.Data.Sensitive: instance Monoid a => Monoid (Sensitive a)
+ Network.AWS.Data.Sensitive: instance Ord a => Ord (Sensitive a)
+ Network.AWS.Data.Sensitive: instance Read a => Read (Sensitive a)
+ Network.AWS.Data.Sensitive: instance Selector S1_0_0Sensitive
+ Network.AWS.Data.Sensitive: instance Show (Sensitive a)
+ Network.AWS.Data.Sensitive: instance ToByteString a => ToByteString (Sensitive a)
+ Network.AWS.Data.Sensitive: instance ToJSON a => ToJSON (Sensitive a)
+ Network.AWS.Data.Sensitive: instance ToQuery a => ToQuery (Sensitive a)
+ Network.AWS.Data.Sensitive: instance ToText a => ToText (Sensitive a)
+ Network.AWS.Data.Sensitive: instance ToXML a => ToXML (Sensitive a)
+ Network.AWS.Data.Sensitive: instance Typeable Sensitive
+ Network.AWS.Data.Sensitive: newtype Sensitive a
+ Network.AWS.Data.Text: class FromText a
+ Network.AWS.Data.Text: class ToText a
+ Network.AWS.Data.Text: data Text :: *
+ Network.AWS.Data.Text: fromText :: FromText a => Text -> Either String a
+ Network.AWS.Data.Text: fromTextError :: Text -> Parser a
+ Network.AWS.Data.Text: instance FromText Bool
+ Network.AWS.Data.Text: instance FromText ByteString
+ Network.AWS.Data.Text: instance FromText Char
+ Network.AWS.Data.Text: instance FromText Double
+ Network.AWS.Data.Text: instance FromText Int
+ Network.AWS.Data.Text: instance FromText Integer
+ Network.AWS.Data.Text: instance FromText Natural
+ Network.AWS.Data.Text: instance FromText Scientific
+ Network.AWS.Data.Text: instance FromText StdMethod
+ Network.AWS.Data.Text: instance FromText Text
+ Network.AWS.Data.Text: instance ToText (Digest a)
+ Network.AWS.Data.Text: instance ToText Bool
+ Network.AWS.Data.Text: instance ToText ByteString
+ Network.AWS.Data.Text: instance ToText Char
+ Network.AWS.Data.Text: instance ToText Double
+ Network.AWS.Data.Text: instance ToText Int
+ Network.AWS.Data.Text: instance ToText Int64
+ Network.AWS.Data.Text: instance ToText Integer
+ Network.AWS.Data.Text: instance ToText Natural
+ Network.AWS.Data.Text: instance ToText Scientific
+ Network.AWS.Data.Text: instance ToText StdMethod
+ Network.AWS.Data.Text: instance ToText String
+ Network.AWS.Data.Text: instance ToText Text
+ Network.AWS.Data.Text: instance ToText a => ToText (CI a)
+ Network.AWS.Data.Text: matchCI :: Text -> a -> Parser a
+ Network.AWS.Data.Text: parser :: FromText a => Parser a
+ Network.AWS.Data.Text: showText :: ToText a => a -> String
+ Network.AWS.Data.Text: takeLowerText :: Parser Text
+ Network.AWS.Data.Text: takeText :: Parser Text
+ Network.AWS.Data.Text: toText :: ToText a => a -> Text
+ Network.AWS.Data.Text: toTextCI :: ToText a => a -> CI Text
+ Network.AWS.Data.Time: AWSFormat :: Format
+ Network.AWS.Data.Time: BasicFormat :: Format
+ Network.AWS.Data.Time: ISO8601Format :: Format
+ Network.AWS.Data.Time: POSIXFormat :: Format
+ Network.AWS.Data.Time: RFC822Format :: Format
+ Network.AWS.Data.Time: Time :: UTCTime -> Time a
+ Network.AWS.Data.Time: _Time :: Iso' (Time a) UTCTime
+ Network.AWS.Data.Time: data Format
+ Network.AWS.Data.Time: data Time :: Format -> *
+ Network.AWS.Data.Time: data UTCTime :: *
+ Network.AWS.Data.Time: instance Constructor C1_0Format
+ Network.AWS.Data.Time: instance Constructor C1_0Time
+ Network.AWS.Data.Time: instance Constructor C1_1Format
+ Network.AWS.Data.Time: instance Constructor C1_2Format
+ Network.AWS.Data.Time: instance Constructor C1_3Format
+ Network.AWS.Data.Time: instance Constructor C1_4Format
+ Network.AWS.Data.Time: instance Data Format
+ Network.AWS.Data.Time: instance Datatype D1Format
+ Network.AWS.Data.Time: instance Datatype D1Time
+ Network.AWS.Data.Time: instance Eq (Time a)
+ Network.AWS.Data.Time: instance Eq Format
+ Network.AWS.Data.Time: instance FromJSON AWSTime
+ Network.AWS.Data.Time: instance FromJSON BasicTime
+ Network.AWS.Data.Time: instance FromJSON ISO8601
+ Network.AWS.Data.Time: instance FromJSON POSIX
+ Network.AWS.Data.Time: instance FromJSON RFC822
+ Network.AWS.Data.Time: instance FromText AWSTime
+ Network.AWS.Data.Time: instance FromText BasicTime
+ Network.AWS.Data.Time: instance FromText ISO8601
+ Network.AWS.Data.Time: instance FromText POSIX
+ Network.AWS.Data.Time: instance FromText RFC822
+ Network.AWS.Data.Time: instance FromXML AWSTime
+ Network.AWS.Data.Time: instance FromXML BasicTime
+ Network.AWS.Data.Time: instance FromXML ISO8601
+ Network.AWS.Data.Time: instance FromXML POSIX
+ Network.AWS.Data.Time: instance FromXML RFC822
+ Network.AWS.Data.Time: instance Generic (Time $a)
+ Network.AWS.Data.Time: instance Generic Format
+ Network.AWS.Data.Time: instance Ord (Time a)
+ Network.AWS.Data.Time: instance Read (Time a)
+ Network.AWS.Data.Time: instance Read Format
+ Network.AWS.Data.Time: instance Show (Time a)
+ Network.AWS.Data.Time: instance Show Format
+ Network.AWS.Data.Time: instance TimeFormat AWSTime
+ Network.AWS.Data.Time: instance TimeFormat BasicTime
+ Network.AWS.Data.Time: instance TimeFormat ISO8601
+ Network.AWS.Data.Time: instance TimeFormat RFC822
+ Network.AWS.Data.Time: instance ToByteString AWSTime
+ Network.AWS.Data.Time: instance ToByteString BasicTime
+ Network.AWS.Data.Time: instance ToByteString ISO8601
+ Network.AWS.Data.Time: instance ToByteString RFC822
+ Network.AWS.Data.Time: instance ToJSON AWSTime
+ Network.AWS.Data.Time: instance ToJSON BasicTime
+ Network.AWS.Data.Time: instance ToJSON ISO8601
+ Network.AWS.Data.Time: instance ToJSON POSIX
+ Network.AWS.Data.Time: instance ToJSON RFC822
+ Network.AWS.Data.Time: instance ToQuery AWSTime
+ Network.AWS.Data.Time: instance ToQuery BasicTime
+ Network.AWS.Data.Time: instance ToQuery ISO8601
+ Network.AWS.Data.Time: instance ToQuery RFC822
+ Network.AWS.Data.Time: instance ToText AWSTime
+ Network.AWS.Data.Time: instance ToText BasicTime
+ Network.AWS.Data.Time: instance ToText ISO8601
+ Network.AWS.Data.Time: instance ToText POSIX
+ Network.AWS.Data.Time: instance ToText RFC822
+ Network.AWS.Data.Time: instance ToXML AWSTime
+ Network.AWS.Data.Time: instance ToXML BasicTime
+ Network.AWS.Data.Time: instance ToXML ISO8601
+ Network.AWS.Data.Time: instance ToXML POSIX
+ Network.AWS.Data.Time: instance ToXML RFC822
+ Network.AWS.Data.Time: instance Typeable $a => Data (Time $a)
+ Network.AWS.Data.Time: instance Typeable 'AWSFormat
+ Network.AWS.Data.Time: instance Typeable 'BasicFormat
+ Network.AWS.Data.Time: instance Typeable 'ISO8601Format
+ Network.AWS.Data.Time: instance Typeable 'POSIXFormat
+ Network.AWS.Data.Time: instance Typeable 'RFC822Format
+ Network.AWS.Data.Time: instance Typeable Format
+ Network.AWS.Data.Time: instance Typeable Time
+ Network.AWS.Data.Time: type AWSTime = Time AWSFormat
+ Network.AWS.Data.Time: type BasicTime = Time BasicFormat
+ Network.AWS.Data.Time: type ISO8601 = Time ISO8601Format
+ Network.AWS.Data.Time: type POSIX = Time POSIXFormat
+ Network.AWS.Data.Time: type RFC822 = Time RFC822Format
+ Network.AWS.Data.XML: (.@) :: FromXML a => [Node] -> Text -> Either String a
+ Network.AWS.Data.XML: (.@?) :: FromXML a => [Node] -> Text -> Either String (Maybe a)
+ Network.AWS.Data.XML: (@=) :: ToXML a => Name -> a -> XML
+ Network.AWS.Data.XML: XMany :: [Node] -> XML
+ Network.AWS.Data.XML: XNull :: XML
+ Network.AWS.Data.XML: XOne :: Node -> XML
+ Network.AWS.Data.XML: childNodesOf :: Text -> Node -> Maybe [Node]
+ Network.AWS.Data.XML: class FromXML a
+ Network.AWS.Data.XML: class ToElement a
+ Network.AWS.Data.XML: class ToXML a
+ Network.AWS.Data.XML: data XML
+ Network.AWS.Data.XML: decodeXML :: FromXML a => LazyByteString -> Either String a
+ Network.AWS.Data.XML: encodeXML :: ToElement a => a -> LazyByteString
+ Network.AWS.Data.XML: findElement :: Text -> [Node] -> Either String [Node]
+ Network.AWS.Data.XML: instance FromXML Bool
+ Network.AWS.Data.XML: instance FromXML ByteString
+ Network.AWS.Data.XML: instance FromXML Char
+ Network.AWS.Data.XML: instance FromXML Double
+ Network.AWS.Data.XML: instance FromXML Int
+ Network.AWS.Data.XML: instance FromXML Integer
+ Network.AWS.Data.XML: instance FromXML Natural
+ Network.AWS.Data.XML: instance FromXML Text
+ Network.AWS.Data.XML: instance FromXML [Node]
+ Network.AWS.Data.XML: instance FromXML a => FromXML (Maybe a)
+ Network.AWS.Data.XML: instance Monoid XML
+ Network.AWS.Data.XML: instance Show XML
+ Network.AWS.Data.XML: instance ToElement Element
+ Network.AWS.Data.XML: instance ToXML Bool
+ Network.AWS.Data.XML: instance ToXML ByteString
+ Network.AWS.Data.XML: instance ToXML Double
+ Network.AWS.Data.XML: instance ToXML Int
+ Network.AWS.Data.XML: instance ToXML Integer
+ Network.AWS.Data.XML: instance ToXML Natural
+ Network.AWS.Data.XML: instance ToXML Text
+ Network.AWS.Data.XML: instance ToXML XML
+ Network.AWS.Data.XML: instance ToXML a => ToXML (Maybe a)
+ Network.AWS.Data.XML: listXMLNodes :: XML -> [Node]
+ Network.AWS.Data.XML: localName :: Node -> Maybe Text
+ Network.AWS.Data.XML: mkElement :: ToXML a => Name -> a -> Element
+ Network.AWS.Data.XML: parseXML :: FromXML a => [Node] -> Either String a
+ Network.AWS.Data.XML: parseXMLList :: FromXML a => Text -> [Node] -> Either String [a]
+ Network.AWS.Data.XML: parseXMLText :: FromText a => String -> [Node] -> Either String a
+ Network.AWS.Data.XML: toElement :: ToElement a => a -> Element
+ Network.AWS.Data.XML: toXML :: ToXML a => a -> XML
+ Network.AWS.Data.XML: toXMLList :: (IsList a, ToXML (Item a)) => Name -> a -> XML
+ Network.AWS.Data.XML: toXMLNodes :: ToXML a => a -> [Node]
+ Network.AWS.Data.XML: toXMLText :: ToText a => a -> XML
+ Network.AWS.Data.XML: withContent :: String -> [Node] -> Either String (Maybe Text)
+ Network.AWS.Data.XML: withElement :: Text -> ([Node] -> Either String a) -> [Node] -> Either String a
+ Network.AWS.Endpoint: defaultEndpoint :: Service s -> Region -> Endpoint
+ Network.AWS.Error: decodeError :: Abbrev -> Status -> [Header] -> LazyByteString -> Either String ServiceError -> Error
+ Network.AWS.Error: getErrorCode :: Status -> [Header] -> ErrorCode
+ Network.AWS.Error: getRequestId :: [Header] -> Maybe RequestId
+ Network.AWS.Error: hasCode :: (Applicative f, Choice p) => ErrorCode -> Optic' p f ServiceError ServiceError
+ Network.AWS.Error: hasStatus :: (Applicative f, Choice p) => Int -> Optic' p f ServiceError ServiceError
+ Network.AWS.Error: httpStatus :: AsError a => Getting (First Status) a Status
+ Network.AWS.Error: parseJSONError :: Abbrev -> Status -> [Header] -> LazyByteString -> Error
+ Network.AWS.Error: parseRESTError :: Abbrev -> Status -> [Header] -> a -> Error
+ Network.AWS.Error: parseXMLError :: Abbrev -> Status -> [Header] -> LazyByteString -> Error
+ Network.AWS.Error: serviceError :: Abbrev -> Status -> [Header] -> Maybe ErrorCode -> Maybe ErrorMessage -> Maybe RequestId -> ServiceError
+ Network.AWS.Pager: choice :: (Alternative f, ToText a, ToText b) => (s -> f a) -> (s -> f b) -> Getter s (f Text)
+ Network.AWS.Pager: class AWSRequest a => AWSPager a
+ Network.AWS.Pager: class AWSTruncated a
+ Network.AWS.Pager: instance AWSTruncated (HashMap k v)
+ Network.AWS.Pager: instance AWSTruncated (Maybe Bool)
+ Network.AWS.Pager: instance AWSTruncated (Maybe Text)
+ Network.AWS.Pager: instance AWSTruncated Bool
+ Network.AWS.Pager: instance AWSTruncated [a]
+ Network.AWS.Pager: page :: AWSPager a => a -> Rs a -> Maybe a
+ Network.AWS.Pager: stop :: AWSTruncated a => a -> Bool
+ Network.AWS.Pager: truncated :: AWSTruncated a => a -> Bool
+ Network.AWS.Prelude: (.!@) :: Functor f => f (Maybe a) -> a -> f a
+ Network.AWS.Prelude: may :: Applicative f => ([a] -> f b) -> [a] -> f (Maybe b)
+ Network.AWS.Request: contentMD5 :: Request a -> Request a
+ Network.AWS.Request: contentSHA256 :: Request a -> Request a
+ Network.AWS.Request: defaultRequest :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
+ Network.AWS.Request: delete :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
+ Network.AWS.Request: get :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
+ Network.AWS.Request: head' :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
+ Network.AWS.Request: post :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
+ Network.AWS.Request: postBody :: (ToPath a, ToQuery a, ToHeaders a, ToBody a) => a -> Request a
+ Network.AWS.Request: postJSON :: (ToQuery a, ToPath a, ToHeaders a, ToJSON a) => a -> Request a
+ Network.AWS.Request: postQuery :: (ToQuery a, ToPath a, ToHeaders a) => a -> Request a
+ Network.AWS.Request: postXML :: (ToQuery a, ToPath a, ToHeaders a, ToElement a) => a -> Request a
+ Network.AWS.Request: put :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a
+ Network.AWS.Request: putBody :: (ToPath a, ToQuery a, ToHeaders a, ToBody a) => a -> Request a
+ Network.AWS.Request: putJSON :: (ToQuery a, ToPath a, ToHeaders a, ToJSON a) => a -> Request a
+ Network.AWS.Request: putXML :: (ToPath a, ToQuery a, ToHeaders a, ToElement a) => a -> Request a
+ Network.AWS.Request: queryString :: Lens' Request ByteString
+ Network.AWS.Request: requestHeaders :: Lens' Request RequestHeaders
+ Network.AWS.Request: requestURL :: ClientRequest -> ByteString
+ Network.AWS.Response: deserialise :: MonadResource m => (LazyByteString -> Either String b) -> (Int -> ResponseHeaders -> b -> Either String (Rs a)) -> Logger -> Service s -> Request a -> ClientResponse -> m (Response a)
+ Network.AWS.Response: receive :: MonadResource m => (Int -> ResponseHeaders -> ResponseBody -> m (Either String (Rs a))) -> Service s -> Request a -> ClientResponse -> m (Response a)
+ Network.AWS.Response: receiveBody :: MonadResource m => (Int -> ResponseHeaders -> RsBody -> Either String (Rs a)) -> Logger -> Service s -> Request a -> ClientResponse -> m (Response a)
+ Network.AWS.Response: receiveEmpty :: MonadResource m => (Int -> ResponseHeaders -> () -> Either String (Rs a)) -> Logger -> Service s -> Request a -> ClientResponse -> m (Response a)
+ Network.AWS.Response: receiveJSON :: MonadResource m => (Int -> ResponseHeaders -> Object -> Either String (Rs a)) -> Logger -> Service s -> Request a -> ClientResponse -> m (Response a)
+ Network.AWS.Response: receiveNull :: MonadResource m => Rs a -> Logger -> Service s -> Request a -> ClientResponse -> m (Response a)
+ Network.AWS.Response: receiveXML :: MonadResource m => (Int -> ResponseHeaders -> [Node] -> Either String (Rs a)) -> Logger -> Service s -> Request a -> ClientResponse -> m (Response a)
+ Network.AWS.Response: receiveXMLWrapper :: MonadResource m => Text -> (Int -> ResponseHeaders -> [Node] -> Either String (Rs a)) -> Logger -> Service s -> Request a -> ClientResponse -> m (Response a)
+ Network.AWS.Response: sinkLBS :: MonadResource m => ResponseBody -> m LazyByteString
+ Network.AWS.Sign.V2: data V2
+ Network.AWS.Sign.V2: instance AWSSigner V2
+ Network.AWS.Sign.V2: instance ToLog (Meta V2)
+ Network.AWS.Sign.V4: data V4
+ Network.AWS.Sign.V4: instance AWSPresigner V4
+ Network.AWS.Sign.V4: instance AWSSigner V4
+ Network.AWS.Sign.V4: instance ToByteString (Tag s ByteString)
+ Network.AWS.Sign.V4: instance ToByteString CredentialScope
+ Network.AWS.Sign.V4: instance ToLog (Meta V4)
+ Network.AWS.Sign.V4: instance ToLog (Tag s ByteString)
+ Network.AWS.Types: Error :: LogLevel
+ Network.AWS.Types: ErrorCode :: Text -> ErrorCode
+ Network.AWS.Types: ErrorMessage :: Text -> ErrorMessage
+ Network.AWS.Types: RequestId :: Text -> RequestId
+ Network.AWS.Types: Seconds :: Int -> Seconds
+ Network.AWS.Types: SerializeError :: SerializeError -> Error
+ Network.AWS.Types: SerializeError' :: !Abbrev -> !Status -> String -> SerializeError
+ Network.AWS.Types: ServiceError' :: !Abbrev -> !Status -> [Header] -> !ErrorCode -> Maybe ErrorMessage -> Maybe RequestId -> ServiceError
+ Network.AWS.Types: SessionToken :: ByteString -> SessionToken
+ Network.AWS.Types: TransportError :: HttpException -> Error
+ Network.AWS.Types: _Coerce :: (Coercible a b, Coercible b a) => Iso' a b
+ Network.AWS.Types: _Default :: Monoid a => Iso' (Maybe a) a
+ Network.AWS.Types: _Error :: AsError a => Prism' a Error
+ Network.AWS.Types: _Seconds :: Iso' Seconds Int
+ Network.AWS.Types: _SerializeError :: AsError a => Prism' a SerializeError
+ Network.AWS.Types: _TransportError :: AsError a => Prism' a HttpException
+ Network.AWS.Types: _serializeAbbrev :: SerializeError -> !Abbrev
+ Network.AWS.Types: _serializeMessage :: SerializeError -> String
+ Network.AWS.Types: _serializeStatus :: SerializeError -> !Status
+ Network.AWS.Types: _serviceAbbrev :: ServiceError -> !Abbrev
+ Network.AWS.Types: _serviceCode :: ServiceError -> !ErrorCode
+ Network.AWS.Types: _serviceHeaders :: ServiceError -> [Header]
+ Network.AWS.Types: _serviceMessage :: ServiceError -> Maybe ErrorMessage
+ Network.AWS.Types: _serviceRequestId :: ServiceError -> Maybe RequestId
+ Network.AWS.Types: _serviceStatus :: ServiceError -> !Status
+ Network.AWS.Types: _svcEndpoint :: Service s -> Region -> Endpoint
+ Network.AWS.Types: _svcError :: Service s -> Abbrev -> Status -> [Header] -> LazyByteString -> Error
+ Network.AWS.Types: _svcStatus :: Service s -> Status -> Bool
+ Network.AWS.Types: _svcTimeout :: Service s -> Maybe Seconds
+ Network.AWS.Types: class AsError a where _TransportError = _Error . _TransportError _SerializeError = _Error . _SerializeError _ServiceError = _Error . _ServiceError
+ Network.AWS.Types: data Abbrev
+ Network.AWS.Types: data Error
+ Network.AWS.Types: data HttpException :: *
+ Network.AWS.Types: data SerializeError
+ Network.AWS.Types: instance AsError Error
+ Network.AWS.Types: instance AsError SomeException
+ Network.AWS.Types: instance Bounded Seconds
+ Network.AWS.Types: instance Constructor C1_0Seconds
+ Network.AWS.Types: instance Data Endpoint
+ Network.AWS.Types: instance Data Region
+ Network.AWS.Types: instance Data Seconds
+ Network.AWS.Types: instance Datatype D1Seconds
+ Network.AWS.Types: instance Enum Seconds
+ Network.AWS.Types: instance Eq Abbrev
+ Network.AWS.Types: instance Eq ErrorCode
+ Network.AWS.Types: instance Eq ErrorMessage
+ Network.AWS.Types: instance Eq RequestId
+ Network.AWS.Types: instance Eq Seconds
+ Network.AWS.Types: instance Eq SerializeError
+ Network.AWS.Types: instance Eq ServiceError
+ Network.AWS.Types: instance Eq SessionToken
+ Network.AWS.Types: instance Exception Error
+ Network.AWS.Types: instance FromJSON Abbrev
+ Network.AWS.Types: instance FromJSON ErrorCode
+ Network.AWS.Types: instance FromJSON ErrorMessage
+ Network.AWS.Types: instance FromJSON RequestId
+ Network.AWS.Types: instance FromText Abbrev
+ Network.AWS.Types: instance FromText ErrorCode
+ Network.AWS.Types: instance FromText ErrorMessage
+ Network.AWS.Types: instance FromText RequestId
+ Network.AWS.Types: instance FromXML Abbrev
+ Network.AWS.Types: instance FromXML ErrorCode
+ Network.AWS.Types: instance FromXML ErrorMessage
+ Network.AWS.Types: instance FromXML RequestId
+ Network.AWS.Types: instance Generic Seconds
+ Network.AWS.Types: instance Integral Seconds
+ Network.AWS.Types: instance IsString Abbrev
+ Network.AWS.Types: instance IsString ErrorCode
+ Network.AWS.Types: instance IsString ErrorMessage
+ Network.AWS.Types: instance IsString RequestId
+ Network.AWS.Types: instance IsString SessionToken
+ Network.AWS.Types: instance Num Seconds
+ Network.AWS.Types: instance Ord Abbrev
+ Network.AWS.Types: instance Ord ErrorCode
+ Network.AWS.Types: instance Ord ErrorMessage
+ Network.AWS.Types: instance Ord RequestId
+ Network.AWS.Types: instance Ord Seconds
+ Network.AWS.Types: instance Read Seconds
+ Network.AWS.Types: instance Real Seconds
+ Network.AWS.Types: instance Show (Request a)
+ Network.AWS.Types: instance Show Abbrev
+ Network.AWS.Types: instance Show Error
+ Network.AWS.Types: instance Show ErrorCode
+ Network.AWS.Types: instance Show ErrorMessage
+ Network.AWS.Types: instance Show RequestId
+ Network.AWS.Types: instance Show Seconds
+ Network.AWS.Types: instance Show SerializeError
+ Network.AWS.Types: instance Show ServiceError
+ Network.AWS.Types: instance ToByteString Seconds
+ Network.AWS.Types: instance ToByteString SessionToken
+ Network.AWS.Types: instance ToLog (Request a)
+ Network.AWS.Types: instance ToLog Abbrev
+ Network.AWS.Types: instance ToLog AccessKey
+ Network.AWS.Types: instance ToLog Auth
+ Network.AWS.Types: instance ToLog AuthEnv
+ Network.AWS.Types: instance ToLog Error
+ Network.AWS.Types: instance ToLog ErrorCode
+ Network.AWS.Types: instance ToLog ErrorMessage
+ Network.AWS.Types: instance ToLog Region
+ Network.AWS.Types: instance ToLog RequestId
+ Network.AWS.Types: instance ToLog Seconds
+ Network.AWS.Types: instance ToLog SerializeError
+ Network.AWS.Types: instance ToLog ServiceError
+ Network.AWS.Types: instance ToQuery Seconds
+ Network.AWS.Types: instance ToText Abbrev
+ Network.AWS.Types: instance ToText ErrorCode
+ Network.AWS.Types: instance ToText ErrorMessage
+ Network.AWS.Types: instance ToText RequestId
+ Network.AWS.Types: instance ToText Seconds
+ Network.AWS.Types: instance ToText SessionToken
+ Network.AWS.Types: instance Typeable Endpoint
+ Network.AWS.Types: instance Typeable Error
+ Network.AWS.Types: instance Typeable Region
+ Network.AWS.Types: instance Typeable Seconds
+ Network.AWS.Types: instance Typeable SerializeError
+ Network.AWS.Types: microseconds :: Seconds -> Int
+ Network.AWS.Types: newtype ErrorCode
+ Network.AWS.Types: newtype ErrorMessage
+ Network.AWS.Types: newtype RequestId
+ Network.AWS.Types: newtype Seconds
+ Network.AWS.Types: newtype SessionToken
+ Network.AWS.Types: seconds :: Seconds -> Int
+ Network.AWS.Types: serializeAbbrev :: Lens' SerializeError Abbrev
+ Network.AWS.Types: serializeMessage :: Lens' SerializeError String
+ Network.AWS.Types: serializeStatus :: Lens' SerializeError Status
+ Network.AWS.Types: serviceAbbrev :: Lens' ServiceError Abbrev
+ Network.AWS.Types: serviceCode :: Lens' ServiceError ErrorCode
+ Network.AWS.Types: serviceHeaders :: Lens' ServiceError [Header]
+ Network.AWS.Types: serviceMessage :: Lens' ServiceError (Maybe ErrorMessage)
+ Network.AWS.Types: serviceRequestId :: Lens' ServiceError (Maybe RequestId)
+ Network.AWS.Types: serviceStatus :: Lens' ServiceError Status
+ Network.AWS.Waiter: AcceptFailure :: Accept
+ Network.AWS.Waiter: AcceptRetry :: Accept
+ Network.AWS.Waiter: AcceptSuccess :: Accept
+ Network.AWS.Waiter: Wait :: ByteString -> !Int -> !Seconds -> [Acceptor a] -> Wait a
+ Network.AWS.Waiter: _waitAcceptors :: Wait a -> [Acceptor a]
+ Network.AWS.Waiter: _waitAttempts :: Wait a -> !Int
+ Network.AWS.Waiter: _waitDelay :: Wait a -> !Seconds
+ Network.AWS.Waiter: _waitName :: Wait a -> ByteString
+ Network.AWS.Waiter: accept :: Wait a -> Acceptor a
+ Network.AWS.Waiter: data Accept
+ Network.AWS.Waiter: data Wait a
+ Network.AWS.Waiter: instance Eq Accept
+ Network.AWS.Waiter: instance Show Accept
+ Network.AWS.Waiter: instance ToLog Accept
+ Network.AWS.Waiter: matchAll :: Eq b => b -> Accept -> Fold (Rs a) b -> Acceptor a
+ Network.AWS.Waiter: matchAny :: Eq b => b -> Accept -> Fold (Rs a) b -> Acceptor a
+ Network.AWS.Waiter: matchError :: ErrorCode -> Accept -> Acceptor a
+ Network.AWS.Waiter: matchStatus :: Int -> Accept -> Acceptor a
+ Network.AWS.Waiter: nonEmpty :: Fold a Text -> Fold a Bool
+ Network.AWS.Waiter: type Acceptor a = Request a -> Either Error (Response a) -> Maybe Accept
- Network.AWS.Types: AuthEnv :: !AccessKey -> !SecretKey -> Maybe SecurityToken -> Maybe UTCTime -> AuthEnv
+ Network.AWS.Types: AuthEnv :: !AccessKey -> !SecretKey -> Maybe SessionToken -> Maybe UTCTime -> AuthEnv
- Network.AWS.Types: Exponential :: !Double -> !Int -> !Int -> (Status -> Er a -> Bool) -> Retry a
+ Network.AWS.Types: Exponential :: !Double -> !Int -> !Int -> (ServiceError -> Maybe Text) -> Retry
- Network.AWS.Types: Request :: !StdMethod -> !ByteString -> Query -> [Header] -> RqBody -> Request a
+ Network.AWS.Types: Request :: !StdMethod -> !RawPath -> !QueryString -> ![Header] -> !RqBody -> Request a
- Network.AWS.Types: Service :: !Text -> !ByteString -> !ByteString -> Maybe ByteString -> Maybe ByteString -> (Status -> Maybe (LazyByteString -> ServiceError (Er a))) -> Retry a -> Service a
+ Network.AWS.Types: Service :: !Abbrev -> ByteString -> ByteString -> (Region -> Endpoint) -> Maybe Seconds -> (Status -> Bool) -> (Abbrev -> Status -> [Header] -> LazyByteString -> Error) -> Retry -> Service s
- Network.AWS.Types: ServiceError :: Abbrev -> Status -> a -> ServiceError a
+ Network.AWS.Types: ServiceError :: ServiceError -> Error
- Network.AWS.Types: Signed :: Meta v -> ClientRequest -> Signed a v
+ Network.AWS.Types: Signed :: Meta v -> ClientRequest -> Signed v a
- Network.AWS.Types: _ServiceError :: Prism' (ServiceError a_avh9) (Abbrev, Status, a_avh9)
+ Network.AWS.Types: _ServiceError :: AsError a => Prism' a ServiceError
- Network.AWS.Types: _authToken :: AuthEnv -> Maybe SecurityToken
+ Network.AWS.Types: _authToken :: AuthEnv -> Maybe SessionToken
- Network.AWS.Types: _retryAttempts :: Retry a -> !Int
+ Network.AWS.Types: _retryAttempts :: Retry -> !Int
- Network.AWS.Types: _retryBase :: Retry a -> !Double
+ Network.AWS.Types: _retryBase :: Retry -> !Double
- Network.AWS.Types: _retryCheck :: Retry a -> Status -> Er a -> Bool
+ Network.AWS.Types: _retryCheck :: Retry -> ServiceError -> Maybe Text
- Network.AWS.Types: _retryGrowth :: Retry a -> !Int
+ Network.AWS.Types: _retryGrowth :: Retry -> !Int
- Network.AWS.Types: _rqBody :: Request a -> RqBody
+ Network.AWS.Types: _rqBody :: Request a -> !RqBody
- Network.AWS.Types: _rqHeaders :: Request a -> [Header]
+ Network.AWS.Types: _rqHeaders :: Request a -> ![Header]
- Network.AWS.Types: _rqPath :: Request a -> !ByteString
+ Network.AWS.Types: _rqPath :: Request a -> !RawPath
- Network.AWS.Types: _rqQuery :: Request a -> Query
+ Network.AWS.Types: _rqQuery :: Request a -> !QueryString
- Network.AWS.Types: _sgMeta :: Signed a v -> Meta v
+ Network.AWS.Types: _sgMeta :: Signed v a -> Meta v
- Network.AWS.Types: _sgRequest :: Signed a v -> ClientRequest
+ Network.AWS.Types: _sgRequest :: Signed v a -> ClientRequest
- Network.AWS.Types: _svcAbbrev :: Service a -> !Text
+ Network.AWS.Types: _svcAbbrev :: Service s -> !Abbrev
- Network.AWS.Types: _svcPrefix :: Service a -> !ByteString
+ Network.AWS.Types: _svcPrefix :: Service s -> ByteString
- Network.AWS.Types: _svcRetry :: Service a -> Retry a
+ Network.AWS.Types: _svcRetry :: Service s -> Retry
- Network.AWS.Types: _svcVersion :: Service a -> !ByteString
+ Network.AWS.Types: _svcVersion :: Service s -> ByteString
- Network.AWS.Types: class (AWSService (Sv a), AWSSigner (Sg (Sv a))) => AWSRequest a where type family Sv a :: * type family Rs a :: *
+ Network.AWS.Types: class AWSService (Sv a) => AWSRequest a where type family Rs a :: * type family Sv a :: *
- Network.AWS.Types: class (AWSSigner (Sg a), Show (Er a)) => AWSService a where type family Sg a :: * type family Er a :: *
+ Network.AWS.Types: class AWSSigner (Sg a) => AWSService a where type family Sg a :: *
- Network.AWS.Types: data Retry a
+ Network.AWS.Types: data Retry
- Network.AWS.Types: data Service a
+ Network.AWS.Types: data Service s
- Network.AWS.Types: data ServiceError a
+ Network.AWS.Types: data ServiceError
- Network.AWS.Types: data Signed a v
+ Network.AWS.Types: data Signed v a
- Network.AWS.Types: presigned :: (AWSPresigner v, AWSService (Sv a), v ~ Sg (Sv a)) => AuthEnv -> Region -> Request a -> UTCTime -> Integer -> Signed a v
+ Network.AWS.Types: presigned :: (AWSPresigner v, v ~ Sg s) => AuthEnv -> Region -> UTCTime -> Seconds -> Service s -> Request a -> Signed v a
- Network.AWS.Types: response :: (AWSRequest a, MonadResource m) => Logger -> Request a -> Either HttpException ClientResponse -> m (Response' a)
+ Network.AWS.Types: response :: (AWSRequest a, MonadResource m) => Logger -> Service s -> Request a -> ClientResponse -> m (Response a)
- Network.AWS.Types: rqBody :: Lens (Request a_avgl) (Request a_awmW) RqBody RqBody
+ Network.AWS.Types: rqBody :: Lens' (Request a) RqBody
- Network.AWS.Types: rqHeaders :: Lens (Request a_avgl) (Request a_awmX) [Header] [Header]
+ Network.AWS.Types: rqHeaders :: Lens' (Request a) [Header]
- Network.AWS.Types: rqMethod :: Lens (Request a_avgl) (Request a_awmY) StdMethod StdMethod
+ Network.AWS.Types: rqMethod :: Lens' (Request a) StdMethod
- Network.AWS.Types: rqPath :: Lens (Request a_avgl) (Request a_awmZ) ByteString ByteString
+ Network.AWS.Types: rqPath :: Lens' (Request a) RawPath
- Network.AWS.Types: rqQuery :: Lens (Request a_avgl) (Request a_awn0) Query Query
+ Network.AWS.Types: rqQuery :: Lens' (Request a) QueryString
- Network.AWS.Types: service :: AWSService a => Service a
+ Network.AWS.Types: service :: (AWSService a, Sv p ~ a) => Proxy p -> Service a
- Network.AWS.Types: serviceOf :: AWSService (Sv a) => Request a -> Service (Sv a)
+ Network.AWS.Types: serviceOf :: AWSService (Sv a) => a -> Service (Sv a)
- Network.AWS.Types: sgMeta :: Lens' (Signed a v) (Meta v)
+ Network.AWS.Types: sgMeta :: ToLog (Meta v) => Lens' (Signed v a) (Meta v)
- Network.AWS.Types: sgRequest :: Lens' (Signed a v) ClientRequest
+ Network.AWS.Types: sgRequest :: Lens' (Signed v a) ClientRequest
- Network.AWS.Types: signed :: (AWSSigner v, AWSService (Sv a), v ~ Sg (Sv a)) => AuthEnv -> Region -> Request a -> UTCTime -> Signed a v
+ Network.AWS.Types: signed :: (AWSSigner v, v ~ Sg s) => AuthEnv -> Region -> UTCTime -> Service s -> Request a -> Signed v a
- Network.AWS.Types: type Response a = Either (ServiceError (Er (Sv a))) (Rs a)
+ Network.AWS.Types: type Response a = (Status, Rs a)

Files

amazonka-core.cabal view
@@ -1,6 +1,6 @@ name:                  amazonka-core-version:               0.3.6-synopsis:              Core functionality and data types for Amazonka libraries.+version:               1.0.0+synopsis:              Core data types and functionality for Amazonka libraries. homepage:              https://github.com/brendanhay/amazonka license:               OtherLicense license-file:          LICENSE@@ -13,15 +13,12 @@ cabal-version:         >= 1.10  description:-    Core functionality, serialisation primitives, and data types for+    Core data types, functionality and serialisation primitives for     Amazonka related Amazon Web Services SDKs.     .     The external interface of this library is stable with respect to the-    downstream Amazonka libraries, only, and as such is probably not suitable+    downstream Amazonka libraries, only, and as such is not suitable     for use in non-Amazonka projects.-    .-    /Warning:/ This is an experimental preview release which is still under-    heavy development and not intended for public consumption, caveat emptor!  source-repository head     type:              git@@ -38,61 +35,51 @@     ghc-options:       -Wall      exposed-modules:-          Network.AWS.Data+          Network.AWS.Compat.Locale+        , Network.AWS.Compat.Time+        , Network.AWS.Data.Base64+        , Network.AWS.Data.Body+        , Network.AWS.Data.ByteString+        , Network.AWS.Data.Crypto+        , Network.AWS.Data.Headers+        , Network.AWS.Data.JSON+        , Network.AWS.Data.List1+        , Network.AWS.Data.Log+        , Network.AWS.Data.Map+        , Network.AWS.Data.Numeric+        , Network.AWS.Data.Path+        , Network.AWS.Data.Query+        , Network.AWS.Data.Sensitive+        , Network.AWS.Data.Text+        , Network.AWS.Data.Time+        , Network.AWS.Data.XML+        , Network.AWS.Endpoint         , Network.AWS.Error-        , Network.AWS.Pagination+        , Network.AWS.Pager         , Network.AWS.Prelude-        , Network.AWS.Request.JSON-        , Network.AWS.Request.Query-        , Network.AWS.Request.RestJSON-        , Network.AWS.Request.RestXML-        , Network.AWS.Request.S3+        , Network.AWS.Request         , Network.AWS.Response-        , Network.AWS.Signing+        , Network.AWS.Sign.V2+        , Network.AWS.Sign.V4         , Network.AWS.Types-        , Network.AWS.Waiters--    other-modules:-          Network.AWS.Compat.Internal.Locale-        , Network.AWS.Compat.Internal.Time-        , Network.AWS.Data.Internal.Base64-        , Network.AWS.Data.Internal.Body-        , Network.AWS.Data.Internal.ByteString-        , Network.AWS.Data.Internal.Header-        , Network.AWS.Data.Internal.JSON-        , Network.AWS.Data.Internal.List-        , Network.AWS.Data.Internal.Map-        , Network.AWS.Data.Internal.Numeric-        , Network.AWS.Data.Internal.Path-        , Network.AWS.Data.Internal.Query-        , Network.AWS.Data.Internal.Sensitive-        , Network.AWS.Data.Internal.Text-        , Network.AWS.Data.Internal.Time-        , Network.AWS.Data.Internal.URI-        , Network.AWS.Data.Internal.XML-        , Network.AWS.Request.Internal-        , Network.AWS.Signing.Internal-        , Network.AWS.Signing.Internal.V2-        , Network.AWS.Signing.Internal.V4+        , Network.AWS.Waiter      build-depends:-          aeson                >  0.7.0.6-        , attoparsec           >= 0.12+          aeson                >= 0.8+        , attoparsec           >= 0.11.3         , base                 >= 4.7     && < 5-        , base16-bytestring    >= 0.1-        , base64-bytestring    >= 1         , bifunctors           >= 4.1         , bytestring           >= 0.9-        , case-insensitive     >= 1.2     && < 2+        , case-insensitive     >= 1.2         , conduit              >= 1.1         , conduit-extra        >= 1.1-        , cryptohash           >= 0.11-        , data-default-class   >= 0.0.1+        , cryptonite           >= 0.4+        , exceptions           >= 0.6         , hashable             >= 1.2-        , http-client          >= 0.4.3   && < 0.5+        , http-client          >= 0.4.9         , http-types           >= 0.8         , lens                 >= 4.4-        , mmorph               >= 1       && < 2+        , memory               >= 0.6         , mtl                  >= 2.1.3.1         , resourcet            >= 1.1         , scientific           >= 0.3@@ -102,8 +89,8 @@         , transformers         >= 0.2         , transformers-compat  >= 0.3         , unordered-containers >= 0.2.5-        , vector               >= 0.10.9         , xml-conduit          >= 1.2+        , xml-types            >= 0.3.4      if !impl(ghc>=7.9)         build-depends:@@ -123,22 +110,31 @@     hs-source-dirs:    test     main-is:           Main.hs -    ghc-options:       -Wall -threaded -with-rtsopts=-N+    ghc-options:       -Wall -threaded      other-modules:-          Test.AWS.Data+          Test.AWS.Arbitrary+        , Test.AWS.Data.Base64         , Test.AWS.Data.List-        , Test.AWS.Data.Map+        , Test.AWS.Data.Maybe         , Test.AWS.Data.Numeric         , Test.AWS.Data.Time-        , Test.AWS.TH-        , Test.AWS.Types+        , Test.AWS.Sign.V4+        , Test.AWS.Util      build-depends:-          amazonka-core-        , aeson+          aeson+        , amazonka-core         , base+        , bytestring+        , case-insensitive+        , http-types+        , lens         , tasty         , tasty-hunit+        , tasty-quickcheck         , template-haskell         , text+        , time+        , QuickCheck+        , quickcheck-unicode
− src/Network/AWS/Compat/Internal/Locale.hs
@@ -1,22 +0,0 @@-{-# LANGUAGE CPP #-}---- Module      : Network.AWS.Data.Compat.Internal.Locale--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Compat.Internal.Locale-    ( defaultTimeLocale-    , iso8601DateFormat-    ) where--#if MIN_VERSION_time(1,5,0)-import           Data.Time.Format (defaultTimeLocale, iso8601DateFormat)-#else-import           System.Locale    (defaultTimeLocale, iso8601DateFormat)-#endif
− src/Network/AWS/Compat/Internal/Time.hs
@@ -1,24 +0,0 @@-{-# LANGUAGE CPP #-}---- Module      : Network.AWS.Compat.Internal.Time--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Compat.Internal.Time-    ( parseTime-    ) where--#if MIN_VERSION_time(1,5,0)-import           Data.Time.Format (ParseTime, TimeLocale, parseTimeM)--parseTime :: ParseTime a => TimeLocale -> String -> String -> Maybe a-parseTime = parseTimeM True-#else-import           Data.Time.Format (parseTime)-#endif
+ src/Network/AWS/Compat/Locale.hs view
@@ -0,0 +1,20 @@+{-# LANGUAGE CPP #-}++-- |+-- Module      : Network.AWS.Compat.Locale+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Compat.Locale+    ( defaultTimeLocale+    , iso8601DateFormat+    ) where++#if MIN_VERSION_time(1,5,0)+import           Data.Time.Format (defaultTimeLocale, iso8601DateFormat)+#else+import           System.Locale    (defaultTimeLocale, iso8601DateFormat)+#endif
+ src/Network/AWS/Compat/Time.hs view
@@ -0,0 +1,22 @@+{-# LANGUAGE CPP #-}++-- |+-- Module      : Network.AWS.Compat.Time+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Compat.Time+    ( parseTime+    ) where++#if MIN_VERSION_time(1,5,0)+import           Data.Time.Format (ParseTime, TimeLocale, parseTimeM)++parseTime :: ParseTime a => TimeLocale -> String -> String -> Maybe a+parseTime = parseTimeM True+#else+import           Data.Time.Format (parseTime)+#endif
− src/Network/AWS/Data.hs
@@ -1,72 +0,0 @@--- Module      : Network.AWS.Data--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)---- | Serialisation classes and primitives for the various---   formats used to communicate with AWS.-module Network.AWS.Data-    (-    -- * ByteString-      module Network.AWS.Data.Internal.ByteString-    , module Network.AWS.Data.Internal.Base64--    -- * Text-    , module Network.AWS.Data.Internal.Text--    -- * Numeric-    , module Network.AWS.Data.Internal.Numeric--    -- * Time-    , module Network.AWS.Data.Internal.Time--    -- * Sensitive-    , module Network.AWS.Data.Internal.Sensitive--    -- * HTTP-    -- ** Body-    , module Network.AWS.Data.Internal.Body--    -- ** Headers-    , module Network.AWS.Data.Internal.Header--    -- ** Path-    , module Network.AWS.Data.Internal.Path--    -- ** Query-    , module Network.AWS.Data.Internal.Query--    -- ** URI-    , module Network.AWS.Data.Internal.URI--    -- * XML-    , module Network.AWS.Data.Internal.XML--    -- * JSON-    , module Network.AWS.Data.Internal.JSON--    -- * Collections-    , module Network.AWS.Data.Internal.List-    , module Network.AWS.Data.Internal.Map-    ) where--import Network.AWS.Data.Internal.Base64-import Network.AWS.Data.Internal.Body-import Network.AWS.Data.Internal.ByteString-import Network.AWS.Data.Internal.Header-import Network.AWS.Data.Internal.JSON-import Network.AWS.Data.Internal.List-import Network.AWS.Data.Internal.Map-import Network.AWS.Data.Internal.Numeric-import Network.AWS.Data.Internal.Path-import Network.AWS.Data.Internal.Query-import Network.AWS.Data.Internal.Sensitive-import Network.AWS.Data.Internal.Text-import Network.AWS.Data.Internal.Time-import Network.AWS.Data.Internal.URI-import Network.AWS.Data.Internal.XML
+ src/Network/AWS/Data/Base64.hs view
@@ -0,0 +1,60 @@+{-# LANGUAGE DeriveDataTypeable         #-}+{-# LANGUAGE DeriveGeneric              #-}+{-# LANGUAGE GeneralizedNewtypeDeriving #-}++-- |+-- Module      : Network.AWS.Data.Base64+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.Base64+    ( Base64 (..)+    , _Base64+    ) where++import           Control.Lens+import           Data.Aeson.Types+import qualified Data.Attoparsec.Text        as AText+import qualified Data.ByteArray.Encoding     as BA+import           Data.Data                   (Data, Typeable)+import qualified Data.Text.Encoding          as Text+import           GHC.Generics                (Generic)+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.JSON+import           Network.AWS.Data.Query+import           Network.AWS.Data.Text+import           Network.AWS.Data.XML++import           Prelude++-- | Base64 encoded binary data.+--+-- Encoding\/decoding is automatically deferred to serialisation and deserialisation+-- respectively.+newtype Base64 = Base64 { unBase64 :: ByteString }+    deriving (Eq, Read, Ord, Data, Typeable, Generic)++_Base64 :: Iso' Base64 ByteString+_Base64 = iso unBase64 Base64++-- FIXME: probably a mistake to wrap a ByteString since+-- the underlying serialisers (JSON, XML) use Text internally.+instance FromText Base64 where+    parser = AText.takeText >>=+        either fail (return . Base64)+            . BA.convertFromBase BA.Base64+            . Text.encodeUtf8++instance ToByteString Base64 where+    toBS = BA.convertToBase BA.Base64 . unBase64++instance Show     Base64 where show      = show . toBS+instance ToText   Base64 where toText    = Text.decodeUtf8 . toBS+instance ToQuery  Base64 where toQuery   = toQuery . toBS+instance FromXML  Base64 where parseXML  = parseXMLText "Base64"+instance ToXML    Base64 where toXML     = toXMLText+instance FromJSON Base64 where parseJSON = parseJSONText "Base64"+instance ToJSON   Base64 where toJSON    = toJSONText
+ src/Network/AWS/Data/Body.hs view
@@ -0,0 +1,102 @@+{-# LANGUAGE DeriveDataTypeable #-}+{-# LANGUAGE DeriveGeneric      #-}+{-# LANGUAGE OverloadedStrings  #-}+{-# LANGUAGE PackageImports     #-}++-- |+-- Module      : Network.AWS.Data.Body+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.Body where++import           Control.Monad.Trans.Resource+import           Data.Aeson+import qualified Data.ByteString.Char8        as BS8+import qualified Data.ByteString.Lazy         as LBS+import qualified Data.ByteString.Lazy.Char8   as LBS8+import           Data.Conduit+import           Data.String+import           Data.Text                    (Text)+import qualified Data.Text.Encoding           as Text+import qualified Data.Text.Lazy               as LText+import qualified Data.Text.Lazy.Encoding      as LText+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Crypto+import           Network.AWS.Data.Query       (QueryString)+import           Network.AWS.Data.XML         (encodeXML)+import           Network.HTTP.Client+import           Text.XML                     (Element)++import           Prelude++-- | A streaming, exception safe response body.+newtype RsBody = RsBody+    { bodyResponse :: ResumableSource (ResourceT IO) ByteString+    }++instance Show RsBody where+    show = const "RsBody { ResumableSource (ResourceT IO) ByteString }"++-- | An opaque request body containing a 'SHA256' hash.+data RqBody = RqBody+    { bodySHA256  :: Digest SHA256+    , bodyRequest :: RequestBody+    }++instance Show RqBody where+    show b = "RqBody { RequestBody "+        ++ BS8.unpack (digestToBase Base16 (bodySHA256 b)) ++ " }"++instance IsString RqBody where+    fromString = toBody . LBS8.pack++bodyStream :: RqBody -> Bool+bodyStream x =+    case bodyRequest x of+        RequestBodyLBS           {} -> False+        RequestBodyBS            {} -> False+        RequestBodyBuilder       {} -> False+        RequestBodyStream        {} -> True+        RequestBodyStreamChunked {} -> True++bodyCalculateMD5 :: RqBody -> Maybe (Digest MD5)+bodyCalculateMD5 x =+    let md5 = Just . hashMD5+     in case bodyRequest x of+        RequestBodyLBS           lbs -> md5 (toBS lbs)+        RequestBodyBS            bs  -> md5 bs+        RequestBodyBuilder     _ b   -> md5 (toBS b)+        _                            -> Nothing++-- | Anything that can be safely converted to a 'RqBody'.+class ToBody a where+    -- | Convert a value to a request body.+    toBody :: a -> RqBody++instance ToBody RqBody where+    toBody = id++instance ToBody LBS.ByteString where+    toBody x = RqBody (hashlazy x) (RequestBodyLBS x)++instance ToBody ByteString where+    toBody x = RqBody (hash x) (RequestBodyBS x)++instance ToBody Text where+    toBody = toBody . Text.encodeUtf8++instance ToBody LText.Text where+    toBody = toBody . LText.encodeUtf8++instance ToBody Value where+    toBody = toBody . encode++instance ToBody Element where+    toBody = toBody . encodeXML++instance ToBody QueryString where+    toBody = toBody . toBS
+ src/Network/AWS/Data/ByteString.hs view
@@ -0,0 +1,71 @@+{-# LANGUAGE DefaultSignatures #-}+{-# LANGUAGE FlexibleInstances #-}+{-# LANGUAGE LambdaCase        #-}+{-# LANGUAGE OverloadedStrings #-}+{-# LANGUAGE PackageImports    #-}+{-# LANGUAGE RecordWildCards   #-}++-- |+-- Module      : Network.AWS.Data.ByteString+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)++--+module Network.AWS.Data.ByteString+    (+    -- * ByteString+      ByteString+    , LazyByteString+    , ToByteString (..)+    , showBS+    , stripBS+    ) where++import           Data.ByteString              (ByteString)+import           Data.ByteString.Builder      (Builder)+import qualified Data.ByteString.Char8        as BS8+import qualified Data.ByteString.Lazy         as LBS+import qualified Data.ByteString.Lazy.Builder as Build+import           Data.CaseInsensitive         (CI)+import qualified Data.CaseInsensitive         as CI+import           Data.Char+import qualified Data.Text.Encoding           as Text+import           Data.Time                    (UTCTime)+import           Network.AWS.Data.Text+import           Network.HTTP.Types+import           Numeric+import           Numeric.Natural++import           Prelude++type LazyByteString = LBS.ByteString++showBS :: ToByteString a => a -> String+showBS = BS8.unpack . toBS++stripBS :: ByteString -> ByteString+stripBS = BS8.dropWhile isSpace . fst . BS8.spanEnd isSpace++class ToByteString a where+    toBS :: a -> ByteString++    default toBS :: ToText a => a -> ByteString+    toBS = Text.encodeUtf8 . toText++instance ToByteString ByteString     where toBS = id+instance ToByteString Builder        where toBS = toBS . Build.toLazyByteString+instance ToByteString LazyByteString where toBS = LBS.toStrict+instance ToByteString Text           where toBS = Text.encodeUtf8+instance ToByteString String         where toBS = BS8.pack+instance ToByteString Int            where toBS = toBS . Build.intDec+instance ToByteString Integer        where toBS = toBS . Build.integerDec+instance ToByteString Natural        where toBS = toBS . toInteger+instance ToByteString Double         where toBS = toBS . ($ "") . showFFloat Nothing+instance ToByteString StdMethod      where toBS = renderStdMethod+instance ToByteString UTCTime        where toBS = BS8.pack . show++instance ToByteString a => ToByteString (CI a) where+    toBS = toBS . CI.original
+ src/Network/AWS/Data/Crypto.hs view
@@ -0,0 +1,60 @@+{-# LANGUAGE DeriveDataTypeable #-}+{-# LANGUAGE DeriveGeneric      #-}+{-# LANGUAGE OverloadedStrings  #-}+{-# LANGUAGE PackageImports     #-}++-- |+-- Module      : Network.AWS.Data.Crypto+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.Crypto+    (+    -- * Conversion+      digestToBS+    , digestToBase++    -- * Algorithms+    , hmacSHA256+    , hashSHA256+    , hashMD5++    -- * Contexts+    , hash+    , hashlazy+    , hashInit+    , hashUpdate+    , hashFinalize++    -- * Re-exported+    , HMAC+    , Digest+    , HashAlgorithm+    , SHA256 (..)+    , MD5    (..)+    , Base   (..)+    ) where++import           "cryptonite" Crypto.Hash+import           "cryptonite" Crypto.MAC.HMAC+import           Data.ByteArray+import           Data.ByteArray.Encoding+import           Data.ByteString         (ByteString)++digestToBS :: ByteArrayAccess a => a -> ByteString+digestToBS = convert++digestToBase :: ByteArrayAccess a => Base -> a -> ByteString+digestToBase = convertToBase++hmacSHA256 :: (ByteArrayAccess a, ByteArray b) => a -> b -> HMAC SHA256+hmacSHA256 = hmac++hashSHA256 :: ByteArrayAccess a => a -> Digest SHA256+hashSHA256 = hashWith SHA256++hashMD5 :: ByteArrayAccess a => a -> Digest MD5+hashMD5 = hashWith MD5
+ src/Network/AWS/Data/Headers.hs view
@@ -0,0 +1,112 @@+{-# LANGUAGE DefaultSignatures #-}+{-# LANGUAGE FlexibleContexts  #-}+{-# LANGUAGE FlexibleInstances #-}+{-# LANGUAGE OverloadedStrings #-}+{-# LANGUAGE TupleSections     #-}++-- |+-- Module      : Network.AWS.Data.Headers+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.Headers+    ( module Network.AWS.Data.Headers+    , HeaderName+    , Header+    ) where++import qualified Data.ByteString.Char8       as BS8+import qualified Data.CaseInsensitive        as CI+import           Data.Monoid+import qualified Data.Text.Encoding          as Text+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Text+import           Network.HTTP.Types++import           Prelude++infixl 7 .#, .#?++(.#) :: FromText a => ResponseHeaders -> HeaderName -> Either String a+hs .# k = hs .#? k >>= note+  where+    note Nothing  = Left (BS8.unpack $ "Unable to find header: " <> CI.original k)+    note (Just x) = Right x++(.#?) :: FromText a => ResponseHeaders -> HeaderName -> Either String (Maybe a)+hs .#? k =+    maybe (Right Nothing)+          (fmap Just . fromText . Text.decodeUtf8)+          (k `lookup` hs)++infixr 7 =#++(=#) :: ToHeader a => HeaderName -> a -> [Header]+(=#) = toHeader++hdr :: HeaderName -> ByteString -> [Header] -> [Header]+hdr k v hs = (k, v) : filter ((/= k) . fst) hs++class ToHeaders a where+    toHeaders :: a -> [Header]+    toHeaders = const mempty++class ToHeader a where+    toHeader :: HeaderName -> a -> [Header]++    default toHeader :: ToText a => HeaderName -> a -> [Header]+    toHeader k = toHeader k . toText++instance ToHeader Text where+    toHeader k v = [(k, Text.encodeUtf8 v)]++instance ToHeader ByteString where+    toHeader k v = [(k, v)]++instance ToText a => ToHeader (Maybe a) where+    toHeader k = maybe [] (toHeader k . toText)++hHost :: HeaderName+hHost = "Host"++hAMZToken :: HeaderName+hAMZToken = "X-Amz-Security-Token"++hAMZTarget :: HeaderName+hAMZTarget = "X-Amz-Target"++hAMZAlgorithm :: HeaderName+hAMZAlgorithm = "X-Amz-Algorithm"++hAMZCredential :: HeaderName+hAMZCredential = "X-Amz-Credential"++hAMZExpires :: HeaderName+hAMZExpires = "X-Amz-Expires"++hAMZSignedHeaders :: HeaderName+hAMZSignedHeaders = "X-Amz-SignedHeaders"++hAMZContentSHA256 :: HeaderName+hAMZContentSHA256 = "X-Amz-Content-SHA256"++hAMZDate :: HeaderName+hAMZDate = "X-Amz-Date"++hMetaPrefix :: HeaderName+hMetaPrefix = "X-Amz-"++hAMZRequestId :: HeaderName+hAMZRequestId = "X-Amz-Request-Id"++hAMZNRequestId :: HeaderName+hAMZNRequestId = "X-Amzn-RequestId"++hAMZNErrorType :: HeaderName+hAMZNErrorType = "X-Amzn-ErrorType"++hAMZNAuth :: HeaderName+hAMZNAuth = "X-Amzn-Authorization"
− src/Network/AWS/Data/Internal/Base64.hs
@@ -1,47 +0,0 @@-{-# LANGUAGE DeriveGeneric              #-}-{-# LANGUAGE GeneralizedNewtypeDeriving #-}---- Module      : Network.AWS.Data.Internal.Base64--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.Base64-    ( Base64 (..)-    ) where--import           Data.Aeson.Types-import qualified Data.Attoparsec.Text                 as AText-import           Data.ByteString                      (ByteString)-import qualified Data.ByteString.Base64               as Base64-import qualified Data.Text.Encoding                   as Text-import           GHC.Generics-import           Network.AWS.Data.Internal.ByteString-import           Network.AWS.Data.Internal.JSON-import           Network.AWS.Data.Internal.Query-import           Network.AWS.Data.Internal.Text-import           Network.AWS.Data.Internal.XML---- | Base64 encoded binary data.------ Encoding/decoding is deferred to serialisation/deserialisation respectively.-newtype Base64 = Base64 { unBase64 :: ByteString }-    deriving (Eq, Read, Ord, Generic)--instance FromText Base64 where-    parser = AText.takeText >>=-        either fail (return . Base64) . Base64.decode . Text.encodeUtf8--instance Show         Base64 where show      = show . toBS-instance ToText       Base64 where toText    = Text.decodeUtf8 . toBS-instance ToByteString Base64 where toBS      = Base64.encode . unBase64-instance ToQuery      Base64 where toQuery   = toQuery . toText-instance FromXML      Base64 where parseXML  = parseXMLText "Base64"-instance ToXML        Base64 where toXML     = toXMLText-instance FromJSON     Base64 where parseJSON = parseJSONText "Base64"-instance ToJSON       Base64 where toJSON    = toJSONText
− src/Network/AWS/Data/Internal/Body.hs
@@ -1,91 +0,0 @@-{-# LANGUAGE OverloadedStrings #-}-{-# LANGUAGE TemplateHaskell   #-}---- Module      : Network.AWS.Data.Internal.Body--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.Body where--import           Control.Lens-import           Control.Monad.Morph-import           Control.Monad.Trans.Resource-import           Crypto.Hash-import           Data.Aeson-import           Data.ByteString                      (ByteString)-import qualified Data.ByteString.Lazy                 as LBS-import qualified Data.ByteString.Lazy.Char8           as LBS8-import           Data.Conduit-import           Data.List                            (intersperse)-import           Data.Monoid-import           Data.String-import           Network.AWS.Data.Internal.ByteString-import           Network.HTTP.Client--data RsBody = RsBody (ResumableSource (ResourceT IO) ByteString)--makePrisms ''RsBody--instance ToBuilder RsBody where-    build = const "RsBody { ResumableSource (ResourceT IO) ByteString }"--instance Show RsBody where-    show = LBS8.unpack . buildBS--connectBody :: MonadResource m => RsBody -> Sink ByteString m a -> m a-connectBody (RsBody src) sink = hoist liftResourceT src $$+- sink--data RqBody = RqBody-    { _bdyHash :: Digest SHA256-    , _bdyBody :: RequestBody-    }--makeLenses ''RqBody--bodyHash :: RqBody -> ByteString-bodyHash = digestToHexByteString . _bdyHash--instance ToBuilder RqBody where-    build x@(RqBody _ b) = mconcat $ intersperse "\n"-        [ "    Body {"-        , "      hash    = "  <> build (bodyHash x)-        , "      payload =\n" <> build b-        , "    }"-        ]--instance Show RqBody where-    show = LBS8.unpack . buildBS . _bdyBody--instance IsString RqBody where-    fromString = toBody . LBS8.pack--isStreaming :: RqBody -> Bool-isStreaming b =-    case _bdyBody b of-        RequestBodyLBS           {} -> False-        RequestBodyBS            {} -> False-        RequestBodyBuilder       {} -> False-        RequestBodyStream        {} -> True-        RequestBodyStreamChunked {} -> True--class ToBody a where-    toBody :: a -> RqBody-    toBody = const (RqBody (hash "") (RequestBodyLBS mempty))--instance ToBody RqBody where-    toBody = id--instance ToBody LBS.ByteString where-    toBody lbs = RqBody (hashlazy lbs) (RequestBodyLBS lbs)--instance ToBody ByteString where-    toBody = toBody . LBS.fromStrict--instance ToBody Value where-    toBody = toBody . encode
− src/Network/AWS/Data/Internal/ByteString.hs
@@ -1,171 +0,0 @@-{-# LANGUAGE DefaultSignatures #-}-{-# LANGUAGE FlexibleInstances #-}-{-# LANGUAGE LambdaCase        #-}-{-# LANGUAGE OverloadedStrings #-}-{-# LANGUAGE RecordWildCards   #-}---- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.ByteString-    ( LazyByteString-    , ToByteString (..)-    , ToBuilder    (..)-    , showBS-    , buildBS-    , stripBS-    ) where--import           Crypto.Hash-import           Data.ByteString                (ByteString)-import qualified Data.ByteString                as BS-import           Data.ByteString.Builder        (Builder)-import qualified Data.ByteString.Builder        as Build-import qualified Data.ByteString.Char8          as BS8-import qualified Data.ByteString.Lazy           as LBS-import           Data.CaseInsensitive           (CI)-import qualified Data.CaseInsensitive           as CI-import           Data.Char-import           Data.Int-import           Data.List                      (intersperse)-import           Data.Monoid-import           Data.Text                      (Text)-import qualified Data.Text.Encoding             as Text-import           Data.Time                      (UTCTime)-import           Network.AWS.Data.Internal.Text-import           Network.HTTP.Client-import           Network.HTTP.Types-import           Numeric.Natural--type LazyByteString = LBS.ByteString--showBS :: ToByteString a => a -> String-showBS = BS8.unpack . toBS--class ToByteString a where-    toBS :: a -> ByteString--    default toBS :: ToText a => a -> ByteString-    toBS = Text.encodeUtf8 . toText--instance ToByteString ByteString     where toBS = id-instance ToByteString Builder        where toBS = toBS . Build.toLazyByteString-instance ToByteString LazyByteString where toBS = LBS.toStrict-instance ToByteString Text           where toBS = Text.encodeUtf8-instance ToByteString Int            where toBS = toBS . buildBS-instance ToByteString Integer        where toBS = toBS . buildBS-instance ToByteString Natural        where toBS = toBS . buildBS-instance ToByteString Double         where toBS = toBS . buildBS-instance ToByteString StdMethod      where toBS = renderStdMethod-instance ToByteString (Digest a)     where toBS = digestToHexByteString-instance ToByteString UTCTime        where toBS = BS8.pack . show--instance ToByteString a => ToByteString (CI a) where-    toBS = toBS . CI.original--buildBS :: ToBuilder a => a -> LazyByteString-buildBS = Build.toLazyByteString . build--class ToBuilder a where-    build :: a -> Builder--    default build :: ToByteString a => a -> Builder-    build = build . toBS--instance ToBuilder Builder        where build = id-instance ToBuilder ByteString     where build = Build.byteString-instance ToBuilder LazyByteString where build = Build.lazyByteString-instance ToBuilder Text           where build = Build.byteString . toBS-instance ToBuilder Char           where build = Build.charUtf8-instance ToBuilder [Char]         where build = Build.stringUtf8-instance ToBuilder Int            where build = Build.intDec-instance ToBuilder Int64          where build = Build.int64Dec-instance ToBuilder Integer        where build = Build.integerDec-instance ToBuilder Natural        where build = Build.integerDec . toInteger-instance ToBuilder Double         where build = Build.doubleDec-instance ToBuilder StdMethod-instance ToBuilder (Digest a)--instance ToBuilder Bool where-    build True  = "True"-    build False = "False"--instance ToBuilder UTCTime where-    build = Build.stringUtf8 . show--instance ToBuilder a => ToBuilder (Maybe a) where-    build Nothing  = "Nothing"-    build (Just x) = "Just " <> build x--instance ToBuilder a => ToBuilder (CI a) where-    build = build . CI.foldedCase--instance ToBuilder [Header] where-    build = mconcat-          . intersperse "; "-          . map (\(k, v) -> build k <> ": " <> build v)--instance ToBuilder HttpVersion where-    build HttpVersion{..} = "HTTP/"-        <> build httpMajor-        <> build '.'-        <> build httpMinor--instance ToBuilder RequestBody where-    build = \case-        RequestBodyLBS lbs-            | n <= m               -> build lbs-            | otherwise            -> "      <lazy:"    <> build n <> ">"-          where-            n = LBS.length lbs--        RequestBodyBS bs-            | n <= fromIntegral m  -> build bs-            | otherwise            -> "      <strict:"  <> build n <> ">"-          where-            n = BS.length bs--        RequestBodyBuilder n _     -> "      <builder:" <> build n <> ">"-        RequestBodyStream  n _     -> "      <stream:"  <> build n <> ">"-        RequestBodyStreamChunked _ -> "      <chunked>"-      where-        m :: Int64-        m = 4096--instance ToBuilder Request where-    build x = mconcat $ intersperse "\n"-        [ "[Client Request] {"-        , "  host              = " <> build (host            x)-        , "  port              = " <> build (port            x)-        , "  secure            = " <> build (secure          x)-        , "  headers           = " <> build (requestHeaders  x)-        , "  path              = " <> build (path            x)-        , "  query             = " <> build (queryString     x)-        , "  method            = " <> build (method          x)-        , "  redirect count    = " <> build (redirectCount   x)-        , "  response timeout  = " <> build (responseTimeout x)-        , "  request version   = " <> build (requestVersion  x)-        , "}"-        ]--instance ToBuilder (Response a) where-    build x = mconcat $ intersperse "\n"-        [ "[Client Response] {"-        , "  status code    = " <> build (statusCode      s)-        , "  status message = " <> build (statusMessage   s)-        , "  version        = " <> build (responseVersion x)-        , "  headers        = " <> build (responseHeaders x)-        , "  cookies        = " <> build (show (responseCookieJar x))-        , "}"-        ]-      where-        s = responseStatus x--stripBS :: ByteString -> ByteString-stripBS = BS8.dropWhile isSpace . fst . BS8.spanEnd isSpace
− src/Network/AWS/Data/Internal/Header.hs
@@ -1,108 +0,0 @@-{-# LANGUAGE DefaultSignatures #-}-{-# LANGUAGE FlexibleContexts  #-}-{-# LANGUAGE FlexibleInstances #-}-{-# LANGUAGE OverloadedStrings #-}---- Module      : Network.AWS.Data.Internal.Header--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.Header where--import           Data.ByteString.Char8                (ByteString)-import qualified Data.ByteString.Char8                as BS-import qualified Data.CaseInsensitive                 as CI-import           Data.Foldable                        as Fold-import           Data.HashMap.Strict                  (HashMap)-import qualified Data.HashMap.Strict                  as Map-import           Data.Monoid-import           Data.Text                            (Text)-import qualified Data.Text.Encoding                   as Text-import           Network.AWS.Data.Internal.ByteString-import           Network.AWS.Data.Internal.Text-import           Network.HTTP.Types--(~:) :: FromText a => ResponseHeaders -> HeaderName -> Either String a-hs ~: k = hs ~:? k >>= note-  where-    note Nothing  = Left (BS.unpack $ "Unable to find header: " <> CI.original k)-    note (Just x) = Right x--(~:?) :: FromText a => ResponseHeaders -> HeaderName -> Either String (Maybe a)-hs ~:? k =-    maybe (Right Nothing)-          (fmap Just . fromText . Text.decodeUtf8)-          (k `lookup` hs)--class ToHeaders a where-    toHeaders :: a -> [Header]-    toHeaders = const mempty--(=:) :: ToHeader a => HeaderName -> a -> [Header]-(=:) = toHeader--hdr :: HeaderName -> ByteString -> [Header] -> [Header]-hdr k v hs = (k, v) : filter ((/= k) . fst) hs--hdrs :: [Header] -> [Header] -> [Header]-hdrs xs ys = Fold.foldr' (uncurry hdr) ys xs--toHeaderText :: ToText a => HeaderName -> a -> [Header]-toHeaderText k = toHeader k . toText--class ToHeader a where-    toHeader :: HeaderName -> a -> [Header]--    default toHeader :: ToText a => HeaderName -> a -> [Header]-    toHeader k = toHeader k . toText--instance ToHeader Text where-    toHeader k = toHeader k . Text.encodeUtf8--instance ToHeader ByteString where-    toHeader k = toHeader k . Just--instance ToByteString a => ToHeader (Maybe a) where-    toHeader k = maybe [] (\v -> [(k, toBS v)])--instance (ToByteString k, ToByteString v) => ToHeader (HashMap k v) where-    toHeader p = map (\(k, v) -> (p <> CI.mk (toBS k), toBS v)) . Map.toList--hHost :: HeaderName-hHost = "Host"--hAMZToken :: HeaderName-hAMZToken = "X-Amz-Security-Token"--hAMZTarget :: HeaderName-hAMZTarget = "X-Amz-Target"--hAMZAlgorithm :: HeaderName-hAMZAlgorithm = "X-Amz-Algorithm"--hAMZCredential :: HeaderName-hAMZCredential = "X-Amz-Credential"--hAMZExpires :: HeaderName-hAMZExpires = "X-Amz-Expires"--hAMZSignedHeaders :: HeaderName-hAMZSignedHeaders = "X-Amz-SignedHeaders"--hAMZContentSHA256 :: HeaderName-hAMZContentSHA256 = "X-Amz-Content-SHA256"--hAMZAuth :: HeaderName-hAMZAuth = "X-Amzn-Authorization"--hAMZDate :: HeaderName-hAMZDate = "X-Amz-Date"--hMetaPrefix :: HeaderName-hMetaPrefix = "X-Amz-"
− src/Network/AWS/Data/Internal/JSON.hs
@@ -1,58 +0,0 @@-{-# LANGUAGE OverloadedStrings #-}---- Module      : Network.AWS.Data.Internal.JSON--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.JSON-    (-    -- * FromJSON-      FromJSON (..)-    , parseJSONText-    , eitherDecode'-    -- ** Parser a-    , withObject-    , (.:)-    , (.:?)-    , (.!=)-    -- ** Either String a-    , (.:>)-    , (.:?>)--    -- * ToJSON-    , ToJSON   (..)-    , toJSONText-    , Object-    , object-    , (.=)-    ) where--import           Data.Aeson                     (eitherDecode')-import           Data.Aeson.Types-import qualified Data.HashMap.Strict            as Map-import           Data.Text                      (Text)-import           Network.AWS.Data.Internal.Text--parseJSONText :: FromText a => String -> Value -> Parser a-parseJSONText n = withText n (either fail return . fromText)--toJSONText :: ToText a => a -> Value-toJSONText = String . toText--(.:>) :: FromJSON a => Object -> Text -> Either String a-(.:>) o k =-    case Map.lookup k o of-        Nothing -> Left $ "key " ++ show k ++ " not present"-        Just v  -> parseEither parseJSON v--(.:?>) :: FromJSON a => Object -> Text -> Either String (Maybe a)-(.:?>) o k =-    case Map.lookup k o of-        Nothing -> Right Nothing-        Just v  -> parseEither parseJSON v
− src/Network/AWS/Data/Internal/List.hs
@@ -1,117 +0,0 @@-{-# LANGUAGE DataKinds                  #-}-{-# LANGUAGE DeriveFoldable             #-}-{-# LANGUAGE DeriveTraversable          #-}-{-# LANGUAGE FlexibleContexts           #-}-{-# LANGUAGE GeneralizedNewtypeDeriving #-}-{-# LANGUAGE KindSignatures             #-}-{-# LANGUAGE LambdaCase                 #-}-{-# LANGUAGE OverloadedStrings          #-}-{-# LANGUAGE RoleAnnotations            #-}-{-# LANGUAGE ScopedTypeVariables        #-}-{-# LANGUAGE StandaloneDeriving         #-}-{-# LANGUAGE TypeFamilies               #-}---- Module      : Network.AWS.Data.Internal.List--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.List where--import           Control.Lens                    hiding (coerce, element)-import           Control.Monad-import           Data.Aeson-import           Data.Coerce-import           Data.Foldable                   (Foldable)-import           Data.List.NonEmpty              (NonEmpty(..))-import           Data.Maybe-import           Data.Monoid-import           Data.Proxy-import           Data.Semigroup                  (Semigroup)-import           Data.String-import qualified Data.Text                       as Text-import qualified Data.Vector                     as Vector-import           GHC.Exts-import           GHC.TypeLits-import           Network.AWS.Data.Internal.Query-import           Network.AWS.Data.Internal.XML-import           Text.XML--newtype List (e :: Symbol) a = List { list :: [a] }-    deriving (Eq, Ord, Read, Show, Semigroup, Monoid)--newtype List1 (e :: Symbol) a = List1 { list1 :: NonEmpty a }-    deriving (Eq, Ord, Read, Show, Semigroup)--deriving instance Functor     (List1 e)-deriving instance Foldable    (List1 e)-deriving instance Traversable (List1 e)--type role List  phantom representational-type role List1 phantom representational--_List :: (Coercible a b, Coercible b a) => Iso' (List e a) [b]-_List = iso (coerce . list) (List . coerce)--_List1 :: (Coercible a b, Coercible b a) => Iso' (List1 e a) (NonEmpty b)-_List1 = iso (coerce . list1) (List1 . coerce)--instance IsList (List e a) where-    type Item (List e a) = a--    fromList = List-    toList   = list--fromList1 :: List1 e a -> List e a-fromList1 = List . toList . list1--toList1 :: List e a -> Either String (List1 e a)-toList1 (List (x:xs))-          = Right $ List1 (x :| xs)-toList1 _ = Left  $ "Unexpected empty list, expected at least 1 element."--instance (KnownSymbol e, ToQuery a) => ToQuery (List e a) where-    toQuery = toQueryList n . toList . list-      where-        n = fromString $ symbolVal (Proxy :: Proxy e)--instance (KnownSymbol e, ToQuery a) => ToQuery (List1 e a) where-    toQuery = toQueryList n . toList . list1-      where-        n = fromString $ symbolVal (Proxy :: Proxy e)--instance FromJSON a => FromJSON (List e a) where-    parseJSON = fmap List . parseJSON--instance FromJSON a => FromJSON (List1 e a) where-    parseJSON = withArray "List1" $ \case-        v | Vector.null v -> fail "Empty array, expected at least 1 element."-        v                 -> traverse parseJSON-            . List1 $ Vector.unsafeHead v :| Vector.toList (Vector.unsafeTail v)--instance ToJSON a => ToJSON (List e a) where-    toJSON = toJSON . list--instance ToJSON a => ToJSON (List1 e a) where-    toJSON = toJSON . toList . list1--instance (KnownSymbol e, FromXML a) => FromXML (List e a) where-    parseXML = fmap List . traverse parseXML . mapMaybe (childNodes n)-      where-        n = Text.pack $ symbolVal (Proxy :: Proxy e)--instance (KnownSymbol e, FromXML a) => FromXML (List1 e a) where-    parseXML = parseXML >=> toList1--instance (KnownSymbol e, ToXML a) => ToXML (List e a) where-    toXML = map (NodeElement . element n . toXML) . list-      where-        n = fromString $ symbolVal (Proxy :: Proxy e)--instance (KnownSymbol e, ToXML a) => ToXML (List1 e a) where-    toXML = toXML . fromList1
− src/Network/AWS/Data/Internal/Map.hs
@@ -1,172 +0,0 @@-{-# LANGUAGE DataKinds                  #-}-{-# LANGUAGE FlexibleInstances          #-}-{-# LANGUAGE GeneralizedNewtypeDeriving #-}-{-# LANGUAGE KindSignatures             #-}-{-# LANGUAGE OverloadedStrings          #-}-{-# LANGUAGE RoleAnnotations            #-}-{-# LANGUAGE ScopedTypeVariables        #-}-{-# LANGUAGE TupleSections              #-}-{-# LANGUAGE TypeFamilies               #-}-{-# LANGUAGE ViewPatterns               #-}---- Module      : Network.AWS.Data.Internal.Map--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.Map-    ( Map  (..)-    , _Map-    , (~::)--    , EMap (..)-    , _EMap-    ) where--import           Control.Applicative-import           Control.Lens                         hiding (coerce, element)-import           Data.Aeson-import           Data.Bifunctor-import qualified Data.ByteString.Char8                as BS-import           Data.CaseInsensitive                 (CI)-import qualified Data.CaseInsensitive                 as CI-import           Data.Coerce-import           Data.HashMap.Strict                  (HashMap)-import qualified Data.HashMap.Strict                  as Map-import           Data.Hashable                        (Hashable)-import           Data.Maybe-import           Data.Monoid-import           Data.Proxy-import           Data.Semigroup                       (Semigroup)-import           Data.String-import           Data.Text                            (Text)-import qualified Data.Text                            as Text-import qualified Data.Text.Encoding                   as Text-import           GHC.Exts-import           GHC.TypeLits-import           Network.AWS.Data.Internal.ByteString-import           Network.AWS.Data.Internal.Header-import           Network.AWS.Data.Internal.Query-import           Network.AWS.Data.Internal.Text-import           Network.AWS.Data.Internal.XML-import           Network.HTTP.Types.Header-import           Text.XML--newtype Map k v = Map-    { fromMap :: HashMap k v-    } deriving (Eq, Read, Show, Monoid, Semigroup)--type role Map nominal representational--_Map :: (Coercible a b, Coercible b a) => Iso' (Map k a) (HashMap k b)-_Map = iso (coerce . fromMap) (Map . coerce)--instance (Eq k, Hashable k) => IsList (Map k v) where-    type Item (Map k v) = (k, v)--    fromList = Map . Map.fromList-    toList   = Map.toList . fromMap--instance (Eq k, Hashable k, FromText k, FromJSON v) => FromJSON (Map k v) where-    parseJSON = withObject "HashMap" $-          fmap (Map . Map.fromList)-        . traverse g-        . Map.toList-      where-        g (k, v) = (,)-            <$> either fail return (fromText k)-            <*> parseJSON v--instance (Eq k, Hashable k, ToText k, ToJSON v) => ToJSON (Map k v) where-    toJSON = Object . Map.fromList . map (bimap toText toJSON) . toList--(~::) :: ResponseHeaders-      -> CI Text-      -> Either String (Map (CI Text) Text)-hs ~:: (CI.foldedCase -> p) = Right . fromList $ mapMaybe f hs-  where-    f (CI.map Text.decodeUtf8 -> k, Text.decodeUtf8 -> v) =-        (,v) . CI.mk <$> Text.stripPrefix p (CI.foldedCase k)--instance ToHeader (Map (CI Text) Text) where-    toHeader (CI.foldedCase -> p) = map (first CI.mk . f) . toList-      where-        f (CI.foldedCase -> toBS -> k, toBS -> v)-            | BS.isPrefixOf p k = (k, v)-            | otherwise         = (p <> k, v)--newtype EMap (e :: Symbol) (i :: Symbol) (j :: Symbol) k v = EMap-    { fromEMap :: HashMap k v-    } deriving (Eq, Read, Show, Monoid, Semigroup)--type role EMap phantom phantom phantom nominal representational--_EMap :: (Coercible a b, Coercible b a) => Iso' (EMap e i j k a) (HashMap k b)-_EMap = iso (coerce . fromEMap) (EMap . coerce)--instance (Eq k, Hashable k) => IsList (EMap e i j k v) where-    type Item (EMap e i j k v) = (k, v)--    fromList = EMap . Map.fromList-    toList   = Map.toList . fromEMap--instance ( KnownSymbol e-         , KnownSymbol i-         , KnownSymbol j-         , Eq k-         , Hashable k-         , ToQuery k-         , ToQuery v-         ) => ToQuery (EMap e i j k v) where-    toQuery m = e =? (mconcat . zipWith go idx $ toList m)-      where-        go n (k, v) = toBS n =? toQuery (i, k) <> toQuery (j, v)--        idx = [1..] :: [Integer]--        i = BS.pack $ symbolVal (Proxy :: Proxy i)-        j = BS.pack $ symbolVal (Proxy :: Proxy j)-        e = BS.pack $ symbolVal (Proxy :: Proxy e)--instance ( KnownSymbol e-         , KnownSymbol i-         , KnownSymbol j-         , Eq k-         , Hashable k-         , FromXML k-         , FromXML v-         ) => FromXML (EMap e i j k v) where-    parseXML = fmap fromList . traverse go . mapMaybe (childNodes e)-      where-        go ns = (,)-            <$> withElement i parseXML ns-            <*> withElement j parseXML ns--        i = fromString $ symbolVal (Proxy :: Proxy i)-        j = fromString $ symbolVal (Proxy :: Proxy j)-        e = fromString $ symbolVal (Proxy :: Proxy e)--instance ( KnownSymbol e-         , KnownSymbol i-         , KnownSymbol j-         , Eq k-         , Hashable k-         , ToXML k-         , ToXML v-         ) => ToXML (EMap e i j k v) where-    toXML = map (uncurry go) . toList-      where-        go k v =-            NodeElement $ element e-                [ NodeElement (element i (toXML k))-                , NodeElement (element j (toXML v))-                ]--        i = fromString $ symbolVal (Proxy :: Proxy i)-        j = fromString $ symbolVal (Proxy :: Proxy j)-        e = fromString $ symbolVal (Proxy :: Proxy e)
− src/Network/AWS/Data/Internal/Numeric.hs
@@ -1,61 +0,0 @@-{-# LANGUAGE GeneralizedNewtypeDeriving #-}-{-# LANGUAGE ScopedTypeVariables        #-}-{-# LANGUAGE TemplateHaskell            #-}---- Module      : Network.AWS.Data.Internal.Numeric--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.Numeric where--import Control.Lens.TH-import Control.Monad-import Data.Aeson.Types-import Data.Monoid-import Data.Scientific-import Network.AWS.Data.Internal.ByteString-import Network.AWS.Data.Internal.Query-import Network.AWS.Data.Internal.Text-import Network.AWS.Data.Internal.XML-import Numeric.Natural--newtype Nat = Nat { unNat :: Natural }-    deriving-        ( Eq-        , Ord-        , Read-        , Show-        , Enum-        , Num-        , Real-        , Integral-        , ToByteString-        , FromText-        , ToText-        , FromXML-        , ToXML-        , ToQuery-        )--instance FromJSON Nat where-    parseJSON = parseJSON >=> go-      where-        go n = case floatingOrInteger n of-            Left  (_ :: Double) -> fail (floatErr n)-            Right i-                | n < 0         -> fail (negateErr n)-                | otherwise     -> return . Nat $ fromInteger i--        floatErr  = mappend "Cannot convert float to Natural: " . show-        negateErr = mappend "Cannot convert negative number to Natural: " . show--instance ToJSON Nat where-    toJSON = Number . flip scientific 0 . toInteger . unNat--makePrisms ''Nat
− src/Network/AWS/Data/Internal/Path.hs
@@ -1,23 +0,0 @@--- Module      : Network.AWS.Data.Internal.Path--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.Path-    ( ToPath (..)-    ) where--import Data.Monoid-import Data.Text   (Text)--class ToPath a where-    toPath :: a -> Text-    toPath = const mempty--instance ToPath Text where-    toPath = id
− src/Network/AWS/Data/Internal/Query.hs
@@ -1,152 +0,0 @@-{-# LANGUAGE DefaultSignatures   #-}-{-# LANGUAGE DeriveDataTypeable  #-}-{-# LANGUAGE FlexibleContexts    #-}-{-# LANGUAGE FlexibleInstances   #-}-{-# LANGUAGE OverloadedStrings   #-}-{-# LANGUAGE ScopedTypeVariables #-}-{-# LANGUAGE TemplateHaskell     #-}-{-# LANGUAGE TypeFamilies        #-}-{-# LANGUAGE TypeOperators       #-}-{-# LANGUAGE ViewPatterns        #-}---- Module      : Network.AWS.Data.Internal.Query--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.Query-    ( ToQuery (..)-    , renderQuery--    , Query-    , valuesOf--    , (=?)-    , pair-    , toQueryList-    ) where--import           Control.Lens-import           Data.ByteString                      (ByteString)-import qualified Data.ByteString.Char8                as BS-import           Data.Data-import           Data.Data.Lens-import           Data.List                            (sort)-import           Data.Monoid-import           Data.String-import           Data.Text                            (Text)-import qualified Data.Text.Encoding                   as Text-import           GHC.Exts-import           Network.AWS.Data.Internal.ByteString-import           Network.AWS.Data.Internal.Text-import           Network.HTTP.Types.URI               (urlEncode)-import           Numeric.Natural--data Query-    = List  [Query]-    | Pair  ByteString Query-    | Value (Maybe ByteString)-      deriving (Eq, Show, Data, Typeable)--makePrisms ''Query--instance Monoid Query where-    mempty = List []--    mappend a b = case (a, b) of-        (List l, List r) -> List (l ++ r)-        (List l, r)      -> List (r : l)-        (l,      List r) -> List (l : r)-        (l,      r)      -> List [l, r]--instance Plated Query where-    plate = uniplate--instance ToByteString Query where-    toBS = renderQuery--instance ToBuilder Query--instance ToText Query where-    toText = Text.decodeUtf8 . toBS--instance IsString Query where-    fromString = toQuery . BS.pack--valuesOf :: Traversal' Query (Maybe ByteString)-valuesOf = deep _Value--pair :: ToQuery a => ByteString -> a -> Query -> Query-pair k v = mappend (Pair k (toQuery v))--(=?) :: ToQuery a => ByteString -> a -> Query-(=?) k v = Pair k (toQuery v)--toQueryList :: (IsList a, ToQuery (Item a)) => ByteString -> a -> Query-toQueryList n = mconcat . zipWith (\i v -> n =? (toBS i, v)) idx . toList-  where-    idx = [1..] :: [Int]--renderQuery :: Query -> ByteString-renderQuery = intercalate . sort . enc Nothing-  where-    enc k (List xs)   = concatMap (enc k) xs-    enc k (Pair (urlEncode True -> k') x)-        | Just n <- k = enc (Just $ n <> "." <> k') x-        | otherwise   = enc (Just k') x-    enc k (Value (Just (urlEncode True -> v)))-        | Just n <- k = [n <> vsep <> v]-        | otherwise   = [v <> vsep]-    enc k _-        | Just n <- k = [n <> vsep]-        | otherwise   = []--    intercalate []     = mempty-    intercalate [x]    = x-    intercalate (x:xs) = x <> ksep <> intercalate xs--    ksep = "&"-    vsep = "="--class ToQuery a where-    toQuery :: a -> Query--    default toQuery :: ToText a => a -> Query-    toQuery = toQuery . toText--instance ToQuery Query where-    toQuery = id--instance (ToByteString k, ToQuery v) => ToQuery (k, v) where-    toQuery (k, v) = Pair (toBS k) (toQuery v)--instance ToQuery Char where-    toQuery = toQuery . BS.singleton--instance ToQuery ByteString where-    toQuery "" = Value Nothing-    toQuery bs = Value (Just bs)--instance ToQuery Text    where toQuery = toQuery . Text.encodeUtf8-instance ToQuery Int     where toQuery = toQuery . toBS-instance ToQuery Integer where toQuery = toQuery . toBS-instance ToQuery Double  where toQuery = toQuery . toBS-instance ToQuery Natural where toQuery = toQuery . toBS--instance ToQuery a => ToQuery (Maybe a) where-    toQuery (Just x) = toQuery x-    toQuery Nothing  = mempty--instance ToQuery a => ToQuery [a] where-    toQuery = List . zipWith (\n v -> toBS n =? toQuery v) idx-      where-        idx = [1..] :: [Integer]--instance ToQuery Bool where-    toQuery True  = toQuery ("true"  :: ByteString)-    toQuery False = toQuery ("false" :: ByteString)
− src/Network/AWS/Data/Internal/Sensitive.hs
@@ -1,46 +0,0 @@-{-# LANGUAGE GeneralizedNewtypeDeriving #-}---- Module      : Network.AWS.Data.Internal.Sensitive--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.Sensitive where--import Control.Lens-import Data.Monoid-import Data.String-import Network.AWS.Data.Internal.ByteString-import Network.AWS.Data.Internal.JSON-import Network.AWS.Data.Internal.Query-import Network.AWS.Data.Internal.Text-import Network.AWS.Data.Internal.XML---- | read . show /= isomorphic-newtype Sensitive a = Sensitive { desensitise :: a }-    deriving-        ( Eq-        , Ord-        , Read-        , IsString-        , Monoid-        , ToByteString-        , FromText-        , ToText-        , FromXML-        , ToXML-        , ToQuery-        , ToJSON-        , FromJSON-        )--instance Show (Sensitive a) where-    show = const "******"--_Sensitive :: Iso' (Sensitive a) a-_Sensitive = iso desensitise Sensitive
− src/Network/AWS/Data/Internal/Text.hs
@@ -1,105 +0,0 @@-{-# LANGUAGE DefaultSignatures #-}-{-# LANGUAGE FlexibleInstances #-}-{-# LANGUAGE OverloadedStrings #-}---- Module      : Network.AWS.Data.Internal.Text--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.Text-    ( FromText (..)-    , fromText-    , takeLowerText-    , matchCI--    , ToText   (..)-    , showText-    ) where--import           Control.Applicative-import           Crypto.Hash-import           Data.Attoparsec.Text              (Parser)-import qualified Data.Attoparsec.Text              as AText-import           Data.ByteString                   (ByteString)-import           Data.CaseInsensitive              (CI)-import qualified Data.CaseInsensitive              as CI-import           Data.Int-import           Data.Monoid-import           Data.Scientific-import           Data.Text                         (Text)-import qualified Data.Text                         as Text-import qualified Data.Text.Encoding                as Text-import qualified Data.Text.Lazy                    as LText-import           Data.Text.Lazy.Builder            (Builder)-import qualified Data.Text.Lazy.Builder            as Build-import qualified Data.Text.Lazy.Builder.Int        as Build-import qualified Data.Text.Lazy.Builder.RealFloat  as Build-import qualified Data.Text.Lazy.Builder.Scientific as Build-import           Network.HTTP.Client-import           Network.HTTP.Types-import           Numeric.Natural--fromText :: FromText a => Text -> Either String a-fromText = AText.parseOnly parser--takeLowerText :: Parser Text-takeLowerText = Text.toLower <$> AText.takeText--matchCI :: Text -> a -> Parser a-matchCI x y = AText.asciiCI x <* AText.endOfInput >> return y--class FromText a where-    parser :: Parser a--instance FromText Text       where parser = AText.takeText-instance FromText ByteString where parser = Text.encodeUtf8 <$> AText.takeText-instance FromText Int        where parser = AText.signed AText.decimal-instance FromText Integer    where parser = AText.signed AText.decimal-instance FromText Scientific where parser = AText.signed AText.scientific-instance FromText Natural    where parser = AText.decimal-instance FromText Double     where parser = AText.signed AText.rational--instance FromText Bool where-    parser = matchCI "false" False <|> matchCI "true" True--showText :: ToText a => a -> String-showText = Text.unpack . toText--class ToText a where-    toText :: a -> Text--instance (ToText a, ToText b) => ToText (a, b) where-    toText (a, b) = "(" <> toText a <> ", " <> toText b <> ")"--instance ToText a => ToText [a] where-    toText xs = "[" <> Text.intercalate ", " (map toText xs) <> "]"--instance ToText a => ToText (CI a) where-    toText = toText . CI.original--instance ToText (Response a) where-    toText rs = Text.pack . show $ rs { responseBody = () }--instance ToText Text       where toText = id-instance ToText ByteString where toText = Text.decodeUtf8-instance ToText Int        where toText = shortText . Build.decimal-instance ToText Int64      where toText = shortText . Build.decimal-instance ToText Integer    where toText = shortText . Build.decimal-instance ToText Natural    where toText = shortText . Build.decimal-instance ToText Scientific where toText = shortText . Build.scientificBuilder-instance ToText Double     where toText = shortText . Build.realFloat-instance ToText StdMethod  where toText = toText . renderStdMethod-instance ToText (Digest a) where toText = toText . digestToHexByteString--instance ToText Bool where-    toText True  = "true"-    toText False = "false"--shortText :: Builder -> Text-shortText = LText.toStrict . Build.toLazyTextWith 32
− src/Network/AWS/Data/Internal/Time.hs
@@ -1,177 +0,0 @@-{-# LANGUAGE DataKinds           #-}-{-# LANGUAGE FlexibleContexts    #-}-{-# LANGUAGE FlexibleInstances   #-}-{-# LANGUAGE GADTs               #-}-{-# LANGUAGE KindSignatures      #-}-{-# LANGUAGE LambdaCase          #-}-{-# LANGUAGE OverloadedStrings   #-}-{-# LANGUAGE ScopedTypeVariables #-}-{-# LANGUAGE StandaloneDeriving  #-}---- Module      : Network.AWS.Data.Internal.Time--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.Time-    ( Format (..)-    , Time   (..)-    , _Time--    , UTCTime-    , RFC822-    , ISO8601-    , BasicTime-    , AWSTime-    , POSIX--    , parseTime-    , defaultTimeLocale-    , iso8601DateFormat-    ) where--import           Control.Applicative-import           Control.Lens-import           Data.Aeson-import           Data.Attoparsec.Text                 (Parser)-import qualified Data.Attoparsec.Text                 as AText-import qualified Data.ByteString.Char8                as BS-import           Data.Scientific-import           Data.Tagged-import qualified Data.Text                            as Text-import           Data.Time                            (UTCTime)-import           Data.Time.Clock.POSIX-import           Data.Time.Format                     (formatTime)-import           Network.AWS.Compat.Internal.Locale   (defaultTimeLocale,-                                                       iso8601DateFormat)-import           Network.AWS.Compat.Internal.Time     (parseTime)-import           Network.AWS.Data.Internal.ByteString-import           Network.AWS.Data.Internal.JSON-import           Network.AWS.Data.Internal.Query-import           Network.AWS.Data.Internal.Text-import           Network.AWS.Data.Internal.XML--data Format-    = RFC822Format-    | ISO8601Format-    | BasicFormat-    | AWSFormat-    | POSIXFormat-      deriving (Eq, Read, Show)--data Time :: Format -> * where-    Time :: UTCTime -> Time a--deriving instance Eq   (Time a)-deriving instance Ord  (Time a)-deriving instance Read (Time a)-deriving instance Show (Time a)--_Time :: Iso' (Time a) UTCTime-_Time = iso (\(Time t) -> t) Time--convert :: Time a -> Time b-convert (Time t) = Time t--type RFC822    = Time 'RFC822Format-type ISO8601   = Time 'ISO8601Format-type BasicTime = Time 'BasicFormat-type AWSTime   = Time 'AWSFormat-type POSIX     = Time 'POSIXFormat--class TimeFormat a where-    format :: Tagged a String--instance TimeFormat RFC822    where format = Tagged "%a, %d %b %Y %H:%M:%S GMT"-instance TimeFormat ISO8601   where format = Tagged (iso8601DateFormat (Just "%X%QZ"))-instance TimeFormat BasicTime where format = Tagged "%Y%m%d"-instance TimeFormat AWSTime   where format = Tagged "%Y%m%dT%H%M%SZ"--instance FromText BasicTime where parser = parseFormattedTime-instance FromText AWSTime   where parser = parseFormattedTime--instance FromText RFC822 where-    parser = (convert :: ISO8601 -> RFC822) <$> parseFormattedTime-         <|> parseFormattedTime--instance FromText ISO8601 where-    parser = (convert :: RFC822 -> ISO8601) <$> parseFormattedTime-         <|> parseFormattedTime--instance FromText POSIX where-    parser = Time . posixSecondsToUTCTime . realToFrac-        <$> (parser :: Parser Scientific)--parseFormattedTime :: forall a. TimeFormat (Time a) => Parser (Time a)-parseFormattedTime = do-    x <- Text.unpack <$> AText.takeText-    p (parseTime defaultTimeLocale (untag f) x) x-  where-    p :: Maybe UTCTime -> String -> Parser (Time a)-    p Nothing  s = fail   ("Unable to parse " ++ untag f ++ " from " ++ s)-    p (Just x) _ = return (Time x)--    f :: Tagged (Time a) String-    f = format--instance ToText RFC822    where toText = Text.pack . renderFormattedTime-instance ToText ISO8601   where toText = Text.pack . renderFormattedTime-instance ToText BasicTime where toText = Text.pack . renderFormattedTime-instance ToText AWSTime   where toText = Text.pack . renderFormattedTime--instance ToText POSIX where-    toText (Time t) = toText (truncate (utcTimeToPOSIXSeconds t) :: Integer)--renderFormattedTime :: forall a. TimeFormat (Time a) => Time a -> String-renderFormattedTime (Time t) = formatTime defaultTimeLocale (untag f) t-  where-    f :: Tagged (Time a) String-    f = format--instance FromXML RFC822    where parseXML = parseXMLText "RFC822"-instance FromXML ISO8601   where parseXML = parseXMLText "ISO8601"-instance FromXML AWSTime   where parseXML = parseXMLText "AWSTime"-instance FromXML BasicTime where parseXML = parseXMLText "BasicTime"-instance FromXML POSIX     where parseXML = parseXMLText "POSIX"--instance FromJSON RFC822    where parseJSON = parseJSONText "RFC822"-instance FromJSON ISO8601   where parseJSON = parseJSONText "ISO8601"-instance FromJSON AWSTime   where parseJSON = parseJSONText "AWSTime"-instance FromJSON BasicTime where parseJSON = parseJSONText "BasicTime"--instance FromJSON POSIX where-    parseJSON = withScientific "POSIX"-        $ pure-        . Time-        . posixSecondsToUTCTime-        . realToFrac--instance ToByteString RFC822    where toBS = BS.pack . renderFormattedTime-instance ToByteString ISO8601   where toBS = BS.pack . renderFormattedTime-instance ToByteString BasicTime where toBS = BS.pack . renderFormattedTime-instance ToByteString AWSTime   where toBS = BS.pack . renderFormattedTime--instance ToQuery RFC822    where toQuery = toQuery . toBS-instance ToQuery ISO8601   where toQuery = toQuery . toBS-instance ToQuery BasicTime where toQuery = toQuery . toBS-instance ToQuery AWSTime   where toQuery = toQuery . toBS--instance ToXML RFC822    where toXML = toXMLText-instance ToXML ISO8601   where toXML = toXMLText-instance ToXML AWSTime   where toXML = toXMLText-instance ToXML BasicTime where toXML = toXMLText-instance ToXML POSIX     where toXML = toXMLText--instance ToJSON RFC822    where toJSON = toJSONText-instance ToJSON ISO8601   where toJSON = toJSONText-instance ToJSON AWSTime   where toJSON = toJSONText-instance ToJSON BasicTime where toJSON = toJSONText--instance ToJSON POSIX where-    toJSON (Time t) = Number $-        scientific (truncate (utcTimeToPOSIXSeconds t) :: Integer) 0
− src/Network/AWS/Data/Internal/URI.hs
@@ -1,56 +0,0 @@-{-# LANGUAGE OverloadedStrings #-}---- Module      : Network.AWS.Data.Internal.URI--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.URI-    ( collapsePath-    ) where--import           Data.ByteString.Char8 (ByteString)-import qualified Data.ByteString.Char8 as BS-import qualified Data.Foldable         as Fold-import           Data.Monoid--collapsePath :: ByteString -> ByteString-collapsePath bs-    | BS.null bs   = slash-    | BS.null path = slash-    | otherwise    = tl (hd path)-  where-    path = BS.intercalate slash-        . reverse-        . Fold.foldl' go []-        . filter (/= mempty)-        $ BS.split sep bs--    hd x | BS.head x  == sep = x-         | otherwise         = sep `BS.cons` x--    tl x | BS.last x  == sep = x-         | BS.last bs == sep = x `BS.snoc` sep-         | otherwise         = x--    go acc c | c == dot  = acc-    go acc c | c == dots = remv acc c-    go acc c             = c : acc--    remv []       _ = []-    remv (x : xs) c-        | x == dot  = c : xs-        | x == dots = c : x : xs-        | otherwise = xs--    dot  = "."-    dots = ".."--    slash = BS.singleton sep--    sep  = '/'
− src/Network/AWS/Data/Internal/XML.hs
@@ -1,199 +0,0 @@-{-# LANGUAGE DefaultSignatures   #-}-{-# LANGUAGE LambdaCase          #-}-{-# LANGUAGE OverloadedStrings   #-}-{-# LANGUAGE ScopedTypeVariables #-}---- Module      : Network.AWS.Data.Internal.XML--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Data.Internal.XML-    (-    -- * FromXML-      FromXML   (..)-    , decodeXML-    , parseXMLText-    , childNodes-    , findElement-    , withContent-    , withElement-    , localName-    , (.@)-    , (.@?)-    , (.!@)--    -- * ToXML-    , ToXML     (..)-    , ToXMLRoot (..)-    , encodeXML-    , toXMLText-    , namespaced-    , element-    , nodes-    , (=@)-    , extractRoot-    , unsafeToXML-    ) where--import           Control.Applicative-import           Control.Monad-import           Data.Default.Class-import           Data.Maybe-import           Data.Monoid-import           Data.Text                            (Text)-import           Network.AWS.Data.Internal.ByteString-import           Network.AWS.Data.Internal.Text-import           Numeric.Natural-import           Text.XML--decodeXML :: LazyByteString -> Either String [Node]-decodeXML = either failure success . parseLBS def-  where-    failure = Left  . show-    success = Right . elementNodes . documentRoot--encodeXML :: ToXMLRoot a => a -> LazyByteString-encodeXML = maybe mempty (renderLBS def . d) . toXMLRoot-  where-    d x = Document-        { documentPrologue = p-        , documentRoot     = x-        , documentEpilogue = []-        }--    p = Prologue-        { prologueBefore  = []-        , prologueDoctype = Nothing-        , prologueAfter   = []-        }--parseXMLText :: FromText a => String -> [Node] -> Either String a-parseXMLText n = withContent n >=> maybe err fromText-  where-    err = Left $ "empty node list, when expecting single node " ++ n--toXMLText :: ToText a => a -> [Node]-toXMLText x = [NodeContent (toText x)]--(.@) :: FromXML a => [Node] -> Text -> Either String a-ns .@ n = findElement n ns >>= parseXML--(.@?) :: FromXML a => [Node] -> Text -> Either String (Maybe a)-ns .@? n =-    case findElement n ns of-        Left _   -> Right Nothing-        Right xs -> parseXML xs--(.!@) :: Either String (Maybe a) -> a -> Either String a-f .!@ x = fromMaybe x <$> f--namespaced :: Text -> Text -> [Node] -> Maybe Element-namespaced g l = Just . element (Name l (Just g) Nothing)--element :: Name -> [Node] -> Element-element n = Element n mempty--nodes :: Name -> [Node] -> [Node]-nodes n ns = [NodeElement (element n ns)]--(=@) :: ToXML a => Name -> a -> Node-n =@ x = NodeElement (element n (toXML x))--extractRoot :: Text -> [Node] -> Maybe Element-extractRoot g ns =-    case ns of-        [NodeElement x] -> Just x { elementName = rename x }-        _               -> Nothing-  where-    rename x = (elementName x) { nameNamespace = Just g }---- | /Caution:/ This is for use with types which are 'flattened' in--- AWS service model terminology.------ It is applied by the generator/templating in safe contexts only.-unsafeToXML :: (Show a, ToXML a) => a -> Node-unsafeToXML x =-    fromMaybe (error $ "Failed to unflatten node-list for: " ++ show x)-              (listToMaybe (toXML x))--withContent :: String -> [Node] -> Either String (Maybe Text)-withContent n = exactly >=> \case-    Just  x -> Just <$> content x-    Nothing -> return Nothing-  where-    exactly :: [Node] -> Either String (Maybe Node)-    exactly = \case-        [x] -> Right (Just x)-        []  -> Right Nothing-        _   -> Left $-            "encountered node list, when expecting exactly one node: " ++ n--    content :: Node -> Either String Text-    content (NodeContent x)-        = Right x-    content (NodeElement e)-        = let k = show (elementName e)-           in Left $ "unexpected element " ++ k ++ ", when expecting node content: " ++ n-    content _ = Left $ "unrecognised element, when expecting node content: " ++ n--withElement :: Text -> ([Node] -> Either String a) -> [Node] -> Either String a-withElement n f = findElement n >=> f--findElement :: Text -> [Node] -> Either String [Node]-findElement n ns = maybe err Right . listToMaybe $ mapMaybe (childNodes n) ns-  where-    err = Left $ "unable to find element "-        ++ show n-        ++ " in nodes "-        ++ show (mapMaybe localName ns)--childNodes :: Text -> Node -> Maybe [Node]-childNodes n (NodeElement e)-    | nameLocalName (elementName e) == n = Just (elementNodes e)-childNodes _ _ = Nothing--localName :: Node -> Maybe Text-localName (NodeElement e) = Just (nameLocalName (elementName e))-localName _               = Nothing--class FromXML a where-    parseXML :: [Node] -> Either String a--instance FromXML a => FromXML (Maybe a) where-    parseXML [] = pure Nothing-    parseXML ns = Just <$> parseXML ns--instance FromXML Text where-    parseXML = withContent "Text" >=> fromText . fromMaybe mempty--instance FromXML Int     where parseXML = parseXMLText "Int"-instance FromXML Integer where parseXML = parseXMLText "Integer"-instance FromXML Natural where parseXML = parseXMLText "Natural"-instance FromXML Double  where parseXML = parseXMLText "Double"-instance FromXML Bool    where parseXML = parseXMLText "Bool"--class ToXMLRoot a where-    toXMLRoot :: a -> Maybe Element--class ToXML a where-    toXML :: a -> [Node]--    default toXML :: ToXMLRoot a => a -> [Node]-    toXML = maybeToList . fmap NodeElement . toXMLRoot--instance ToXML a => ToXML (Maybe a) where-    toXML (Just x) = toXML x-    toXML Nothing  = []--instance ToXML Text    where toXML = toXMLText-instance ToXML Int     where toXML = toXMLText-instance ToXML Integer where toXML = toXMLText-instance ToXML Natural where toXML = toXMLText-instance ToXML Double  where toXML = toXMLText-instance ToXML Bool    where toXML = toXMLText
+ src/Network/AWS/Data/JSON.hs view
@@ -0,0 +1,63 @@+{-# LANGUAGE OverloadedStrings #-}++-- |+-- Module      : Network.AWS.Data.JSON+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.JSON+    (+    -- * FromJSON+      FromJSON (..)+    , parseJSONText+    , eitherDecode'++    -- ** Parser a+    , withObject+    , (.:)+    , (.:?)+    , (.!=)++    -- ** Either String a+    , eitherParseJSON+    , (.:>)+    , (.?>)++    -- * ToJSON+    , ToJSON   (..)+    , toJSONText+    , Value    (Object)+    , object+    , (.=)+    ) where++import           Data.Aeson            (eitherDecode')+import           Data.Aeson.Types+import qualified Data.HashMap.Strict   as Map+import           Network.AWS.Data.Text++import           Prelude++parseJSONText :: FromText a => String -> Value -> Parser a+parseJSONText n = withText n (either fail return . fromText)++toJSONText :: ToText a => a -> Value+toJSONText = String . toText++eitherParseJSON :: FromJSON a => Object -> Either String a+eitherParseJSON = parseEither parseJSON . Object++(.:>) :: FromJSON a => Object -> Text -> Either String a+(.:>) o k =+    case Map.lookup k o of+        Nothing -> Left $ "key " ++ show k ++ " not present"+        Just v  -> parseEither parseJSON v++(.?>) :: FromJSON a => Object -> Text -> Either String (Maybe a)+(.?>) o k =+    case Map.lookup k o of+        Nothing -> Right Nothing+        Just v  -> parseEither parseJSON v
+ src/Network/AWS/Data/List1.hs view
@@ -0,0 +1,83 @@+{-# LANGUAGE DeriveDataTypeable         #-}+{-# LANGUAGE DeriveFoldable             #-}+{-# LANGUAGE DeriveGeneric              #-}+{-# LANGUAGE DeriveTraversable          #-}+{-# LANGUAGE GeneralizedNewtypeDeriving #-}+{-# LANGUAGE TypeFamilies               #-}++-- |+-- Module      : Network.AWS.Data.List1+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.List1 where++import           Control.Applicative+import           Control.Lens         (Iso', iso)+import           Control.Monad+import           Data.Aeson+import           Data.Coerce+import           Data.Data            (Data, Typeable)+import           Data.Foldable        (Foldable)+import           Data.List.NonEmpty   (NonEmpty (..))+import qualified Data.List.NonEmpty   as NonEmpty+import           Data.Semigroup+import           Data.Text            (Text)+import           Data.Traversable     (Traversable, traverse)+import           GHC.Exts+import           GHC.Generics         (Generic)+import           Network.AWS.Data.XML+import           Text.XML             (Node)++import           Prelude++newtype List1 a = List1 { toNonEmpty :: NonEmpty a }+    deriving+        ( Functor+        , Monad+        , Applicative+        , Foldable+        , Traversable+        , Semigroup+        , Eq+        , Ord+        , Read+        , Show+        , Data+        , Typeable+        , Generic+        )++_List1 :: (Coercible a b, Coercible b a) => Iso' (List1 a) (NonEmpty b)+_List1 = iso (coerce . toNonEmpty) (List1 . coerce)++instance IsList (List1 a) where+   type Item (List1 a) = a++   fromList = List1 . NonEmpty.fromList+   toList   = NonEmpty.toList . toNonEmpty++instance FromJSON a => FromJSON (List1 a) where+    parseJSON = withArray "List1" (go >=> traverse parseJSON)+      where+        go = maybe (fail "Error parsing empty List1 when expecting at least one element.")+                   (pure . List1)+           . NonEmpty.nonEmpty+           . toList++instance ToJSON a => ToJSON (List1 a) where+    toJSON = toJSON . toList++parseXMLList1 :: FromXML a+              => Text+              -> [Node]+              -> Either String (List1 a)+parseXMLList1 n = parseXMLList n >=> parse+  where+    parse xs =+       maybe (Left $ "Error parsing empty List1 when expecting at least one element: " ++ show n)+             (Right . List1)+             (NonEmpty.nonEmpty xs)
+ src/Network/AWS/Data/Log.hs view
@@ -0,0 +1,144 @@+{-# LANGUAGE FlexibleInstances #-}+{-# LANGUAGE LambdaCase        #-}+{-# LANGUAGE OverloadedStrings #-}+{-# LANGUAGE RecordWildCards   #-}++-- |+-- Module      : Network.AWS.Data.Log+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.Log where++import qualified Data.ByteString              as BS+import           Data.ByteString.Builder      (Builder)+import qualified Data.ByteString.Lazy         as LBS+import qualified Data.ByteString.Lazy.Builder as Build+import           Data.CaseInsensitive         (CI)+import qualified Data.CaseInsensitive         as CI+import           Data.Int+import           Data.List                    (intersperse)+import           Data.Monoid+import qualified Data.Text                    as Text+import qualified Data.Text.Encoding           as Text+import qualified Data.Text.Lazy               as LText+import qualified Data.Text.Lazy.Encoding      as LText+import           Data.Time                    (UTCTime)+import           Data.Word+import           GHC.Float+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Path+import           Network.AWS.Data.Query+import           Network.AWS.Data.Text+import           Network.HTTP.Client+import           Network.HTTP.Types+import           Numeric++import           Prelude++class ToLog a where+    -- | Convert a value to a loggable builder.+    build :: a -> Builder++instance ToLog Builder        where build = id+instance ToLog LBS.ByteString where build = Build.lazyByteString+instance ToLog ByteString     where build = Build.byteString+instance ToLog Int            where build = Build.intDec+instance ToLog Int8           where build = Build.int8Dec+instance ToLog Int16          where build = Build.int16Dec+instance ToLog Int32          where build = Build.int32Dec+instance ToLog Int64          where build = Build.int64Dec+instance ToLog Integer        where build = Build.integerDec+instance ToLog Word           where build = Build.wordDec+instance ToLog Word8          where build = Build.word8Dec+instance ToLog Word16         where build = Build.word16Dec+instance ToLog Word32         where build = Build.word32Dec+instance ToLog Word64         where build = Build.word64Dec+instance ToLog UTCTime        where build = Build.stringUtf8 . show+instance ToLog Float          where build = build . ($ "") . showFFloat Nothing+instance ToLog Double         where build = build . ($ "") . showFFloat Nothing+instance ToLog Text           where build = build . Text.encodeUtf8+instance ToLog LText.Text     where build = build . LText.encodeUtf8+instance ToLog Char           where build = build . Text.singleton+instance ToLog [Char]         where build = build . LText.pack+instance ToLog StdMethod      where build = build . renderStdMethod+instance ToLog QueryString    where build = build . toBS+instance ToLog EscapedPath    where build = build . toBS++-- | Intercalate a list of 'Builder's with newlines.+buildLines :: [Builder] -> Builder+buildLines = mconcat . intersperse "\n"++instance ToLog a => ToLog (CI a) where+    build = build . CI.foldedCase++instance ToLog a => ToLog (Maybe a) where+    build Nothing  = "Nothing"+    build (Just x) = "Just " <> build x++instance ToLog Bool where+    build True  = "True"+    build False = "False"++instance ToLog Status where+    build x = build (statusCode x) <> " " <> build (statusMessage x)++instance ToLog [Header] where+    build = mconcat+        . intersperse "; "+        . map (\(k, v) -> build k <> ": " <> build v)++instance ToLog HttpVersion where+    build HttpVersion{..} =+           "HTTP/"+        <> build httpMajor+        <> build '.'+        <> build httpMinor++instance ToLog RequestBody where+    build = \case+        RequestBodyBuilder     n _ -> " <msger:"   <> build n <> ">"+        RequestBodyStream      n _ -> " <stream:"  <> build n <> ">"+        RequestBodyStreamChunked _ -> " <chunked>"++        RequestBodyLBS lbs+            | n <= 4096            -> build lbs+            | otherwise            -> " <lazy:" <> build n <> ">"+          where+            n = LBS.length lbs++        RequestBodyBS bs+            | n <= 4096            -> build bs+            | otherwise            -> " <strict:" <> build n <> ">"+          where+            n = BS.length bs++instance ToLog HttpException where+    build x = "[HttpException] {\n" <> build (show x) <> "\n}"++instance ToLog Request where+    build x = buildLines+        [ "[Client Request] {"+        , "  host    = " <> build (host            x)+        , "  port    = " <> build (port            x)+        , "  secure  = " <> build (secure          x)+        , "  headers = " <> build (requestHeaders  x)+        , "  path    = " <> build (path            x)+        , "  query   = " <> build (queryString     x)+        , "  method  = " <> build (method          x)+        , "  timeout = " <> build (responseTimeout x)+        , "}"+        ]++instance ToLog (Response a) where+    build x = buildLines+        [ "[Client Response] {"+        , "  status  = " <> build (responseStatus  x)+        , "  version = " <> build (responseVersion x)+        , "  headers = " <> build (responseHeaders x)+        , "  cookies = " <> build (show (responseCookieJar x))+        , "}"+        ]
+ src/Network/AWS/Data/Map.hs view
@@ -0,0 +1,129 @@+{-# LANGUAGE DeriveDataTypeable         #-}+{-# LANGUAGE DeriveGeneric              #-}+{-# LANGUAGE DeriveFoldable             #-}+{-# LANGUAGE DeriveTraversable          #-}+{-# LANGUAGE GeneralizedNewtypeDeriving #-}+{-# LANGUAGE RoleAnnotations            #-}+{-# LANGUAGE TupleSections              #-}+{-# LANGUAGE TypeFamilies               #-}++-- |+-- Module      : Network.AWS.Data.Map+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.Map+    ( Map (..)+    , _Map+    , parseXMLMap+    , parseHeadersMap+    , toQueryMap+    ) where++import           Control.Applicative+import           Control.Lens                (Iso', iso)+import           Data.Aeson+import           Data.Bifunctor+import qualified Data.ByteString             as BS+import qualified Data.CaseInsensitive        as CI+import           Data.Coerce+import           Data.Data                   (Data,Typeable)+import           Data.Foldable               hiding (toList)+import           Data.Hashable+import           Data.HashMap.Strict         (HashMap)+import qualified Data.HashMap.Strict         as Map+import           Data.Maybe+import           Data.Semigroup+import qualified Data.Text.Encoding          as Text+import           Data.Traversable+import           GHC.Exts+import           GHC.Generics                (Generic)+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Headers+import           Network.AWS.Data.Query+import           Network.AWS.Data.Text+import           Network.AWS.Data.XML+import           Network.HTTP.Types          (ResponseHeaders)+import           Text.XML                    (Node)++import           Prelude++newtype Map k v = Map { toMap :: HashMap k v }+    deriving+        ( Functor+        , Foldable+        , Traversable+        , Monoid+        , Semigroup+        , Eq+        , Read+        , Show+        , Data+        , Typeable+        , Generic+        )++type role Map nominal representational++_Map :: (Coercible a b, Coercible b a) => Iso' (Map k a) (HashMap k b)+_Map = iso (coerce . toMap) (Map . coerce)++instance (Hashable k, Eq k) => IsList (Map k v) where+   type Item (Map k v) = (k, v)++   fromList = Map . Map.fromList+   toList   = Map.toList . toMap++instance (Eq k, Hashable k, FromText k, FromJSON v) => FromJSON (Map k v) where+    parseJSON = withObject "HashMap" (fmap fromList . traverse f . toList)+      where+        f (k, v) = (,)+            <$> either fail return (fromText k)+            <*> parseJSON v++instance (Eq k, Hashable k, ToText k, ToJSON v) => ToJSON (Map k v) where+    toJSON = Object . fromList . map (bimap toText toJSON) . toList++instance (Eq k, Hashable k, ToByteString k, ToText v) => ToHeader (Map k v) where+    toHeader p = map (bimap k v) . toList+      where+        k = mappend p . CI.mk . toBS+        v = Text.encodeUtf8 . toText++parseXMLMap :: (Eq k, Hashable k, FromText k, FromXML v)+            => Text+            -> Text+            -> Text+            -> [Node]+            -> Either String (Map k v)+parseXMLMap e k v = fmap fromList . traverse f . mapMaybe (childNodesOf e)+  where+    f ns = (,)+       <$> (ns .@ k >>= fromText)+       <*>  ns .@ v++parseHeadersMap :: FromText a+                => ByteString+                -> ResponseHeaders+                -> Either String (Map Text a)+parseHeadersMap p = fmap fromList . traverse g . filter f+  where+    f = BS.isPrefixOf p . CI.foldedCase . fst++    g (k, v) = (Text.decodeUtf8 . BS.drop n $ CI.original k,) <$>+        fromText (Text.decodeUtf8 v)++    n = BS.length p++toQueryMap :: (Hashable k, Eq k, ToQuery k, ToQuery v)+           => ByteString+           -> ByteString+           -> ByteString+           -> Map k v+           -> QueryString+toQueryMap e k v = toQueryList e . map f . toList+  where+    f (x, y) = QList [k =: toQuery x, v =: toQuery y]
+ src/Network/AWS/Data/Numeric.hs view
@@ -0,0 +1,68 @@+{-# LANGUAGE DeriveDataTypeable         #-}+{-# LANGUAGE DeriveGeneric              #-}+{-# LANGUAGE GeneralizedNewtypeDeriving #-}+{-# LANGUAGE ScopedTypeVariables        #-}++-- |+-- Module      : Network.AWS.Data.Numeric+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.Numeric where++import           Control.Lens+import           Control.Monad+import           Data.Aeson.Types+import           Data.Data                   (Data, Typeable)+import           Data.Monoid+import           Data.Scientific+import           GHC.Generics                (Generic)+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Query+import           Network.AWS.Data.Text+import           Network.AWS.Data.XML+import           Numeric.Natural++import           Prelude++newtype Nat = Nat { unNat :: Natural }+    deriving+        ( Eq+        , Ord+        , Read+        , Show+        , Enum+        , Num+        , Real+        , Integral+        , Data+        , Typeable+        , Generic+        , ToByteString+        , FromText+        , ToText+        , FromXML+        , ToXML+        , ToQuery+        )++_Nat :: Iso' Nat Natural+_Nat = iso unNat Nat++instance FromJSON Nat where+    parseJSON = parseJSON >=> go+      where+        go n = case floatingOrInteger n of+            Left  (_ :: Double) -> fail (floatErr n)+            Right i+                | n < 0         -> fail (negateErr n)+                | otherwise     -> return . Nat $ fromInteger i++        floatErr  = mappend "Cannot convert float to Natural: " . show+        negateErr = mappend "Cannot convert negative number to Natural: " . show++instance ToJSON Nat where+    toJSON = Number . flip scientific 0 . toInteger . unNat
+ src/Network/AWS/Data/Path.hs view
@@ -0,0 +1,99 @@+{-# LANGUAGE DataKinds          #-}+{-# LANGUAGE DefaultSignatures  #-}+{-# LANGUAGE FlexibleInstances  #-}+{-# LANGUAGE GADTs              #-}+{-# LANGUAGE KindSignatures     #-}+{-# LANGUAGE LambdaCase         #-}+{-# LANGUAGE OverloadedStrings  #-}+{-# LANGUAGE StandaloneDeriving #-}++-- |+-- Module      : Network.AWS.Data.Path+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.Path+    (+    -- * Path Types+      RawPath+    , EscapedPath++    -- * Constructing Paths+    , ToPath (..)+    , rawPath++    -- * Manipulating Paths+    , escapePath+    , collapsePath+    ) where++import qualified Data.ByteString.Char8       as BS8+import           Data.Monoid+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Text+import           Network.HTTP.Types.URI++import           Prelude++class ToPath a where+    toPath :: a -> ByteString++instance ToPath ByteString where+    toPath = id++instance ToPath Text where+    toPath = toBS++rawPath :: ToPath a => a -> Path 'NoEncoding+rawPath = Raw . filter (not . BS8.null) . BS8.split sep . toPath++data Encoding = NoEncoding | Percent+    deriving (Eq, Show)++data Path :: Encoding -> * where+    Raw     :: [ByteString] -> Path 'NoEncoding+    Encoded :: [ByteString] -> Path 'Percent++deriving instance Show (Path a)+deriving instance Eq   (Path a)++type RawPath     = Path 'NoEncoding+type EscapedPath = Path 'Percent++instance Monoid RawPath where+    mempty                    = Raw []+    mappend (Raw xs) (Raw ys) = Raw (xs ++ ys)++instance ToByteString EscapedPath where+    toBS (Encoded []) = slash+    toBS (Encoded xs) = slash <> BS8.intercalate slash xs++escapePath :: Path a -> EscapedPath+escapePath (Raw     xs) = Encoded (map (urlEncode True) xs)+escapePath (Encoded xs) = Encoded xs++collapsePath :: Path a -> Path a+collapsePath = \case+    Raw     xs -> Raw     (go xs)+    Encoded xs -> Encoded (go xs)+  where+    go = reverse . f . reverse++    f :: [ByteString] -> [ByteString]+    f []            = []+    f (x:xs)+        | x == dot  = f xs+        | x == dots = drop 1 (f xs)+        | otherwise = x : f xs++    dot  = "."+    dots = ".."++slash :: ByteString+slash = BS8.singleton sep++sep :: Char+sep = '/'
+ src/Network/AWS/Data/Query.hs view
@@ -0,0 +1,135 @@+{-# LANGUAGE DefaultSignatures   #-}+{-# LANGUAGE DeriveDataTypeable  #-}+{-# LANGUAGE FlexibleContexts    #-}+{-# LANGUAGE FlexibleInstances   #-}+{-# LANGUAGE LambdaCase          #-}+{-# LANGUAGE OverloadedStrings   #-}+{-# LANGUAGE ScopedTypeVariables #-}+{-# LANGUAGE TypeFamilies        #-}+{-# LANGUAGE TypeOperators       #-}+{-# LANGUAGE ViewPatterns        #-}++-- |+-- Module      : Network.AWS.Data.Query+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.Query where++import           Data.ByteString.Builder     (Builder)+import qualified Data.ByteString.Builder     as Build+import qualified Data.ByteString.Char8       as BS8+import qualified Data.ByteString.Lazy        as LBS+import           Data.Data+import           Data.List                   (sort)+import           Data.Monoid+import           Data.String+import qualified Data.Text.Encoding          as Text+import           GHC.Exts+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Text+import           Network.HTTP.Types.URI      (urlEncode)+import           Numeric.Natural++import           Prelude++data QueryString+    = QList  [QueryString]+    | QPair  ByteString QueryString+    | QValue (Maybe ByteString)+      deriving (Eq, Show, Data, Typeable)++instance Monoid QueryString where+    mempty = QList []++    mappend a b = case (a, b) of+        (QList l, QList r) -> QList (l ++ r)+        (QList l, r)       -> QList (r : l)+        (l,       QList r) -> QList (l : r)+        (l,       r)       -> QList [l, r]++instance IsString QueryString where+    fromString [] = mempty+    fromString xs = QPair (BS8.pack xs) (QValue Nothing)++-- FIXME: use Builder+instance ToByteString QueryString where+    toBS = LBS.toStrict . Build.toLazyByteString . cat . sort . enc Nothing+      where+        enc :: Maybe ByteString -> QueryString -> [ByteString]+        enc p = \case+            QList xs          -> concatMap (enc p) xs++            QPair (urlEncode True -> k) x+                | Just n <- p -> enc (Just (n <> kdelim <> k)) x -- <prev>.key <recur>+                | otherwise   -> enc (Just k)                  x -- key <recur>++            QValue (Just (urlEncode True -> v))+                | Just n <- p -> [n <> vsep <> v] -- key=value+                | otherwise   -> [v <> vsep]      -- value= -- note: required for signing.++            _   | Just n <- p -> [n <> vsep]      -- key=+                                                  -- note: this case required for request signing+                | otherwise   -> []++        cat :: [ByteString] -> Builder+        cat []     = mempty+        cat [x]    = Build.byteString x+        cat (x:xs) = Build.byteString x <> ksep <> cat xs++        kdelim = "."+        ksep   = "&"+        vsep   = "="++pair :: ToQuery a => ByteString -> a -> QueryString -> QueryString+pair k v = mappend (QPair k (toQuery v))++infixr 7 =:++(=:) :: ToQuery a => ByteString -> a -> QueryString+k =: v = QPair k (toQuery v)++toQueryList :: (IsList a, ToQuery (Item a))+            => ByteString+            -> a+            -> QueryString+toQueryList k = QPair k . QList . zipWith f [1..] . toList+  where+    f :: ToQuery a => Int -> a -> QueryString+    f n v = toBS n =: toQuery v++class ToQuery a where+    toQuery :: a -> QueryString++    default toQuery :: ToText a => a -> QueryString+    toQuery = toQuery . toText++instance ToQuery QueryString where+    toQuery = id++instance (ToByteString k, ToQuery v) => ToQuery (k, v) where+    toQuery (k, v) = QPair (toBS k) (toQuery v)++instance ToQuery Char where+    toQuery = toQuery . BS8.singleton++instance ToQuery ByteString where+    toQuery "" = QValue Nothing+    toQuery bs = QValue (Just bs)++instance ToQuery Text    where toQuery = toQuery . Text.encodeUtf8+instance ToQuery Int     where toQuery = toQuery . toBS+instance ToQuery Integer where toQuery = toQuery . toBS+instance ToQuery Double  where toQuery = toQuery . toBS+instance ToQuery Natural where toQuery = toQuery . toBS++instance ToQuery a => ToQuery (Maybe a) where+    toQuery (Just x) = toQuery x+    toQuery Nothing  = mempty++instance ToQuery Bool where+    toQuery True  = toQuery ("true"  :: ByteString)+    toQuery False = toQuery ("false" :: ByteString)
+ src/Network/AWS/Data/Sensitive.hs view
@@ -0,0 +1,53 @@+{-# LANGUAGE DeriveDataTypeable         #-}+{-# LANGUAGE DeriveGeneric              #-}+{-# LANGUAGE GeneralizedNewtypeDeriving #-}++-- |+-- Module      : Network.AWS.Data.Sensitive+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.Sensitive where++import           Control.Lens+import           Data.Data                   (Data, Typeable)+import           Data.Monoid+import           Data.String+import           GHC.Generics                (Generic)+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.JSON+import           Network.AWS.Data.Query+import           Network.AWS.Data.Text+import           Network.AWS.Data.XML++import           Prelude++-- | /Note/: read . show /= isomorphic+newtype Sensitive a = Sensitive { desensitise :: a }+    deriving+        ( Eq+        , Ord+        , Read+        , IsString+        , Monoid+        , Data+        , Typeable+        , Generic+        , ToByteString+        , FromText+        , ToText+        , FromXML+        , ToXML+        , ToQuery+        , ToJSON+        , FromJSON+        )++instance Show (Sensitive a) where+    show = const "******"++_Sensitive :: Iso' (Sensitive a) a+_Sensitive = iso desensitise Sensitive
+ src/Network/AWS/Data/Text.hs view
@@ -0,0 +1,138 @@+{-# LANGUAGE DefaultSignatures #-}+{-# LANGUAGE FlexibleInstances #-}+{-# LANGUAGE OverloadedStrings #-}+{-# LANGUAGE PackageImports    #-}++-- |+-- Module      : Network.AWS.Data.Text+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.Text+    ( Text++    -- * Deserialisation+    , FromText (..)+    , fromText+    , fromTextError+    , takeLowerText+    , takeText+    , matchCI++    -- * Serialisation+    , ToText   (..)+    , toTextCI+    , showText+    ) where++import           Control.Applicative+import           Data.Attoparsec.Text              (Parser)+import qualified Data.Attoparsec.Text              as A+import           Data.ByteString                   (ByteString)+import qualified Data.ByteString.Char8             as BS8+import           Data.CaseInsensitive              (CI)+import qualified Data.CaseInsensitive              as CI+import           Data.Int+import           Data.Monoid+import           Data.Scientific+import           Data.Text                         (Text)+import qualified Data.Text                         as Text+import qualified Data.Text.Encoding                as Text+import qualified Data.Text.Lazy                    as LText+import           Data.Text.Lazy.Builder            (Builder)+import qualified Data.Text.Lazy.Builder            as Build+import qualified Data.Text.Lazy.Builder.Int        as Build+import qualified Data.Text.Lazy.Builder.Scientific as Build+import           Network.AWS.Data.Crypto+import           Network.HTTP.Types+import           Numeric+import           Numeric.Natural++-- | Fail parsing with a 'Text' error.+--+-- Constrained to the actual attoparsec monad to avoid+-- exposing 'fail' usage directly.+fromTextError :: Text -> Parser a+fromTextError = fail . Text.unpack++fromText :: FromText a => Text -> Either String a+fromText = A.parseOnly parser++takeLowerText :: Parser Text+takeLowerText = Text.toLower <$> A.takeText++takeText :: Parser Text+takeText = A.takeText++matchCI :: Text -> a -> Parser a+matchCI x y = A.asciiCI x <* A.endOfInput >> return y++class FromText a where+    parser :: Parser a++instance FromText Text where+    parser = A.takeText++instance FromText ByteString where+    parser = Text.encodeUtf8 <$> A.takeText++instance FromText Char where+    parser = A.anyChar <* A.endOfInput++instance FromText Int where+    parser = A.signed A.decimal <* A.endOfInput++instance FromText Integer where+    parser = A.signed A.decimal <* A.endOfInput++instance FromText Scientific where+    parser = A.signed A.scientific <* A.endOfInput++instance FromText Natural where+    parser = A.decimal <* A.endOfInput++instance FromText Double where+    parser = A.signed A.rational <* A.endOfInput++instance FromText Bool where+    parser = matchCI "false" False <|> matchCI "true" True++instance FromText StdMethod where+    parser = do+        bs <- Text.encodeUtf8 <$> A.takeText+        either (fail . BS8.unpack) pure (parseMethod bs)++showText :: ToText a => a -> String+showText = Text.unpack . toText++class ToText a where+    toText :: a -> Text++instance ToText a => ToText (CI a) where+    toText = toText . CI.original++instance ToText Text       where toText = id+instance ToText ByteString where toText = Text.decodeUtf8+instance ToText Char       where toText = Text.singleton+instance ToText String     where toText = Text.pack+instance ToText Int        where toText = shortText . Build.decimal+instance ToText Int64      where toText = shortText . Build.decimal+instance ToText Integer    where toText = shortText . Build.decimal+instance ToText Natural    where toText = shortText . Build.decimal+instance ToText Scientific where toText = shortText . Build.scientificBuilder+instance ToText Double     where toText = toText . ($ "") . showFFloat Nothing+instance ToText StdMethod  where toText = toText . renderStdMethod+instance ToText (Digest a) where toText = toText . digestToBase Base16++instance ToText Bool where+    toText True  = "true"+    toText False = "false"++shortText :: Builder -> Text+shortText = LText.toStrict . Build.toLazyTextWith 32++toTextCI :: ToText a => a -> CI Text+toTextCI = CI.mk . toText
+ src/Network/AWS/Data/Time.hs view
@@ -0,0 +1,193 @@+{-# LANGUAGE DataKinds                  #-}+{-# LANGUAGE DeriveDataTypeable         #-}+{-# LANGUAGE DeriveGeneric              #-}+{-# LANGUAGE FlexibleContexts           #-}+{-# LANGUAGE FlexibleInstances          #-}+{-# LANGUAGE GADTs                      #-}+{-# LANGUAGE GeneralizedNewtypeDeriving #-}+{-# LANGUAGE KindSignatures             #-}+{-# LANGUAGE LambdaCase                 #-}+{-# LANGUAGE OverloadedStrings          #-}+{-# LANGUAGE ScopedTypeVariables        #-}+{-# LANGUAGE StandaloneDeriving         #-}++-- |+-- Module      : Network.AWS.Data.Time+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.Time+    (+    -- * Time+      Format (..)+    , Time   (..)+    , _Time+    -- ** Formats+    , UTCTime+    , RFC822+    , ISO8601+    , BasicTime+    , AWSTime+    , POSIX+    ) where++import           Control.Applicative+import           Control.Lens+import           Data.Aeson+import           Data.Attoparsec.Text        (Parser)+import qualified Data.Attoparsec.Text        as AText+import qualified Data.ByteString.Char8       as BS+import           Data.Data                   (Data, Typeable)+import           Data.Monoid+import           Data.Scientific+import           Data.Tagged+import qualified Data.Text                   as Text+import           Data.Time                   (UTCTime)+import           Data.Time.Clock.POSIX+import           Data.Time.Format            (formatTime)+import           GHC.Generics                (Generic)+import           Network.AWS.Compat.Locale+import           Network.AWS.Compat.Time+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.JSON+import           Network.AWS.Data.Query+import           Network.AWS.Data.Text+import           Network.AWS.Data.XML++import           Prelude++data Format+    = RFC822Format+    | ISO8601Format+    | BasicFormat+    | AWSFormat+    | POSIXFormat+      deriving (Eq, Read, Show, Data, Typeable, Generic)++deriving instance Typeable 'RFC822Format+deriving instance Typeable 'ISO8601Format+deriving instance Typeable 'BasicFormat+deriving instance Typeable 'AWSFormat+deriving instance Typeable 'POSIXFormat++data Time :: Format -> * where+    Time :: UTCTime -> Time a+      deriving (Data, Typeable, Generic)++deriving instance Eq   (Time a)+deriving instance Ord  (Time a)+deriving instance Read (Time a)+deriving instance Show (Time a)++_Time :: Iso' (Time a) UTCTime+_Time = iso (\(Time t) -> t) Time++convert :: Time a -> Time b+convert (Time t) = Time t++type RFC822    = Time 'RFC822Format+type ISO8601   = Time 'ISO8601Format+type BasicTime = Time 'BasicFormat+type AWSTime   = Time 'AWSFormat+type POSIX     = Time 'POSIXFormat++class TimeFormat a where+    format :: Tagged a String++instance TimeFormat RFC822    where format = Tagged "%a, %d %b %Y %H:%M:%S GMT"+instance TimeFormat ISO8601   where format = Tagged (iso8601DateFormat (Just "%X%Q%Z"))+instance TimeFormat BasicTime where format = Tagged "%Y%m%d"+instance TimeFormat AWSTime   where format = Tagged "%Y%m%dT%H%M%SZ"++instance FromText BasicTime where parser = parseFormattedTime+instance FromText AWSTime   where parser = parseFormattedTime++instance FromText RFC822 where+    parser = (convert :: ISO8601 -> RFC822) <$> parseFormattedTime+         <|> parseFormattedTime++instance FromText ISO8601 where+    parser = (convert :: RFC822 -> ISO8601) <$> parseFormattedTime+         <|> parseFormattedTime++instance FromText POSIX where+    parser = Time . posixSecondsToUTCTime . realToFrac+        <$> (parser :: Parser Scientific)++parseFormattedTime :: forall a. TimeFormat (Time a) => Parser (Time a)+parseFormattedTime = do+    x <- Text.unpack <$> AText.takeText+    p (parseTime defaultTimeLocale (untag f) x) x+  where+    p :: Maybe UTCTime -> String -> Parser (Time a)+    p (Just x) _ = return (Time x)+    p Nothing  s = fail $ mconcat+        [ "Failure parsing Date format "+        , untag f+        , " from value: '"+        , s+        , "'"+        ]++    f :: Tagged (Time a) String+    f = format++instance ToText RFC822    where toText = Text.pack . renderFormattedTime+instance ToText ISO8601   where toText = Text.pack . renderFormattedTime+instance ToText BasicTime where toText = Text.pack . renderFormattedTime+instance ToText AWSTime   where toText = Text.pack . renderFormattedTime++instance ToText POSIX where+    toText (Time t) = toText (truncate (utcTimeToPOSIXSeconds t) :: Integer)++renderFormattedTime :: forall a. TimeFormat (Time a) => Time a -> String+renderFormattedTime (Time t) = formatTime defaultTimeLocale (untag f) t+  where+    f :: Tagged (Time a) String+    f = format++instance FromXML RFC822    where parseXML = parseXMLText "RFC822"+instance FromXML ISO8601   where parseXML = parseXMLText "ISO8601"+instance FromXML AWSTime   where parseXML = parseXMLText "AWSTime"+instance FromXML BasicTime where parseXML = parseXMLText "BasicTime"+instance FromXML POSIX     where parseXML = parseXMLText "POSIX"++instance FromJSON RFC822    where parseJSON = parseJSONText "RFC822"+instance FromJSON ISO8601   where parseJSON = parseJSONText "ISO8601"+instance FromJSON AWSTime   where parseJSON = parseJSONText "AWSTime"+instance FromJSON BasicTime where parseJSON = parseJSONText "BasicTime"++instance FromJSON POSIX where+    parseJSON = withScientific "POSIX"+        $ pure+        . Time+        . posixSecondsToUTCTime+        . realToFrac++instance ToByteString RFC822    where toBS = BS.pack . renderFormattedTime+instance ToByteString ISO8601   where toBS = BS.pack . renderFormattedTime+instance ToByteString BasicTime where toBS = BS.pack . renderFormattedTime+instance ToByteString AWSTime   where toBS = BS.pack . renderFormattedTime++instance ToQuery RFC822    where toQuery = toQuery . toBS+instance ToQuery ISO8601   where toQuery = toQuery . toBS+instance ToQuery BasicTime where toQuery = toQuery . toBS+instance ToQuery AWSTime   where toQuery = toQuery . toBS++instance ToXML RFC822    where toXML = toXMLText+instance ToXML ISO8601   where toXML = toXMLText+instance ToXML AWSTime   where toXML = toXMLText+instance ToXML BasicTime where toXML = toXMLText+instance ToXML POSIX     where toXML = toXMLText++instance ToJSON RFC822    where toJSON = toJSONText+instance ToJSON ISO8601   where toJSON = toJSONText+instance ToJSON AWSTime   where toJSON = toJSONText+instance ToJSON BasicTime where toJSON = toJSONText++instance ToJSON POSIX where+    toJSON (Time t) = Number $+        scientific (truncate (utcTimeToPOSIXSeconds t) :: Integer) 0
+ src/Network/AWS/Data/XML.hs view
@@ -0,0 +1,213 @@+{-# LANGUAGE DefaultSignatures   #-}+{-# LANGUAGE FlexibleContexts    #-}+{-# LANGUAGE FlexibleInstances   #-}+{-# LANGUAGE LambdaCase          #-}+{-# LANGUAGE OverloadedStrings   #-}+{-# LANGUAGE ScopedTypeVariables #-}++-- |+-- Module      : Network.AWS.Data.XML+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Data.XML where++import           Control.Applicative+import           Control.Monad+import           Data.Bifunctor+import qualified Data.ByteString.Lazy        as LBS+import           Data.Conduit+import           Data.Conduit.Lazy           (lazyConsume)+import qualified Data.Conduit.List           as Conduit+import           Data.Maybe+import           Data.Monoid+import           Data.Traversable            (traverse)+import           Data.XML.Types              (Event (..))+import           GHC.Exts+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Text+import           Numeric.Natural+import           System.IO.Unsafe            (unsafePerformIO)+import           Text.XML+import qualified Text.XML.Stream.Render      as Stream+import           Text.XML.Unresolved         (toEvents)++import           Prelude++infixl 7 .@, .@?++(.@) :: FromXML a => [Node] -> Text -> Either String a+ns .@ n = findElement n ns >>= parseXML++(.@?) :: FromXML a => [Node] -> Text -> Either String (Maybe a)+ns .@? n =+    case findElement n ns of+        Left _   -> Right Nothing+        Right xs -> parseXML xs++infixr 7 @=++(@=) :: ToXML a => Name -> a -> XML+n @= x =+    case toXML x of+        XNull -> XNull+        xs    -> XOne . NodeElement $ mkElement n xs++decodeXML :: FromXML a => LazyByteString -> Either String a+decodeXML = either failure success . parseLBS def+  where+    failure = Left  . show+    success = parseXML . elementNodes . documentRoot++-- The following is taken from xml-conduit.Text.XML which uses+-- unsafePerformIO anyway, with the following caveat:+--   'not generally safe, but we know that runResourceT+--    will not deallocate any of the resources being used+--    by the process.'+encodeXML :: ToElement a => a -> LazyByteString+encodeXML x = LBS.fromChunks . unsafePerformIO . lazyConsume+     $  Conduit.sourceList (toEvents doc)+    =$= Conduit.map rename+    =$= Stream.renderBytes def+  where+    doc = toXMLDocument $ Document+        { documentRoot     = root+        , documentEpilogue = []+        , documentPrologue =+            Prologue+                { prologueBefore  = []+                , prologueDoctype = Nothing+                , prologueAfter   = []+                }+        }++    rename = \case+        EventBeginElement n xs -> EventBeginElement (f n) (map (first f) xs)+        EventEndElement   n    -> EventEndElement   (f n)+        evt                    -> evt+      where+        f n | isNothing (nameNamespace n) = n { nameNamespace = ns }+            | otherwise                   = n++    ns   = nameNamespace (elementName root)+    root = toElement x++class FromXML a where+    parseXML :: [Node] -> Either String a++instance FromXML [Node] where+    parseXML = pure++instance FromXML a => FromXML (Maybe a) where+    parseXML [] = pure Nothing+    parseXML ns = Just <$> parseXML ns++instance FromXML Text where+    parseXML = fmap (fromMaybe mempty) . withContent "Text"++instance FromXML Char       where parseXML = parseXMLText "Char"+instance FromXML ByteString where parseXML = parseXMLText "ByteString"+instance FromXML Int        where parseXML = parseXMLText "Int"+instance FromXML Integer    where parseXML = parseXMLText "Integer"+instance FromXML Natural    where parseXML = parseXMLText "Natural"+instance FromXML Double     where parseXML = parseXMLText "Double"+instance FromXML Bool       where parseXML = parseXMLText "Bool"++class ToElement a where+    toElement :: a -> Element++instance ToElement Element where+    toElement = id++-- | Provides a way to make the operators for ToXML instance+-- declaration be consistent WRT to single nodes or lists of nodes.+data XML+    = XNull+    | XOne  Node+    | XMany [Node]+      deriving (Show)++instance Monoid XML where+    mempty              = XNull+    mappend XNull XNull = XNull+    mappend a     b     = XMany (listXMLNodes a <> listXMLNodes b)++listXMLNodes :: XML -> [Node]+listXMLNodes = \case+    XNull    -> []+    XOne  n  -> [n]+    XMany ns -> ns++class ToXML a where+    toXML :: a -> XML++toXMLNodes :: ToXML a => a -> [Node]+toXMLNodes = listXMLNodes . toXML++instance ToXML XML where+    toXML = id++instance ToXML a => ToXML (Maybe a) where+    toXML (Just x) = toXML x+    toXML Nothing  = XNull++instance ToXML Text       where toXML = toXMLText+instance ToXML ByteString where toXML = toXMLText+instance ToXML Int        where toXML = toXMLText+instance ToXML Integer    where toXML = toXMLText+instance ToXML Natural    where toXML = toXMLText+instance ToXML Double     where toXML = toXMLText+instance ToXML Bool       where toXML = toXMLText++parseXMLList :: FromXML a+             => Text+             -> [Node]+             -> Either String [a]+parseXMLList n = traverse parseXML . mapMaybe (childNodesOf n)++parseXMLText :: FromText a => String -> [Node] -> Either String a+parseXMLText n = withContent n >=>+    maybe (Left $ "empty node list, when expecting single node " ++ n)+        fromText++toXMLList :: (IsList a, ToXML (Item a)) => Name -> a -> XML+toXMLList n = XMany . map (NodeElement . mkElement n) . toList++toXMLText :: ToText a => a -> XML+toXMLText = XOne . NodeContent . toText++mkElement :: ToXML a => Name -> a -> Element+mkElement n = Element n mempty . listXMLNodes . toXML++withContent :: String -> [Node] -> Either String (Maybe Text)+withContent k = \case+    []              -> Right Nothing+    [NodeContent x] -> Right (Just x)+    _               -> Left $ "encountered many nodes, when expecting text: " ++ k++withElement :: Text -> ([Node] -> Either String a) -> [Node] -> Either String a+withElement n f = findElement n >=> f++findElement :: Text -> [Node] -> Either String [Node]+findElement n ns =+    maybe (Left missing) Right . listToMaybe $ mapMaybe (childNodesOf n) ns+  where+    missing = "unable to find element "+        ++ show n+        ++ " in nodes "+        ++ show (mapMaybe localName ns)++childNodesOf :: Text -> Node -> Maybe [Node]+childNodesOf n x = case x of+    NodeElement e+        | Just n' <- localName x+        , n == n' -> Just (elementNodes e)+    _             -> Nothing++localName :: Node -> Maybe Text+localName = \case+    NodeElement e -> Just (nameLocalName (elementName e))+    _             -> Nothing
+ src/Network/AWS/Endpoint.hs view
@@ -0,0 +1,95 @@+{-# LANGUAGE LambdaCase        #-}+{-# LANGUAGE OverloadedStrings #-}+{-# LANGUAGE RecordWildCards   #-}++-- |+-- Module      : Network.AWS.Types+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Endpoint where++import qualified Data.CaseInsensitive        as CI+import qualified Data.HashSet                as Set+import           Data.Monoid+import           Network.AWS.Data.ByteString+import           Network.AWS.Types++import           Prelude++-- | Determine the full host address and credential scope for a 'Service'+-- within the specified 'Region'.+defaultEndpoint :: Service s -> Region -> Endpoint+defaultEndpoint Service{..} r = go (CI.mk _svcPrefix)+  where+    go = \case+        "iam"+            | china     -> region "iam.cn-north-1.amazonaws.com.cn"+            | govcloud  -> region "iam.us-gov.amazonaws.com"+            | otherwise -> global "iam.amazonaws.com"++        "sdb"+            | virginia  -> region "sdb.amazonaws.com"++        "sts"+            | china     -> region "sts.cn-north-1.amazonaws.com.cn"+            | govcloud  -> region ("sts." <> reg <> ".amazonaws.com")+            | otherwise -> global "sts.amazonaws.com"++        "s3"+            | virginia  -> global "s3.amazonaws.com"+            | china     -> region ("s3." <> reg <> ".amazonaws.com.cn")+            | s3        -> region ("s3-" <> reg <> ".amazonaws.com")++        "rds"+            | virginia  -> global "rds.amazonaws.com"++        "route53"+            | not china -> global "route53.amazonaws.com"++        "emr"+            | virginia  -> global "elasticmapreduce.us-east-1.amazonaws.com"+            | china     -> region "elasticmapreduce.cn-north-1.amazonaws.com.cn"+            | frankfurt -> region "elasticmapreduce.eu-central-1.amazonaws.com"+            | otherwise -> region (reg <> ".elasticmapreduce.amazonaws.com")++        "sqs"+            | virginia  -> global "queue.amazonaws.com"+            | china     -> region (reg <> ".queue.amazonaws.com.cn")++        "importexport"+            | not china -> region "importexport.amazonaws.com"++        "cloudfront"+            | not china -> global "cloudfront.amazonaws.com"++        _   | china     -> region (_svcPrefix <> "." <> reg <> ".amazonaws.com.cn")+            | otherwise -> region (_svcPrefix <> "." <> reg <> ".amazonaws.com")++    virginia  = r == NorthVirginia+    frankfurt = r == Frankfurt+    china     = r == Beijing+    govcloud  = r == GovCloud || r == GovCloudFIPS++    s3 = r `Set.member` except++    region h = Endpoint { _endpointHost = h, _endpointScope = reg }+    global h = Endpoint { _endpointHost = h, _endpointScope = "us-east-1" }++    reg = toBS r++    except = Set.fromList+        [ GovCloud+        , GovCloudFIPS+        , Ireland+        , NorthCalifornia+        , NorthVirginia+        , Oregon+        , SaoPaulo+        , Singapore+        , Sydney+        , Tokyo+        ]
src/Network/AWS/Error.hs view
@@ -1,167 +1,137 @@-{-# LANGUAGE DeriveGeneric              #-}-{-# LANGUAGE FlexibleContexts           #-}-{-# LANGUAGE GeneralizedNewtypeDeriving #-}-{-# LANGUAGE LambdaCase                 #-}-{-# LANGUAGE OverloadedStrings          #-}-{-# LANGUAGE RecordWildCards            #-}-{-# LANGUAGE TemplateHaskell            #-}-{-# LANGUAGE TypeFamilies               #-}-{-# LANGUAGE ViewPatterns               #-}+{-# LANGUAGE LambdaCase        #-}+{-# LANGUAGE OverloadedStrings #-}+{-# LANGUAGE ViewPatterns      #-} +-- | -- Module      : Network.AWS.Error--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0. -- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental+-- Stability   : provisional -- Portability : non-portable (GHC extensions)--module Network.AWS.Error-    (-    -- * Status Checks-      statusSuccess--    -- * Classes-    , AWSError     (..)-    , AWSErrorCode (..)--    -- * Types-    , ErrorCode    (..)-    , ErrorType    (..)-    , ServiceError (..)--    -- * REST Errors-    , RESTError-    , restRequestId-    , restType-    , restCode-    , restMessage-    , restError--    -- * JSON Errors-    , JSONError-    , jsonType-    , jsonCode-    , jsonMessage-    , jsonError-    ) where+--+module Network.AWS.Error where  import           Control.Applicative import           Control.Lens+import           Control.Monad import           Data.Aeson-import qualified Data.ByteString.Lazy       as LBS-import           Data.ByteString.Lazy.Char8 (unpack)-import           Data.String-import           Data.Text                  (Text)-import           GHC.Generics-import           Network.AWS.Data+import           Data.Aeson.Types            (parseEither)+import qualified Data.ByteString.Lazy        as LBS+import           Data.Maybe+import           Data.Monoid+import qualified Data.Text                   as Text+import qualified Data.Text.Encoding          as Text+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Headers+import           Network.AWS.Data.XML import           Network.AWS.Types-import           Network.HTTP.Types+import           Network.HTTP.Client+import           Network.HTTP.Types.Status   (Status (..))  statusSuccess :: Status -> Bool-statusSuccess (statusCode -> n) = n >= 200 && n < 400--class AWSError a where-    awsError :: a -> ServiceError String--instance Show a => AWSError (ServiceError a) where-    awsError = \case-        HttpError       e     -> HttpError e-        SerializerError a e   -> SerializerError a e-        ServiceError    a s x -> ServiceError a s (show x)-        Errors          xs    -> Errors (map awsError xs)+statusSuccess (statusCode -> n) = n >= 200 && n < 300 -newtype ErrorCode = ErrorCode Text-    deriving (Eq, Ord, Show, FromXML, FromJSON, IsString, Generic)+httpStatus :: AsError a => Getting (First Status) a Status+httpStatus = _Error . f+  where+    f g = \case+        TransportError (StatusCodeException s h c)+            -> TransportError <$> (StatusCodeException <$> g s <*> pure h <*> pure c)+        TransportError e+            -> pure (TransportError e)+        SerializeError (SerializeError' a s e)+            -> g s <&> \x -> SerializeError (SerializeError' a x e)+        ServiceError e+            -> g (_serviceStatus e) <&> \x -> ServiceError (e { _serviceStatus = x }) -class AWSErrorCode a where-    awsErrorCode :: a -> Maybe ErrorCode+hasStatus :: (Applicative f, Choice p)+          => Int+          -> Optic' p f ServiceError ServiceError+hasStatus n = filtered ((n ==) . fromEnum . _serviceStatus) -data ErrorType-    = Receiver-    | Sender-      deriving (Eq, Ord, Enum, Show, Generic)+hasCode :: (Applicative f, Choice p)+        => ErrorCode+        -> Optic' p f ServiceError ServiceError+hasCode c = filtered ((c ==) . _serviceCode) -instance FromText ErrorType where-    parser = takeLowerText >>= \case-        "receiver" -> pure Receiver-        "sender"   -> pure Sender-        e          -> fail $ "Failure parsing ErrorType from " ++ show e+serviceError :: Abbrev+             -> Status+             -> [Header]+             -> Maybe ErrorCode+             -> Maybe ErrorMessage+             -> Maybe RequestId+             -> ServiceError+serviceError a s h c m r =+    ServiceError' a s h (fromMaybe (getErrorCode s h) c) m (r <|> getRequestId h) -instance FromXML ErrorType where-    parseXML = parseXMLText "Type"+getRequestId :: [Header] -> Maybe RequestId+getRequestId h =+    either (const Nothing) Just (h .# hAMZRequestId <|> h .# hAMZNRequestId) -data RESTError = RESTError-    { _restRequestId :: Text-    , _restType      :: Maybe ErrorType-    , _restCode      :: Maybe ErrorCode-    , _restMessage   :: Text-    } deriving (Eq, Show, Generic)+getErrorCode :: Status -> [Header] -> ErrorCode+getErrorCode s h =+    fromMaybe (ErrorCode . Text.decodeUtf8 $ statusMessage s) $+        case h .# hAMZNErrorType of+            Left  _ -> Nothing+            Right t -> fmap ErrorCode . lastOf traverse $ Text.split (== '#') t -makeLenses ''RESTError+parseJSONError :: Abbrev+               -> Status+               -> [Header]+               -> LazyByteString+               -> Error+parseJSONError a s h bs = decodeError a s h bs (parse bs)+  where+    parse = eitherDecode' >=> parseEither (withObject "JSONError" go) -instance AWSErrorCode RESTError where-    awsErrorCode = _restCode+    go o = do+        c <- (Just <$> o .: "__type") <|> o .:? "code"+        m <- msg c o+        return $! serviceError a s h c m Nothing -instance FromXML RESTError where-    parseXML x = withElement "Error" f x <|> f x-      where-        f y = RESTError-            <$> x .@  "RequestId"-            <*> y .@? "Type"-            <*> y .@? "Code"-            <*> y .@  "Message"+    msg c o =+        if c == Just "RequestEntityTooLarge"+            then pure (Just "Request body must be less than 1 MB")+            else Just <$> o .:  "message"+                      <|> o .:? "Message" -restError :: FromXML (Er a)-          => (Status -> Bool)-          -> Service a-          -> Status-          -> Maybe (LBS.ByteString -> ServiceError (Er a))-restError f Service{..} s-    | f s       = Nothing-    | otherwise = Just go+parseXMLError :: Abbrev+              -> Status+              -> [Header]+              -> LazyByteString+              -> Error+parseXMLError a s h bs = decodeError a s h bs (decodeXML bs >>= go)   where-    go x = either failure success (decodeXML x >>= parseXML)-      where-        failure e = SerializerError _svcAbbrev (e ++ ":\n" ++ unpack x)-        success   = ServiceError _svcAbbrev s--data JSONError = JSONError-    { _jsonType    :: Maybe Text-    , _jsonCode    :: Maybe ErrorCode-    , _jsonMessage :: Text-    } deriving (Eq, Show, Generic)--makeLenses ''JSONError+    go x = do+        (c, m, r) <- xml x <|> ec2 x+        return $! serviceError a s h c m r -instance AWSErrorCode JSONError where-    awsErrorCode = _jsonCode+    xml x = withElement "Error"  (gen x) x <|> gen x x+    ec2 x = withElement "Errors" (gen x) x -instance FromJSON JSONError where-    parseJSON = withObject "JSONError" $ \o -> rest o <|> post o-      where-        rest o = JSONError-             <$> o .:? "Type"-             <*> o .:? "Code"-             <*> o .:  "Message"+    gen x y = (,,)+        <$> y .@? "Code"+        <*> y .@? "Message"+        <*> x .@? "RequestId" -        post o = JSONError-             <$> o .:? "__type"-             <*> o .:? "code"-             <*> o .:  "message"+parseRESTError :: Abbrev+               -> Status+               -> [Header]+               -> a+               -> Error+parseRESTError a s h _ =+    ServiceError (serviceError a s h Nothing Nothing Nothing) -jsonError :: FromJSON (Er a)-          => (Status -> Bool)-          -> Service a-          -> Status-          -> Maybe (LBS.ByteString -> ServiceError (Er a))-jsonError f Service{..} s-    | f s       = Nothing-    | otherwise = Just go-  where-    go x = either failure success (eitherDecode' x)-      where-        failure e = SerializerError _svcAbbrev (e ++ ":\n" ++ unpack x)-        success   = ServiceError _svcAbbrev s+decodeError :: Abbrev+            -> Status+            -> [Header]+            -> LazyByteString+            -> Either String ServiceError+            -> Error+decodeError a s h bs e+    | LBS.null bs = parseRESTError a s h bs+    | otherwise   =+        either (SerializeError . SerializeError' a s)+               ServiceError+               e
+ src/Network/AWS/Pager.hs view
@@ -0,0 +1,63 @@+{-# LANGUAGE FlexibleInstances #-}+{-# LANGUAGE RankNTypes        #-}++-- |+-- Module      : Network.AWS.Pager+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Pager+    ( AWSPager     (..)+    , AWSTruncated (..)+    , stop+    , choice+    ) where++import           Control.Applicative+import           Control.Lens          hiding (index)+import           Data.HashMap.Strict   (HashMap)+import qualified Data.HashMap.Strict   as Map+import           Data.Text             (Text)+import           Network.AWS.Data.Text (ToText (..))+import           Network.AWS.Types++import           Prelude++-- | Specify how an 'AWSRequest' and it's associated 'Rs' response can+-- generate a subsequent request, if available.+class AWSRequest a => AWSPager a where+    page :: a -> Rs a -> Maybe a++-- | Generalise IsTruncated and other optional/required+-- response pagination fields.+class AWSTruncated a where+    truncated :: a -> Bool++instance AWSTruncated Bool where+    truncated = id++instance AWSTruncated (Maybe Bool) where+    truncated (Just x) = x+    truncated Nothing  = False++instance AWSTruncated (Maybe Text) where+    truncated (Just _) = True+    truncated Nothing  = False++instance AWSTruncated [a] where+    truncated = not . null++instance AWSTruncated (HashMap k v) where+    truncated = not . Map.null++stop :: AWSTruncated a => a -> Bool+stop = not . truncated++choice :: (Alternative f, ToText a, ToText b)+       => (s -> f a)+       -> (s -> f b)+       -> Getter s (f Text)+choice f g = to $ \x -> (toText <$> f x) <|> (toText <$> g x)
− src/Network/AWS/Pagination.hs
@@ -1,64 +0,0 @@-{-# LANGUAGE FlexibleInstances #-}-{-# LANGUAGE RankNTypes        #-}---- Module      : Network.AWS.Pagination--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Pagination-    ( more-    , stop-    , index-    , choice-    ) where--import           Control.Applicative-import           Control.Lens        hiding (index)-import           Data.HashMap.Strict (HashMap)-import qualified Data.HashMap.Strict as Map-import           Data.Text           (Text)-import           Network.AWS.Data    (ToText(..))---- | Generalise IsTruncated and other optional/required--- response pagination fields.-class AWSMore a where-    more :: a -> Bool--instance AWSMore Bool where-    more = id--instance AWSMore (Maybe Bool) where-    more (Just x) = x-    more Nothing  = False--instance AWSMore (Maybe Text) where-    more (Just _) = True-    more Nothing  = False--instance AWSMore [a] where-    more = not . null--instance AWSMore (HashMap k v) where-    more = not . Map.null--stop :: AWSMore a => a -> Bool-stop = not . more--index :: ToText c => Getter a [b] -> Getter b c -> Getter a (Maybe Text)-index f g = f . to lastMay . to (fmap (toText . view g))--choice :: Alternative f => (a -> f b) -> (a -> f b) -> a -> f b-choice f g x = f x <|> g x--lastMay :: [a] -> Maybe a-lastMay []     = Nothing-lastMay (x:xs) = Just (go x xs)-  where-    go y []     = y-    go _ (y:ys) = go y ys
src/Network/AWS/Prelude.hs view
@@ -1,92 +1,57 @@--- Module      : Network.AWS.Prelude.Types+-- |+-- Module      : Network.AWS.Prelude -- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.+-- License     : Mozilla Public License, v. 2.0. -- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental+-- Stability   : provisional -- Portability : non-portable (GHC extensions)-+-- module Network.AWS.Prelude-    (-    -- * Re-exported-      module Export--    -- * Primitives-    , ByteString-    , CI-    , ClientRequest-    , ClientResponse-    , Exception-    , HashMap-    , HttpException-    , Natural-    , NonEmpty     (..)-    , RequestBody-    , Response-    , Text--    -- * Classes-    , AWSPager     (..)-    , AWSRequest   (..)-    , AWSService   (..)-    , Generic-    , IsString     (..)-    , Semigroup--    -- * Retries-    , Retry        (..)--    -- * Errors-    , AWSError     (..)-    , AWSErrorCode (..)-    , ServiceError (..)-    , RESTError-    , restError-    , JSONError-    , jsonError-    , statusSuccess--    -- * Shared-    , Empty        (..)-    , Service      (..)--    -- * HTTP-    , StdMethod    (..)-    , Status       (..)+    ( module Network.AWS.Prelude+    , module Export     ) where -import           Control.Exception         (Exception)-import           Data.ByteString           (ByteString)-import           Data.CaseInsensitive      (CI)-import           Data.HashMap.Strict       (HashMap)-import           Data.List.NonEmpty        (NonEmpty (..))-import           Data.Semigroup            (Semigroup)-import           Data.String               (IsString (..))-import           Data.Text                 (Text)-import           GHC.Generics              (Generic)-import           Network.AWS.Error-import           Network.AWS.Types-import           Network.HTTP.Client       (HttpException, RequestBody)-import           Network.HTTP.Types.Method (StdMethod (..))-import           Network.HTTP.Types.Status (Status (..))-import           Numeric.Natural           (Natural)+import           Control.Applicative         as Export (Applicative, pure,+                                                        (<$>), (<*>), (<|>))+import           Control.Lens                as Export hiding ((.=))+import           Data.Data                   as Export (Data, Typeable)+import           Data.Foldable               as Export (Foldable)+import           Data.Hashable               as Export (Hashable)+import           Data.HashMap.Strict         as Export (HashMap)+import           Data.List.NonEmpty          as Export (NonEmpty (..))+import           Data.Maybe                  as Export+import           Data.Monoid                 as Export (First, mconcat, mempty,+                                                        (<>))+import           GHC.Generics                as Export (Generic)+import           Network.AWS.Data.Base64     as Export+import           Network.AWS.Data.Body       as Export+import           Network.AWS.Data.ByteString as Export+import           Network.AWS.Data.Crypto     as Export hiding (Base (..))+import           Network.AWS.Data.Headers    as Export+import           Network.AWS.Data.JSON       as Export+import           Network.AWS.Data.List1      as Export+import           Network.AWS.Data.Map        as Export+import           Network.AWS.Data.Numeric    as Export+import           Network.AWS.Data.Path       as Export+import           Network.AWS.Data.Query      as Export+import           Network.AWS.Data.Sensitive  as Export+import           Network.AWS.Data.Text       as Export+import           Network.AWS.Data.Time       as Export+import           Network.AWS.Data.XML        as Export+import           Network.AWS.Endpoint        as Export+import           Network.AWS.Error           as Export+import           Network.AWS.Types           as Export hiding (AccessKey,+                                                        Endpoint, Seconds,+                                                        SecretKey)+import           Network.HTTP.Types.Status   as Export (Status (..))+import           Network.HTTP.Types.URI      as Export (urlDecode, urlEncode)+import           Numeric.Natural             as Export (Natural) -import           Control.Applicative       as Export-import           Data.Bifunctor            as Export-import           Data.Coerce               as Export-import           Data.Default.Class        as Export-import           Data.Hashable             as Export-import           Data.Maybe                as Export-import           Data.Monoid               as Export hiding (All, Any, Sum)-import           Data.Tagged               as Export-import           Network.AWS.Data          as Export hiding (Object, Query)-import           Network.AWS.Pagination    as Export-import           Network.AWS.Response      as Export-import           Prelude                   as Export hiding (error, head)+infixl 7 .!@ -import           Control.Lens              as Export (Iso', Lens', Prism', iso,-                                                      lens, mapping, prism, to,-                                                      withIso, (%~), (&), (.~),-                                                      (<>~), (?~), (^.))+(.!@) :: Functor f => f (Maybe a) -> a -> f a+f .!@ x = fromMaybe x <$> f++may :: Applicative f => ([a] -> f b) -> [a] -> f (Maybe b)+may _ [] = pure Nothing+may f xs = Just <$> f xs
+ src/Network/AWS/Request.hs view
@@ -0,0 +1,158 @@+{-# LANGUAGE LambdaCase        #-}+{-# LANGUAGE OverloadedStrings #-}++-- |+-- Module      : Network.AWS.Request+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Request+    (+    -- * Requests+      head'+    , delete+    , get++    -- ** Empty body+    , post+    , put++    -- ** Specialised body+    , postXML+    , postJSON+    , postQuery+    , postBody++    , putXML+    , putJSON+    , putBody++    -- ** Constructors+    , defaultRequest++    -- ** Hashing+    , contentSHA256+    , contentMD5++    -- ** Lenses+    , requestHeaders+    , queryString+    , requestURL+    ) where++import           Control.Lens+import           Data.Maybe+import           Data.Monoid+import           Network.AWS.Data.Body+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Crypto+import           Network.AWS.Data.Headers+import           Network.AWS.Data.JSON+import           Network.AWS.Data.Path+import           Network.AWS.Data.Query+import           Network.AWS.Data.XML+import           Network.AWS.Types+import qualified Network.HTTP.Client.Internal as Client+import           Network.HTTP.Types           (StdMethod (..))+import qualified Network.HTTP.Types           as HTTP++head' :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a+head' x = get x & rqMethod .~ HEAD++delete :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a+delete x = get x & rqMethod .~ DELETE++get :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a+get = contentSHA256 . defaultRequest++post :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a+post x = get x & rqMethod .~ POST++put :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a+put x = get x & rqMethod .~ PUT++postXML :: (ToQuery a, ToPath a, ToHeaders a, ToElement a) => a -> Request a+postXML x = putXML x & rqMethod .~ POST++postJSON :: (ToQuery a, ToPath a, ToHeaders a, ToJSON a) => a -> Request a+postJSON x = putJSON x & rqMethod .~ POST++postQuery :: (ToQuery a, ToPath a, ToHeaders a) => a -> Request a+postQuery x = Request+    { _rqMethod  = POST+    , _rqPath    = rawPath x+    , _rqQuery   = mempty+    , _rqBody    = toBody (toQuery x)+    , _rqHeaders =+        hdr HTTP.hContentType "application/x-www-form-urlencoded; charset=utf-8"+            (toHeaders x)+    } & contentSHA256++postBody :: (ToPath a, ToQuery a, ToHeaders a, ToBody a) => a -> Request a+postBody x = putBody x & rqMethod .~ POST++putXML :: (ToPath a, ToQuery a, ToHeaders a, ToElement a) => a -> Request a+putXML x = defaultRequest x+    & rqMethod .~ PUT+    & rqBody   .~ toBody (toElement x)+    & contentSHA256++putJSON :: (ToQuery a, ToPath a, ToHeaders a, ToJSON a) => a -> Request a+putJSON x = defaultRequest x+    & rqMethod .~ PUT+    & rqBody   .~ toBody (toJSON x)+    & contentSHA256++putBody :: (ToPath a, ToQuery a, ToHeaders a, ToBody a) => a -> Request a+putBody x = defaultRequest x+    & rqMethod .~ PUT+    & rqBody   .~ toBody x+    & contentSHA256++defaultRequest :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a+defaultRequest x = Request+    { _rqMethod  = GET+    , _rqPath    = rawPath x+    , _rqQuery   = toQuery x+    , _rqHeaders = toHeaders x+    , _rqBody    = ""+    }++contentSHA256 :: Request a -> Request a+contentSHA256 rq = rq & rqHeaders %~+    hdr hAMZContentSHA256 (rq ^. rqBody . to (digestToBase Base16 . bodySHA256))++contentMD5 :: Request a -> Request a+contentMD5 rq+    | missing, Just x <- md5 = rq & rqHeaders %~ hdr HTTP.hContentMD5 x+    | otherwise              = rq+  where+    missing = isNothing $ lookup HTTP.hContentMD5 (rq ^. rqHeaders)+    md5     = rq ^. rqBody . to (fmap (digestToBase Base64) . bodyCalculateMD5)++queryString :: Lens' Client.Request ByteString+queryString f x =+    f (Client.queryString x) <&> \y -> x { Client.queryString = y }++requestHeaders :: Lens' Client.Request HTTP.RequestHeaders+requestHeaders f x =+    f (Client.requestHeaders x) <&> \y -> x { Client.requestHeaders = y }++requestURL :: ClientRequest -> ByteString+requestURL x =+       scheme (Client.secure      x)+    <> toBS   (Client.host        x)+    <> port   (Client.port        x)+    <> toBS   (Client.path        x)+    <> toBS   (Client.queryString x)+  where+    scheme True = "https://"+    scheme _    = "http://"++    port = \case+        80  -> ""+        443 -> ""+        n   -> ":" <> toBS n
− src/Network/AWS/Request/Internal.hs
@@ -1,66 +0,0 @@-{-# LANGUAGE OverloadedStrings #-}---- Module      : Network.AWS.Request.Internal--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Request.Internal-    (-    -- * Requests-      defaultRequest--    -- * Lenses-    , method-    , host-    , path-    , queryString-    , requestBody-    , requestHeaders-    ) where--import           Control.Lens-import           Data.ByteString              (ByteString)-import           Data.Default.Class-import qualified Data.Text.Encoding           as Text-import           Network.AWS.Data-import           Network.AWS.Types-import qualified Network.HTTP.Client.Internal as HTTP-import qualified Network.HTTP.Types           as HTTP--defaultRequest :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a-defaultRequest x = def-    & rqPath    .~ Text.encodeUtf8 (toPath x)-    & rqQuery   .~ toQuery x-    & rqHeaders .~ toHeaders x-{-# INLINE defaultRequest #-}--method :: Lens' HTTP.Request HTTP.Method-method f x = f (HTTP.method x) <&> \y -> x { HTTP.method = y }-{-# INLINE method #-}--host :: Lens' HTTP.Request ByteString-host f x = f (HTTP.host x) <&> \y -> x { HTTP.host = y }-{-# INLINE host #-}--path :: Lens' HTTP.Request ByteString-path f x = f (HTTP.path x) <&> \y -> x { HTTP.path = y }-{-# INLINE path #-}--queryString :: Lens' HTTP.Request ByteString-queryString f x = f (HTTP.queryString x) <&> \y -> x { HTTP.queryString = y }-{-# INLINE queryString #-}--requestBody :: Lens' HTTP.Request HTTP.RequestBody-requestBody f x = f (HTTP.requestBody x) <&> \y -> x { HTTP.requestBody = y }-{-# INLINE requestBody #-}--requestHeaders :: Lens' HTTP.Request HTTP.RequestHeaders-requestHeaders f x =-    f (HTTP.requestHeaders x) <&> \y -> x { HTTP.requestHeaders = y }-{-# INLINE requestHeaders #-}
− src/Network/AWS/Request/JSON.hs
@@ -1,46 +0,0 @@-{-# LANGUAGE FlexibleContexts    #-}-{-# LANGUAGE OverloadedStrings   #-}-{-# LANGUAGE ScopedTypeVariables #-}---- Module      : Network.AWS.Request.JSON--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Request.JSON-    ( post-    ) where--import Control.Applicative-import Control.Lens                 hiding (Action)-import Data.Aeson-import Data.Monoid-import Network.AWS.Data-import Network.AWS.Request.Internal-import Network.AWS.Types-import Network.HTTP.Types.Header-import Network.HTTP.Types.Method--post :: forall a. (AWSService (Sv a), ToQuery a, ToPath a, ToHeaders a, ToJSON a)-     => Action-     -> a-     -> Request a-post a x = defaultRequest x-    & rqMethod   .~ POST-    & rqHeaders <>~ hs-    & rqBody     .~ toBody (toJSON x)-  where-    hs = toHeader hAMZTarget   target-      ++ toHeader hContentType content--    target  = (\p -> p <> "." <> toBS a) <$> _svcTargetPrefix svc-    content = ("application/x-amz-json-" <>) <$> _svcJSONVersion svc--    svc :: Service (Sv a)-    svc = service-{-# INLINE post #-}
− src/Network/AWS/Request/Query.hs
@@ -1,38 +0,0 @@-{-# LANGUAGE FlexibleContexts    #-}-{-# LANGUAGE OverloadedStrings   #-}-{-# LANGUAGE ScopedTypeVariables #-}---- Module      : Network.AWS.Request.Query--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Request.Query-    ( post-    ) where--import Control.Lens                 hiding (Action)-import Data.Monoid-import Network.AWS.Data-import Network.AWS.Request.Internal-import Network.AWS.Types-import Network.HTTP.Types.Method--post :: forall a. (AWSService (Sv a), ToQuery a, ToPath a, ToHeaders a)-     => Action-     -> a-     -> Request a-post a x = defaultRequest x & rqMethod .~ POST & rqQuery <>~ qry-  where-    qry = pair "Version" (_svcVersion svc)-        . pair "Action"  (toBS a)-        $ mempty--    svc :: Service (Sv a)-    svc = service-{-# INLINE post #-}
− src/Network/AWS/Request/RestJSON.hs
@@ -1,69 +0,0 @@-{-# LANGUAGE FlexibleContexts    #-}-{-# LANGUAGE OverloadedStrings   #-}-{-# LANGUAGE ScopedTypeVariables #-}---- Module      : Network.AWS.Request.RestJSON--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Request.RestJSON-    ( get-    , delete-    , post-    , put-    , stream-    ) where--import           Control.Applicative-import           Control.Lens                 hiding (Action)-import           Data.Aeson-import           Data.Monoid-import           Network.AWS.Data-import           Network.AWS.Request.Internal-import           Network.AWS.Types-import           Network.HTTP.Types.Header-import           Network.HTTP.Types.Method--get :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a-get = defaultRequest-{-# INLINE get #-}--delete :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a-delete x = get x & rqMethod .~ DELETE-{-# INLINE delete #-}--post :: (AWSService (Sv a), ToQuery a, ToPath a, ToHeaders a, ToJSON a)-     => a-     -> Request a-post x = put x & rqMethod .~ POST-{-# INLINE post #-}--put :: forall a. (AWSService (Sv a), ToQuery a, ToPath a, ToHeaders a, ToJSON a)-    => a-    -> Request a-put x = get x-    & rqMethod   .~ PUT-    & rqHeaders <>~ toHeader hContentType ct-    & rqBody     .~ toBody (toJSON x)-  where-    ct = ("application/x-amz-json-" <>) <$> _svcJSONVersion svc--    svc :: Service (Sv a)-    svc = service-{-# INLINE put #-}--stream :: (AWSService (Sv a), ToPath a, ToQuery a, ToHeaders a, ToBody a)-       => StdMethod-       -> a-       -> Request a-stream m x = content $ get x & rqMethod .~ m & rqBody .~ toBody x-{-# INLINE stream #-}--content :: Request a -> Request a-content rq = rq & rqHeaders %~ hdr hAMZContentSHA256 (bodyHash (rq ^. rqBody))
− src/Network/AWS/Request/RestXML.hs
@@ -1,44 +0,0 @@--- Module      : Network.AWS.Request.RestXML--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Request.RestXML-    ( get-    , head-    , delete-    , post-    , put-    ) where--import Control.Lens-import Network.AWS.Data-import Network.AWS.Request.Internal-import Network.AWS.Types-import Network.HTTP.Types.Method-import Prelude                      hiding (head)--get :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a-get = defaultRequest-{-# INLINE get #-}--delete :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a-delete x = get x & rqMethod .~ DELETE-{-# INLINE delete #-}--head :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a-head x = get x & rqMethod .~ HEAD-{-# INLINE head #-}--post :: (ToPath a, ToQuery a, ToHeaders a, ToXMLRoot a) => a -> Request a-post x = put x & rqMethod .~ POST-{-# INLINE post #-}--put :: (ToPath a, ToQuery a, ToHeaders a, ToXMLRoot a) => a -> Request a-put x = get x & rqMethod .~ PUT & rqBody .~ toBody (encodeXML x)-{-# INLINE put #-}
− src/Network/AWS/Request/S3.hs
@@ -1,55 +0,0 @@--- Module      : Network.AWS.Request.S3--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Request.S3-    ( get-    , head-    , delete-    , post-    , put-    , stream-    ) where--import           Control.Lens-import           Network.AWS.Data-import           Network.AWS.Request.Internal-import           Network.AWS.Types-import           Network.HTTP.Types.Method-import           Prelude                      hiding (head)--get :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a-get = content . defaultRequest-{-# INLINE get #-}--delete :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a-delete x = get x & rqMethod .~ DELETE-{-# INLINE delete #-}--head :: (ToPath a, ToQuery a, ToHeaders a) => a -> Request a-head x = get x & rqMethod .~ HEAD-{-# INLINE head #-}--post :: (ToPath a, ToQuery a, ToHeaders a, ToXMLRoot a) => a -> Request a-post x = put x & rqMethod .~ POST-{-# INLINE post #-}--put :: (ToPath a, ToQuery a, ToHeaders a, ToXMLRoot a) => a -> Request a-put x = content $ get x & rqMethod .~ PUT & rqBody .~ toBody (encodeXML x)-{-# INLINE put #-}--stream :: (ToPath a, ToQuery a, ToHeaders a, ToBody a)-       => StdMethod-       -> a-       -> Request a-stream m x = content $ get x & rqMethod .~ m & rqBody .~ toBody x-{-# INLINE stream #-}--content :: Request a -> Request a-content rq = rq & rqHeaders %~ hdr hAMZContentSHA256 (bodyHash (rq ^. rqBody))
src/Network/AWS/Response.hs view
@@ -1,144 +1,131 @@-{-# LANGUAGE FlexibleContexts    #-}-{-# LANGUAGE OverloadedStrings   #-}-{-# LANGUAGE ScopedTypeVariables #-}-{-# LANGUAGE TupleSections       #-}-{-# LANGUAGE TypeFamilies        #-}+{-# LANGUAGE FlexibleContexts  #-}+{-# LANGUAGE OverloadedStrings #-}+{-# LANGUAGE RecordWildCards   #-}+{-# LANGUAGE TupleSections     #-}+{-# LANGUAGE TypeFamilies      #-} +-- | -- Module      : Network.AWS.Response--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0. -- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental+-- Stability   : provisional -- Portability : non-portable (GHC extensions)--module Network.AWS.Response-    (-    -- * Responses-      nullResponse-    , headerResponse-    , xmlResponse-    , xmlHeaderResponse-    , jsonResponse-    , jsonHeaderResponse-    , bodyResponse-    ) where+--+module Network.AWS.Response where -import           Control.Applicative-import           Control.Monad+import           Control.Monad.Catch import           Control.Monad.IO.Class import           Control.Monad.Trans.Resource import           Data.Aeson-import           Data.Bifunctor-import qualified Data.ByteString.Lazy         as LBS import           Data.Conduit import qualified Data.Conduit.Binary          as Conduit import           Data.Monoid-import           Network.AWS.Data             (FromXML (..), LazyByteString,-                                               build, decodeXML)+import           Data.Text                    (Text)+import           Network.AWS.Data.Body+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Log+import           Network.AWS.Data.XML import           Network.AWS.Types import           Network.HTTP.Client          hiding (Request, Response) import           Network.HTTP.Types import           Text.XML                     (Node) -nullResponse :: (MonadResource m, AWSService (Sv a))-             => Rs a-             -> Logger-             -> Request a-             -> Either HttpException ClientResponse-             -> m (Response' a)-nullResponse rs l = receive l $ \_ _ _ bdy ->-    liftResourceT (bdy $$+- return (Right rs))--headerResponse :: (MonadResource m, AWSService (Sv a))-               => (ResponseHeaders -> Either String (Rs a))-               -> Logger-               -> Request a-               -> Either HttpException ClientResponse-               -> m (Response' a)-headerResponse f = deserialise (const (Right ())) (\hs _ _ -> f hs)+import           Prelude -xmlResponse :: (MonadResource m, AWSService (Sv a), FromXML (Rs a))-            => Logger+receiveNull :: MonadResource m+            => Rs a+            -> Logger+            -> Service s             -> Request a-            -> Either HttpException ClientResponse-            -> m (Response' a)-xmlResponse = deserialise (decodeXML >=> parseXML) (\_ _ -> Right)+            -> ClientResponse+            -> m (Response a)+receiveNull rs _ = receive $ \_ _ x ->+    liftResourceT (x $$+- return (Right rs)) -xmlHeaderResponse :: (MonadResource m, AWSService (Sv a))-                  => (ResponseHeaders -> [Node] -> Either String (Rs a))+receiveEmpty :: MonadResource m+             => (Int -> ResponseHeaders -> () -> Either String (Rs a))+             -> Logger+             -> Service s+             -> Request a+             -> ClientResponse+             -> m (Response a)+receiveEmpty f _ = receive $ \s h x ->+    liftResourceT (x $$+- return (f s h ()))++receiveXMLWrapper :: MonadResource m+                  => Text+                  -> (Int -> ResponseHeaders -> [Node] -> Either String (Rs a))                   -> Logger+                  -> Service s                   -> Request a-                  -> Either HttpException ClientResponse-                  -> m (Response' a)-xmlHeaderResponse f = deserialise decodeXML (\hs _ -> f hs)+                  -> ClientResponse+                  -> m (Response a)+receiveXMLWrapper n f = receiveXML (\s h x -> x .@ n >>= f s h) -jsonResponse :: (MonadResource m, AWSService (Sv a), FromJSON (Rs a))-             => Logger-             -> Request a-             -> Either HttpException ClientResponse-             -> m (Response' a)-jsonResponse = deserialise eitherDecode' (\_ _ -> Right)+receiveXML :: MonadResource m+           => (Int -> ResponseHeaders -> [Node] -> Either String (Rs a))+           -> Logger+           -> Service s+           -> Request a+           -> ClientResponse+           -> m (Response a)+receiveXML = deserialise decodeXML -jsonHeaderResponse :: (MonadResource m, AWSService (Sv a))-                   => (ResponseHeaders -> Int -> Object -> Either String (Rs a))-                   -> Logger-                   -> Request a-                   -> Either HttpException ClientResponse-                   -> m (Response' a)-jsonHeaderResponse = deserialise eitherDecode'+receiveJSON :: MonadResource m+            => (Int -> ResponseHeaders -> Object -> Either String (Rs a))+            -> Logger+            -> Service s+            -> Request a+            -> ClientResponse+            -> m (Response a)+receiveJSON = deserialise eitherDecode' -bodyResponse :: (MonadResource m, AWSService (Sv a))-             => (ResponseHeaders -> Int -> ResponseBody -> Either String (Rs a))-             -> Logger-             -> Request a-             -> Either HttpException ClientResponse-             -> m (Response' a)-bodyResponse f l = receive l $ \a hs s bdy ->-    return (SerializerError a `first` f hs s bdy)+receiveBody :: MonadResource m+            => (Int -> ResponseHeaders -> RsBody -> Either String (Rs a))+            -> Logger+            -> Service s+            -> Request a+            -> ClientResponse+            -> m (Response a)+receiveBody f _ = receive $ \s h x -> return (f s h (RsBody x)) -deserialise :: (AWSService (Sv a), MonadResource m)-            => (LazyByteString  -> Either String b)-            -> (ResponseHeaders -> Int -> b -> Either String (Rs a))+deserialise :: MonadResource m+            => (LazyByteString -> Either String b)+            -> (Int -> ResponseHeaders -> b -> Either String (Rs a))             -> Logger+            -> Service s             -> Request a-            -> Either HttpException ClientResponse-            -> m (Response' a)-deserialise g f l = receive l $ \a hs s bdy -> do-    lbs <- sinkLbs l bdy-    return $! case g lbs of-        Left  e -> Left (SerializerError a e)-        Right o ->-            case f hs s o of-                Left  e -> Left (SerializerError a e)-                Right x -> Right x+            -> ClientResponse+            -> m (Response a)+deserialise g f l = receive $ \s h x -> do+    lbs <- sinkLBS x+    liftIO . l Debug . build $ "[Raw Response Body] {\n" <> lbs <> "\n}"+    return $! g lbs >>= f s h -receive :: forall m a. (MonadResource m, AWSService (Sv a))-        => Logger-        -> (Abbrev -> ResponseHeaders -> Int -> ResponseBody -> m (Response a))+receive :: MonadResource m+        => (Int -> ResponseHeaders -> ResponseBody -> m (Either String (Rs a)))+        -> Service s         -> Request a-        -> Either HttpException ClientResponse-        -> m (Response' a)-receive l f = const (either (return . Left . HttpError) success)+        -> ClientResponse+        -> m (Response a)+receive f Service{..} _ rs+    | not (_svcStatus s) = sinkLBS x >>= serviceErr+    | otherwise          = do+        p <- f (fromEnum s) h x+        either serializeErr+               (return . (s,))+               p   where-    success rs = do-        let s   = responseStatus  rs-            bdy = responseBody    rs-            hs  = responseHeaders rs-        case _svcHandle svc s of-            Just g  -> Left . g <$> sinkLbs l bdy-            Nothing -> do-                x <- f (_svcAbbrev svc) hs (fromEnum s) bdy-                case x of-                    Left  e -> return (Left e)-                    Right y -> return (Right (s, y))+    s = responseStatus  rs+    h = responseHeaders rs+    x = responseBody    rs -    svc = service :: Service (Sv a)+    serviceErr :: MonadThrow m => LazyByteString -> m a+    serviceErr = throwM . _svcError _svcAbbrev s h -sinkLbs :: MonadResource m => Logger -> ResponseBody -> m LBS.ByteString-sinkLbs l bdy = do-    lbs <- liftResourceT (bdy $$+- Conduit.sinkLbs)-    liftIO $ l Trace ("[Client Response Body] {\n" <> build lbs <> "\n}")-    return lbs+    serializeErr :: MonadThrow m => String -> m a+    serializeErr e = throwM (SerializeError (SerializeError' _svcAbbrev s e))++sinkLBS :: MonadResource m => ResponseBody -> m LazyByteString+sinkLBS bdy = liftResourceT (bdy $$+- Conduit.sinkLbs)
+ src/Network/AWS/Sign/V2.hs view
@@ -0,0 +1,98 @@+{-# LANGUAGE FlexibleInstances #-}+{-# LANGUAGE OverloadedStrings #-}+{-# LANGUAGE RecordWildCards   #-}+{-# LANGUAGE TupleSections     #-}+{-# LANGUAGE TypeFamilies      #-}++-- |+-- Module      : Network.AWS.Sign.V2+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Sign.V2+    ( V2+    , Meta (..)+    ) where++import           Control.Applicative+import qualified Data.ByteString.Char8        as BS8+import           Data.List                    (intersperse)+import           Data.Monoid+import           Data.Time+import           Network.AWS.Data.Body+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Crypto+import           Network.AWS.Data.Headers+import           Network.AWS.Data.Log+import           Network.AWS.Data.Path+import           Network.AWS.Data.Query+import           Network.AWS.Data.Time+import           Network.AWS.Types+import qualified Network.HTTP.Client.Internal as Client+import           Network.HTTP.Types           hiding (toQuery)++import           Prelude++data V2++data instance Meta V2 = Meta+    { metaTime      :: !UTCTime+    , metaEndpoint  :: !Endpoint+    , metaSignature :: !ByteString+    }++instance ToLog (Meta V2) where+    build Meta{..} = mconcat $ intersperse "\n"+        [ "[Version 2 Metadata] {"+        , "  time      = " <> build metaTime+        , "  endpoint  = " <> build (_endpointHost metaEndpoint)+        , "  signature = " <> build metaSignature+        , "}"+        ]++instance AWSSigner V2 where+    signed AuthEnv{..} r t Service{..} Request{..} = Signed meta rq+      where+        meta = Meta t end signature++        rq = clientRequest+            { Client.method         = meth+            , Client.host           = _endpointHost+            , Client.path           = path'+            , Client.queryString    = toBS authorised+            , Client.requestHeaders = headers+            , Client.requestBody    = bodyRequest _rqBody+            }++        meth  = toBS _rqMethod+        path' = toBS (escapePath _rqPath)++        end@Endpoint{..} = _svcEndpoint r++        authorised = pair "Signature" (urlEncode True signature) query++        signature = digestToBase Base64+            . hmacSHA256 (toBS _authSecret)+            $ BS8.intercalate "\n"+                [ meth+                , _endpointHost+                , path'+                , toBS query+                ]++        query =+             pair "Version"          _svcVersion+           . pair "SignatureVersion" ("2"          :: ByteString)+           . pair "SignatureMethod"  ("HmacSHA256" :: ByteString)+           . pair "Timestamp"        time+           . pair "AWSAccessKeyId"   (toBS _authAccess)+           $ _rqQuery <> maybe mempty toQuery token++        token = ("SecurityToken" :: ByteString,) . toBS <$> _authToken++        headers = hdr hDate time _rqHeaders++        time = toBS (Time t :: ISO8601)
+ src/Network/AWS/Sign/V4.hs view
@@ -0,0 +1,274 @@+{-# LANGUAGE DataKinds         #-}+{-# LANGUAGE FlexibleInstances #-}+{-# LANGUAGE OverloadedStrings #-}+{-# LANGUAGE PackageImports    #-}+{-# LANGUAGE RankNTypes        #-}+{-# LANGUAGE RecordWildCards   #-}+{-# LANGUAGE TupleSections     #-}+{-# LANGUAGE TypeFamilies      #-}++-- |+-- Module      : Network.AWS.Sign.V4+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Sign.V4+    ( V4+    , Meta (..)+    ) where++import           Control.Applicative+import           Control.Lens+import           Data.Bifunctor+import qualified Data.ByteString.Char8        as BS8+import qualified Data.CaseInsensitive         as CI+import qualified Data.Foldable                as Fold+import           Data.Function                (on)+import           Data.List                    (nubBy, sortBy)+import           Data.Monoid+import           GHC.TypeLits+import           Network.AWS.Data.Body+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Crypto+import           Network.AWS.Data.Headers+import           Network.AWS.Data.Log+import           Network.AWS.Data.Path+import           Network.AWS.Data.Query+import           Network.AWS.Data.Time+import           Network.AWS.Request+import           Network.AWS.Types+import qualified Network.HTTP.Client.Internal as Client+import           Network.HTTP.Types.Header++import           Prelude++data V4++data instance Meta V4 = Meta+    { metaTime             :: !UTCTime+    , metaMethod           :: !Method+    , metaPath             :: !Path+    , metaEndpoint         :: !Endpoint+    , metaCredential       :: !Credential+    , metaCanonicalQuery   :: !CanonicalQuery+    , metaCanonicalRequest :: !CanonicalRequest+    , metaCanonicalHeaders :: !CanonicalHeaders+    , metaSignedHeaders    :: !SignedHeaders+    , metaStringToSign     :: !StringToSign+    , metaSignature        :: !Signature+    , metaHeaders          :: ![Header]+    , metaBody             :: Client.RequestBody+    }++instance ToLog (Meta V4) where+    build Meta{..} = buildLines+        [ "[Version 4 Metadata] {"+        , "  time              = " <> build metaTime+        , "  endpoint          = " <> build (_endpointHost metaEndpoint)+        , "  credential        = " <> build metaCredential+        , "  signed headers    = " <> build metaSignedHeaders+        , "  signature         = " <> build metaSignature+        , "  string to sign    = {"+        , build metaStringToSign+        , "}"+        , "  canonical request = {"+        , build metaCanonicalRequest+        , "  }"+        , "}"+        ]++instance AWSPresigner V4 where+    presigned auth reg ts ex svc rq = finalise meta authorise+      where+        authorise = queryString+            <>~ ("&X-Amz-Signature=" <> toBS (metaSignature meta))++        meta = sign auth reg ts svc presign digest (prepare rq)++        presign c shs =+              pair (CI.original hAMZAlgorithm)     algorithm+            . pair (CI.original hAMZCredential)    (toBS c)+            . pair (CI.original hAMZDate)          (Time ts :: AWSTime)+            . pair (CI.original hAMZExpires)       ex+            . pair (CI.original hAMZSignedHeaders) (toBS shs)+            . pair (CI.original hAMZToken)         (toBS <$> _authToken auth)++        digest = Tag "UNSIGNED-PAYLOAD"++        prepare = rqHeaders .~ []++instance AWSSigner V4 where+    signed auth reg ts svc rq = finalise meta authorise+      where+        authorise = requestHeaders+            <>~ [(hAuthorization, authorisation meta)]++        meta = sign auth reg ts svc presign digest (prepare rq)++        presign _ _ = id++        digest = Tag . digestToBase Base16 . bodySHA256 $ _rqBody rq++        prepare = rqHeaders %~+            ( hdr hHost    (_endpointHost (_svcEndpoint svc reg))+            . hdr hAMZDate (toBS (Time ts :: AWSTime))+            . maybe id (hdr hAMZToken . toBS) (_authToken auth)+            )++-- | Used to tag provenance. This allows keeping the same layout as+-- the signing documentation, passing 'ByteString's everywhere, with+-- some type guarantees.+--+-- Data.Tagged is not used for no reason other than syntactic length and+-- the ToByteString instance.+newtype Tag (s :: Symbol) a = Tag { unTag :: a }++instance ToByteString (Tag s ByteString) where toBS  = unTag+instance ToLog        (Tag s ByteString) where build = build . unTag++instance ToByteString CredentialScope where+    toBS = BS8.intercalate "/" . unTag++type Hash              = Tag "body-digest"        ByteString+type StringToSign      = Tag "string-to-sign"     ByteString+type Credential        = Tag "credential"         ByteString+type CredentialScope   = Tag "credential-scope"   [ByteString]+type CanonicalRequest  = Tag "canonical-request"  ByteString+type CanonicalHeaders  = Tag "canonical-headers"  ByteString+type CanonicalQuery    = Tag "canonical-query"    ByteString+type SignedHeaders     = Tag "signed-headers"     ByteString+type NormalisedHeaders = Tag "normalised-headers" [(ByteString, ByteString)]+type Method            = Tag "method"             ByteString+type Path              = Tag "path"               ByteString+type Signature         = Tag "signature"          ByteString++authorisation :: Meta V4 -> ByteString+authorisation Meta{..} = algorithm+    <> " Credential="     <> toBS metaCredential+    <> ", SignedHeaders=" <> toBS metaSignedHeaders+    <> ", Signature="     <> toBS metaSignature++finalise :: Meta V4 -> (ClientRequest -> ClientRequest) -> Signed V4 a+finalise meta authorise = Signed meta . authorise $ clientRequest+    { Client.method         = toBS (metaMethod meta)+    , Client.host           = _endpointHost (metaEndpoint meta)+    , Client.path           = toBS (metaPath meta)+    , Client.queryString    = '?' `BS8.cons` toBS (metaCanonicalQuery meta)+    , Client.requestHeaders = metaHeaders meta+    , Client.requestBody    = metaBody meta+    }++sign :: AuthEnv+     -> Region+     -> UTCTime+     -> Service s+     -> (Credential -> SignedHeaders -> QueryString -> QueryString)+     -> Hash+     -> Request a+     -> Meta V4+sign auth reg ts svc presign digest rq = Meta+    { metaTime             = ts+    , metaMethod           = method+    , metaPath             = path+    , metaEndpoint         = end+    , metaCredential       = cred+    , metaCanonicalQuery   = query+    , metaCanonicalRequest = crq+    , metaCanonicalHeaders = chs+    , metaSignedHeaders    = shs+    , metaStringToSign     = sts+    , metaSignature        = signature (_authSecret auth) scope sts+    , metaHeaders          = _rqHeaders rq+    , metaBody             = bodyRequest (_rqBody rq)+    }+  where+    query = canonicalQuery . presign cred shs $ _rqQuery rq++    sts   = stringToSign ts scope crq+    cred  = credential (_authAccess auth) scope+    scope = credentialScope svc end ts+    crq   = canonicalRequest method path digest query chs shs++    chs     = canonicalHeaders headers+    shs     = signedHeaders    headers+    headers = normaliseHeaders (_rqHeaders rq)++    end    = _svcEndpoint svc reg+    method = Tag . toBS $ _rqMethod rq+    path   = escapedPath svc rq++algorithm :: ByteString+algorithm = "AWS4-HMAC-SHA256"++signature :: SecretKey -> CredentialScope -> StringToSign -> Signature+signature k c = Tag . digestToBase Base16 . hmacSHA256 signingKey . unTag+  where+    signingKey = Fold.foldl' hmac ("AWS4" <> toBS k) (unTag c)++    hmac x y = digestToBS (hmacSHA256 x y)++stringToSign :: UTCTime -> CredentialScope -> CanonicalRequest -> StringToSign+stringToSign t c r = Tag $ BS8.intercalate "\n"+    [ algorithm+    , toBS (Time t :: AWSTime)+    , toBS c+    , digestToBase Base16 . hashSHA256 $ toBS r+    ]++credential :: AccessKey -> CredentialScope -> Credential+credential k c = Tag (toBS k <> "/" <> toBS c)++credentialScope :: Service s -> Endpoint -> UTCTime -> CredentialScope+credentialScope s e t = Tag+    [ toBS (Time t :: BasicTime)+    , toBS (_endpointScope e)+    , toBS (_svcPrefix     s)+    , "aws4_request"+    ]++canonicalRequest :: Method+                 -> Path+                 -> Hash+                 -> CanonicalQuery+                 -> CanonicalHeaders+                 -> SignedHeaders+                 -> CanonicalRequest+canonicalRequest meth path digest query chs shs = Tag $+   BS8.intercalate "\n"+       [ toBS meth+       , toBS path+       , toBS query+       , toBS chs+       , toBS shs+       , toBS digest+       ]++escapedPath :: Service s -> Request a -> Path+escapedPath s r = Tag . toBS . escapePath $+    case _svcAbbrev s of+        "S3" -> _rqPath r+        _    -> collapsePath (_rqPath r)++canonicalQuery :: QueryString -> CanonicalQuery+canonicalQuery = Tag . toBS++-- FIXME: the following use of stripBS is too naive, should remove+-- all internal whitespace, replacing with a single space char,+-- unless quoted with \"...\"+canonicalHeaders :: NormalisedHeaders -> CanonicalHeaders+canonicalHeaders = Tag . Fold.foldMap (uncurry f) . unTag+  where+    f k v = k <> ":" <> stripBS v <> "\n"++signedHeaders :: NormalisedHeaders -> SignedHeaders+signedHeaders = Tag . BS8.intercalate ";" . map fst . unTag++normaliseHeaders :: [Header] -> NormalisedHeaders+normaliseHeaders = Tag+    . map    (first CI.foldedCase)+    . nubBy  ((==)    `on` fst)+    . sortBy (compare `on` fst)+    . filter ((/= "authorization") . fst)
− src/Network/AWS/Signing.hs
@@ -1,31 +0,0 @@-{-# LANGUAGE ConstraintKinds   #-}-{-# LANGUAGE FlexibleContexts  #-}-{-# LANGUAGE OverloadedStrings #-}-{-# LANGUAGE TypeFamilies      #-}---- Module      : Network.AWS.Signing.Internal--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Signing-    (-    -- * Version 2-      V2--    -- * Version 4-    , V4--    -- * Signing functions-    , sign-    , presign-    ) where--import Network.AWS.Signing.Internal-import Network.AWS.Signing.Internal.V2-import Network.AWS.Signing.Internal.V4
− src/Network/AWS/Signing/Internal.hs
@@ -1,43 +0,0 @@-{-# LANGUAGE ConstraintKinds   #-}-{-# LANGUAGE FlexibleContexts  #-}-{-# LANGUAGE OverloadedStrings #-}-{-# LANGUAGE TypeFamilies      #-}---- Module      : Network.AWS.Signing.Internal--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Signing.Internal where--import           Control.Monad.IO.Class-import qualified Crypto.Hash.SHA256     as SHA256-import qualified Crypto.MAC.HMAC        as HMAC-import           Data.ByteString        (ByteString)-import           Data.Time-import           Network.AWS.Types--sign :: (MonadIO m, AWSRequest a, AWSSigner (Sg (Sv a)))-     => Auth      -- ^ AWS authentication credentials.-     -> Region    -- ^ AWS Region.-     -> Request a -- ^ Request to sign.-     -> UTCTime   -- ^ Signing time.-     -> m (Signed a (Sg (Sv a)))-sign a r rq t = withAuth a $ \e -> return (signed e r rq t)--presign :: (MonadIO m, AWSRequest a, AWSPresigner (Sg (Sv a)))-        => Auth      -- ^ AWS authentication credentials.-        -> Region    -- ^ AWS Region.-        -> Request a -- ^ Request to presign.-        -> UTCTime   -- ^ Signing time.-        -> Integer   -- ^ Expiry time in seconds.-        -> m (Signed a (Sg (Sv a)))-presign a r rq t ex = withAuth a $ \e -> return (presigned e r rq t ex)--hmacSHA256 :: ByteString -> ByteString -> ByteString-hmacSHA256 = HMAC.hmac SHA256.hash 64
− src/Network/AWS/Signing/Internal/V2.hs
@@ -1,95 +0,0 @@-{-# LANGUAGE FlexibleInstances #-}-{-# LANGUAGE OverloadedStrings #-}-{-# LANGUAGE RecordWildCards   #-}-{-# LANGUAGE TupleSections     #-}-{-# LANGUAGE TypeFamilies      #-}---- Module      : Network.AWS.Signaing.Internal.V2--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Signing.Internal.V2-    ( V2-    ) where--import           Control.Applicative-import           Control.Lens-import           Data.ByteString              (ByteString)-import qualified Data.ByteString.Base64       as Base64-import qualified Data.ByteString.Char8        as BS-import           Data.List                    (intersperse)-import           Data.Monoid-import           Data.Time-import           Network.AWS.Data-import           Network.AWS.Request.Internal-import           Network.AWS.Signing.Internal-import           Network.AWS.Types-import           Network.HTTP.Types           hiding (toQuery)--data V2--data instance Meta V2 = Meta-    { _mSignature :: ByteString-    , _mTime      :: UTCTime-    }--instance ToBuilder (Meta V2) where-    build Meta{..} = mconcat $ intersperse "\n"-        [ "[Version 2 Metadata] {"-        , "  signature = " <> build _mSignature-        , "  time      = " <> build _mTime-        , "}"-        ]--instance AWSSigner V2 where-    signed AuthEnv{..} r x@Request{..} t = Signed meta rq-      where-        meta = Meta-            { _mSignature = signature-            , _mTime      = t-            }--        rq = clientRequest-            & method         .~ meth-            & host           .~ _endpointHost-            & path           .~ _rqPath-            & queryString    .~ toBS authorised-            & requestHeaders .~ headers-            & requestBody    .~ _bdyBody _rqBody--        meth = toBS _rqMethod--        Endpoint{..} = endpoint svc r--        authorised = pair "Signature" (urlEncode True signature) query--        signature = Base64.encode-            . hmacSHA256 (toBS _authSecret)-            $ BS.intercalate "\n"-                [ meth-                , _endpointHost-                , _rqPath-                , toBS query-                ]--        query =-             pair "Version"          (_svcVersion svc)-           . pair "SignatureVersion" ("2"          :: ByteString)-           . pair "SignatureMethod"  ("HmacSHA256" :: ByteString)-           . pair "Timestamp"        time-           . pair "AWSAccessKeyId"   (toBS _authAccess)-           $ _rqQuery <> maybe mempty toQuery token--        token = ("SecurityToken" :: ByteString,) . toBS <$> _authToken--        headers = hdr hDate time _rqHeaders--        time = toBS (Time t :: ISO8601)--        svc = serviceOf x
− src/Network/AWS/Signing/Internal/V4.hs
@@ -1,201 +0,0 @@-{-# LANGUAGE FlexibleInstances #-}-{-# LANGUAGE OverloadedStrings #-}-{-# LANGUAGE RecordWildCards   #-}-{-# LANGUAGE TupleSections     #-}-{-# LANGUAGE TypeFamilies      #-}---- Module      : Network.AWS.Signing.Internal.V4--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Signing.Internal.V4-    ( V4-    ) where--import           Control.Applicative-import           Control.Lens-import qualified Crypto.Hash.SHA256           as SHA256-import           Data.ByteString              (ByteString)-import qualified Data.ByteString.Base16       as Base16-import qualified Data.ByteString.Char8        as BS-import qualified Data.CaseInsensitive         as CI-import qualified Data.Foldable                as Fold-import           Data.Function                hiding ((&))-import           Data.List                    (groupBy, intersperse, sortBy, sort)-import           Data.Maybe-import           Data.Monoid-import           Data.Ord-import           Data.Time-import           Network.AWS.Data-import           Network.AWS.Request.Internal-import           Network.AWS.Signing.Internal-import           Network.AWS.Types-import           Network.HTTP.Types.Header--data V4--data instance Meta V4 = Meta-    { _mAlgorithm :: ByteString-    , _mScope     :: ByteString-    , _mSigned    :: ByteString-    , _mCReq      :: ByteString-    , _mSTS       :: ByteString-    , _mSignature :: ByteString-    , _mTime      :: UTCTime-    }--instance ToBuilder (Meta V4) where-    build Meta{..} = mconcat $ intersperse "\n"-        [ "[Version 4 Metadata] {"-        , "  algorithm         = " <> build _mAlgorithm-        , "  credential scope  = " <> build _mScope-        , "  signed headers    = " <> build _mSigned-        , "  canonical request = {"-        , build _mCReq-        , "  }"-        , "  string to sign    = " <> build _mSTS-        , "  signature         = " <> build _mSignature-        , "  time              = " <> build _mTime-        , "}"-        ]--instance AWSPresigner V4 where-    presigned a r rq t ex = out & sgRequest-        . queryString <>~ auth (out ^. sgMeta)-      where-        out = finalise qry hash r service a inp t--        qry cs sh =-              pair (CI.original hAMZAlgorithm)     algorithm-            . pair (CI.original hAMZCredential)    cs-            . pair (CI.original hAMZDate)          (Time t :: AWSTime)-            . pair (CI.original hAMZExpires)       ex-            . pair (CI.original hAMZSignedHeaders) sh-            . pair (CI.original hAMZToken)         (toBS <$> _authToken a)--        inp = rq & rqHeaders .~ []--        auth = mappend "&X-Amz-Signature=" . _mSignature--        hash = "UNSIGNED-PAYLOAD"--instance AWSSigner V4 where-    signed a r rq t = out & sgRequest-        %~ requestHeaders-        %~ hdr hAuthorization (authorisation $ out ^. sgMeta)-      where-        out = finalise (\_ _ -> id) hash r service a inp t--        inp = rq & rqHeaders %~ hdr hAMZDate date . hdrs (maybeToList tok)--        date = toBS (Time t :: AWSTime)-        tok  = (hAMZToken,) . toBS <$> _authToken a-        hash = bodyHash (_rqBody rq)--authorisation :: Meta V4 -> ByteString-authorisation Meta{..} = BS.concat-    [ _mAlgorithm-    , " Credential="-    , _mScope-    , ", SignedHeaders="-    , _mSigned-    , ", Signature="-    , _mSignature-    ]--algorithm :: ByteString-algorithm = "AWS4-HMAC-SHA256"--finalise :: (ByteString -> ByteString -> Query -> Query)-         -> ByteString-         -> Region-         -> Service (Sv a)-         -> AuthEnv-         -> Request a-         -> UTCTime-         -> Signed a V4-finalise qry hash r s@Service{..} AuthEnv{..} Request{..} t =-    Signed meta rq-  where-    meta = Meta-        { _mAlgorithm = algorithm-        , _mCReq      = canonicalRequest-        , _mScope     = accessScope-        , _mSigned    = signedHeaders-        , _mSTS       = stringToSign-        , _mSignature = signature-        , _mTime      = t-        }--    rq = clientRequest-        & method         .~ meth-        & host           .~ _endpointHost-        & path           .~ _rqPath-        & queryString    .~ BS.cons '?' (toBS query)-        & requestHeaders .~ headers-        & requestBody    .~ _bdyBody _rqBody--    meth  = toBS _rqMethod-    query = qry accessScope signedHeaders _rqQuery--    Endpoint{..} = endpoint s r--    canonicalQuery = toBS (query & valuesOf %~ Just . fromMaybe "")--    headers = sortBy (comparing fst) (hdr hHost _endpointHost _rqHeaders)--    joinedHeaders = map f $ groupBy ((==) `on` fst) headers-      where-        f []     = ("", "")-        f (h:hs) = (fst h, g (h : hs))--        g = BS.intercalate "," . sort . map snd--    signedHeaders = mconcat-        . intersperse ";"-        . map (CI.foldedCase . fst)-        $ joinedHeaders--    canonicalHeaders = Fold.foldMap f joinedHeaders-      where-        f (k, v) = CI.foldedCase k-            <> ":"-            <> stripBS v-            <> "\n"--    canonicalRequest = mconcat $ intersperse "\n"-       [ meth-       , collapsePath _rqPath-       , canonicalQuery-       , canonicalHeaders-       , signedHeaders-       , hash-       ]--    scope =-        [ toBS (Time t :: BasicTime)-        , toBS _endpointScope-        , toBS _svcPrefix-        , "aws4_request"-        ]--    credentialScope = BS.intercalate "/" scope--    accessScope = toBS _authAccess <> "/" <> credentialScope--    signingKey = Fold.foldl1 hmacSHA256 $ ("AWS4" <> toBS _authSecret) : scope--    stringToSign = BS.intercalate "\n"-        [ algorithm-        , toBS (Time t :: AWSTime)-        , credentialScope-        , Base16.encode (SHA256.hash canonicalRequest)-        ]--    signature = Base16.encode (hmacSHA256 signingKey stringToSign)
src/Network/AWS/Types.hs view
@@ -1,73 +1,62 @@-{-# LANGUAGE BangPatterns               #-}-{-# LANGUAGE DefaultSignatures          #-} {-# LANGUAGE DeriveDataTypeable         #-} {-# LANGUAGE DeriveGeneric              #-} {-# LANGUAGE FlexibleContexts           #-}-{-# LANGUAGE FlexibleInstances          #-} {-# LANGUAGE GADTs                      #-} {-# LANGUAGE GeneralizedNewtypeDeriving #-} {-# LANGUAGE LambdaCase                 #-} {-# LANGUAGE OverloadedStrings          #-}+{-# LANGUAGE PackageImports             #-}+{-# LANGUAGE RankNTypes                 #-} {-# LANGUAGE RecordWildCards            #-}+{-# LANGUAGE ScopedTypeVariables        #-} {-# LANGUAGE StandaloneDeriving         #-}-{-# LANGUAGE TemplateHaskell            #-}-{-# LANGUAGE TupleSections              #-} {-# LANGUAGE TypeFamilies               #-}+{-# LANGUAGE ViewPatterns               #-} +-- | -- Module      : Network.AWS.Types--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0. -- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental+-- Stability   : provisional -- Portability : non-portable (GHC extensions)-+-- module Network.AWS.Types     (     -- * Authentication     -- ** Credentials-      AccessKey     (..)-    , SecretKey     (..)-    , SecurityToken (..)+      AccessKey       (..)+    , SecretKey       (..)+    , SessionToken    (..)     -- ** Environment-    , AuthEnv       (..)-    , Auth          (..)+    , AuthEnv         (..)+    , Auth            (..)     , withAuth +    -- * Logging+    , LogLevel        (..)+    , Logger+     -- * Services-    , AWSService    (..)     , Abbrev-    , Service       (..)+    , AWSService      (..)+    , Service         (..)     , serviceOf      -- * Retries-    , Retry         (..)--    -- * Endpoints-    , Endpoint      (..)-    , endpoint--    -- * Errors-    , ServiceError  (..)-    , _HttpError-    , _SerializerError-    , _ServiceError-    , _Errors+    , Retry           (..)      -- * Signing-    , AWSSigner     (..)-    , AWSPresigner  (..)-    , Signed        (..)+    , AWSSigner       (..)+    , AWSPresigner    (..)     , Meta+    , Signed          (..)     , sgMeta     , sgRequest      -- * Requests-    , AWSRequest    (..)-    , AWSPager      (..)-    , Request       (..)+    , AWSRequest      (..)+    , Request         (..)     , rqMethod     , rqHeaders     , rqPath@@ -76,338 +65,439 @@      -- * Responses     , Response-    , Response'-    , Empty         (..) -    -- * Logging-    , LogLevel      (..)-    , Logger+    -- * Errors+    , AsError      (..)+    , Error        (..)+    -- ** HTTP Errors+    , HttpException+    -- ** Serialize Errors+    , SerializeError  (..)+    , serializeAbbrev+    , serializeStatus+    , serializeMessage+    -- ** Service Errors+    , ServiceError    (..)+    , serviceAbbrev+    , serviceStatus+    , serviceHeaders+    , serviceCode+    , serviceMessage+    , serviceRequestId+    -- ** Error Types+    , ErrorCode       (..)+    , ErrorMessage    (..)+    , RequestId       (..)      -- * Regions-    , Region        (..)--    -- * Query Actions-    , Action        (..)+    , Endpoint        (..)+    , Region          (..) -    -- * Convenience+    -- * HTTP     , ClientRequest     , ClientResponse     , ResponseBody     , clientRequest++    -- ** Seconds+    , Seconds         (..)+    , _Seconds+    , seconds+    , microseconds++    -- * Isomorphisms+    , _Coerce+    , _Default     ) where +import           Control.Exception+import           Control.Exception.Lens       (exception) import           Control.Applicative import           Control.Concurrent           (ThreadId)-import           Control.Exception            (Exception)-import           Control.Lens                 hiding (Action)+import           Control.Lens                 hiding (coerce) import           Control.Monad.IO.Class import           Control.Monad.Trans.Resource import           Data.Aeson                   hiding (Error)-import           Data.ByteString              (ByteString) import qualified Data.ByteString              as BS import           Data.ByteString.Builder      (Builder)-import qualified Data.CaseInsensitive         as CI+import qualified Data.ByteString.Builder      as Build+import qualified Data.ByteString.Lazy.Char8   as LBS8+import           Data.Coerce import           Data.Conduit-import           Data.Default.Class-import qualified Data.HashSet                 as Set+import           Data.Data                    (Data, Typeable) import           Data.Hashable import           Data.IORef-import           Data.List                    (intersperse) import           Data.Monoid+import           Data.Proxy import           Data.String-import           Data.Text                    (Text) import qualified Data.Text.Encoding           as Text import           Data.Time-import           Data.Typeable-import           GHC.Generics-import           Network.AWS.Data+import           GHC.Generics                 (Generic)+import           Network.AWS.Data.Body+import           Network.AWS.Data.Crypto+import           Network.AWS.Data.Log+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Path+import           Network.AWS.Data.Query+import           Network.AWS.Data.Text+import           Network.AWS.Data.XML+import           Network.HTTP.Client          hiding (Request, Response, Proxy) import qualified Network.HTTP.Client          as Client-import           Network.HTTP.Client          hiding (Request, Response) import           Network.HTTP.Types.Header import           Network.HTTP.Types.Method import           Network.HTTP.Types.Status    (Status)+import           Text.XML                     (def) +import           Prelude++-- | A convenience alias to avoid type ambiguity.+type ClientRequest = Client.Request++-- | A convenience alias encapsulating the common 'Response'.+type ClientResponse = Client.Response ResponseBody++-- | A convenience alias encapsulating the common 'Response' body.+type ResponseBody = ResumableSource (ResourceT IO) ByteString++-- | Construct a 'ClientRequest' using common parameters such as TLS and prevent+-- throwing errors when receiving erroneous status codes in respones.+clientRequest :: ClientRequest+clientRequest = def+    { Client.secure        = True+    , Client.port          = 443+    , Client.redirectCount = 0+    , Client.checkStatus   = \_ _ _ -> Nothing+    }+ -- | Abbreviated service name.-type Abbrev = Text+newtype Abbrev = Abbrev Text+    deriving (Eq, Ord, Show, IsString, FromXML, FromJSON, FromText, ToText, ToLog) --- | An error type representing the subset of errors that can be directly--- attributed to this library.-data ServiceError a-    = HttpError        HttpException-    | SerializerError  Abbrev String-    | ServiceError     Abbrev Status a-    | Errors           [ServiceError a]+newtype ErrorCode = ErrorCode Text+    deriving (Eq, Ord, Show, IsString, FromXML, FromJSON, FromText, ToText, ToLog)++newtype ErrorMessage = ErrorMessage Text+    deriving (Eq, Ord, Show, IsString, FromXML, FromJSON, FromText, ToText, ToLog)++newtype RequestId = RequestId Text+    deriving (Eq, Ord, Show, IsString, FromXML, FromJSON, FromText, ToText, ToLog)++-- | An error type representing errors that can be attributed to this library.+data Error+    = TransportError HttpException+    | SerializeError SerializeError+    | ServiceError   ServiceError       deriving (Show, Typeable) -instance (Show a, Typeable a) => Exception (ServiceError a)+instance Exception Error -instance Monoid (ServiceError a) where-    mempty      = Errors []-    mappend a b = Errors (f a <> f b)-      where-        f (Errors xs) = xs-        f x           = [x]+instance ToLog Error where+    build = \case+        TransportError e -> build e+        SerializeError e -> build e+        ServiceError   e -> build e --- | The properties (such as endpoint) for a service, as well as it's--- associated signing algorithm and error types.-class (AWSSigner (Sg a), Show (Er a)) => AWSService a where-    -- | Signing algorithm supported by the service.-    type Sg a :: *+data SerializeError = SerializeError'+    { _serializeAbbrev  :: !Abbrev+    , _serializeStatus  :: !Status+    , _serializeMessage :: String+    } deriving (Eq, Show, Typeable) -    -- | The general service error.-    type Er a :: *+instance ToLog SerializeError where+    build SerializeError'{..} = buildLines+        [ "[SerializeError] {"+        , "  service = " <> build _serializeAbbrev+        , "  status  = " <> build _serializeStatus+        , "  build = " <> build _serializeMessage+        , "}"+        ] -    service :: Service a+serializeAbbrev :: Lens' SerializeError Abbrev+serializeAbbrev = lens _serializeAbbrev (\s a -> s { _serializeAbbrev = a }) -serviceOf :: AWSService (Sv a) => Request a -> Service (Sv a)-serviceOf = const service+serializeStatus :: Lens' SerializeError Status+serializeStatus = lens _serializeStatus (\s a -> s { _serializeStatus = a }) --- | An alias for the common response 'Either' containing a service error in the--- 'Left' case, or the expected response in the 'Right'.-type Response  a = Either (ServiceError (Er (Sv a))) (Rs a)+serializeMessage :: Lens' SerializeError String+serializeMessage = lens _serializeMessage (\s a -> s { _serializeMessage = a }) -type Response' a = Either (ServiceError (Er (Sv a))) (Status, Rs a)+data ServiceError = ServiceError'+    { _serviceAbbrev    :: !Abbrev+    , _serviceStatus    :: !Status+    , _serviceHeaders   :: [Header]+    , _serviceCode      :: !ErrorCode+    , _serviceMessage   :: Maybe ErrorMessage+    , _serviceRequestId :: Maybe RequestId+    } deriving (Eq, Show, Typeable) +instance ToLog ServiceError where+    build ServiceError'{..} = buildLines+        [ "[ServiceError] {"+        , "  service    = " <> build _serviceAbbrev+        , "  status     = " <> build _serviceStatus+        , "  code       = " <> build _serviceCode+        , "  build    = " <> build _serviceMessage+        , "  request-id = " <> build _serviceRequestId+        , "}"+        ]++serviceAbbrev :: Lens' ServiceError Abbrev+serviceAbbrev = lens _serviceAbbrev (\s a -> s { _serviceAbbrev = a })++serviceStatus :: Lens' ServiceError Status+serviceStatus = lens _serviceStatus (\s a -> s { _serviceStatus = a })++serviceHeaders :: Lens' ServiceError [Header]+serviceHeaders = lens _serviceHeaders (\s a -> s { _serviceHeaders = a })++serviceCode :: Lens' ServiceError ErrorCode+serviceCode = lens _serviceCode (\s a -> s { _serviceCode = a })++serviceMessage :: Lens' ServiceError (Maybe ErrorMessage)+serviceMessage = lens _serviceMessage (\s a -> s { _serviceMessage = a })++serviceRequestId :: Lens' ServiceError (Maybe RequestId)+serviceRequestId = lens _serviceRequestId (\s a -> s { _serviceRequestId = a })++class AsError a where+    -- | A general Amazonka error.+    _Error          :: Prism' a Error+    {-# MINIMAL _Error #-}++    -- | An error occured while communicating over HTTP with a remote service.+    _TransportError :: Prism' a HttpException++    -- | A serialisation error occured when attempting to deserialise a response.+    _SerializeError :: Prism' a SerializeError++    -- | A service specific error returned by the remote service.+    _ServiceError   :: Prism' a ServiceError++    _TransportError = _Error . _TransportError+    _SerializeError = _Error . _SerializeError+    _ServiceError   = _Error . _ServiceError++instance AsError SomeException where+    _Error = exception++instance AsError Error where+    _Error = id++    _TransportError = prism TransportError $ \case+        TransportError e -> Right e+        x                -> Left x++    _SerializeError = prism SerializeError $ \case+        SerializeError e -> Right e+        x                -> Left  x++    _ServiceError = prism ServiceError $ \case+        ServiceError e -> Right e+        x              -> Left  x++data Endpoint = Endpoint+    { _endpointHost  :: ByteString+    , _endpointScope :: ByteString+    } deriving (Eq, Show, Data, Typeable)+ data LogLevel-    = Info  -- ^ Informational messages supplied by the user, not used by the library.-    | Debug -- ^ Info level + debug messages + non-streaming response bodies.-    | Trace -- ^ Debug level + potentially sensitive signing metadata.+    = Error -- ^ Error messages only.+    | Info  -- ^ Info messages supplied by the user - this level is not emitted by the library.+    | Debug -- ^ Useful debug information + info + error levels.+    | Trace -- ^ Includes potentially sensitive signing metadata, and non-streaming response bodies.       deriving (Eq, Ord, Enum, Show) +-- | A function threaded through various request and serialisation routines+-- to log informational and debug messages. type Logger = LogLevel -> Builder -> IO () --- | Specify how a request can be de/serialised.-class (AWSService (Sv a), AWSSigner (Sg (Sv a))) => AWSRequest a where-    -- | The service definition for a request.-    type Sv a :: *+-- | Constants and predicates used to create a 'RetryPolicy'.+data Retry = Exponential+    { _retryBase     :: !Double+    , _retryGrowth   :: !Int+    , _retryAttempts :: !Int+    , _retryCheck    :: ServiceError -> Maybe Text+      -- ^ Returns a descriptive name for logging+      -- if the request should be retried.+    } -    -- | The successful, expected response associated with a request.-    type Rs a :: *+-- | Attributes and functions specific to an AWS service.+data Service s = Service+    { _svcAbbrev   :: !Abbrev+    , _svcPrefix   :: ByteString+    , _svcVersion  :: ByteString+    , _svcEndpoint :: Region -> Endpoint+    , _svcTimeout  :: Maybe Seconds+    , _svcStatus   :: Status -> Bool+    , _svcError    :: Abbrev -> Status -> [Header] -> LazyByteString -> Error+    , _svcRetry    :: Retry+    } -    request  :: a -> Request a-    response :: MonadResource m-             => Logger-             -> Request a-             -> Either HttpException ClientResponse-             -> m (Response' a)+-- | An unsigned request.+data Request a = Request+    { _rqMethod    :: !StdMethod+    , _rqPath      :: !RawPath+    , _rqQuery     :: !QueryString+    , _rqHeaders   :: ![Header]+    , _rqBody      :: !RqBody+    } --- | Specify how an 'AWSRequest' and it's associated 'Rs' response can generate--- a subsequent request, if available.-class AWSRequest a => AWSPager a where-    page :: a -> Rs a -> Maybe a+instance Show (Request a) where+    show = LBS8.unpack . Build.toLazyByteString . build +instance ToLog (Request a) where+    build Request{..} = buildLines+        [ "[Raw Request] {"+        , "  method    = "  <> build _rqMethod+        , "  path      = "  <> build (escapePath _rqPath)+        , "  query     = "  <> build _rqQuery+        , "  headers   = "  <> build _rqHeaders+        , "  body      = {"+        , "    hash    = "  <> build (digestToBase Base16 (bodySHA256 _rqBody))+        , "    payload =\n" <> build (bodyRequest _rqBody)+        , "  }"+        , "}"+        ]++rqBody :: Lens' (Request a) RqBody+rqBody = lens _rqBody (\s a -> s { _rqBody = a })++rqHeaders :: Lens' (Request a) [Header]+rqHeaders = lens _rqHeaders (\s a -> s { _rqHeaders = a })++rqMethod :: Lens' (Request a) StdMethod+rqMethod = lens _rqMethod (\s a -> s { _rqMethod = a })++rqPath :: Lens' (Request a) RawPath+rqPath = lens _rqPath (\s a -> s { _rqPath = a })++rqQuery :: Lens' (Request a) QueryString+rqQuery = lens _rqQuery (\s a -> s { _rqQuery = a })++class AWSSigner v where+    signed :: v ~ Sg s+           => AuthEnv+           -> Region+           -> UTCTime+           -> Service s+           -> Request a+           -> Signed  v a++class AWSPresigner v where+    presigned :: v ~ Sg s+              => AuthEnv+              -> Region+              -> UTCTime+              -> Seconds+              -> Service s+              -> Request a+              -> Signed  v a+ -- | Signing metadata data specific to a signing algorithm. ----- /Note:/ this is used for test and debug purposes, or is otherwise ignored.+-- /Note:/ this is used for logging purposes, and is otherwise ignored. data family Meta v :: *  -- | A signed 'ClientRequest' and associated metadata specific to the signing -- algorithm that was used.-data Signed a v where-    Signed :: ToBuilder (Meta v)+data Signed v a where+    Signed :: ToLog (Meta v)            => { _sgMeta    :: Meta v               , _sgRequest :: ClientRequest               }-           -> Signed a v+           -> Signed v a -sgMeta :: Lens' (Signed a v) (Meta v)+sgMeta :: ToLog (Meta v) => Lens' (Signed v a) (Meta v) sgMeta f (Signed m rq) = f m <&> \y -> Signed y rq -sgRequest :: Lens' (Signed a v) ClientRequest+-- Lens' specifically since 'a' cannot be substituted.+sgRequest :: Lens' (Signed v a) ClientRequest sgRequest f (Signed m rq) = f rq <&> \y -> Signed m y -class AWSSigner v where-    signed :: (AWSService (Sv a), v ~ Sg (Sv a))-           => AuthEnv-           -> Region-           -> Request a-           -> UTCTime-           -> Signed a v+class AWSSigner (Sg a) => AWSService a where+    -- | The default signing algorithm for the service.+    type Sg a :: * -class AWSPresigner v where-    presigned :: (AWSService (Sv a), v ~ Sg (Sv a))-              => AuthEnv-              -> Region-              -> Request a-              -> UTCTime-              -> Integer-              -> Signed a v+    service :: Sv p ~ a => Proxy p -> Service a +serviceOf :: forall a. AWSService (Sv a) => a -> Service (Sv a)+serviceOf = const $ service (Proxy :: Proxy a)++type Response a = (Status, Rs a)++-- | Specify how a request can be de/serialised.+class AWSService (Sv a) => AWSRequest a where+    -- | The successful, expected response associated with a request.+    type Rs a :: *++    -- | The default sevice configuration for the request.+    type Sv a :: *++    request  :: a -> Request a+    response :: MonadResource m+             => Logger+             -> Service s+             -> Request a+             -> ClientResponse+             -> m (Response a)+ -- | Access key credential. newtype AccessKey = AccessKey ByteString-    deriving (Eq, Show, IsString, ToText, ToByteString, ToBuilder)+    deriving (Eq, Show, IsString, ToText, ToByteString, ToLog)  -- | Secret key credential. newtype SecretKey = SecretKey ByteString     deriving (Eq, IsString, ToText, ToByteString) --- | A security token used by STS to temporarily authorise access to+-- | A session token used by STS to temporarily authorise access to -- an AWS resource.-newtype SecurityToken = SecurityToken ByteString+newtype SessionToken = SessionToken ByteString     deriving (Eq, IsString, ToText, ToByteString)  -- | The authorisation environment. data AuthEnv = AuthEnv     { _authAccess :: !AccessKey     , _authSecret :: !SecretKey-    , _authToken  :: Maybe SecurityToken+    , _authToken  :: Maybe SessionToken     , _authExpiry :: Maybe UTCTime     } +instance ToLog AuthEnv where+    build AuthEnv{..} = buildLines+        [ "[Amazonka Auth] {"+        , "  access key     = ****" <> key _authAccess+        , "  secret key     = ****"+        , "  security token = " <> build (const "****" <$> _authToken :: Maybe Builder)+        , "  expiry         = " <> build _authExpiry+        , "}"+        ]+      where+        -- An attempt to preserve sanity when debugging which keys+        -- have been loaded by the auth module.+        key (AccessKey k) = build . BS.reverse . BS.take 6 $ BS.reverse k+ instance FromJSON AuthEnv where     parseJSON = withObject "AuthEnv" $ \o -> AuthEnv         <$> f AccessKey (o .: "AccessKeyId")         <*> f SecretKey (o .: "SecretAccessKey")-        <*> fmap (f SecurityToken) (o .:? "Token")+        <*> fmap (f SessionToken) (o .:? "Token")         <*> o .:? "Expiration"       where         f g = fmap (g . Text.encodeUtf8) -instance ToBuilder AuthEnv where-    build AuthEnv{..} = mconcat $ intersperse "\n"-        [ "[Amazonka Auth] {"-        , "  access key     = " <> build _authAccess-        , "  secret key     = ****"-        , "  security token = " <> maybe "Nothing" (const "Just ****") _authToken-        , "  expiry         = " <> build _authExpiry-        , "}"-        ]- -- | An authorisation environment containing AWS credentials, and potentially -- a reference which can be refreshed out-of-band as temporary credentials expire. data Auth     = Ref  ThreadId (IORef AuthEnv)     | Auth AuthEnv -instance ToBuilder Auth where+instance ToLog Auth where     build (Ref t _) = "[Amazonka Auth] { <thread:" <> build (show t) <> "> }"     build (Auth  e) = build e  withAuth :: MonadIO m => Auth -> (AuthEnv -> m a) -> m a-withAuth (Auth  e) f = f e withAuth (Ref _ r) f = liftIO (readIORef r) >>= f--data Endpoint = Endpoint-    { _endpointHost  :: ByteString-    , _endpointScope :: ByteString-    } deriving (Eq, Show)---- | Determine the full host address and credential scope for a 'Service' within--- the specified 'Region'.-endpoint :: Service a -> Region -> Endpoint-endpoint Service{..} r = go (CI.mk _svcPrefix)-  where-    go = \case-        "iam"-            | china     -> region "iam.cn-north-1.amazonaws.com.cn"-            | govcloud  -> region "iam.us-gov.amazonaws.com"-            | otherwise -> global "iam.amazonaws.com"--        "sdb"-            | virginia  -> region "sdb.amazonaws.com"--        "sts"-            | china     -> region "sts.cn-north-1.amazonaws.com.cn"-            | govcloud  -> region ("sts." <> reg <> ".amazonaws.com")-            | otherwise -> global "sts.amazonaws.com"--        "s3"-            | virginia  -> global "s3.amazonaws.com"-            | china     -> region ("s3." <> reg <> ".amazonaws.com.cn")-            | s3        -> region ("s3-" <> reg <> ".amazonaws.com")--        "rds"-            | virginia  -> global "rds.amazonaws.com"--        "route53"-            | not china -> global "route53.amazonaws.com"--        "emr"-            | virginia  -> global "elasticmapreduce.us-east-1.amazonaws.com"-            | otherwise -> region (reg <> ".elasticmapreduce.amazonaws.com")--        "sqs"-            | virginia  -> global "queue.amazonaws.com"-            | china     -> region (reg <> ".queue.amazonaws.com.cn")--        "importexport"-            | not china -> region "importexport.amazonaws.com"--        "cloudfront"-            | not china -> global "cloudfront.amazonaws.com"--        _   | china     -> region (_svcPrefix <> "." <> reg <> ".amazonaws.com.cn")-            | otherwise -> region (_svcPrefix <> "." <> reg <> ".amazonaws.com")--    virginia = r == NorthVirginia--    s3 = r `Set.member` except--    govcloud = "us-gov" `BS.isPrefixOf` reg-    china    = "cn-"    `BS.isPrefixOf` reg--    region h = Endpoint { _endpointHost = h, _endpointScope = reg }-    global h = Endpoint { _endpointHost = h, _endpointScope = "us-east-1" }--    reg = toBS r--    except = Set.fromList-        [ GovCloud-        , GovCloudFIPS-        , Ireland-        , NorthCalifornia-        , NorthVirginia-        , Oregon-        , SaoPaulo-        , Singapore-        , Sydney-        , Tokyo-        ]---- | Attributes specific to an AWS service.-data Service a = Service-    { _svcAbbrev       :: !Text-    , _svcPrefix       :: !ByteString-    , _svcVersion      :: !ByteString-    , _svcTargetPrefix :: Maybe ByteString-    , _svcJSONVersion  :: Maybe ByteString-    , _svcHandle       :: Status -> Maybe (LazyByteString -> ServiceError (Er a))-    , _svcRetry        :: Retry a-    }---- | Constants and predicates used to create a 'RetryPolicy'.-data Retry a = Exponential-    { _retryBase     :: !Double-    , _retryGrowth   :: !Int-    , _retryAttempts :: !Int-    , _retryCheck    :: Status -> Er a -> Bool-    }---- | An unsigned request.-data Request a = Request-    { _rqMethod  :: !StdMethod-    , _rqPath    :: !ByteString-    , _rqQuery   :: Query-    , _rqHeaders :: [Header]-    , _rqBody    :: RqBody-    }--instance Default (Request a) where-    def = Request GET "/" mempty mempty ""--instance ToBuilder (Request a) where-    build Request{..} = mconcat $ intersperse "\n"-        [ "[Raw Request] {"-        , "  method  = "  <> build _rqMethod-        , "  path    = "  <> build _rqPath-        , "  query   = "  <> build _rqQuery-        , "  headers = "  <> build _rqHeaders-        , "  body    = {"-        , "    hash    = "  <> build (bodyHash _rqBody)-        , "    payload =\n" <> build (_bdyBody _rqBody)-        , "  }"-        , "}"-        ]+withAuth (Auth  e) f = f e  -- | The sum of available AWS regions. data Region@@ -423,13 +513,10 @@     | GovCloud        -- ^ AWS GovCloud / us-gov-west-1     | GovCloudFIPS    -- ^ AWS GovCloud (FIPS 140-2) S3 Only / fips-us-gov-west-1     | SaoPaulo        -- ^ South America / sa-east-1-      deriving (Eq, Ord, Read, Show, Generic)+      deriving (Eq, Ord, Read, Show, Data, Typeable, Generic)  instance Hashable Region -instance Default Region where-    def = NorthVirginia- instance FromText Region where     parser = takeLowerText >>= \case         "eu-west-1"          -> pure Ireland@@ -463,38 +550,52 @@         SaoPaulo        -> "sa-east-1"  instance ToByteString Region-instance ToBuilder    Region +instance ToLog Region where+    build = build . toBS+ instance FromXML Region where parseXML = parseXMLText "Region" instance ToXML   Region where toXML    = toXMLText --- | A service's query action.-newtype Action = Action Text-    deriving (Eq, Ord, Show, IsString, ToText, ToByteString)--data Empty = Empty-    deriving (Eq, Show)+-- | An integral value representing seconds.+newtype Seconds = Seconds Int+    deriving+        ( Eq+        , Ord+        , Read+        , Show+        , Enum+        , Num+        , Bounded+        , Integral+        , Real+        , Data+        , Typeable+        , Generic+        , ToQuery+        , ToByteString+        , ToText+        ) -instance ToJSON Empty where-    toJSON = const Null+_Seconds :: Iso' Seconds Int+_Seconds = iso seconds Seconds --- | A convenience alias to avoid type ambiguity.-type ClientRequest = Client.Request+instance ToLog Seconds where+    build (Seconds n) = build n <> "s" --- | A convenience alias encapsulating the common 'Response'.-type ClientResponse = Client.Response ResponseBody+seconds :: Seconds -> Int+seconds (Seconds n) = n --- | A convenience alias encapsulating the common 'Response' body.-type ResponseBody = ResumableSource (ResourceT IO) ByteString+microseconds :: Seconds -> Int+microseconds (Seconds n) = n * 1000000 --- | Construct a 'ClientRequest' using common parameters such as TLS and prevent--- throwing errors when receiving erroneous status codes in respones.-clientRequest :: ClientRequest-clientRequest = def-    { Client.secure      = True-    , Client.port        = 443-    , Client.checkStatus = \_ _ _ -> Nothing-    }+_Coerce :: (Coercible a b, Coercible b a) => Iso' a b+_Coerce = iso coerce coerce -makePrisms ''ServiceError-makeLenses ''Request+-- | Invalid Iso, should be a Prism but exists for ease of composition+-- with the current 'Lens . Iso' chaining to hide internal types from the user.+_Default :: Monoid a => Iso' (Maybe a) a+_Default = iso f Just+  where+    f (Just x) = x+    f Nothing  = mempty
+ src/Network/AWS/Waiter.hs view
@@ -0,0 +1,94 @@+{-# LANGUAGE FlexibleContexts  #-}+{-# LANGUAGE LambdaCase        #-}+{-# LANGUAGE OverloadedStrings #-}+{-# LANGUAGE RankNTypes        #-}++-- |+-- Module      : Network.AWS.Waiter+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : This Source Code Form is subject to the terms of+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : provisional+-- Portability : non-portable (GHC extensions)+--+module Network.AWS.Waiter+    (+    -- * Types+      Acceptor+    , Accept (..)+    , Wait   (..)++    -- * Acceptors+    , accept++    -- * Matchers+    , matchAll+    , matchAny+    , matchError+    , matchStatus++    -- * Util+    , nonEmpty+    ) where++import           Control.Applicative+import           Control.Lens+import           Data.Maybe+import           Data.Text                   (Text)+import qualified Data.Text                   as Text+import           Network.AWS.Data.ByteString+import           Network.AWS.Data.Log+import           Network.AWS.Error+import           Network.AWS.Types++import           Prelude++type Acceptor a = Request a -> Either Error (Response a) -> Maybe Accept++data Accept+    = AcceptSuccess+    | AcceptFailure+    | AcceptRetry+      deriving (Eq, Show)++instance ToLog Accept where+    build = \case+        AcceptSuccess -> "Success"+        AcceptFailure -> "Failure"+        AcceptRetry   -> "Retry"++-- | Timing and acceptance criteria to check fulfillment of a remote operation.+data Wait a = Wait+    { _waitName      :: ByteString+    , _waitAttempts  :: !Int+    , _waitDelay     :: !Seconds+    , _waitAcceptors :: [Acceptor a]+    }++accept :: Wait a -> Acceptor a+accept w rq rs = listToMaybe . mapMaybe (\f -> f rq rs) $ _waitAcceptors w++matchAll :: Eq b => b -> Accept -> Fold (Rs a) b -> Acceptor a+matchAll x a l = match (allOf l (== x)) a++matchAny :: Eq b => b -> Accept -> Fold (Rs a) b -> Acceptor a+matchAny x a l = match (anyOf l (== x)) a++matchStatus :: Int -> Accept -> Acceptor a+matchStatus x a _ = \case+    Right (s, _) | x == fromEnum s                          -> Just a+    Left  e      | Just x == (fromEnum <$> e ^? httpStatus) -> Just a+    _                                                       -> Nothing++matchError :: ErrorCode -> Accept -> Acceptor a+matchError c a _ = \case+    Left e | Just c == e ^? _ServiceError . serviceCode -> Just a+    _                                                   -> Nothing++match :: (Rs a -> Bool) -> Accept -> Acceptor a+match f a _ = \case+    Right (_, rs) | f rs -> Just a+    _                    -> Nothing++nonEmpty :: Fold a Text -> Fold a Bool+nonEmpty l = l . to Text.null
− src/Network/AWS/Waiters.hs
@@ -1,101 +0,0 @@-{-# LANGUAGE FlexibleContexts  #-}-{-# LANGUAGE LambdaCase        #-}-{-# LANGUAGE OverloadedStrings #-}-{-# LANGUAGE RankNTypes        #-}---- Module      : Network.AWS.Waiters--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Network.AWS.Waiters-    (-    -- * Types-      Acceptor-    , Accept (..)-    , Wait   (..)--    -- * Acceptors-    , accept--    -- * Matchers-    , matchAll-    , matchAny-    , matchError-    , matchStatus--    -- * Util-    , nonEmpty--    -- * Lenses-    , module Control.Lens-    ) where--import           Control.Lens-import           Data.ByteString    (ByteString)-import           Data.Maybe-import           Data.Text          (Text)-import qualified Data.Text          as Text-import           Network.AWS.Data-import           Network.AWS.Error-import           Network.AWS.Types-import           Network.HTTP.Types--type Acceptor a = Request a -> Response' a -> Maybe Accept--data Accept-    = AcceptSuccess-    | AcceptFailure-    | AcceptRetry-      deriving (Eq, Show)--instance ToBuilder Accept where-    build = \case-        AcceptSuccess -> "Success"-        AcceptFailure -> "Failure"-        AcceptRetry   -> "Retry"---- | Timing and acceptance criteria to check fulfillment of a remote operation.-data Wait a = Wait-    { _waitName      :: !ByteString-    , _waitAttempts  :: !Int-    , _waitDelay     :: !Int-    , _waitAcceptors :: [Acceptor a]-    }--accept :: Wait a -> Acceptor a-accept w rq rs = listToMaybe . mapMaybe (\f -> f rq rs) $ _waitAcceptors w--matchAll :: Eq b => b -> Accept -> Fold (Rs a) b -> Acceptor a-matchAll x a l = match (allOf l (== x)) a--matchAny :: Eq b => b -> Accept -> Fold (Rs a) b -> Acceptor a-matchAny x a l = match (anyOf l (== x)) a--matchStatus :: Int -> Accept -> Acceptor a-matchStatus x a _ = \case-    Left (ServiceError _ s _)-        | x == statusCode s -> Just a-    Right (s, _)-        | x == statusCode s -> Just a-    _                       -> Nothing--matchError :: AWSErrorCode (Er (Sv a)) => ErrorCode -> Accept -> Acceptor a-matchError c a _ = \case-    Left (ServiceError _ _ e)-        | Just c == awsErrorCode e -> Just a-    _                              -> Nothing--match :: (Rs a -> Bool) -> Accept -> Acceptor a-match f a _ = \case-    Right (_, rs)-        | f rs -> Just a-    _          -> Nothing--nonEmpty :: Fold a Text -> Fold a Bool-nonEmpty l = l . to Text.null
test/Main.hs view
@@ -1,19 +1,38 @@+{-# LANGUAGE TemplateHaskell #-}++-- | -- Module      : Main--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0. -- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com> -- Stability   : experimental -- Portability : non-portable (GHC extensions)-+-- module Main (main) where -import qualified Test.AWS.Data as Data+import qualified Test.AWS.Data.Base64  as Base64+import qualified Test.AWS.Data.List    as List+import qualified Test.AWS.Data.Maybe   as Maybe+import qualified Test.AWS.Data.Numeric as Numeric+import qualified Test.AWS.Data.Time    as Time+import qualified Test.AWS.Sign.V4      as V4 import           Test.Tasty  main :: IO ()-main = defaultMain $ testGroup "amazonka"-    [ Data.tests-    ]+main = defaultMain $+    testGroup "amazonka-core"+        [ testGroup "primitives"+            [ Numeric.tests+            , Time.tests+            , Base64.tests+            , Maybe.tests+            ]++        , testGroup "collections"+            [ List.tests+            ]++        , testGroup "signing"+            [ V4.tests+            ]+        ]
+ test/Test/AWS/Arbitrary.hs view
@@ -0,0 +1,122 @@+{-# LANGUAGE FlexibleInstances #-}+{-# LANGUAGE OverloadedStrings #-}++{-# OPTIONS_GHC -fno-warn-orphans #-}++-- |+-- Module      : Test.AWS.Arbitrary+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : experimental+-- Portability : non-portable (GHC extensions)+--+module Test.AWS.Arbitrary where++import qualified Data.ByteString.Char8   as BS8+import           Data.CaseInsensitive    (CI, FoldCase)+import qualified Data.CaseInsensitive    as CI+import           Data.String+import qualified Data.Text               as Text+import           Data.Time+import           Network.AWS.Data.Query+import           Network.AWS.Prelude+import           Network.HTTP.Types+import           Test.QuickCheck.Gen     as QC+import qualified Test.QuickCheck.Unicode as Unicode+import           Test.Tasty.QuickCheck++instance Arbitrary (Request ()) where+    arbitrary = Request+        <$> arbitrary+        <*> arbitrary+        <*> arbitrary+        <*> arbitrary+        <*> arbitrary++instance Arbitrary Abbrev where+    arbitrary = fromString <$> QC.elements+        [ "IAM"+        , "SDB"+        , "STS"+        , "S3"+        , "EC2"+        , "RDS"+        , "EMR"+        , "SQS"+        , "SNS"+        , "ImportExport"+        , "CloudFront"+        , "SES"+        , "Route53"+        ]++instance Arbitrary StdMethod where+    arbitrary = QC.elements+        [ GET+        , POST+        , HEAD+        , PUT+        , DELETE+        , TRACE+        , CONNECT+        , OPTIONS+        , PATCH+        ]++instance Arbitrary Region where+    arbitrary = QC.elements+        [ Ireland+        , Frankfurt+        , Tokyo+        , Singapore+        , Sydney+        , Beijing+        , NorthVirginia+        , NorthCalifornia+        , Oregon+        , GovCloud+        , GovCloudFIPS+        , SaoPaulo+        ]++instance Arbitrary RqBody where+    arbitrary = toBody <$> (arbitrary :: Gen ByteString)++instance Arbitrary RawPath where+    arbitrary = do+        xs <- listOf (BS8.pack . getNonEmpty <$> arbitrary)+        return $! rawPath (BS8.intercalate "/" xs)++instance Arbitrary QueryString where+    arbitrary = oneof+        [ QList  <$> arbitrary+        , QPair  <$> arbitrary <*> arbitrary+        , QValue <$> arbitrary+        ]++instance (Arbitrary a, FoldCase a) => Arbitrary (CI a) where+    arbitrary = CI.mk <$> arbitrary++instance Arbitrary Text where+    arbitrary = Text.pack <$> suchThat Unicode.string (not . null)++instance Arbitrary ByteString where+    arbitrary = BS8.pack <$> suchThat Unicode.string (not . null)++instance Arbitrary DiffTime where+    arbitrary = arbitrarySizedFractional+    shrink    = shrinkRealFrac++instance Arbitrary UTCTime where+    arbitrary = UTCTime+        <$> arbitrary+        <*> (fromRational . toRational <$> choose (0 :: Double, 86400))++    shrink u@(UTCTime day dayTime) =+           [ u { utctDay     = d } | d <- shrink day     ]+        ++ [ u { utctDayTime = t } | t <- shrink dayTime ]++instance Arbitrary Day where+    arbitrary = ModifiedJulianDay <$> (2000 +) <$> arbitrary+    shrink    = fmap ModifiedJulianDay . shrink . toModifiedJulianDay
− test/Test/AWS/Data.hs
@@ -1,25 +0,0 @@--- Module      : Test.AWS.Data--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Test.AWS.Data (tests) where--import qualified Test.AWS.Data.List    as List-import qualified Test.AWS.Data.Map     as Map-import qualified Test.AWS.Data.Numeric as Numeric-import qualified Test.AWS.Data.Time    as Time-import           Test.Tasty--tests :: TestTree-tests = testGroup "data types"-    [ List.tests-    , Map.tests-    , Numeric.tests-    , Time.tests-    ]
+ test/Test/AWS/Data/Base64.hs view
@@ -0,0 +1,46 @@+{-# LANGUAGE OverloadedStrings #-}++-- |+-- Module      : Test.AWS.Data.Base64+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : experimental+-- Portability : non-portable (GHC extensions)+--+module Test.AWS.Data.Base64 (tests) where++import           Data.Monoid+import           Data.String+import           Network.AWS.Prelude+import           Network.HTTP.Types+import           Test.AWS.Util+import           Test.Tasty++tests :: TestTree+tests = testGroup "base64"+    [ testGroup "text"+        [ testFromText "deserialise" encoded decoded+        , testToText   "serialise"   encoded decoded+        ]++    , testGroup "query"+        [ testToQuery "serialise" ("x=" <> urlEncode True encoded) decoded+        ]++    , testGroup "xml"+        [ testFromXML "deserialise" encoded decoded+        , testToXML   "serialise"   encoded decoded+        ]++    , testGroup "json"+        [ testFromJSON "deserialise" (str encoded) decoded+        , testToJSON   "serialise"   (str encoded) decoded+        ]+    ]++encoded :: IsString a => a+encoded = "U2VkIHV0IHBlcnNwaWNpYXRpcyB1bmRlIG9tbmlzIGlzdGUgbmF0dXMgZXJyb3Igc2l0IHZvbHVwdGF0ZW0="++decoded :: Base64+decoded = Base64 "Sed ut perspiciatis unde omnis iste natus error sit voluptatem"
test/Test/AWS/Data/List.hs view
@@ -1,99 +1,176 @@-{-# LANGUAGE DataKinds         #-} {-# LANGUAGE OverloadedStrings #-}-{-# LANGUAGE QuasiQuotes       #-} +-- | -- Module      : Test.AWS.Data.List--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0. -- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com> -- Stability   : experimental -- Portability : non-portable (GHC extensions)-+-- module Test.AWS.Data.List (tests) where -import Network.AWS.Prelude-import Test.AWS.TH-import Test.AWS.Types-import Test.Tasty-import Test.Tasty.HUnit+import           Network.AWS.Prelude+import           Test.AWS.Util+import           Test.Tasty  tests :: TestTree tests = testGroup "list"-    [ testGroup "deserialise xml"-        [ testCase "entries" $-            assertXML unflattened (Entries items)-        , testCase "flattened" $-            assertXML flattened items+    [ testGroup "query"+        [ testGroup "serialise"+            [ testGroup "non-flattened"+                [ testToQuery "absent"+                    "x.name=absent"+                    (NonFlat "absent" absent)++                , testToQuery "primitive"+                    "x.itemSet.item.1=1&x.itemSet.item.2=2&x.itemSet.item.3=3&x.name=primitive"+                    (NonFlat "primitive" (Just ([1, 2, 3] :: [Int])))++                , testToQuery "complex"+                    "x.itemSet.item.1.value=1&x.itemSet.item.2.value=2&x.name=complex"+                    (NonFlat "complex" (Just [Item 1, Item 2]))+                ]++            , testGroup "flattened"+                [ testToQuery "absent/empty"+                    "x.name=empty"+                    (Flat "empty" empty)++                , testToQuery "primitive"+                    "x.item.1=4&x.item.2=5&x.item.3=6&x.name=primitive"+                    (Flat "primitive" (Just ([4, 5, 6] :: [Int])))++                , testToQuery "complex"+                    "x.item.1.value=9&x.item.2.value=10&x.name=complex"+                    (Flat "complex" (Just [Item 9, Item 10]))+                ]+            ]         ]-    ] -data Item = Item-    { itemText :: Text-    , itemDate :: Text-    , itemInt  :: Int-    } deriving (Eq, Show)+    , testGroup "xml"+        [ testGroup "deserialise"+            [ testGroup "non-flattened"+                [ testFromXML "absent"+                    "<name>absent</name>"+                    (NonFlat "absent" absent) -instance FromXML Item where-    parseXML x = Item-        <$> x .@ "Text"-        <*> x .@ "Date"-        <*> x .@ "Int"+                , testFromXML "empty"+                    "<name>empty</name><itemSet/>"+                    (NonFlat "empty" absent) -items :: List "Item" Item-items = List-    [ Item-        { itemText = "828ef3fdfa96f00ad9f27c383fc9ac7"-        , itemDate = "2006-01-01T12:00:00.000Z"-        , itemInt  = 5-        }-    , Item-        { itemText = "fe3f123jfa96f00ad9f27c383fc9sd1"-        , itemDate = "2014-11-02T01:20:12"-        , itemInt  = 123-        }+                , testFromXML "primitive"+                    "<name>primitive</name><itemSet><item>1</item><item>2</item><item>3</item></itemSet>"+                    (NonFlat "primitive" (Just ([1, 2, 3] :: [Int])))++                , testFromXML "complex"+                    "<name>complex</name><itemSet><item><value>1</value></item><item><value>2</value></item></itemSet>"+                    (NonFlat "complex" (Just [Item 1, Item 2]))+                ]++            , testGroup "flattened"+                [ testFromXML "absent/empty"+                    "<name>empty</name>"+                    (Flat "empty" empty)++                , testFromXML "primitive"+                    "<name>primitive</name><item>4</item><item>5</item><item>6</item>"+                    (Flat "primitive" (Just ([4, 5, 6] :: [Int])))++                , testFromXML "complex"+                    "<name>complex</name><item><value>9</value></item><item><value>10</value></item>"+                    (Flat "complex" (Just [Item 9, Item 10]))+                ]+            ]++        , testGroup "serialise"+            [ testGroup "non-flattened"+                [ testToXML "absent"+                    "<name>absent</name>"+                    (NonFlat "absent" absent)++                , testToXML "primitive"+                    "<name>primitive</name><itemSet><item>1</item><item>2</item><item>3</item></itemSet>"+                    (NonFlat "primitive" (Just ([1, 2, 3] :: [Int])))++                , testToXML "complex"+                    "<name>complex</name><itemSet><item><value>1</value></item><item><value>2</value></item></itemSet>"+                    (NonFlat "complex" (Just [Item 1, Item 2]))+                ]++            , testGroup "flattened"+                [ testToXML "absent/empty"+                    "<name>empty</name>"+                    (Flat "empty" empty)++                , testToXML "primitive"+                    "<name>primitive</name><item>4</item><item>5</item><item>6</item>"+                    (Flat "primitive" (Just ([4, 5, 6] :: [Int])))++                , testToXML "complex"+                    "<name>complex</name><item><value>9</value></item><item><value>10</value></item>"+                    (Flat "complex" (Just [Item 9, Item 10]))+                ]+            ]+        ]     ] -unflattened :: LazyByteString-unflattened = [doc|-    <?xml version="1.0" encoding="UTF-8"?>-    <Wrapper>-      <Foo>foo</Foo>-      <Bar>N</Bar>-      <Baz>Ned</Baz>-      <Entries>-        <Item>-          <Date>2006-01-01T12:00:00.000Z</Date>-          <Text>828ef3fdfa96f00ad9f27c383fc9ac7</Text>-          <Int>5</Int>-        </Item>-        <Item>-          <Date>2014-11-02T01:20:12</Date>-          <Text>fe3f123jfa96f00ad9f27c383fc9sd1</Text>-          <Int>123</Int>-        </Item>-      </Entries>-    </Wrapper>-    |]+empty :: Maybe [Int]+empty = Just [] -flattened :: LazyByteString-flattened = [doc|-    <?xml version="1.0" encoding="UTF-8"?>-    <Wrapper>-      <Foo>foo</Foo>-      <Bar>N</Bar>-      <Baz>Ned</Baz>-      <Item>-        <Date>2006-01-01T12:00:00.000Z</Date>-        <Text>828ef3fdfa96f00ad9f27c383fc9ac7</Text>-        <Int>5</Int>-      </Item>-      <Item>-        <Date>2014-11-02T01:20:12</Date>-        <Text>fe3f123jfa96f00ad9f27c383fc9sd1</Text>-        <Int>123</Int>-      </Item>-    </Wrapper>-    |]+absent :: Maybe [Int]+absent = Nothing++data NonFlat a = NonFlat Text (Maybe [a])+    deriving (Eq, Show)++instance ToQuery a => ToQuery (NonFlat a) where+    toQuery (NonFlat n x) = mconcat+        [ "name"    =: n+        , "itemSet" =: toQuery (toQueryList "item" <$> x)+        ]++instance FromXML a => FromXML (NonFlat a) where+    parseXML x = NonFlat+         <$>  x .@  "name"+         <*> (x .@? "itemSet"+                .!@ mempty+                >>= may (parseXMLList "item"))++instance ToXML a => ToXML (NonFlat a) where+    toXML (NonFlat n x) = mconcat+        [ "name"    @= n+        , "itemSet" @= toXML (toXMLList "item" <$> x)+        ]++data Flat a = Flat Text (Maybe [a])+    deriving (Eq, Show)++instance ToQuery a => ToQuery (Flat a) where+    toQuery (Flat n x) = mconcat+        [ "name" =: n+        , toQuery (toQueryList "item" <$> x)+        ]++instance FromXML a => FromXML (Flat a) where+    parseXML x = Flat+         <$> x .@  "name"+         <*> may (parseXMLList "item") x++instance ToXML a => ToXML (Flat a) where+    toXML (Flat n x) = mconcat+        [ "name" @= n+        , toXML (toXMLList "item" <$> x)+        ]++newtype Item = Item Int+    deriving (Eq, Show)++instance ToQuery Item where+    toQuery (Item n) = "value" =: n++instance FromXML Item where+    parseXML x = Item <$> x .@ "value"++instance ToXML Item where+    toXML (Item n) = "value" @= n
− test/Test/AWS/Data/Map.hs
@@ -1,84 +0,0 @@-{-# LANGUAGE DataKinds         #-}-{-# LANGUAGE OverloadedStrings #-}-{-# LANGUAGE QuasiQuotes       #-}---- Module      : Test.AWS.Data.Map--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Test.AWS.Data.Map (tests) where--import GHC.Exts-import Network.AWS.Prelude-import Test.AWS.TH-import Test.AWS.Types-import Test.Tasty-import Test.Tasty.HUnit--tests :: TestTree-tests = testGroup "map"-    [ testGroup "deserialise xml"-        [ testCase "entries" $-            assertXML unflattened (Entries entries)-        , testCase "flattened" $-            assertXML flattened entries-        ]-    ]--entries :: EMap "entry" "key" "value" Text Text-entries = fromList-    [ ("foo", "828ef3fdfa96f00ad9f27c383fc9ac7")-    , ("bar", "fe3f123jfa96f00ad9f27c383fc9sd1")-    , ("baz", "e50e9ce187d0a3a62f2ac0a5d89bf0a")-    ]--unflattened :: LazyByteString-unflattened = [doc|-    <?xml version="1.0" encoding="UTF-8"?>-    <Wrapper>-      <Random>N</Random>-      <Entries>-        <entry>-          <key>baz</key>-          <value>e50e9ce187d0a3a62f2ac0a5d89bf0a</value>-        </entry>-        <entry>-          <key>foo</key>-          <value>828ef3fdfa96f00ad9f27c383fc9ac7</value>-        </entry>-        <entry>-          <key>bar</key>-          <value>fe3f123jfa96f00ad9f27c383fc9sd1</value>-        </entry>-      </Entries>-      <Item>test</Item>-    </Wrapper>-    |]--flattened :: LazyByteString-flattened = [doc|-    <?xml version="1.0" encoding="UTF-8"?>-    <Wrapper>-      <Foo>foo</Foo>-      <Bar>N</Bar>-      <entry>-        <key>foo</key>-        <value>828ef3fdfa96f00ad9f27c383fc9ac7</value>-      </entry>-      <entry>-        <key>bar</key>-        <value>fe3f123jfa96f00ad9f27c383fc9sd1</value>-      </entry>-      <entry>-        <key>baz</key>-        <value>e50e9ce187d0a3a62f2ac0a5d89bf0a</value>-      </entry>-      <Baz>Ned</Baz>-    </Wrapper>-    |]
+ test/Test/AWS/Data/Maybe.hs view
@@ -0,0 +1,40 @@+{-# LANGUAGE OverloadedStrings #-}++-- |+-- Module      : Test.AWS.Data.Maybe+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : experimental+-- Portability : non-portable (GHC extensions)+--+module Test.AWS.Data.Maybe (tests) where++import           Network.AWS.Prelude+import           Test.AWS.Util+import           Test.Tasty+import           Test.Tasty.HUnit++tests :: TestTree+tests = testGroup "maybe"+    [ testGroup "xml"+        [ testGroup "serialise"+            [ testCase "nothing" $+                wrapXML "<Key>foo</Key>"+                    @?= encodeXML (X (Item "foo" Nothing))++            , testCase "just" $+                wrapXML "<Key>bar</Key><Num>23</Num>"+                    @?= encodeXML (X (Item "bar" (Just 23)))+            ]+        ]+    ]++data Item = Item Text (Maybe Int)+    deriving (Eq, Show)++instance ToXML Item where+    toXML (Item x y) = mconcat+        [ "Key" @= x+        , "Num" @= y+        ]
test/Test/AWS/Data/Numeric.hs view
@@ -1,103 +1,128 @@-{-# LANGUAGE OverloadedStrings  #-}-{-# LANGUAGE RecordWildCards    #-}+{-# LANGUAGE OverloadedStrings #-}+{-# LANGUAGE RecordWildCards   #-} +-- | -- Module      : Test.AWS.Data.Numeric--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0. -- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com> -- Stability   : experimental -- Portability : non-portable (GHC extensions)-+-- module Test.AWS.Data.Numeric (tests) where -import Data.Aeson-import Network.AWS.Prelude-import Test.Tasty-import Test.Tasty.HUnit+import           Control.Applicative+import           Network.AWS.Prelude+import           Test.AWS.Util+import           Test.Tasty  tests :: TestTree tests = testGroup "numeric"-    [ testGroup "JSON serialization"-        [ testEncode encodeItems-        , testDecode decodeItems-        ]-    ]+    [ testGroup "json"+        [ testGroup "deserialisation"+            [ testFromJSON "natural"+                "123" (Nat 123) --- With a basic record, checks several serialization edge cases--- between String, Int, and Nat values for numbers.-data Item = Item-     { itemNat :: Maybe Nat-     , itemInt :: Maybe Int-     , itemStr :: Maybe String-     } deriving (Eq, Show)+            , testFromJSON "int"+                (toLazyBS maxInt) maxInt -instance ToJSON Item where-    toJSON Item{..} = object-        [ "item_nat" .= itemNat-        , "item_int" .= itemInt-        , "item_str" .= itemStr+            , testFromJSON "negative int"+                (toLazyBS minInt) minInt++            , testFromJSON "integer"+                "891324" (891324 :: Integer)++            , testFromJSON "negative integer"+                "-998" (-998 :: Integer)++            , testFromJSON "double"+                "46.39212" (46.39212 :: Double)++            , testFromJSON "negative double"+                "-1.09231" (-1.09231 :: Double)++            , testFromJSON "numeric text"+                "\"22\"" ("22" :: Text)+            ]++        , testGroup "serialisation"+            [ testToJSON "natural"+                "123" (Nat 123)++            , testToJSON "int"+                (toLazyBS maxInt) maxInt++            , testToJSON "negative int"+                (toLazyBS minInt) minInt++            , testToJSON "integer"+                "891324" (891324 :: Integer)++            , testToJSON "negative integer"+                "-998" (-998 :: Integer)++            , testToJSON "double"+                "46.39212" (46.39212 :: Double)++            , testToJSON "negative double"+                "-1.09231" (-1.09231 :: Double)++            , testToJSON "numeric string"+                "\"22\"" ("22" :: String)+            ]         ] -instance FromJSON Item where-    parseJSON = withObject "Item" $ \o -> Item-        <$> o .:? "item_nat"-        <*> o .:? "item_int"-        <*> o .:? "item_str"+    , testGroup "xml"+        [ testGroup "deserialisation"+            [ testFromXML "natural"+                "123" (Nat 123) -encodeItems :: [(Item, LazyByteString)]-encodeItems =-    [ ( Item (Just $ Nat 1) (Just 1) Nothing-      , "{\"item_str\":null,\"item_nat\":1,\"item_int\":1}"-      )+            , testFromXML "int"+                (toLazyBS maxInt) maxInt -    , ( Item (Just $ Nat 1) (Just 1) (Just "1")-      , "{\"item_str\":\"1\",\"item_nat\":1,\"item_int\":1}"-      )-    ]+            , testFromXML "negative int"+                (toLazyBS minInt) minInt -testEncode :: [(Item, LazyByteString)] -> TestTree-testEncode = testCase "Numeric JSON Encoding"-    . mapM_ (\(input, e) -> e @=? encode input)+            , testFromXML "integer"+                "891324" (891324 :: Integer) -decodeItems :: [(Maybe Item, LazyByteString)]-decodeItems =-    [ ( Just (Item (Just $ Nat 1) (Just 1) Nothing)-      , "{\"item_nat\":1,\"item_int\":1}"-      )+            , testFromXML "negative integer"+                "-998" (-998 :: Integer) -    , ( Just (Item (Just $ Nat 1) (Just (-1)) (Just "1"))-      , "{\"item_nat\":1,\"item_int\":-1, \"item_str\":\"1\"}"-      )+            , testFromXML "double"+                "46.39212" (46.39212 :: Double) -    , ( Nothing-      , "{\"item_nat\":1,\"item_int\":-1, \"item_str\":1}"-      )+            , testFromXML "negative double"+                "-1.09231" (-1.09231 :: Double) -    , ( Just (Item (Just $ Nat 1) (Just (-1)) Nothing)-      , "{\"item_nat\":1,\"item_int\":-1}"-      )+            , testFromXML "numeric string"+                "22" ("22" :: Text)+            ] -    , ( Just (Item (Just $ Nat 1) (Just (-1)) Nothing)-      , "{\"item_nat\":1.0,\"item_int\":-1}"-      )+        , testGroup "serialisation"+            [ testToXML "natural"+                "123" (Nat 123) -    , ( Nothing-      , "{\"item_nat\":-1,\"item_int\":1}"-      )+            ,  testToXML "int"+                (toLazyBS maxInt) maxInt -    , ( Nothing-      , "{\"item_nat\":1.2,\"item_int\":1}"-      )+            , testToXML "negative int"+                (toLazyBS minInt) minInt -    , ( Nothing-      , "{\"item_nat\":\"1\",\"item_int\":1}"-      )-    ]+            , testToXML "integer"+                "891324" (891324 :: Integer) -testDecode :: [(Maybe Item, LazyByteString)] -> TestTree-testDecode = testCase "Numeric JSON Decoding" . mapM_ check-  where-    check (e, input) = e @=? (decode input :: Maybe Item)+            , testToXML "negative integer"+                "-998" (-998 :: Integer)++            , testToXML "double"+                "46.39212" (46.39212 :: Double)++            , testToXML "negative double"+                "-1.09231" (-1.09231 :: Double)++            , testToXML "numeric text"+                "22" ("22" :: Text)+            ]+        ]+    ]
test/Test/AWS/Data/Time.hs view
@@ -1,94 +1,156 @@ {-# LANGUAGE DataKinds         #-} {-# LANGUAGE OverloadedStrings #-}-{-# LANGUAGE QuasiQuotes       #-} {-# LANGUAGE RecordWildCards   #-} +-- | -- Module      : Test.AWS.Data.Time--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0. -- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com> -- Stability   : experimental -- Portability : non-portable (GHC extensions)-+-- module Test.AWS.Data.Time (tests) where -import           Data.Aeson-import           Network.AWS.Data+import           Network.AWS.Compat.Locale+import           Network.AWS.Compat.Time import           Network.AWS.Prelude-import           Test.AWS.Types+import           Test.AWS.Util import           Test.Tasty-import           Test.Tasty.HUnit  tests :: TestTree tests = testGroup "time"-    [ testGroup "deserialise xml"-        [ testCase "RFC822" $-            assertXML "<T>Fri, 07 Nov 2014 04:42:13 GMT</T>" (ref :: RFC822)-        , testCase "ISO8601" $-            assertXML "<T>2014-11-07T04:42:13.000Z</T>" (ref :: ISO8601)-        , testCase "AWS" $-            assertXML "<T>20141107T044213Z</T>" (ref :: AWSTime)-        , testCase "POSIX integer" $-            assertXML "<T>1415335333</T>" (ref :: POSIX)-        , testCase "POSIX scientific" $-            assertXML "<T>1.415335333E9</T>" (ref :: POSIX)+    [ testGroup "text"+        [ testGroup "deserialise"+            [ testFromText "rfc822"+                "Fri, 07 Nov 2014 04:42:13 GMT" (time :: RFC822)++            , testFromText "iso8601"+                "2014-11-07T04:42:13.000Z" (time :: ISO8601)++            , testFromText "aws"+                "20141107T044213Z" (time :: AWSTime)++            , testGroup "posix"+                [ testFromText "integer"+                    "1415335333" (time :: POSIX)++                , testFromText "double"+                    "1415335333.000" (time :: POSIX)++                , testFromText "scientific"+                    "1.415335333E9" (time :: POSIX)+                ]+            ]++        , testGroup "serialise"+            [ testToText "rfc822"+                "Fri, 07 Nov 2014 04:42:13 GMT" (time :: RFC822)++            , testToText "iso8601"+                "2014-11-07T04:42:13UTC" (time :: ISO8601)++            , testToText "aws"+                "20141107T044213Z" (time :: AWSTime)++            , testToText "posix"+                "1415335333" (time :: POSIX)+            ]         ]-    , testGroup "deserialise json"-        [ testCase "RFC822" $-            assertJSON "{\"time_rfc\":\"Fri, 07 Nov 2014 04:42:13 GMT\"}"-                       (defaultTimeItem {timeRFC = Just ref})-        , testCase "ISO8601" $-            assertJSON "{\"time_iso\":\"2014-11-07T04:42:13.000Z\"}"-                       (defaultTimeItem {timeISO = Just ref})-        , testCase "AWS" $-            assertJSON "{\"time_aws\":\"20141107T044213Z\"}"-                       (defaultTimeItem {timeAWS = Just ref})-        , testCase "POSIX integer" $-            assertJSON "{\"time_posix\":1415335333}"-                       (defaultTimeItem {timePOSIX = Just ref})-        , testCase "POSIX scientific" $-            assertJSON "{\"time_posix\":1.415335333E9}"-                       (defaultTimeItem {timePOSIX = Just ref})++    , testGroup "query"+        [ testGroup "serialise"+            [ testToQuery "rfc822"+                "x=Fri%2C%2007%20Nov%202014%2004%3A42%3A13%20GMT" (time :: RFC822)++            , testToQuery "iso8601"+                "x=2014-11-07T04%3A42%3A13UTC" (time :: ISO8601)++            , testToQuery "aws"+                "x=20141107T044213Z" (time :: AWSTime)+            ]         ]-    , testGroup "serialise json"-        [ testCase "POSIX integer" $-            (@?=) (encode $ defaultTimeItem {timePOSIX = Just ref})-                  "{\"time_aws\":null,\"time_iso\":null,\-                  \\"time_posix\":1415335333,\"time_rfc\":null}"++    , testGroup "xml"+        [ testGroup "deserialise"+            [ testFromXML "rfc822"+                "Fri, 07 Nov 2014 04:42:13 GMT" (time :: RFC822)++            , testFromXML "iso8601"+                "2014-11-07T04:42:13.000Z" (time :: ISO8601)++            , testFromXML "aws"+                "20141107T044213Z" (time :: AWSTime)++            , testGroup "posix"+                [ testFromXML "integer"+                    "1415335333" (time :: POSIX)++                , testFromXML "double"+                    "1415335333.000" (time :: POSIX)++                , testFromXML "scientific"+                    "1.415335333E9" (time :: POSIX)+                ]+            ]++        , testGroup "serialise"+            [ testToXML "rfc822"+                "Fri, 07 Nov 2014 04:42:13 GMT" (time :: RFC822)++            , testToXML "iso8601"+                "2014-11-07T04:42:13UTC" (time :: ISO8601)++            , testToXML "aws"+                "20141107T044213Z" (time :: AWSTime)++            , testToXML "posix"+                "1415335333" (time :: POSIX)+            ]         ]-    ] -ref :: Time a-ref = Time $ fromMaybe (error "Unable to parse time") (parseTime locale format ts)-  where-    locale = defaultTimeLocale-    format = iso8601DateFormat (Just "%H:%M:%S")-    ts = "2014-11-07T04:42:13"+    , testGroup "json"+        [ testGroup "deserialise"+            [ testFromJSON "rfc822"+                (str "Fri, 07 Nov 2014 04:42:13 GMT") (time :: RFC822) -data TimeItem = TimeItem-     { timeRFC   :: Maybe RFC822-     , timeISO   :: Maybe ISO8601-     , timeAWS   :: Maybe AWSTime-     , timePOSIX :: Maybe POSIX-     } deriving (Eq, Show)+            , testFromJSON "iso8601"+                (str "2014-11-07T04:42:13.000Z") (time :: ISO8601) -defaultTimeItem :: TimeItem-defaultTimeItem = TimeItem Nothing Nothing Nothing Nothing+            , testFromJSON "aws"+                (str "20141107T044213Z") (time :: AWSTime) -instance ToJSON TimeItem where-    toJSON TimeItem{..} = object-        [ "time_rfc"   .= timeRFC-        , "time_iso"   .= timeISO-        , "time_aws"   .= timeAWS-        , "time_posix" .= timePOSIX+            , testGroup "posix"+                [ testFromJSON "integer"+                    "1415335333" (time :: POSIX)++                , testFromJSON "double"+                    "1415335333.000" (time :: POSIX)++                , testFromJSON "scientific"+                    "1.415335333E9" (time :: POSIX)+                ]+            ]++        , testGroup "serialise"+            [ testToJSON "rfc822"+                (str "Fri, 07 Nov 2014 04:42:13 GMT") (time :: RFC822)++            , testToJSON "iso8601"+                (str "2014-11-07T04:42:13UTC") (time :: ISO8601)++            , testToJSON "aws"+                (str "20141107T044213Z") (time :: AWSTime)++            , testToJSON "posix"+                "1415335333" (time :: POSIX)+            ]         ]+    ] -instance FromJSON TimeItem where-    parseJSON = withObject "TimeItem" $ \o -> TimeItem-        <$> o .:? "time_rfc"-        <*> o .:? "time_iso"-        <*> o .:? "time_aws"-        <*> o .:? "time_posix"+time :: Time a+time = Time . fromMaybe (error msg) $ parseTime defaultTimeLocale fmt ts+  where+    msg = "Unable to parse time: " ++ ts+    fmt = (iso8601DateFormat (Just "%H:%M:%S"))+    ts  = "2014-11-07T04:42:13"
+ test/Test/AWS/Sign/V4.hs view
@@ -0,0 +1,100 @@+{-# LANGUAGE OverloadedStrings #-}+{-# LANGUAGE TypeFamilies      #-}++-- |+-- Module      : Test.AWS.Sign.V$+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : experimental+-- Portability : non-portable (GHC extensions)+--+module Test.AWS.Sign.V4 (tests) where++import           Control.Lens+import qualified Data.ByteString.Char8    as BS8+import qualified Data.Foldable            as Fold+import           Data.List                (sort)+import           Data.Monoid+import           Data.String+import qualified Data.Text                as Text+import qualified Data.Text.Encoding       as Text+import           Network.AWS.Prelude+import           Network.AWS.Sign.V4+import           Test.AWS.Arbitrary       ()+import           Test.QuickCheck.Property+import           Test.Tasty+import           Test.Tasty.QuickCheck++-- Write some V4 signing properties:+--  test canonical query+--  test query+--  test canonical headers+--  test signed headers+--  test time format+--  test host, x-amz-date, content-sha256 headers exist+--  test empty path+--  test empty query++tests :: TestTree+tests = testGroup "v4"+    [ testGroup "canonical query"+        [ testProperty "empty" $ queryEmpty+        , testProperty "empty key values" $ queryEmptyKeyValues+        ]+    ]++queryEmpty :: Request () -> Signer -> Property+queryEmpty rq sg = property $+    mempty == toBS (metaCanonicalQuery . sign sg $ rq & rqQuery .~ mempty)++queryEmptyKeyValues :: [NonEmptyList Char] -> Property+queryEmptyKeyValues xs = property $ do+    rq <- arbitrary+    sg <- arbitrary++    let v4 = sign sg $ rq & rqQuery .~ Fold.foldMap (fromString . getNonEmpty) xs++        e  = sort $ map ((<> "=") . urlEncode True . BS8.pack . getNonEmpty) xs+        a  = BS8.split '&' . toBS $ metaCanonicalQuery v4++        m  = "Expected: " ++ show e ++ "\n" +++              "Actual: "  ++ show a++    return . counterexample m $ e == a++newtype Signer = Signer { sign :: Request () -> Meta V4 }++instance Show Signer where+    show = const "V4"++instance Arbitrary Signer where+    arbitrary = do+        a   <- arbitrary+        reg <- arbitrary+        ts  <- arbitrary+        return $ Signer (_sgMeta . signed auth reg ts (testV4 a))++auth :: AuthEnv+auth = AuthEnv "access-key" "super-secret-key" Nothing Nothing++data TestV4++instance AWSService TestV4 where+    type Sg TestV4 = V4++    service = error "service not defined for TestV4."++testV4 :: Abbrev -> Service TestV4+testV4 a = svc+  where+    svc = Service+        { _svcAbbrev   = a+        , _svcPrefix   = Text.encodeUtf8 . Text.toLower $ toText a+        , _svcVersion  = "2012-01-01"+        , _svcEndpoint = defaultEndpoint svc+        , _svcTimeout  = Nothing+        , _svcStatus   = const False+        , _svcError    = error "_svcError not defined."+        , _svcRetry    = error "_svcRetry not defined."+        }
− test/Test/AWS/TH.hs
@@ -1,17 +0,0 @@--- Module      : Test.AWS.TH--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Test.AWS.TH where--import Language.Haskell.TH-import Language.Haskell.TH.Quote--doc :: QuasiQuoter-doc = QuasiQuoter { quoteExp = stringE }
− test/Test/AWS/Types.hs
@@ -1,30 +0,0 @@-{-# LANGUAGE OverloadedStrings #-}---- Module      : Test.AWS.Types--- Copyright   : (c) 2013-2015 Brendan Hay <brendan.g.hay@gmail.com>--- License     : This Source Code Form is subject to the terms of---               the Mozilla Public License, v. 2.0.---               A copy of the MPL can be found in the LICENSE file or---               you can obtain it at http://mozilla.org/MPL/2.0/.--- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>--- Stability   : experimental--- Portability : non-portable (GHC extensions)--module Test.AWS.Types where--import Data.Aeson-import Network.AWS.Data-import Network.AWS.Prelude-import Test.Tasty.HUnit--newtype Entries a = Entries a-    deriving (Eq, Show)--instance FromXML a => FromXML (Entries a) where-    parseXML x = Entries <$> x .@ "Entries"--assertXML :: (FromXML a, Show a, Eq a) => LazyByteString -> a -> Assertion-assertXML s x = (decodeXML s >>= parseXML) @?= Right x--assertJSON :: (FromJSON a, Show a, Eq a) => LazyByteString -> a -> Assertion-assertJSON s x = eitherDecode' s @?= Right x
+ test/Test/AWS/Util.hs view
@@ -0,0 +1,113 @@+{-# LANGUAGE OverloadedStrings #-}++-- |+-- Module      : Test.AWS.Util+-- Copyright   : (c) 2013-2015 Brendan Hay+-- License     : Mozilla Public License, v. 2.0.+-- Maintainer  : Brendan Hay <brendan.g.hay@gmail.com>+-- Stability   : experimental+-- Portability : non-portable (GHC extensions)+--+module Test.AWS.Util where++import           Data.Aeson+import qualified Data.ByteString.Lazy      as LBS+import           Language.Haskell.TH+import           Language.Haskell.TH.Quote+import           Network.AWS.Prelude+import           Test.Tasty+import           Test.Tasty.HUnit++doc :: QuasiQuoter+doc = QuasiQuoter+    { quoteExp  = stringE+    , quotePat  = const $ error "No quotePat  defined."+    , quoteType = const $ error "No quoteType defined."+    , quoteDec  = const $ error "No quoteDec  defined."+    }++-- | Dummy root element for testing nested structures.+newtype X a = X a+    deriving (Eq, Show)++instance ToQuery a => ToQuery (X a) where+    toQuery (X x) = "x" =: x++instance FromXML a => FromXML (X a) where+    parseXML = fmap X . parseXML++instance ToXML a => ToElement (X a) where+    toElement (X x) = mkElement "x" x++instance FromJSON a => FromJSON (X a) where+    parseJSON = withObject "X" (fmap X . (.: "x"))++instance ToJSON a => ToJSON (X a) where+    toJSON (X x) = object ["x" .= x]++testFromText :: (FromText a, Show a, Eq a)+             => TestName+             -> Text+             -> a+             -> TestTree+testFromText n t x = testCase n (Right x @?= fromText t)++testToText :: (ToText a, Show a, Eq a)+           => TestName+           -> Text+           -> a+           -> TestTree+testToText n t x = testCase n (t @?= toText x)++testToQuery :: (ToQuery a, Show a, Eq a)+            => TestName+            -> ByteString+            -> a+            -> TestTree+testToQuery n bs x = testCase n (bs @=? toBS (toQuery (X x)))++testFromXML :: (FromXML a, Show a, Eq a)+            => TestName+            -> LazyByteString+            -> a+            -> TestTree+testFromXML n bs x = testCase n $+     Right (X x) @?= (decodeXML (wrapXML bs) >>= parseXML)++testToXML :: (ToXML a, Show a, Eq a)+          => TestName+          -> LazyByteString+          -> a+          -> TestTree+testToXML n bs x = testCase n $ wrapXML bs @?= encodeXML (X x)++testFromJSON :: (FromJSON a, Show a, Eq a)+             => TestName+             -> LazyByteString+             -> a+             -> TestTree+testFromJSON n bs x = testCase n $+    Right (X x) @?= eitherDecode' ("{\"x\":" <> bs <> "}")++testToJSON :: (ToJSON a, Show a, Eq a)+           => TestName+           -> LazyByteString+           -> a+           -> TestTree+testToJSON n bs x = testCase n (bs @?= encode x)++str :: LazyByteString -> LazyByteString+str bs = "\"" <> bs <> "\""++wrapXML :: LazyByteString -> LazyByteString+wrapXML bs =+    "<?xml version=\"1.0\" encoding=\"UTF-8\"?>" <> "<x>" <> bs <> "</x>"++maxInt :: Int+maxInt = maxBound++minInt :: Int+minInt = minBound++toLazyBS :: ToByteString a => a -> LazyByteString+toLazyBS = LBS.fromStrict . toBS