    {-# LANGUAGE CPP                        #-}
    {-# LANGUAGE DeriveDataTypeable         #-}
    {-# LANGUAGE FlexibleContexts           #-}
    {-# LANGUAGE FlexibleInstances          #-}
    {-# LANGUAGE GeneralizedNewtypeDeriving #-}
    {-# LANGUAGE MultiParamTypeClasses      #-}
    {-# LANGUAGE NoMonomorphismRestriction  #-}
    {-# LANGUAGE OverloadedStrings          #-}
    {-# LANGUAGE RecordWildCards            #-}
    {-# LANGUAGE ScopedTypeVariables        #-}
    {-# LANGUAGE TypeFamilies               #-}
    {-# LANGUAGE UndecidableInstances       #-}

    -----------------------------------------------------------------------------
    -- |
    -- Module      :  Aws.DynamoDb.Core
    -- Copyright   :  Soostone Inc, Chris Allen
    -- License     :  BSD3
    --
    -- Maintainer  :  Ozgun Ataman <ozgun.ataman@soostone.com>
    -- Stability   :  experimental
    --
    -- Shared types and utilities for DyanmoDb functionality.
    ----------------------------------------------------------------------------

    module Aws.DynamoDb.Core
        (
        -- * Configuration and Regions
          Region (..)
        , ddbLocal
        , ddbUsEast1
        , ddbUsWest1
        , ddbUsWest2
        , ddbEuWest1
        , ddbEuWest2
        , ddbEuCentral1
        , ddbApNe1
        , ddbApSe1
        , ddbApSe2
        , ddbSaEast1
        , DdbConfiguration (..)

        -- * DynamoDB values
        , DValue (..)

        -- * Converting to/from 'DValue'
        , DynVal(..)
        , toValue, fromValue
        , Bin (..)
        , OldBool(..)

        -- * Defining new 'DynVal' instances
        , DynData(..)
        , DynBinary(..), DynNumber(..), DynString(..), DynBool(..)

        -- * Working with key/value pairs
        , Attribute (..)
        , parseAttributeJson
        , attributeJson
        , attributesJson

        , attrTuple
        , attr
        , attrAs
        , text, int, double
        , PrimaryKey (..)
        , hk
        , hrk

        -- * Working with objects (attribute collections)
        , Item
        , item
        , attributes
        , ToDynItem (..)
        , FromDynItem (..)
        , fromItem
        , Parser (..)
        , getAttr
        , getAttr'
        , parseAttr

        -- * Common types used by operations
        , Conditions (..)
        , conditionsJson
        , expectsJson

        , Condition (..)
        , conditionJson
        , CondOp (..)
        , CondMerge (..)
        , ConsumedCapacity (..)
        , ReturnConsumption (..)
        , ItemCollectionMetrics (..)
        , ReturnItemCollectionMetrics (..)
        , UpdateReturn (..)
        , QuerySelect (..)
        , querySelectJson

        -- * Size estimation
        , DynSize (..)
        , nullAttr

        -- * Responses & Errors
        , DdbResponse (..)
        , DdbErrCode (..)
        , shouldRetry
        , DdbError (..)

        -- * Internal Helpers
        , ddbSignQuery
        , AmazonError (..)
        , ddbResponseConsumer
        , ddbHttp
        , ddbHttps

        ) where

    -------------------------------------------------------------------------------
    import           Control.Applicative
    import qualified Control.Exception            as C
    import           Control.Monad
    #if MIN_VERSION_base(4,9,0)
    import qualified Control.Monad.Fail           as Fail
    #endif
    import           Control.Monad.Trans
    import           Control.Monad.Trans.Resource (throwM)
    import qualified Crypto.Hash                  as CH
    import           Data.Aeson
    import qualified Data.Aeson                   as A
    import qualified Data.Aeson.Key               as AK
    import qualified Data.Aeson.KeyMap            as KM
    import           Data.Aeson.Parser            as A (json')
    import           Data.Aeson.Types             (Pair, parseEither)
    import qualified Data.Aeson.Types             as A
    import qualified Data.Attoparsec.ByteString   as AttoB (endOfInput)
    import qualified Data.Attoparsec.Text         as Atto
    import qualified Data.ByteArray               as ByteArray
    import qualified Data.ByteString.Base16       as Base16
    import qualified Data.ByteString.Base64       as Base64
    import qualified Data.ByteString.Char8        as B
    import qualified Data.CaseInsensitive         as CI
    import           Data.Conduit
    import           Data.Conduit.Attoparsec      (sinkParser)
    import           Data.Default
    import           Data.Function                (on)
    import           Data.Int
    import           Data.IORef
    import           Data.List
    import qualified Data.Map                     as M
    import           Data.Maybe
    import           Data.Monoid                  ()
    import qualified Data.Semigroup               as Sem
    import           Data.Proxy
    import           Data.Scientific
    import qualified Data.Serialize               as Ser
    import qualified Data.Set                     as S
    import           Data.String
    import           Data.Tagged
    import qualified Data.Text                    as T
    import qualified Data.Text.Encoding           as T
    import           Data.Time
    import           Data.Typeable
    import qualified Data.Vector                  as V
    import           Data.Word
    import qualified Network.HTTP.Conduit         as HTTP
    import qualified Network.HTTP.Types           as HTTP
    import           Safe
    -------------------------------------------------------------------------------
    import           Aws.Core
    -------------------------------------------------------------------------------

    -------------------------------------------------------------------------------
    -- | Boolean values stored in DynamoDb. Only used in defining new
    -- 'DynVal' instances.
    newtype DynBool = DynBool { DynBool -> Bool
    unDynBool :: Bool }
        deriving (DynBool -> DynBool -> Bool
    (DynBool -> DynBool -> Bool)
    -> (DynBool -> DynBool -> Bool) -> Eq DynBool
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: DynBool -> DynBool -> Bool
    == :: DynBool -> DynBool -> Bool
    $c/= :: DynBool -> DynBool -> Bool
    /= :: DynBool -> DynBool -> Bool
    Eq,Int -> DynBool -> ShowS
    [DynBool] -> ShowS
    DynBool -> String
    (Int -> DynBool -> ShowS)
    -> (DynBool -> String) -> ([DynBool] -> ShowS) -> Show DynBool
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> DynBool -> ShowS
    showsPrec :: Int -> DynBool -> ShowS
    $cshow :: DynBool -> String
    show :: DynBool -> String
    $cshowList :: [DynBool] -> ShowS
    showList :: [DynBool] -> ShowS
    Show,ReadPrec [DynBool]
    ReadPrec DynBool
    Int -> ReadS DynBool
    ReadS [DynBool]
    (Int -> ReadS DynBool)
    -> ReadS [DynBool]
    -> ReadPrec DynBool
    -> ReadPrec [DynBool]
    -> Read DynBool
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS DynBool
    readsPrec :: Int -> ReadS DynBool
    $creadList :: ReadS [DynBool]
    readList :: ReadS [DynBool]
    $creadPrec :: ReadPrec DynBool
    readPrec :: ReadPrec DynBool
    $creadListPrec :: ReadPrec [DynBool]
    readListPrec :: ReadPrec [DynBool]
    Read,Eq DynBool
    Eq DynBool =>
    (DynBool -> DynBool -> Ordering)
    -> (DynBool -> DynBool -> Bool)
    -> (DynBool -> DynBool -> Bool)
    -> (DynBool -> DynBool -> Bool)
    -> (DynBool -> DynBool -> Bool)
    -> (DynBool -> DynBool -> DynBool)
    -> (DynBool -> DynBool -> DynBool)
    -> Ord DynBool
    DynBool -> DynBool -> Bool
    DynBool -> DynBool -> Ordering
    DynBool -> DynBool -> DynBool
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: DynBool -> DynBool -> Ordering
    compare :: DynBool -> DynBool -> Ordering
    $c< :: DynBool -> DynBool -> Bool
    < :: DynBool -> DynBool -> Bool
    $c<= :: DynBool -> DynBool -> Bool
    <= :: DynBool -> DynBool -> Bool
    $c> :: DynBool -> DynBool -> Bool
    > :: DynBool -> DynBool -> Bool
    $c>= :: DynBool -> DynBool -> Bool
    >= :: DynBool -> DynBool -> Bool
    $cmax :: DynBool -> DynBool -> DynBool
    max :: DynBool -> DynBool -> DynBool
    $cmin :: DynBool -> DynBool -> DynBool
    min :: DynBool -> DynBool -> DynBool
    Ord,Typeable)

    -------------------------------------------------------------------------------
    -- | Numeric values stored in DynamoDb. Only used in defining new
    -- 'DynVal' instances.
    newtype DynNumber = DynNumber { DynNumber -> Scientific
    unDynNumber :: Scientific }
        deriving (DynNumber -> DynNumber -> Bool
    (DynNumber -> DynNumber -> Bool)
    -> (DynNumber -> DynNumber -> Bool) -> Eq DynNumber
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: DynNumber -> DynNumber -> Bool
    == :: DynNumber -> DynNumber -> Bool
    $c/= :: DynNumber -> DynNumber -> Bool
    /= :: DynNumber -> DynNumber -> Bool
    Eq,Int -> DynNumber -> ShowS
    [DynNumber] -> ShowS
    DynNumber -> String
    (Int -> DynNumber -> ShowS)
    -> (DynNumber -> String)
    -> ([DynNumber] -> ShowS)
    -> Show DynNumber
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> DynNumber -> ShowS
    showsPrec :: Int -> DynNumber -> ShowS
    $cshow :: DynNumber -> String
    show :: DynNumber -> String
    $cshowList :: [DynNumber] -> ShowS
    showList :: [DynNumber] -> ShowS
    Show,ReadPrec [DynNumber]
    ReadPrec DynNumber
    Int -> ReadS DynNumber
    ReadS [DynNumber]
    (Int -> ReadS DynNumber)
    -> ReadS [DynNumber]
    -> ReadPrec DynNumber
    -> ReadPrec [DynNumber]
    -> Read DynNumber
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS DynNumber
    readsPrec :: Int -> ReadS DynNumber
    $creadList :: ReadS [DynNumber]
    readList :: ReadS [DynNumber]
    $creadPrec :: ReadPrec DynNumber
    readPrec :: ReadPrec DynNumber
    $creadListPrec :: ReadPrec [DynNumber]
    readListPrec :: ReadPrec [DynNumber]
    Read,Eq DynNumber
    Eq DynNumber =>
    (DynNumber -> DynNumber -> Ordering)
    -> (DynNumber -> DynNumber -> Bool)
    -> (DynNumber -> DynNumber -> Bool)
    -> (DynNumber -> DynNumber -> Bool)
    -> (DynNumber -> DynNumber -> Bool)
    -> (DynNumber -> DynNumber -> DynNumber)
    -> (DynNumber -> DynNumber -> DynNumber)
    -> Ord DynNumber
    DynNumber -> DynNumber -> Bool
    DynNumber -> DynNumber -> Ordering
    DynNumber -> DynNumber -> DynNumber
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: DynNumber -> DynNumber -> Ordering
    compare :: DynNumber -> DynNumber -> Ordering
    $c< :: DynNumber -> DynNumber -> Bool
    < :: DynNumber -> DynNumber -> Bool
    $c<= :: DynNumber -> DynNumber -> Bool
    <= :: DynNumber -> DynNumber -> Bool
    $c> :: DynNumber -> DynNumber -> Bool
    > :: DynNumber -> DynNumber -> Bool
    $c>= :: DynNumber -> DynNumber -> Bool
    >= :: DynNumber -> DynNumber -> Bool
    $cmax :: DynNumber -> DynNumber -> DynNumber
    max :: DynNumber -> DynNumber -> DynNumber
    $cmin :: DynNumber -> DynNumber -> DynNumber
    min :: DynNumber -> DynNumber -> DynNumber
    Ord,Typeable)

    -------------------------------------------------------------------------------
    -- | String values stored in DynamoDb. Only used in defining new
    -- 'DynVal' instances.
    newtype DynString = DynString { DynString -> Text
    unDynString :: T.Text }
        deriving (DynString -> DynString -> Bool
    (DynString -> DynString -> Bool)
    -> (DynString -> DynString -> Bool) -> Eq DynString
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: DynString -> DynString -> Bool
    == :: DynString -> DynString -> Bool
    $c/= :: DynString -> DynString -> Bool
    /= :: DynString -> DynString -> Bool
    Eq,Int -> DynString -> ShowS
    [DynString] -> ShowS
    DynString -> String
    (Int -> DynString -> ShowS)
    -> (DynString -> String)
    -> ([DynString] -> ShowS)
    -> Show DynString
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> DynString -> ShowS
    showsPrec :: Int -> DynString -> ShowS
    $cshow :: DynString -> String
    show :: DynString -> String
    $cshowList :: [DynString] -> ShowS
    showList :: [DynString] -> ShowS
    Show,ReadPrec [DynString]
    ReadPrec DynString
    Int -> ReadS DynString
    ReadS [DynString]
    (Int -> ReadS DynString)
    -> ReadS [DynString]
    -> ReadPrec DynString
    -> ReadPrec [DynString]
    -> Read DynString
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS DynString
    readsPrec :: Int -> ReadS DynString
    $creadList :: ReadS [DynString]
    readList :: ReadS [DynString]
    $creadPrec :: ReadPrec DynString
    readPrec :: ReadPrec DynString
    $creadListPrec :: ReadPrec [DynString]
    readListPrec :: ReadPrec [DynString]
    Read,Eq DynString
    Eq DynString =>
    (DynString -> DynString -> Ordering)
    -> (DynString -> DynString -> Bool)
    -> (DynString -> DynString -> Bool)
    -> (DynString -> DynString -> Bool)
    -> (DynString -> DynString -> Bool)
    -> (DynString -> DynString -> DynString)
    -> (DynString -> DynString -> DynString)
    -> Ord DynString
    DynString -> DynString -> Bool
    DynString -> DynString -> Ordering
    DynString -> DynString -> DynString
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: DynString -> DynString -> Ordering
    compare :: DynString -> DynString -> Ordering
    $c< :: DynString -> DynString -> Bool
    < :: DynString -> DynString -> Bool
    $c<= :: DynString -> DynString -> Bool
    <= :: DynString -> DynString -> Bool
    $c> :: DynString -> DynString -> Bool
    > :: DynString -> DynString -> Bool
    $c>= :: DynString -> DynString -> Bool
    >= :: DynString -> DynString -> Bool
    $cmax :: DynString -> DynString -> DynString
    max :: DynString -> DynString -> DynString
    $cmin :: DynString -> DynString -> DynString
    min :: DynString -> DynString -> DynString
    Ord,Typeable)

    -------------------------------------------------------------------------------
    -- | Binary values stored in DynamoDb. Only used in defining new
    -- 'DynVal' instances.
    newtype DynBinary = DynBinary { DynBinary -> ByteString
    unDynBinary :: B.ByteString }
        deriving (DynBinary -> DynBinary -> Bool
    (DynBinary -> DynBinary -> Bool)
    -> (DynBinary -> DynBinary -> Bool) -> Eq DynBinary
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: DynBinary -> DynBinary -> Bool
    == :: DynBinary -> DynBinary -> Bool
    $c/= :: DynBinary -> DynBinary -> Bool
    /= :: DynBinary -> DynBinary -> Bool
    Eq,Int -> DynBinary -> ShowS
    [DynBinary] -> ShowS
    DynBinary -> String
    (Int -> DynBinary -> ShowS)
    -> (DynBinary -> String)
    -> ([DynBinary] -> ShowS)
    -> Show DynBinary
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> DynBinary -> ShowS
    showsPrec :: Int -> DynBinary -> ShowS
    $cshow :: DynBinary -> String
    show :: DynBinary -> String
    $cshowList :: [DynBinary] -> ShowS
    showList :: [DynBinary] -> ShowS
    Show,ReadPrec [DynBinary]
    ReadPrec DynBinary
    Int -> ReadS DynBinary
    ReadS [DynBinary]
    (Int -> ReadS DynBinary)
    -> ReadS [DynBinary]
    -> ReadPrec DynBinary
    -> ReadPrec [DynBinary]
    -> Read DynBinary
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS DynBinary
    readsPrec :: Int -> ReadS DynBinary
    $creadList :: ReadS [DynBinary]
    readList :: ReadS [DynBinary]
    $creadPrec :: ReadPrec DynBinary
    readPrec :: ReadPrec DynBinary
    $creadListPrec :: ReadPrec [DynBinary]
    readListPrec :: ReadPrec [DynBinary]
    Read,Eq DynBinary
    Eq DynBinary =>
    (DynBinary -> DynBinary -> Ordering)
    -> (DynBinary -> DynBinary -> Bool)
    -> (DynBinary -> DynBinary -> Bool)
    -> (DynBinary -> DynBinary -> Bool)
    -> (DynBinary -> DynBinary -> Bool)
    -> (DynBinary -> DynBinary -> DynBinary)
    -> (DynBinary -> DynBinary -> DynBinary)
    -> Ord DynBinary
    DynBinary -> DynBinary -> Bool
    DynBinary -> DynBinary -> Ordering
    DynBinary -> DynBinary -> DynBinary
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: DynBinary -> DynBinary -> Ordering
    compare :: DynBinary -> DynBinary -> Ordering
    $c< :: DynBinary -> DynBinary -> Bool
    < :: DynBinary -> DynBinary -> Bool
    $c<= :: DynBinary -> DynBinary -> Bool
    <= :: DynBinary -> DynBinary -> Bool
    $c> :: DynBinary -> DynBinary -> Bool
    > :: DynBinary -> DynBinary -> Bool
    $c>= :: DynBinary -> DynBinary -> Bool
    >= :: DynBinary -> DynBinary -> Bool
    $cmax :: DynBinary -> DynBinary -> DynBinary
    max :: DynBinary -> DynBinary -> DynBinary
    $cmin :: DynBinary -> DynBinary -> DynBinary
    min :: DynBinary -> DynBinary -> DynBinary
    Ord,Typeable)

    -------------------------------------------------------------------------------
    -- | An internally used closed typeclass for values that have direct
    -- DynamoDb representations. Based on AWS API, this is basically
    -- numbers, strings and binary blobs.
    --
    -- This is here so that any 'DynVal' haskell value can automatically
    -- be lifted to a list or a 'Set' without any instance code
    -- duplication.
    --
    -- Do not try to create your own instances.
    class Ord a => DynData a where
        fromData :: a -> DValue
        toData :: DValue -> Maybe a

    instance DynData DynBool where
        fromData :: DynBool -> DValue
    fromData (DynBool Bool
    i) = Bool -> DValue
    DBool Bool
    i
        toData :: DValue -> Maybe DynBool
    toData (DBool Bool
    i) = DynBool -> Maybe DynBool
    forall a. a -> Maybe a
    Just (DynBool -> Maybe DynBool) -> DynBool -> Maybe DynBool
    forall a b. (a -> b) -> a -> b
    $ Bool -> DynBool
    DynBool Bool
    i
        toData (DNum Scientific
    i) = Bool -> DynBool
    DynBool (Bool -> DynBool) -> Maybe Bool -> Maybe DynBool
    forall a b. (a -> b) -> Maybe a -> Maybe b
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    `fmap` do
            (i' :: Int) <- Scientific -> Maybe Int
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i
            case i' of
              Int
    0 -> Bool -> Maybe Bool
    forall a. a -> Maybe a
    forall (m :: * -> *) a. Monad m => a -> m a
    return Bool
    False
              Int
    1 -> Bool -> Maybe Bool
    forall a. a -> Maybe a
    forall (m :: * -> *) a. Monad m => a -> m a
    return Bool
    True
              Int
    _ -> Maybe Bool
    forall a. Maybe a
    Nothing
        toData DValue
    _ = Maybe DynBool
    forall a. Maybe a
    Nothing

    instance DynData (S.Set DynBool) where
        fromData :: Set DynBool -> DValue
    fromData Set DynBool
    set = Set Bool -> DValue
    DBoolSet ((DynBool -> Bool) -> Set DynBool -> Set Bool
    forall b a. Ord b => (a -> b) -> Set a -> Set b
    S.map DynBool -> Bool
    unDynBool Set DynBool
    set)
        toData :: DValue -> Maybe (Set DynBool)
    toData (DBoolSet Set Bool
    i) = Set DynBool -> Maybe (Set DynBool)
    forall a. a -> Maybe a
    Just (Set DynBool -> Maybe (Set DynBool))
    -> Set DynBool -> Maybe (Set DynBool)
    forall a b. (a -> b) -> a -> b
    $ (Bool -> DynBool) -> Set Bool -> Set DynBool
    forall b a. Ord b => (a -> b) -> Set a -> Set b
    S.map Bool -> DynBool
    DynBool Set Bool
    i
        toData DValue
    _ = Maybe (Set DynBool)
    forall a. Maybe a
    Nothing

    instance DynData DynNumber where
        fromData :: DynNumber -> DValue
    fromData (DynNumber Scientific
    i) = Scientific -> DValue
    DNum Scientific
    i
        toData :: DValue -> Maybe DynNumber
    toData (DNum Scientific
    i) = DynNumber -> Maybe DynNumber
    forall a. a -> Maybe a
    Just (DynNumber -> Maybe DynNumber) -> DynNumber -> Maybe DynNumber
    forall a b. (a -> b) -> a -> b
    $ Scientific -> DynNumber
    DynNumber Scientific
    i
        toData DValue
    _ = Maybe DynNumber
    forall a. Maybe a
    Nothing

    instance DynData (S.Set DynNumber) where
        fromData :: Set DynNumber -> DValue
    fromData Set DynNumber
    set = Set Scientific -> DValue
    DNumSet ((DynNumber -> Scientific) -> Set DynNumber -> Set Scientific
    forall b a. Ord b => (a -> b) -> Set a -> Set b
    S.map DynNumber -> Scientific
    unDynNumber Set DynNumber
    set)
        toData :: DValue -> Maybe (Set DynNumber)
    toData (DNumSet Set Scientific
    i) = Set DynNumber -> Maybe (Set DynNumber)
    forall a. a -> Maybe a
    Just (Set DynNumber -> Maybe (Set DynNumber))
    -> Set DynNumber -> Maybe (Set DynNumber)
    forall a b. (a -> b) -> a -> b
    $ (Scientific -> DynNumber) -> Set Scientific -> Set DynNumber
    forall b a. Ord b => (a -> b) -> Set a -> Set b
    S.map Scientific -> DynNumber
    DynNumber Set Scientific
    i
        toData DValue
    _ = Maybe (Set DynNumber)
    forall a. Maybe a
    Nothing

    instance DynData DynString where
        fromData :: DynString -> DValue
    fromData (DynString Text
    i) = Text -> DValue
    DString Text
    i
        toData :: DValue -> Maybe DynString
    toData (DString Text
    i) = DynString -> Maybe DynString
    forall a. a -> Maybe a
    Just (DynString -> Maybe DynString) -> DynString -> Maybe DynString
    forall a b. (a -> b) -> a -> b
    $ Text -> DynString
    DynString Text
    i
        toData DValue
    _ = Maybe DynString
    forall a. Maybe a
    Nothing

    instance DynData (S.Set DynString) where
        fromData :: Set DynString -> DValue
    fromData Set DynString
    set = Set Text -> DValue
    DStringSet ((DynString -> Text) -> Set DynString -> Set Text
    forall b a. Ord b => (a -> b) -> Set a -> Set b
    S.map DynString -> Text
    unDynString Set DynString
    set)
        toData :: DValue -> Maybe (Set DynString)
    toData (DStringSet Set Text
    i) = Set DynString -> Maybe (Set DynString)
    forall a. a -> Maybe a
    Just (Set DynString -> Maybe (Set DynString))
    -> Set DynString -> Maybe (Set DynString)
    forall a b. (a -> b) -> a -> b
    $ (Text -> DynString) -> Set Text -> Set DynString
    forall b a. Ord b => (a -> b) -> Set a -> Set b
    S.map Text -> DynString
    DynString Set Text
    i
        toData DValue
    _ = Maybe (Set DynString)
    forall a. Maybe a
    Nothing

    instance DynData DynBinary where
        fromData :: DynBinary -> DValue
    fromData (DynBinary ByteString
    i) = ByteString -> DValue
    DBinary ByteString
    i
        toData :: DValue -> Maybe DynBinary
    toData (DBinary ByteString
    i) = DynBinary -> Maybe DynBinary
    forall a. a -> Maybe a
    Just (DynBinary -> Maybe DynBinary) -> DynBinary -> Maybe DynBinary
    forall a b. (a -> b) -> a -> b
    $ ByteString -> DynBinary
    DynBinary ByteString
    i
        toData DValue
    _ = Maybe DynBinary
    forall a. Maybe a
    Nothing

    instance DynData (S.Set DynBinary) where
        fromData :: Set DynBinary -> DValue
    fromData Set DynBinary
    set = Set ByteString -> DValue
    DBinSet ((DynBinary -> ByteString) -> Set DynBinary -> Set ByteString
    forall b a. Ord b => (a -> b) -> Set a -> Set b
    S.map DynBinary -> ByteString
    unDynBinary Set DynBinary
    set)
        toData :: DValue -> Maybe (Set DynBinary)
    toData (DBinSet Set ByteString
    i) = Set DynBinary -> Maybe (Set DynBinary)
    forall a. a -> Maybe a
    Just (Set DynBinary -> Maybe (Set DynBinary))
    -> Set DynBinary -> Maybe (Set DynBinary)
    forall a b. (a -> b) -> a -> b
    $ (ByteString -> DynBinary) -> Set ByteString -> Set DynBinary
    forall b a. Ord b => (a -> b) -> Set a -> Set b
    S.map ByteString -> DynBinary
    DynBinary Set ByteString
    i
        toData DValue
    _ = Maybe (Set DynBinary)
    forall a. Maybe a
    Nothing

    instance DynData DValue where
        fromData :: DValue -> DValue
    fromData = DValue -> DValue
    forall a. a -> a
    id
        toData :: DValue -> Maybe DValue
    toData = DValue -> Maybe DValue
    forall a. a -> Maybe a
    Just

    -------------------------------------------------------------------------------
    -- | Class of Haskell types that can be represented as DynamoDb values.
    --
    -- This is the conversion layer; instantiate this class for your own
    -- types and then use the 'toValue' and 'fromValue' combinators to
    -- convert in application code.
    --
    -- Each Haskell type instantiated with this class will map to a
    -- DynamoDb-supported type that most naturally represents it.
    class DynData (DynRep a) => DynVal a where

        -- | Which of the 'DynData' instances does this data type directly
        -- map to?
        type DynRep a

        -- | Convert to representation
        toRep :: a -> DynRep a

        -- | Convert from representation
        fromRep :: DynRep a -> Maybe a

    -------------------------------------------------------------------------------
    -- | Any singular 'DynVal' can be upgraded to a list.
    instance (DynData (DynRep [a]), DynVal a) => DynVal [a] where
        type DynRep [a] = S.Set (DynRep a)
        fromRep :: DynRep [a] -> Maybe [a]
    fromRep DynRep [a]
    set = (DynRep a -> Maybe a) -> [DynRep a] -> Maybe [a]
    forall (t :: * -> *) (m :: * -> *) a b.
    (Traversable t, Monad m) =>
    (a -> m b) -> t a -> m (t b)
    forall (m :: * -> *) a b. Monad m => (a -> m b) -> [a] -> m [b]
    mapM DynRep a -> Maybe a
    forall a. DynVal a => DynRep a -> Maybe a
    fromRep ([DynRep a] -> Maybe [a]) -> [DynRep a] -> Maybe [a]
    forall a b. (a -> b) -> a -> b
    $ Set (DynRep a) -> [DynRep a]
    forall a. Set a -> [a]
    S.toList Set (DynRep a)
    DynRep [a]
    set
        toRep :: [a] -> DynRep [a]
    toRep [a]
    as = [DynRep a] -> Set (DynRep a)
    forall a. Ord a => [a] -> Set a
    S.fromList ([DynRep a] -> Set (DynRep a)) -> [DynRep a] -> Set (DynRep a)
    forall a b. (a -> b) -> a -> b
    $ (a -> DynRep a) -> [a] -> [DynRep a]
    forall a b. (a -> b) -> [a] -> [b]
    map a -> DynRep a
    forall a. DynVal a => a -> DynRep a
    toRep [a]
    as

    -------------------------------------------------------------------------------
    -- | Any singular 'DynVal' can be upgraded to a 'Set'.
    instance (DynData (DynRep (S.Set a)), DynVal a, Ord a) => DynVal (S.Set a) where
        type DynRep (S.Set a) = S.Set (DynRep a)
        fromRep :: DynRep (Set a) -> Maybe (Set a)
    fromRep DynRep (Set a)
    set = ([a] -> Set a) -> Maybe [a] -> Maybe (Set a)
    forall a b. (a -> b) -> Maybe a -> Maybe b
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    fmap [a] -> Set a
    forall a. Ord a => [a] -> Set a
    S.fromList (Maybe [a] -> Maybe (Set a))
    -> ([DynRep a] -> Maybe [a]) -> [DynRep a] -> Maybe (Set a)
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . (DynRep a -> Maybe a) -> [DynRep a] -> Maybe [a]
    forall (t :: * -> *) (m :: * -> *) a b.
    (Traversable t, Monad m) =>
    (a -> m b) -> t a -> m (t b)
    forall (m :: * -> *) a b. Monad m => (a -> m b) -> [a] -> m [b]
    mapM DynRep a -> Maybe a
    forall a. DynVal a => DynRep a -> Maybe a
    fromRep ([DynRep a] -> Maybe (Set a)) -> [DynRep a] -> Maybe (Set a)
    forall a b. (a -> b) -> a -> b
    $ Set (DynRep a) -> [DynRep a]
    forall a. Set a -> [a]
    S.toList Set (DynRep a)
    DynRep (Set a)
    set
        toRep :: Set a -> DynRep (Set a)
    toRep Set a
    as = (a -> DynRep a) -> Set a -> Set (DynRep a)
    forall b a. Ord b => (a -> b) -> Set a -> Set b
    S.map a -> DynRep a
    forall a. DynVal a => a -> DynRep a
    toRep Set a
    as

    instance DynVal DValue where
        type DynRep DValue = DValue
        fromRep :: DynRep DValue -> Maybe DValue
    fromRep = DValue -> Maybe DValue
    DynRep DValue -> Maybe DValue
    forall a. a -> Maybe a
    Just
        toRep :: DValue -> DynRep DValue
    toRep   = DValue -> DValue
    DValue -> DynRep DValue
    forall a. a -> a
    id

    instance DynVal Bool where
        type DynRep Bool = DynBool
        fromRep :: DynRep Bool -> Maybe Bool
    fromRep (DynBool Bool
    i) = Bool -> Maybe Bool
    forall a. a -> Maybe a
    Just Bool
    i
        toRep :: Bool -> DynRep Bool
    toRep Bool
    i = Bool -> DynBool
    DynBool Bool
    i

    instance DynVal Int where
        type DynRep Int = DynNumber
        fromRep :: DynRep Int -> Maybe Int
    fromRep (DynNumber Scientific
    i) = Scientific -> Maybe Int
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i
        toRep :: Int -> DynRep Int
    toRep Int
    i = Scientific -> DynNumber
    DynNumber (Int -> Scientific
    forall a b. (Integral a, Num b) => a -> b
    fromIntegral Int
    i)

    instance DynVal Int8 where
        type DynRep Int8 = DynNumber
        fromRep :: DynRep Int8 -> Maybe Int8
    fromRep (DynNumber Scientific
    i) = Scientific -> Maybe Int8
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i
        toRep :: Int8 -> DynRep Int8
    toRep Int8
    i = Scientific -> DynNumber
    DynNumber (Int8 -> Scientific
    forall a b. (Integral a, Num b) => a -> b
    fromIntegral Int8
    i)

    instance DynVal Int16 where
        type DynRep Int16 = DynNumber
        fromRep :: DynRep Int16 -> Maybe Int16
    fromRep (DynNumber Scientific
    i) = Scientific -> Maybe Int16
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i
        toRep :: Int16 -> DynRep Int16
    toRep Int16
    i = Scientific -> DynNumber
    DynNumber (Int16 -> Scientific
    forall a b. (Integral a, Num b) => a -> b
    fromIntegral Int16
    i)

    instance DynVal Int32 where
        type DynRep Int32 = DynNumber
        fromRep :: DynRep Int32 -> Maybe Int32
    fromRep (DynNumber Scientific
    i) = Scientific -> Maybe Int32
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i
        toRep :: Int32 -> DynRep Int32
    toRep Int32
    i = Scientific -> DynNumber
    DynNumber (Int32 -> Scientific
    forall a b. (Integral a, Num b) => a -> b
    fromIntegral Int32
    i)

    instance DynVal Int64 where
        type DynRep Int64 = DynNumber
        fromRep :: DynRep Int64 -> Maybe Int64
    fromRep (DynNumber Scientific
    i) = Scientific -> Maybe Int64
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i
        toRep :: Int64 -> DynRep Int64
    toRep Int64
    i = Scientific -> DynNumber
    DynNumber (Int64 -> Scientific
    forall a b. (Integral a, Num b) => a -> b
    fromIntegral Int64
    i)

    instance DynVal Word8 where
        type DynRep Word8 = DynNumber
        fromRep :: DynRep Word8 -> Maybe Word8
    fromRep (DynNumber Scientific
    i) = Scientific -> Maybe Word8
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i
        toRep :: Word8 -> DynRep Word8
    toRep Word8
    i = Scientific -> DynNumber
    DynNumber (Word8 -> Scientific
    forall a b. (Integral a, Num b) => a -> b
    fromIntegral Word8
    i)

    instance DynVal Word16 where
        type DynRep Word16 = DynNumber
        fromRep :: DynRep Word16 -> Maybe Word16
    fromRep (DynNumber Scientific
    i) = Scientific -> Maybe Word16
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i
        toRep :: Word16 -> DynRep Word16
    toRep Word16
    i = Scientific -> DynNumber
    DynNumber (Word16 -> Scientific
    forall a b. (Integral a, Num b) => a -> b
    fromIntegral Word16
    i)

    instance DynVal Word32 where
        type DynRep Word32 = DynNumber
        fromRep :: DynRep Word32 -> Maybe Word32
    fromRep (DynNumber Scientific
    i) = Scientific -> Maybe Word32
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i
        toRep :: Word32 -> DynRep Word32
    toRep Word32
    i = Scientific -> DynNumber
    DynNumber (Word32 -> Scientific
    forall a b. (Integral a, Num b) => a -> b
    fromIntegral Word32
    i)

    instance DynVal Word64 where
        type DynRep Word64 = DynNumber
        fromRep :: DynRep Word64 -> Maybe Word64
    fromRep (DynNumber Scientific
    i) = Scientific -> Maybe Word64
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i
        toRep :: Word64 -> DynRep Word64
    toRep Word64
    i = Scientific -> DynNumber
    DynNumber (Word64 -> Scientific
    forall a b. (Integral a, Num b) => a -> b
    fromIntegral Word64
    i)

    instance DynVal Integer where
        type DynRep Integer = DynNumber
        fromRep :: DynRep Integer -> Maybe Integer
    fromRep (DynNumber Scientific
    i) = Scientific -> Maybe Integer
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i
        toRep :: Integer -> DynRep Integer
    toRep Integer
    i = Scientific -> DynNumber
    DynNumber (Integer -> Scientific
    forall a b. (Integral a, Num b) => a -> b
    fromIntegral Integer
    i)

    instance DynVal T.Text where
        type DynRep T.Text = DynString
        fromRep :: DynRep Text -> Maybe Text
    fromRep (DynString Text
    i) = Text -> Maybe Text
    forall a. a -> Maybe a
    Just Text
    i
        toRep :: Text -> DynRep Text
    toRep Text
    i = Text -> DynString
    DynString Text
    i

    instance DynVal B.ByteString where
        type DynRep B.ByteString = DynBinary
        fromRep :: DynRep ByteString -> Maybe ByteString
    fromRep (DynBinary ByteString
    i) = ByteString -> Maybe ByteString
    forall a. a -> Maybe a
    Just ByteString
    i
        toRep :: ByteString -> DynRep ByteString
    toRep ByteString
    i = ByteString -> DynBinary
    DynBinary ByteString
    i

    instance DynVal Double where
        type DynRep Double = DynNumber
        fromRep :: DynRep Double -> Maybe Double
    fromRep (DynNumber Scientific
    i) = Double -> Maybe Double
    forall a. a -> Maybe a
    Just (Double -> Maybe Double) -> Double -> Maybe Double
    forall a b. (a -> b) -> a -> b
    $ Scientific -> Double
    forall a. RealFloat a => Scientific -> a
    toRealFloat Scientific
    i
        toRep :: Double -> DynRep Double
    toRep Double
    i = Scientific -> DynNumber
    DynNumber (Double -> Scientific
    forall a. RealFloat a => a -> Scientific
    fromFloatDigits Double
    i)

    -------------------------------------------------------------------------------
    -- | Encoded as number of days
    instance DynVal Day where
        type DynRep Day = DynNumber
        fromRep :: DynRep Day -> Maybe Day
    fromRep (DynNumber Scientific
    i) = Integer -> Day
    ModifiedJulianDay (Integer -> Day) -> Maybe Integer -> Maybe Day
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> (Scientific -> Maybe Integer
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i)
        toRep :: Day -> DynRep Day
    toRep (ModifiedJulianDay Integer
    i) = Scientific -> DynNumber
    DynNumber (Integer -> Scientific
    forall a b. (Integral a, Num b) => a -> b
    fromIntegral Integer
    i)

    -------------------------------------------------------------------------------
    -- | Losslessly encoded via 'Integer' picoseconds
    instance DynVal UTCTime where
        type DynRep UTCTime = DynNumber
        fromRep :: DynRep UTCTime -> Maybe UTCTime
    fromRep DynRep UTCTime
    num = Integer -> UTCTime
    fromTS (Integer -> UTCTime) -> Maybe Integer -> Maybe UTCTime
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> DynRep Integer -> Maybe Integer
    forall a. DynVal a => DynRep a -> Maybe a
    fromRep DynRep Integer
    DynRep UTCTime
    num
        toRep :: UTCTime -> DynRep UTCTime
    toRep UTCTime
    x = Integer -> DynRep Integer
    forall a. DynVal a => a -> DynRep a
    toRep (UTCTime -> Integer
    toTS UTCTime
    x)

    -------------------------------------------------------------------------------
    pico :: Rational
    pico :: Rational
    pico = Integer -> Rational
    forall a. Real a => a -> Rational
    toRational (Integer -> Rational) -> Integer -> Rational
    forall a b. (a -> b) -> a -> b
    $ (Integer
    10 :: Integer) Integer -> Integer -> Integer
    forall a b. (Num a, Integral b) => a -> b -> a
    ^ (Integer
    12 :: Integer)

    -------------------------------------------------------------------------------
    dayPico :: Integer
    dayPico :: Integer
    dayPico = Integer
    86400 Integer -> Integer -> Integer
    forall a. Num a => a -> a -> a
    * Rational -> Integer
    forall b. Integral b => Rational -> b
    forall a b. (RealFrac a, Integral b) => a -> b
    round Rational
    pico

    -------------------------------------------------------------------------------
    -- | Convert UTCTime to picoseconds
    --
    -- TODO: Optimize performance?
    toTS :: UTCTime -> Integer
    toTS :: UTCTime -> Integer
    toTS (UTCTime (ModifiedJulianDay Integer
    i) DiffTime
    diff) = Integer
    i' Integer -> Integer -> Integer
    forall a. Num a => a -> a -> a
    + Integer
    diff'
        where
          diff' :: Integer
    diff' = Rational -> Integer
    forall b. Integral b => Rational -> b
    forall a b. (RealFrac a, Integral b) => a -> b
    floor (DiffTime -> Rational
    forall a. Real a => a -> Rational
    toRational DiffTime
    diff Rational -> Rational -> Rational
    forall a. Num a => a -> a -> a
    * Rational
    pico)
          i' :: Integer
    i' = Integer
    i Integer -> Integer -> Integer
    forall a. Num a => a -> a -> a
    * Integer
    dayPico

    -------------------------------------------------------------------------------
    -- | Convert picoseconds to UTCTime
    --
    -- TODO: Optimize performance?
    fromTS :: Integer -> UTCTime
    fromTS :: Integer -> UTCTime
    fromTS Integer
    i = Day -> DiffTime -> UTCTime
    UTCTime (Integer -> Day
    ModifiedJulianDay Integer
    days) DiffTime
    diff
        where
          (Integer
    days, Integer
    secs) = Integer
    i Integer -> Integer -> (Integer, Integer)
    forall a. Integral a => a -> a -> (a, a)
    `divMod` Integer
    dayPico
          diff :: DiffTime
    diff = Rational -> DiffTime
    forall a. Fractional a => Rational -> a
    fromRational ((Integer -> Rational
    forall a. Real a => a -> Rational
    toRational Integer
    secs) Rational -> Rational -> Rational
    forall a. Fractional a => a -> a -> a
    / Rational
    pico)

    -- | Type wrapper for binary data to be written to DynamoDB. Wrap any
    -- 'Serialize' instance in there and 'DynVal' will know how to
    -- automatically handle conversions in binary form.
    newtype Bin a = Bin { forall a. Bin a -> a
    getBin :: a }
        deriving (Bin a -> Bin a -> Bool
    (Bin a -> Bin a -> Bool) -> (Bin a -> Bin a -> Bool) -> Eq (Bin a)
    forall a. Eq a => Bin a -> Bin a -> Bool
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: forall a. Eq a => Bin a -> Bin a -> Bool
    == :: Bin a -> Bin a -> Bool
    $c/= :: forall a. Eq a => Bin a -> Bin a -> Bool
    /= :: Bin a -> Bin a -> Bool
    Eq,Int -> Bin a -> ShowS
    [Bin a] -> ShowS
    Bin a -> String
    (Int -> Bin a -> ShowS)
    -> (Bin a -> String) -> ([Bin a] -> ShowS) -> Show (Bin a)
    forall a. Show a => Int -> Bin a -> ShowS
    forall a. Show a => [Bin a] -> ShowS
    forall a. Show a => Bin a -> String
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: forall a. Show a => Int -> Bin a -> ShowS
    showsPrec :: Int -> Bin a -> ShowS
    $cshow :: forall a. Show a => Bin a -> String
    show :: Bin a -> String
    $cshowList :: forall a. Show a => [Bin a] -> ShowS
    showList :: [Bin a] -> ShowS
    Show,ReadPrec [Bin a]
    ReadPrec (Bin a)
    Int -> ReadS (Bin a)
    ReadS [Bin a]
    (Int -> ReadS (Bin a))
    -> ReadS [Bin a]
    -> ReadPrec (Bin a)
    -> ReadPrec [Bin a]
    -> Read (Bin a)
    forall a. Read a => ReadPrec [Bin a]
    forall a. Read a => ReadPrec (Bin a)
    forall a. Read a => Int -> ReadS (Bin a)
    forall a. Read a => ReadS [Bin a]
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: forall a. Read a => Int -> ReadS (Bin a)
    readsPrec :: Int -> ReadS (Bin a)
    $creadList :: forall a. Read a => ReadS [Bin a]
    readList :: ReadS [Bin a]
    $creadPrec :: forall a. Read a => ReadPrec (Bin a)
    readPrec :: ReadPrec (Bin a)
    $creadListPrec :: forall a. Read a => ReadPrec [Bin a]
    readListPrec :: ReadPrec [Bin a]
    Read,Eq (Bin a)
    Eq (Bin a) =>
    (Bin a -> Bin a -> Ordering)
    -> (Bin a -> Bin a -> Bool)
    -> (Bin a -> Bin a -> Bool)
    -> (Bin a -> Bin a -> Bool)
    -> (Bin a -> Bin a -> Bool)
    -> (Bin a -> Bin a -> Bin a)
    -> (Bin a -> Bin a -> Bin a)
    -> Ord (Bin a)
    Bin a -> Bin a -> Bool
    Bin a -> Bin a -> Ordering
    Bin a -> Bin a -> Bin a
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    forall a. Ord a => Eq (Bin a)
    forall a. Ord a => Bin a -> Bin a -> Bool
    forall a. Ord a => Bin a -> Bin a -> Ordering
    forall a. Ord a => Bin a -> Bin a -> Bin a
    $ccompare :: forall a. Ord a => Bin a -> Bin a -> Ordering
    compare :: Bin a -> Bin a -> Ordering
    $c< :: forall a. Ord a => Bin a -> Bin a -> Bool
    < :: Bin a -> Bin a -> Bool
    $c<= :: forall a. Ord a => Bin a -> Bin a -> Bool
    <= :: Bin a -> Bin a -> Bool
    $c> :: forall a. Ord a => Bin a -> Bin a -> Bool
    > :: Bin a -> Bin a -> Bool
    $c>= :: forall a. Ord a => Bin a -> Bin a -> Bool
    >= :: Bin a -> Bin a -> Bool
    $cmax :: forall a. Ord a => Bin a -> Bin a -> Bin a
    max :: Bin a -> Bin a -> Bin a
    $cmin :: forall a. Ord a => Bin a -> Bin a -> Bin a
    min :: Bin a -> Bin a -> Bin a
    Ord,Typeable,Int -> Bin a
    Bin a -> Int
    Bin a -> [Bin a]
    Bin a -> Bin a
    Bin a -> Bin a -> [Bin a]
    Bin a -> Bin a -> Bin a -> [Bin a]
    (Bin a -> Bin a)
    -> (Bin a -> Bin a)
    -> (Int -> Bin a)
    -> (Bin a -> Int)
    -> (Bin a -> [Bin a])
    -> (Bin a -> Bin a -> [Bin a])
    -> (Bin a -> Bin a -> [Bin a])
    -> (Bin a -> Bin a -> Bin a -> [Bin a])
    -> Enum (Bin a)
    forall a. Enum a => Int -> Bin a
    forall a. Enum a => Bin a -> Int
    forall a. Enum a => Bin a -> [Bin a]
    forall a. Enum a => Bin a -> Bin a
    forall a. Enum a => Bin a -> Bin a -> [Bin a]
    forall a. Enum a => Bin a -> Bin a -> Bin a -> [Bin a]
    forall a.
    (a -> a)
    -> (a -> a)
    -> (Int -> a)
    -> (a -> Int)
    -> (a -> [a])
    -> (a -> a -> [a])
    -> (a -> a -> [a])
    -> (a -> a -> a -> [a])
    -> Enum a
    $csucc :: forall a. Enum a => Bin a -> Bin a
    succ :: Bin a -> Bin a
    $cpred :: forall a. Enum a => Bin a -> Bin a
    pred :: Bin a -> Bin a
    $ctoEnum :: forall a. Enum a => Int -> Bin a
    toEnum :: Int -> Bin a
    $cfromEnum :: forall a. Enum a => Bin a -> Int
    fromEnum :: Bin a -> Int
    $cenumFrom :: forall a. Enum a => Bin a -> [Bin a]
    enumFrom :: Bin a -> [Bin a]
    $cenumFromThen :: forall a. Enum a => Bin a -> Bin a -> [Bin a]
    enumFromThen :: Bin a -> Bin a -> [Bin a]
    $cenumFromTo :: forall a. Enum a => Bin a -> Bin a -> [Bin a]
    enumFromTo :: Bin a -> Bin a -> [Bin a]
    $cenumFromThenTo :: forall a. Enum a => Bin a -> Bin a -> Bin a -> [Bin a]
    enumFromThenTo :: Bin a -> Bin a -> Bin a -> [Bin a]
    Enum)

    instance (Ser.Serialize a) => DynVal (Bin a) where
        type DynRep (Bin a) = DynBinary
        toRep :: Bin a -> DynRep (Bin a)
    toRep (Bin a
    i) = ByteString -> DynBinary
    DynBinary (a -> ByteString
    forall a. Serialize a => a -> ByteString
    Ser.encode a
    i)
        fromRep :: DynRep (Bin a) -> Maybe (Bin a)
    fromRep (DynBinary ByteString
    i) = (String -> Maybe (Bin a))
    -> (a -> Maybe (Bin a)) -> Either String a -> Maybe (Bin a)
    forall a c b. (a -> c) -> (b -> c) -> Either a b -> c
    either (Maybe (Bin a) -> String -> Maybe (Bin a)
    forall a b. a -> b -> a
    const Maybe (Bin a)
    forall a. Maybe a
    Nothing) (Bin a -> Maybe (Bin a)
    forall a. a -> Maybe a
    Just (Bin a -> Maybe (Bin a)) -> (a -> Bin a) -> a -> Maybe (Bin a)
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . a -> Bin a
    forall a. a -> Bin a
    Bin) (Either String a -> Maybe (Bin a))
    -> Either String a -> Maybe (Bin a)
    forall a b. (a -> b) -> a -> b
    $
                                ByteString -> Either String a
    forall a. Serialize a => ByteString -> Either String a
    Ser.decode ByteString
    i

    newtype OldBool = OldBool Bool

    instance DynVal OldBool where
        type DynRep OldBool = DynNumber
        fromRep :: DynRep OldBool -> Maybe OldBool
    fromRep (DynNumber Scientific
    i) = Bool -> OldBool
    OldBool (Bool -> OldBool) -> Maybe Bool -> Maybe OldBool
    forall a b. (a -> b) -> Maybe a -> Maybe b
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    `fmap` do
            (i' :: Int) <- Scientific -> Maybe Int
    forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral Scientific
    i
            case i' of
              Int
    0 -> Bool -> Maybe Bool
    forall a. a -> Maybe a
    forall (m :: * -> *) a. Monad m => a -> m a
    return Bool
    False
              Int
    1 -> Bool -> Maybe Bool
    forall a. a -> Maybe a
    forall (m :: * -> *) a. Monad m => a -> m a
    return Bool
    True
              Int
    _ -> Maybe Bool
    forall a. Maybe a
    Nothing
        toRep :: OldBool -> DynRep OldBool
    toRep (OldBool Bool
    b) = Scientific -> DynNumber
    DynNumber (if Bool
    b then Scientific
    1 else Scientific
    0)

    -------------------------------------------------------------------------------
    -- | Encode a Haskell value.
    toValue :: DynVal a  => a -> DValue
    toValue :: forall a. DynVal a => a -> DValue
    toValue a
    a = DynRep a -> DValue
    forall a. DynData a => a -> DValue
    fromData (DynRep a -> DValue) -> DynRep a -> DValue
    forall a b. (a -> b) -> a -> b
    $ a -> DynRep a
    forall a. DynVal a => a -> DynRep a
    toRep a
    a

    -------------------------------------------------------------------------------
    -- | Decode a Haskell value.
    fromValue :: DynVal a => DValue -> Maybe a
    fromValue :: forall a. DynVal a => DValue -> Maybe a
    fromValue DValue
    d = DValue -> Maybe (DynRep a)
    forall a. DynData a => DValue -> Maybe a
    toData DValue
    d Maybe (DynRep a) -> (DynRep a -> Maybe a) -> Maybe a
    forall a b. Maybe a -> (a -> Maybe b) -> Maybe b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>= DynRep a -> Maybe a
    forall a. DynVal a => DynRep a -> Maybe a
    fromRep

    toIntegral :: (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral :: forall a a1. (Integral a, RealFrac a1) => a1 -> Maybe a
    toIntegral a1
    sc = a -> Maybe a
    forall a. a -> Maybe a
    Just (a -> Maybe a) -> a -> Maybe a
    forall a b. (a -> b) -> a -> b
    $ a1 -> a
    forall b. Integral b => a1 -> b
    forall a b. (RealFrac a, Integral b) => a -> b
    floor a1
    sc

    -- | Value types natively recognized by DynamoDb. We pretty much
    -- exactly reflect the AWS API onto Haskell types.
    data DValue
        = DNull
        | DNum Scientific
        | DString T.Text
        | DBinary B.ByteString
        -- ^ Binary data will automatically be base64 marshalled.
        | DNumSet (S.Set Scientific)
        | DStringSet (S.Set T.Text)
        | DBinSet (S.Set B.ByteString)
        -- ^ Binary data will automatically be base64 marshalled.
        | DBool Bool
        | DBoolSet (S.Set Bool)
        -- ^ Composite data
        | DList (V.Vector DValue)
        | DMap (M.Map T.Text DValue)
        deriving (DValue -> DValue -> Bool
    (DValue -> DValue -> Bool)
    -> (DValue -> DValue -> Bool) -> Eq DValue
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: DValue -> DValue -> Bool
    == :: DValue -> DValue -> Bool
    $c/= :: DValue -> DValue -> Bool
    /= :: DValue -> DValue -> Bool
    Eq,Int -> DValue -> ShowS
    [DValue] -> ShowS
    DValue -> String
    (Int -> DValue -> ShowS)
    -> (DValue -> String) -> ([DValue] -> ShowS) -> Show DValue
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> DValue -> ShowS
    showsPrec :: Int -> DValue -> ShowS
    $cshow :: DValue -> String
    show :: DValue -> String
    $cshowList :: [DValue] -> ShowS
    showList :: [DValue] -> ShowS
    Show,ReadPrec [DValue]
    ReadPrec DValue
    Int -> ReadS DValue
    ReadS [DValue]
    (Int -> ReadS DValue)
    -> ReadS [DValue]
    -> ReadPrec DValue
    -> ReadPrec [DValue]
    -> Read DValue
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS DValue
    readsPrec :: Int -> ReadS DValue
    $creadList :: ReadS [DValue]
    readList :: ReadS [DValue]
    $creadPrec :: ReadPrec DValue
    readPrec :: ReadPrec DValue
    $creadListPrec :: ReadPrec [DValue]
    readListPrec :: ReadPrec [DValue]
    Read,Eq DValue
    Eq DValue =>
    (DValue -> DValue -> Ordering)
    -> (DValue -> DValue -> Bool)
    -> (DValue -> DValue -> Bool)
    -> (DValue -> DValue -> Bool)
    -> (DValue -> DValue -> Bool)
    -> (DValue -> DValue -> DValue)
    -> (DValue -> DValue -> DValue)
    -> Ord DValue
    DValue -> DValue -> Bool
    DValue -> DValue -> Ordering
    DValue -> DValue -> DValue
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: DValue -> DValue -> Ordering
    compare :: DValue -> DValue -> Ordering
    $c< :: DValue -> DValue -> Bool
    < :: DValue -> DValue -> Bool
    $c<= :: DValue -> DValue -> Bool
    <= :: DValue -> DValue -> Bool
    $c> :: DValue -> DValue -> Bool
    > :: DValue -> DValue -> Bool
    $c>= :: DValue -> DValue -> Bool
    >= :: DValue -> DValue -> Bool
    $cmax :: DValue -> DValue -> DValue
    max :: DValue -> DValue -> DValue
    $cmin :: DValue -> DValue -> DValue
    min :: DValue -> DValue -> DValue
    Ord,Typeable)

    instance IsString DValue where
        fromString :: String -> DValue
    fromString String
    t = Text -> DValue
    DString (String -> Text
    T.pack String
    t)

    -------------------------------------------------------------------------------
    -- | Primary keys consist of either just a Hash key (mandatory) or a
    -- hash key and a range key (optional).
    data PrimaryKey = PrimaryKey {
          PrimaryKey -> Attribute
    pkHash  :: Attribute
        , PrimaryKey -> Maybe Attribute
    pkRange :: Maybe Attribute
        } deriving (ReadPrec [PrimaryKey]
    ReadPrec PrimaryKey
    Int -> ReadS PrimaryKey
    ReadS [PrimaryKey]
    (Int -> ReadS PrimaryKey)
    -> ReadS [PrimaryKey]
    -> ReadPrec PrimaryKey
    -> ReadPrec [PrimaryKey]
    -> Read PrimaryKey
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS PrimaryKey
    readsPrec :: Int -> ReadS PrimaryKey
    $creadList :: ReadS [PrimaryKey]
    readList :: ReadS [PrimaryKey]
    $creadPrec :: ReadPrec PrimaryKey
    readPrec :: ReadPrec PrimaryKey
    $creadListPrec :: ReadPrec [PrimaryKey]
    readListPrec :: ReadPrec [PrimaryKey]
    Read,Int -> PrimaryKey -> ShowS
    [PrimaryKey] -> ShowS
    PrimaryKey -> String
    (Int -> PrimaryKey -> ShowS)
    -> (PrimaryKey -> String)
    -> ([PrimaryKey] -> ShowS)
    -> Show PrimaryKey
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> PrimaryKey -> ShowS
    showsPrec :: Int -> PrimaryKey -> ShowS
    $cshow :: PrimaryKey -> String
    show :: PrimaryKey -> String
    $cshowList :: [PrimaryKey] -> ShowS
    showList :: [PrimaryKey] -> ShowS
    Show,Eq PrimaryKey
    Eq PrimaryKey =>
    (PrimaryKey -> PrimaryKey -> Ordering)
    -> (PrimaryKey -> PrimaryKey -> Bool)
    -> (PrimaryKey -> PrimaryKey -> Bool)
    -> (PrimaryKey -> PrimaryKey -> Bool)
    -> (PrimaryKey -> PrimaryKey -> Bool)
    -> (PrimaryKey -> PrimaryKey -> PrimaryKey)
    -> (PrimaryKey -> PrimaryKey -> PrimaryKey)
    -> Ord PrimaryKey
    PrimaryKey -> PrimaryKey -> Bool
    PrimaryKey -> PrimaryKey -> Ordering
    PrimaryKey -> PrimaryKey -> PrimaryKey
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: PrimaryKey -> PrimaryKey -> Ordering
    compare :: PrimaryKey -> PrimaryKey -> Ordering
    $c< :: PrimaryKey -> PrimaryKey -> Bool
    < :: PrimaryKey -> PrimaryKey -> Bool
    $c<= :: PrimaryKey -> PrimaryKey -> Bool
    <= :: PrimaryKey -> PrimaryKey -> Bool
    $c> :: PrimaryKey -> PrimaryKey -> Bool
    > :: PrimaryKey -> PrimaryKey -> Bool
    $c>= :: PrimaryKey -> PrimaryKey -> Bool
    >= :: PrimaryKey -> PrimaryKey -> Bool
    $cmax :: PrimaryKey -> PrimaryKey -> PrimaryKey
    max :: PrimaryKey -> PrimaryKey -> PrimaryKey
    $cmin :: PrimaryKey -> PrimaryKey -> PrimaryKey
    min :: PrimaryKey -> PrimaryKey -> PrimaryKey
    Ord,PrimaryKey -> PrimaryKey -> Bool
    (PrimaryKey -> PrimaryKey -> Bool)
    -> (PrimaryKey -> PrimaryKey -> Bool) -> Eq PrimaryKey
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: PrimaryKey -> PrimaryKey -> Bool
    == :: PrimaryKey -> PrimaryKey -> Bool
    $c/= :: PrimaryKey -> PrimaryKey -> Bool
    /= :: PrimaryKey -> PrimaryKey -> Bool
    Eq,Typeable)

    -------------------------------------------------------------------------------
    -- | Construct a hash-only primary key.
    --
    -- >>> hk "user-id" "ABCD"
    --
    -- >>> hk "user-id" (mkVal 23)
    hk :: T.Text -> DValue -> PrimaryKey
    hk :: Text -> DValue -> PrimaryKey
    hk Text
    k DValue
    v = Attribute -> Maybe Attribute -> PrimaryKey
    PrimaryKey (Text -> DValue -> Attribute
    forall a. DynVal a => Text -> a -> Attribute
    attr Text
    k DValue
    v) Maybe Attribute
    forall a. Maybe a
    Nothing

    -------------------------------------------------------------------------------
    -- | Construct a hash-and-range primary key.
    hrk :: T.Text                   -- ^ Hash key name
        -> DValue                   -- ^ Hash key value
        -> T.Text                   -- ^ Range key name
        -> DValue                   -- ^ Range key value
        -> PrimaryKey
    hrk :: Text -> DValue -> Text -> DValue -> PrimaryKey
    hrk Text
    k DValue
    v Text
    k2 DValue
    v2 = Attribute -> Maybe Attribute -> PrimaryKey
    PrimaryKey (Text -> DValue -> Attribute
    forall a. DynVal a => Text -> a -> Attribute
    attr Text
    k DValue
    v) (Attribute -> Maybe Attribute
    forall a. a -> Maybe a
    Just (Text -> DValue -> Attribute
    forall a. DynVal a => Text -> a -> Attribute
    attr Text
    k2 DValue
    v2))

    instance ToJSON PrimaryKey where
        toJSON :: PrimaryKey -> Value
    toJSON (PrimaryKey Attribute
    h Maybe Attribute
    Nothing) = Attribute -> Value
    forall a. ToJSON a => a -> Value
    toJSON Attribute
    h
        toJSON (PrimaryKey Attribute
    h (Just Attribute
    r)) =
          let Object Object
    p1 = Attribute -> Value
    forall a. ToJSON a => a -> Value
    toJSON Attribute
    h
              Object Object
    p2 = Attribute -> Value
    forall a. ToJSON a => a -> Value
    toJSON Attribute
    r
          in Object -> Value
    Object (Object
    p1 Object -> Object -> Object
    forall v. KeyMap v -> KeyMap v -> KeyMap v
    `KM.union` Object
    p2)

    instance FromJSON PrimaryKey where
        parseJSON :: Value -> Parser PrimaryKey
    parseJSON Value
    p = do
           l <- Value -> Parser [PrimaryKey]
    listPKey Value
    p
           case length l of
              Int
    1 -> PrimaryKey -> Parser PrimaryKey
    forall a. a -> Parser a
    forall (m :: * -> *) a. Monad m => a -> m a
    return (PrimaryKey -> Parser PrimaryKey)
    -> PrimaryKey -> Parser PrimaryKey
    forall a b. (a -> b) -> a -> b
    $ [PrimaryKey] -> PrimaryKey
    forall a. HasCallStack => [a] -> a
    head [PrimaryKey]
    l
              Int
    _ -> String -> Parser PrimaryKey
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail String
    "Unable to parse PrimaryKey"
          where listPKey :: Value -> Parser [PrimaryKey]
    listPKey Value
    p'= ((Key, DValue) -> PrimaryKey) -> [(Key, DValue)] -> [PrimaryKey]
    forall a b. (a -> b) -> [a] -> [b]
    map (\(Key
    k,DValue
    dval)-> Text -> DValue -> PrimaryKey
    hk (Key -> Text
    AK.toText Key
    k) DValue
    dval)
                              ([(Key, DValue)] -> [PrimaryKey])
    -> (KeyMap DValue -> [(Key, DValue)])
    -> KeyMap DValue
    -> [PrimaryKey]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . KeyMap DValue -> [(Key, DValue)]
    forall v. KeyMap v -> [(Key, v)]
    KM.toList (KeyMap DValue -> [PrimaryKey])
    -> Parser (KeyMap DValue) -> Parser [PrimaryKey]
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Value -> Parser (KeyMap DValue)
    forall a. FromJSON a => Value -> Parser a
    parseJSON Value
    p'

    -- | A key-value pair
    data Attribute = Attribute {
          Attribute -> Text
    attrName :: T.Text
        , Attribute -> DValue
    attrVal  :: DValue
        } deriving (ReadPrec [Attribute]
    ReadPrec Attribute
    Int -> ReadS Attribute
    ReadS [Attribute]
    (Int -> ReadS Attribute)
    -> ReadS [Attribute]
    -> ReadPrec Attribute
    -> ReadPrec [Attribute]
    -> Read Attribute
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS Attribute
    readsPrec :: Int -> ReadS Attribute
    $creadList :: ReadS [Attribute]
    readList :: ReadS [Attribute]
    $creadPrec :: ReadPrec Attribute
    readPrec :: ReadPrec Attribute
    $creadListPrec :: ReadPrec [Attribute]
    readListPrec :: ReadPrec [Attribute]
    Read,Int -> Attribute -> ShowS
    [Attribute] -> ShowS
    Attribute -> String
    (Int -> Attribute -> ShowS)
    -> (Attribute -> String)
    -> ([Attribute] -> ShowS)
    -> Show Attribute
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> Attribute -> ShowS
    showsPrec :: Int -> Attribute -> ShowS
    $cshow :: Attribute -> String
    show :: Attribute -> String
    $cshowList :: [Attribute] -> ShowS
    showList :: [Attribute] -> ShowS
    Show,Eq Attribute
    Eq Attribute =>
    (Attribute -> Attribute -> Ordering)
    -> (Attribute -> Attribute -> Bool)
    -> (Attribute -> Attribute -> Bool)
    -> (Attribute -> Attribute -> Bool)
    -> (Attribute -> Attribute -> Bool)
    -> (Attribute -> Attribute -> Attribute)
    -> (Attribute -> Attribute -> Attribute)
    -> Ord Attribute
    Attribute -> Attribute -> Bool
    Attribute -> Attribute -> Ordering
    Attribute -> Attribute -> Attribute
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: Attribute -> Attribute -> Ordering
    compare :: Attribute -> Attribute -> Ordering
    $c< :: Attribute -> Attribute -> Bool
    < :: Attribute -> Attribute -> Bool
    $c<= :: Attribute -> Attribute -> Bool
    <= :: Attribute -> Attribute -> Bool
    $c> :: Attribute -> Attribute -> Bool
    > :: Attribute -> Attribute -> Bool
    $c>= :: Attribute -> Attribute -> Bool
    >= :: Attribute -> Attribute -> Bool
    $cmax :: Attribute -> Attribute -> Attribute
    max :: Attribute -> Attribute -> Attribute
    $cmin :: Attribute -> Attribute -> Attribute
    min :: Attribute -> Attribute -> Attribute
    Ord,Attribute -> Attribute -> Bool
    (Attribute -> Attribute -> Bool)
    -> (Attribute -> Attribute -> Bool) -> Eq Attribute
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: Attribute -> Attribute -> Bool
    == :: Attribute -> Attribute -> Bool
    $c/= :: Attribute -> Attribute -> Bool
    /= :: Attribute -> Attribute -> Bool
    Eq,Typeable)

    -- | Convert attribute to a tuple representation
    attrTuple :: Attribute -> (T.Text, DValue)
    attrTuple :: Attribute -> (Text, DValue)
    attrTuple (Attribute Text
    a DValue
    b) = (Text
    a,DValue
    b)

    -- | Convenience function for constructing key-value pairs
    attr :: DynVal a => T.Text -> a -> Attribute
    attr :: forall a. DynVal a => Text -> a -> Attribute
    attr Text
    k a
    v = Text -> DValue -> Attribute
    Attribute Text
    k (a -> DValue
    forall a. DynVal a => a -> DValue
    toValue a
    v)

    -- | 'attr' with type witness to help with cases where you're manually
    -- supplying values in code.
    --
    -- >> item [ attrAs text "name" "john" ]
    attrAs :: DynVal a => Proxy a -> T.Text -> a -> Attribute
    attrAs :: forall a. DynVal a => Proxy a -> Text -> a -> Attribute
    attrAs Proxy a
    _ Text
    k a
    v = Text -> a -> Attribute
    forall a. DynVal a => Text -> a -> Attribute
    attr Text
    k a
    v

    -- | Type witness for 'Text'. See 'attrAs'.
    text :: Proxy T.Text
    text :: Proxy Text
    text = Proxy Text
    forall {k} (t :: k). Proxy t
    Proxy

    -- | Type witness for 'Integer'. See 'attrAs'.
    int :: Proxy Integer
    int :: Proxy Integer
    int = Proxy Integer
    forall {k} (t :: k). Proxy t
    Proxy

    -- | Type witness for 'Double'. See 'attrAs'.
    double :: Proxy Double
    double :: Proxy Double
    double = Proxy Double
    forall {k} (t :: k). Proxy t
    Proxy

    -- | A DynamoDb object is simply a key-value dictionary.
    type Item = M.Map T.Text DValue

    -------------------------------------------------------------------------------
    -- | Pack a list of attributes into an Item.
    item :: [Attribute] -> Item
    item :: [Attribute] -> Map Text DValue
    item = [(Text, DValue)] -> Map Text DValue
    forall k a. Ord k => [(k, a)] -> Map k a
    M.fromList ([(Text, DValue)] -> Map Text DValue)
    -> ([Attribute] -> [(Text, DValue)])
    -> [Attribute]
    -> Map Text DValue
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . (Attribute -> (Text, DValue)) -> [Attribute] -> [(Text, DValue)]
    forall a b. (a -> b) -> [a] -> [b]
    map Attribute -> (Text, DValue)
    attrTuple

    -------------------------------------------------------------------------------
    -- | Unpack an 'Item' into a list of attributes.
    attributes :: M.Map T.Text DValue -> [Attribute]
    attributes :: Map Text DValue -> [Attribute]
    attributes = ((Text, DValue) -> Attribute) -> [(Text, DValue)] -> [Attribute]
    forall a b. (a -> b) -> [a] -> [b]
    map (\ (Text
    k, DValue
    v) -> Text -> DValue -> Attribute
    Attribute Text
    k DValue
    v) ([(Text, DValue)] -> [Attribute])
    -> (Map Text DValue -> [(Text, DValue)])
    -> Map Text DValue
    -> [Attribute]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Map Text DValue -> [(Text, DValue)]
    forall k a. Map k a -> [(k, a)]
    M.toList

    showT :: Show a => a -> T.Text
    showT :: forall a. Show a => a -> Text
    showT = String -> Text
    T.pack (String -> Text) -> (a -> String) -> a -> Text
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . a -> String
    forall a. Show a => a -> String
    show

    instance ToJSON DValue where
        toJSON :: DValue -> Value
    toJSON DValue
    DNull = [Pair] -> Value
    object [Key
    "NULL" Key -> Bool -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Bool
    True]
        toJSON (DNum Scientific
    i) = [Pair] -> Value
    object [Key
    "N" Key -> Text -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Scientific -> Text
    forall a. Show a => a -> Text
    showT Scientific
    i]
        toJSON (DString Text
    i) = [Pair] -> Value
    object [Key
    "S" Key -> Text -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Text
    i]
        toJSON (DBinary ByteString
    i) = [Pair] -> Value
    object [Key
    "B" Key -> Text -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= (ByteString -> Text
    T.decodeUtf8 (ByteString -> Text) -> ByteString -> Text
    forall a b. (a -> b) -> a -> b
    $ ByteString -> ByteString
    Base64.encode ByteString
    i)]
        toJSON (DNumSet Set Scientific
    i) = [Pair] -> Value
    object [Key
    "NS" Key -> [Text] -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= (Scientific -> Text) -> [Scientific] -> [Text]
    forall a b. (a -> b) -> [a] -> [b]
    map Scientific -> Text
    forall a. Show a => a -> Text
    showT (Set Scientific -> [Scientific]
    forall a. Set a -> [a]
    S.toList Set Scientific
    i)]
        toJSON (DStringSet Set Text
    i) = [Pair] -> Value
    object [Key
    "SS" Key -> [Text] -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Set Text -> [Text]
    forall a. Set a -> [a]
    S.toList Set Text
    i]
        toJSON (DBinSet Set ByteString
    i) = [Pair] -> Value
    object [Key
    "BS" Key -> [Text] -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= (ByteString -> Text) -> [ByteString] -> [Text]
    forall a b. (a -> b) -> [a] -> [b]
    map (ByteString -> Text
    T.decodeUtf8 (ByteString -> Text)
    -> (ByteString -> ByteString) -> ByteString -> Text
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ByteString -> ByteString
    Base64.encode) (Set ByteString -> [ByteString]
    forall a. Set a -> [a]
    S.toList Set ByteString
    i)]
        toJSON (DBool Bool
    i) = [Pair] -> Value
    object [Key
    "BOOL" Key -> Bool -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Bool
    i]
        toJSON (DList Vector DValue
    i) = [Pair] -> Value
    object [Key
    "L" Key -> Vector DValue -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Vector DValue
    i]
        toJSON (DMap Map Text DValue
    i) = [Pair] -> Value
    object [Key
    "M" Key -> Map Text DValue -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Map Text DValue
    i]
        toJSON DValue
    x = String -> Value
    forall a. HasCallStack => String -> a
    error (String -> Value) -> String -> Value
    forall a b. (a -> b) -> a -> b
    $ String
    "aws: bug: DynamoDB can't handle " String -> ShowS
    forall a. [a] -> [a] -> [a]
    ++ DValue -> String
    forall a. Show a => a -> String
    show DValue
    x

    instance FromJSON DValue where
        parseJSON :: Value -> Parser DValue
    parseJSON Value
    o = do
          (obj :: [(T.Text, Value)]) <- Map Text Value -> [(Text, Value)]
    forall k a. Map k a -> [(k, a)]
    M.toList (Map Text Value -> [(Text, Value)])
    -> Parser (Map Text Value) -> Parser [(Text, Value)]
    forall (m :: * -> *) a1 r. Monad m => (a1 -> r) -> m a1 -> m r
    `liftM` Value -> Parser (Map Text Value)
    forall a. FromJSON a => Value -> Parser a
    parseJSON Value
    o
          case obj of
            [(Text
    "NULL", Value
    _)] -> DValue -> Parser DValue
    forall a. a -> Parser a
    forall (m :: * -> *) a. Monad m => a -> m a
    return DValue
    DNull
            [(Text
    "N", Value
    numStr)] -> Scientific -> DValue
    DNum (Scientific -> DValue) -> Parser Scientific -> Parser DValue
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Value -> Parser Scientific
    forall {m :: * -> *}. MonadFail m => Value -> m Scientific
    parseScientific Value
    numStr
            [(Text
    "S", Value
    str)] -> Text -> DValue
    DString (Text -> DValue) -> Parser Text -> Parser DValue
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Value -> Parser Text
    forall a. FromJSON a => Value -> Parser a
    parseJSON Value
    str
            [(Text
    "B", Value
    bin)] -> do
                res <- (ByteString -> Either String ByteString
    Base64.decode (ByteString -> Either String ByteString)
    -> (Text -> ByteString) -> Text -> Either String ByteString
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Text -> ByteString
    T.encodeUtf8) (Text -> Either String ByteString)
    -> Parser Text -> Parser (Either String ByteString)
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Value -> Parser Text
    forall a. FromJSON a => Value -> Parser a
    parseJSON Value
    bin
                either fail (return . DBinary) res
            [(Text
    "NS", Value
    s)] -> do xs <- (Value -> Parser Scientific) -> [Value] -> Parser [Scientific]
    forall (t :: * -> *) (m :: * -> *) a b.
    (Traversable t, Monad m) =>
    (a -> m b) -> t a -> m (t b)
    forall (m :: * -> *) a b. Monad m => (a -> m b) -> [a] -> m [b]
    mapM Value -> Parser Scientific
    forall {m :: * -> *}. MonadFail m => Value -> m Scientific
    parseScientific ([Value] -> Parser [Scientific])
    -> Parser [Value] -> Parser [Scientific]
    forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
    =<< Value -> Parser [Value]
    forall a. FromJSON a => Value -> Parser a
    parseJSON Value
    s
                              return $ DNumSet $ S.fromList xs
            [(Text
    "SS", Value
    s)] -> Set Text -> DValue
    DStringSet (Set Text -> DValue) -> Parser (Set Text) -> Parser DValue
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Value -> Parser (Set Text)
    forall a. FromJSON a => Value -> Parser a
    parseJSON Value
    s
            [(Text
    "BS", Value
    s)] -> do
                xs <- (Text -> Parser ByteString) -> [Text] -> Parser [ByteString]
    forall (t :: * -> *) (m :: * -> *) a b.
    (Traversable t, Monad m) =>
    (a -> m b) -> t a -> m (t b)
    forall (m :: * -> *) a b. Monad m => (a -> m b) -> [a] -> m [b]
    mapM ((String -> Parser ByteString)
    -> (ByteString -> Parser ByteString)
    -> Either String ByteString
    -> Parser ByteString
    forall a c b. (a -> c) -> (b -> c) -> Either a b -> c
    either String -> Parser ByteString
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail ByteString -> Parser ByteString
    forall a. a -> Parser a
    forall (m :: * -> *) a. Monad m => a -> m a
    return (Either String ByteString -> Parser ByteString)
    -> (Text -> Either String ByteString) -> Text -> Parser ByteString
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ByteString -> Either String ByteString
    Base64.decode (ByteString -> Either String ByteString)
    -> (Text -> ByteString) -> Text -> Either String ByteString
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Text -> ByteString
    T.encodeUtf8)
                      ([Text] -> Parser [ByteString])
    -> Parser [Text] -> Parser [ByteString]
    forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
    =<< Value -> Parser [Text]
    forall a. FromJSON a => Value -> Parser a
    parseJSON Value
    s
                return $ DBinSet $ S.fromList xs
            [(Text
    "BOOL", Value
    b)] -> Bool -> DValue
    DBool (Bool -> DValue) -> Parser Bool -> Parser DValue
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Value -> Parser Bool
    forall a. FromJSON a => Value -> Parser a
    parseJSON Value
    b
            [(Text
    "L", Value
    attrs)] -> Vector DValue -> DValue
    DList (Vector DValue -> DValue)
    -> Parser (Vector DValue) -> Parser DValue
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Value -> Parser (Vector DValue)
    forall a. FromJSON a => Value -> Parser a
    parseJSON Value
    attrs
            [(Text
    "M", Value
    attrs)] -> Map Text DValue -> DValue
    DMap (Map Text DValue -> DValue)
    -> Parser (Map Text DValue) -> Parser DValue
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Value -> Parser (Map Text DValue)
    forall a. FromJSON a => Value -> Parser a
    parseJSON Value
    attrs

            [(Text, Value)]
    x -> String -> Parser DValue
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail (String -> Parser DValue) -> String -> Parser DValue
    forall a b. (a -> b) -> a -> b
    $ String
    "aws: unknown dynamodb value: " String -> ShowS
    forall a. [a] -> [a] -> [a]
    ++ [(Text, Value)] -> String
    forall a. Show a => a -> String
    show [(Text, Value)]
    x

          where
            parseScientific :: Value -> m Scientific
    parseScientific (String Text
    str) =
                case Parser Scientific -> Text -> Either String Scientific
    forall a. Parser a -> Text -> Either String a
    Atto.parseOnly Parser Scientific
    Atto.scientific Text
    str of
                  Left String
    e -> String -> m Scientific
    forall a. String -> m a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail (String
    "parseScientific failed: " String -> ShowS
    forall a. [a] -> [a] -> [a]
    ++ String
    e)
                  Right Scientific
    a -> Scientific -> m Scientific
    forall a. a -> m a
    forall (m :: * -> *) a. Monad m => a -> m a
    return Scientific
    a
            parseScientific (Number Scientific
    n) = Scientific -> m Scientific
    forall a. a -> m a
    forall (m :: * -> *) a. Monad m => a -> m a
    return Scientific
    n
            parseScientific Value
    _ = String -> m Scientific
    forall a. String -> m a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail String
    "Unexpected JSON type in parseScientific"

    instance ToJSON Attribute where
        toJSON :: Attribute -> Value
    toJSON Attribute
    a = [Pair] -> Value
    object ([Pair] -> Value) -> [Pair] -> Value
    forall a b. (a -> b) -> a -> b
    $ [Attribute -> Pair
    attributeJson Attribute
    a]

    -------------------------------------------------------------------------------
    -- | Parse a JSON object that contains attributes
    parseAttributeJson :: Value -> A.Parser [Attribute]
    parseAttributeJson :: Value -> Parser [Attribute]
    parseAttributeJson (Object Object
    v) = (Pair -> Parser Attribute) -> [Pair] -> Parser [Attribute]
    forall (t :: * -> *) (m :: * -> *) a b.
    (Traversable t, Monad m) =>
    (a -> m b) -> t a -> m (t b)
    forall (m :: * -> *) a b. Monad m => (a -> m b) -> [a] -> m [b]
    mapM Pair -> Parser Attribute
    conv ([Pair] -> Parser [Attribute]) -> [Pair] -> Parser [Attribute]
    forall a b. (a -> b) -> a -> b
    $ Object -> [Pair]
    forall v. KeyMap v -> [(Key, v)]
    KM.toList Object
    v
        where
          conv :: Pair -> Parser Attribute
    conv (Key
    k, Value
    o) = Text -> DValue -> Attribute
    Attribute (Key -> Text
    AK.toText Key
    k) (DValue -> Attribute) -> Parser DValue -> Parser Attribute
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Value -> Parser DValue
    forall a. FromJSON a => Value -> Parser a
    parseJSON Value
    o
    parseAttributeJson Value
    _ = String -> Parser [Attribute]
    forall a. HasCallStack => String -> a
    error String
    "Attribute JSON must be an Object"

    -- | Convert into JSON object for AWS.
    attributesJson :: [Attribute] -> Value
    attributesJson :: [Attribute] -> Value
    attributesJson [Attribute]
    as = [Pair] -> Value
    object ([Pair] -> Value) -> [Pair] -> Value
    forall a b. (a -> b) -> a -> b
    $ (Attribute -> Pair) -> [Attribute] -> [Pair]
    forall a b. (a -> b) -> [a] -> [b]
    map Attribute -> Pair
    attributeJson [Attribute]
    as

    -- | Convert into JSON pair
    attributeJson :: Attribute -> Pair
    attributeJson :: Attribute -> Pair
    attributeJson (Attribute Text
    nm DValue
    v) = Text -> Key
    AK.fromText Text
    nm Key -> DValue -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= DValue
    v

    -------------------------------------------------------------------------------
    -- | Errors defined by AWS.
    data DdbErrCode
        = AccessDeniedException
        | ConditionalCheckFailedException
        | IncompleteSignatureException
        | InvalidSignatureException
        | LimitExceededException
        | MissingAuthenticationTokenException
        | ProvisionedThroughputExceededException
        | ResourceInUseException
        | ResourceNotFoundException
        | ThrottlingException
        | ValidationException
        | RequestTooLarge
        | InternalFailure
        | InternalServerError
        | ServiceUnavailableException
        | SerializationException
        -- ^ Raised by AWS when the request JSON is missing fields or is
        -- somehow malformed.
        deriving (ReadPrec [DdbErrCode]
    ReadPrec DdbErrCode
    Int -> ReadS DdbErrCode
    ReadS [DdbErrCode]
    (Int -> ReadS DdbErrCode)
    -> ReadS [DdbErrCode]
    -> ReadPrec DdbErrCode
    -> ReadPrec [DdbErrCode]
    -> Read DdbErrCode
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS DdbErrCode
    readsPrec :: Int -> ReadS DdbErrCode
    $creadList :: ReadS [DdbErrCode]
    readList :: ReadS [DdbErrCode]
    $creadPrec :: ReadPrec DdbErrCode
    readPrec :: ReadPrec DdbErrCode
    $creadListPrec :: ReadPrec [DdbErrCode]
    readListPrec :: ReadPrec [DdbErrCode]
    Read,Int -> DdbErrCode -> ShowS
    [DdbErrCode] -> ShowS
    DdbErrCode -> String
    (Int -> DdbErrCode -> ShowS)
    -> (DdbErrCode -> String)
    -> ([DdbErrCode] -> ShowS)
    -> Show DdbErrCode
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> DdbErrCode -> ShowS
    showsPrec :: Int -> DdbErrCode -> ShowS
    $cshow :: DdbErrCode -> String
    show :: DdbErrCode -> String
    $cshowList :: [DdbErrCode] -> ShowS
    showList :: [DdbErrCode] -> ShowS
    Show,DdbErrCode -> DdbErrCode -> Bool
    (DdbErrCode -> DdbErrCode -> Bool)
    -> (DdbErrCode -> DdbErrCode -> Bool) -> Eq DdbErrCode
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: DdbErrCode -> DdbErrCode -> Bool
    == :: DdbErrCode -> DdbErrCode -> Bool
    $c/= :: DdbErrCode -> DdbErrCode -> Bool
    /= :: DdbErrCode -> DdbErrCode -> Bool
    Eq,Typeable)

    -------------------------------------------------------------------------------
    -- | Whether the action should be retried based on the received error.
    shouldRetry :: DdbErrCode -> Bool
    shouldRetry :: DdbErrCode -> Bool
    shouldRetry DdbErrCode
    e = DdbErrCode -> Bool
    go DdbErrCode
    e
        where
          go :: DdbErrCode -> Bool
    go DdbErrCode
    LimitExceededException = Bool
    True
          go DdbErrCode
    ProvisionedThroughputExceededException = Bool
    True
          go DdbErrCode
    ResourceInUseException = Bool
    True
          go DdbErrCode
    ThrottlingException = Bool
    True
          go DdbErrCode
    InternalFailure = Bool
    True
          go DdbErrCode
    InternalServerError = Bool
    True
          go DdbErrCode
    ServiceUnavailableException = Bool
    True
          go DdbErrCode
    _ = Bool
    False

    -------------------------------------------------------------------------------
    -- | Errors related to this library.
    data DdbLibraryError
        = UnknownDynamoErrCode T.Text
        -- ^ A DynamoDB error code we do not know about.
        | JsonProtocolError Value T.Text
        -- ^ A JSON response we could not parse.
        deriving (Int -> DdbLibraryError -> ShowS
    [DdbLibraryError] -> ShowS
    DdbLibraryError -> String
    (Int -> DdbLibraryError -> ShowS)
    -> (DdbLibraryError -> String)
    -> ([DdbLibraryError] -> ShowS)
    -> Show DdbLibraryError
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> DdbLibraryError -> ShowS
    showsPrec :: Int -> DdbLibraryError -> ShowS
    $cshow :: DdbLibraryError -> String
    show :: DdbLibraryError -> String
    $cshowList :: [DdbLibraryError] -> ShowS
    showList :: [DdbLibraryError] -> ShowS
    Show,DdbLibraryError -> DdbLibraryError -> Bool
    (DdbLibraryError -> DdbLibraryError -> Bool)
    -> (DdbLibraryError -> DdbLibraryError -> Bool)
    -> Eq DdbLibraryError
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: DdbLibraryError -> DdbLibraryError -> Bool
    == :: DdbLibraryError -> DdbLibraryError -> Bool
    $c/= :: DdbLibraryError -> DdbLibraryError -> Bool
    /= :: DdbLibraryError -> DdbLibraryError -> Bool
    Eq,Typeable)

    -- | Potential errors raised by DynamoDB
    data DdbError = DdbError {
          DdbError -> Int
    ddbStatusCode :: Int
        -- ^ 200 if successful, 400 for client errors and 500 for
        -- server-side errors.
        , DdbError -> DdbErrCode
    ddbErrCode    :: DdbErrCode
        , DdbError -> Text
    ddbErrMsg     :: T.Text
        } deriving (Int -> DdbError -> ShowS
    [DdbError] -> ShowS
    DdbError -> String
    (Int -> DdbError -> ShowS)
    -> (DdbError -> String) -> ([DdbError] -> ShowS) -> Show DdbError
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> DdbError -> ShowS
    showsPrec :: Int -> DdbError -> ShowS
    $cshow :: DdbError -> String
    show :: DdbError -> String
    $cshowList :: [DdbError] -> ShowS
    showList :: [DdbError] -> ShowS
    Show,DdbError -> DdbError -> Bool
    (DdbError -> DdbError -> Bool)
    -> (DdbError -> DdbError -> Bool) -> Eq DdbError
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: DdbError -> DdbError -> Bool
    == :: DdbError -> DdbError -> Bool
    $c/= :: DdbError -> DdbError -> Bool
    /= :: DdbError -> DdbError -> Bool
    Eq,Typeable)

    instance C.Exception DdbError
    instance C.Exception DdbLibraryError

    -- | Response metadata that is present in every DynamoDB response.
    data DdbResponse = DdbResponse {
          DdbResponse -> Maybe Text
    ddbrCrc   :: Maybe T.Text
        , DdbResponse -> Maybe Text
    ddbrMsgId :: Maybe T.Text
        }

    instance Loggable DdbResponse where
        toLogText :: DdbResponse -> Text
    toLogText (DdbResponse Maybe Text
    id2 Maybe Text
    rid) =
            Text
    "DynamoDB: request ID=" Text -> Text -> Text
    forall a. Monoid a => a -> a -> a
    `mappend`
            Text -> Maybe Text -> Text
    forall a. a -> Maybe a -> a
    fromMaybe Text
    "<none>" Maybe Text
    rid Text -> Text -> Text
    forall a. Monoid a => a -> a -> a
    `mappend`
            Text
    ", x-amz-id-2=" Text -> Text -> Text
    forall a. Monoid a => a -> a -> a
    `mappend`
            Text -> Maybe Text -> Text
    forall a. a -> Maybe a -> a
    fromMaybe Text
    "<none>" Maybe Text
    id2

    instance Sem.Semigroup DdbResponse where
        DdbResponse
    a <> :: DdbResponse -> DdbResponse -> DdbResponse
    <> DdbResponse
    b = Maybe Text -> Maybe Text -> DdbResponse
    DdbResponse (DdbResponse -> Maybe Text
    ddbrCrc DdbResponse
    a Maybe Text -> Maybe Text -> Maybe Text
    forall a. Maybe a -> Maybe a -> Maybe a
    forall (m :: * -> *) a. MonadPlus m => m a -> m a -> m a
    `mplus` DdbResponse -> Maybe Text
    ddbrCrc DdbResponse
    b) (DdbResponse -> Maybe Text
    ddbrMsgId DdbResponse
    a Maybe Text -> Maybe Text -> Maybe Text
    forall a. Maybe a -> Maybe a -> Maybe a
    forall (m :: * -> *) a. MonadPlus m => m a -> m a -> m a
    `mplus` DdbResponse -> Maybe Text
    ddbrMsgId DdbResponse
    b)

    instance Monoid DdbResponse where
        mempty :: DdbResponse
    mempty = Maybe Text -> Maybe Text -> DdbResponse
    DdbResponse Maybe Text
    forall a. Maybe a
    Nothing Maybe Text
    forall a. Maybe a
    Nothing
        mappend :: DdbResponse -> DdbResponse -> DdbResponse
    mappend = DdbResponse -> DdbResponse -> DdbResponse
    forall a. Semigroup a => a -> a -> a
    (Sem.<>)

    data Region = Region {
          Region -> ByteString
    rUri  :: B.ByteString
        , Region -> ByteString
    rName :: B.ByteString
        } deriving (Region -> Region -> Bool
    (Region -> Region -> Bool)
    -> (Region -> Region -> Bool) -> Eq Region
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: Region -> Region -> Bool
    == :: Region -> Region -> Bool
    $c/= :: Region -> Region -> Bool
    /= :: Region -> Region -> Bool
    Eq,Int -> Region -> ShowS
    [Region] -> ShowS
    Region -> String
    (Int -> Region -> ShowS)
    -> (Region -> String) -> ([Region] -> ShowS) -> Show Region
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> Region -> ShowS
    showsPrec :: Int -> Region -> ShowS
    $cshow :: Region -> String
    show :: Region -> String
    $cshowList :: [Region] -> ShowS
    showList :: [Region] -> ShowS
    Show,ReadPrec [Region]
    ReadPrec Region
    Int -> ReadS Region
    ReadS [Region]
    (Int -> ReadS Region)
    -> ReadS [Region]
    -> ReadPrec Region
    -> ReadPrec [Region]
    -> Read Region
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS Region
    readsPrec :: Int -> ReadS Region
    $creadList :: ReadS [Region]
    readList :: ReadS [Region]
    $creadPrec :: ReadPrec Region
    readPrec :: ReadPrec Region
    $creadListPrec :: ReadPrec [Region]
    readListPrec :: ReadPrec [Region]
    Read,Typeable)

    data DdbConfiguration qt = DdbConfiguration {
          forall qt. DdbConfiguration qt -> Region
    ddbcRegion   :: Region
        -- ^ The regional endpoint. Ex: 'ddbUsEast'
        , forall qt. DdbConfiguration qt -> Protocol
    ddbcProtocol :: Protocol
        -- ^ 'HTTP' or 'HTTPS'
        , forall qt. DdbConfiguration qt -> Maybe Int
    ddbcPort     :: Maybe Int
        -- ^ Port override (mostly for local dev connection)
        } deriving (Int -> DdbConfiguration qt -> ShowS
    [DdbConfiguration qt] -> ShowS
    DdbConfiguration qt -> String
    (Int -> DdbConfiguration qt -> ShowS)
    -> (DdbConfiguration qt -> String)
    -> ([DdbConfiguration qt] -> ShowS)
    -> Show (DdbConfiguration qt)
    forall qt. Int -> DdbConfiguration qt -> ShowS
    forall qt. [DdbConfiguration qt] -> ShowS
    forall qt. DdbConfiguration qt -> String
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: forall qt. Int -> DdbConfiguration qt -> ShowS
    showsPrec :: Int -> DdbConfiguration qt -> ShowS
    $cshow :: forall qt. DdbConfiguration qt -> String
    show :: DdbConfiguration qt -> String
    $cshowList :: forall qt. [DdbConfiguration qt] -> ShowS
    showList :: [DdbConfiguration qt] -> ShowS
    Show,Typeable)

    instance Default (DdbConfiguration NormalQuery) where
        def :: DdbConfiguration NormalQuery
    def = Region -> Protocol -> Maybe Int -> DdbConfiguration NormalQuery
    forall qt. Region -> Protocol -> Maybe Int -> DdbConfiguration qt
    DdbConfiguration Region
    ddbUsEast1 Protocol
    HTTPS Maybe Int
    forall a. Maybe a
    Nothing

    instance DefaultServiceConfiguration (DdbConfiguration NormalQuery) where
      defServiceConfig :: DdbConfiguration NormalQuery
    defServiceConfig = Region -> DdbConfiguration NormalQuery
    ddbHttps Region
    ddbUsEast1
      debugServiceConfig :: DdbConfiguration NormalQuery
    debugServiceConfig = Region -> DdbConfiguration NormalQuery
    ddbHttp Region
    ddbUsEast1

    -------------------------------------------------------------------------------
    -- | DynamoDb local connection (for development)
    ddbLocal :: Region
    ddbLocal :: Region
    ddbLocal = ByteString -> ByteString -> Region
    Region ByteString
    "127.0.0.1" ByteString
    "local"

    ddbUsEast1 :: Region
    ddbUsEast1 :: Region
    ddbUsEast1 = ByteString -> ByteString -> Region
    Region ByteString
    "dynamodb.us-east-1.amazonaws.com" ByteString
    "us-east-1"

    ddbUsWest1 :: Region
    ddbUsWest1 :: Region
    ddbUsWest1 = ByteString -> ByteString -> Region
    Region ByteString
    "dynamodb.us-west-1.amazonaws.com" ByteString
    "us-west-1"

    ddbUsWest2 :: Region
    ddbUsWest2 :: Region
    ddbUsWest2 = ByteString -> ByteString -> Region
    Region ByteString
    "dynamodb.us-west-2.amazonaws.com" ByteString
    "us-west-2"

    ddbEuWest1 :: Region
    ddbEuWest1 :: Region
    ddbEuWest1 = ByteString -> ByteString -> Region
    Region ByteString
    "dynamodb.eu-west-1.amazonaws.com" ByteString
    "eu-west-1"

    ddbEuWest2 :: Region
    ddbEuWest2 :: Region
    ddbEuWest2 = ByteString -> ByteString -> Region
    Region ByteString
    "dynamodb.eu-west-2.amazonaws.com" ByteString
    "eu-west-2"

    ddbEuCentral1 :: Region
    ddbEuCentral1 :: Region
    ddbEuCentral1 = ByteString -> ByteString -> Region
    Region ByteString
    "dynamodb.eu-central-1.amazonaws.com" ByteString
    "eu-central-1"

    ddbApNe1 :: Region
    ddbApNe1 :: Region
    ddbApNe1 = ByteString -> ByteString -> Region
    Region ByteString
    "dynamodb.ap-northeast-1.amazonaws.com" ByteString
    "ap-northeast-1"

    ddbApSe1 :: Region
    ddbApSe1 :: Region
    ddbApSe1 = ByteString -> ByteString -> Region
    Region ByteString
    "dynamodb.ap-southeast-1.amazonaws.com" ByteString
    "ap-southeast-1"

    ddbApSe2 :: Region
    ddbApSe2 :: Region
    ddbApSe2 = ByteString -> ByteString -> Region
    Region ByteString
    "dynamodb.ap-southeast-2.amazonaws.com" ByteString
    "ap-southeast-2"

    ddbSaEast1 :: Region
    ddbSaEast1 :: Region
    ddbSaEast1 = ByteString -> ByteString -> Region
    Region ByteString
    "dynamodb.sa-east-1.amazonaws.com" ByteString
    "sa-east-1"

    ddbHttp :: Region -> DdbConfiguration NormalQuery
    ddbHttp :: Region -> DdbConfiguration NormalQuery
    ddbHttp Region
    endpoint = Region -> Protocol -> Maybe Int -> DdbConfiguration NormalQuery
    forall qt. Region -> Protocol -> Maybe Int -> DdbConfiguration qt
    DdbConfiguration Region
    endpoint Protocol
    HTTP Maybe Int
    forall a. Maybe a
    Nothing

    ddbHttps :: Region -> DdbConfiguration NormalQuery
    ddbHttps :: Region -> DdbConfiguration NormalQuery
    ddbHttps Region
    endpoint = Region -> Protocol -> Maybe Int -> DdbConfiguration NormalQuery
    forall qt. Region -> Protocol -> Maybe Int -> DdbConfiguration qt
    DdbConfiguration Region
    endpoint Protocol
    HTTPS Maybe Int
    forall a. Maybe a
    Nothing

    ddbSignQuery
        :: A.ToJSON a
        => B.ByteString
        -> a
        -> DdbConfiguration qt
        -> SignatureData
        -> SignedQuery
    ddbSignQuery :: forall a qt.
    ToJSON a =>
    ByteString
    -> a -> DdbConfiguration qt -> SignatureData -> SignedQuery
    ddbSignQuery ByteString
    target a
    body DdbConfiguration qt
    di SignatureData
    sd
        = SignedQuery {
            sqMethod :: Method
    sqMethod = Method
    Post
          , sqProtocol :: Protocol
    sqProtocol = DdbConfiguration qt -> Protocol
    forall qt. DdbConfiguration qt -> Protocol
    ddbcProtocol DdbConfiguration qt
    di
          , sqHost :: ByteString
    sqHost = ByteString
    host
          , sqPort :: Int
    sqPort = Int -> Maybe Int -> Int
    forall a. a -> Maybe a -> a
    fromMaybe (Protocol -> Int
    defaultPort (DdbConfiguration qt -> Protocol
    forall qt. DdbConfiguration qt -> Protocol
    ddbcProtocol DdbConfiguration qt
    di)) (DdbConfiguration qt -> Maybe Int
    forall qt. DdbConfiguration qt -> Maybe Int
    ddbcPort DdbConfiguration qt
    di)
          , sqPath :: ByteString
    sqPath = ByteString
    "/"
          , sqQuery :: Query
    sqQuery = []
          , sqDate :: Maybe UTCTime
    sqDate = UTCTime -> Maybe UTCTime
    forall a. a -> Maybe a
    Just (UTCTime -> Maybe UTCTime) -> UTCTime -> Maybe UTCTime
    forall a b. (a -> b) -> a -> b
    $ SignatureData -> UTCTime
    signatureTime SignatureData
    sd
          , sqAuthorization :: Maybe (IO ByteString)
    sqAuthorization = IO ByteString -> Maybe (IO ByteString)
    forall a. a -> Maybe a
    Just IO ByteString
    auth
          , sqContentType :: Maybe ByteString
    sqContentType = ByteString -> Maybe ByteString
    forall a. a -> Maybe a
    Just ByteString
    "application/x-amz-json-1.0"
          , sqContentMd5 :: Maybe (Digest MD5)
    sqContentMd5 = Maybe (Digest MD5)
    forall a. Maybe a
    Nothing
          , sqAmzHeaders :: RequestHeaders
    sqAmzHeaders = RequestHeaders
    amzHeaders RequestHeaders -> RequestHeaders -> RequestHeaders
    forall a. [a] -> [a] -> [a]
    ++ RequestHeaders
    -> (ByteString -> RequestHeaders)
    -> Maybe ByteString
    -> RequestHeaders
    forall b a. b -> (a -> b) -> Maybe a -> b
    maybe [] (\ByteString
    tok -> [(CI ByteString
    "x-amz-security-token",ByteString
    tok)]) (Credentials -> Maybe ByteString
    iamToken Credentials
    credentials)
          , sqOtherHeaders :: RequestHeaders
    sqOtherHeaders = []
          , sqBody :: Maybe RequestBody
    sqBody = RequestBody -> Maybe RequestBody
    forall a. a -> Maybe a
    Just (RequestBody -> Maybe RequestBody)
    -> RequestBody -> Maybe RequestBody
    forall a b. (a -> b) -> a -> b
    $ ByteString -> RequestBody
    HTTP.RequestBodyLBS ByteString
    bodyLBS
          , sqStringToSign :: ByteString
    sqStringToSign = ByteString
    canonicalRequest
          }
        where
            credentials :: Credentials
    credentials = SignatureData -> Credentials
    signatureCredentials SignatureData
    sd

            Region{ByteString
    rUri :: Region -> ByteString
    rName :: Region -> ByteString
    rUri :: ByteString
    rName :: ByteString
    ..} = DdbConfiguration qt -> Region
    forall qt. DdbConfiguration qt -> Region
    ddbcRegion DdbConfiguration qt
    di
            host :: ByteString
    host = ByteString
    rUri

            sigTime :: ByteString
    sigTime = String -> UTCTime -> ByteString
    fmtTime String
    "%Y%m%dT%H%M%SZ" (UTCTime -> ByteString) -> UTCTime -> ByteString
    forall a b. (a -> b) -> a -> b
    $ SignatureData -> UTCTime
    signatureTime SignatureData
    sd

            bodyLBS :: ByteString
    bodyLBS = a -> ByteString
    forall a. ToJSON a => a -> ByteString
    A.encode a
    body
            bodyHash :: ByteString
    bodyHash = ByteString -> ByteString
    Base16.encode (ByteString -> ByteString) -> ByteString -> ByteString
    forall a b. (a -> b) -> a -> b
    $ Digest SHA256 -> ByteString
    forall bin bout.
    (ByteArrayAccess bin, ByteArray bout) =>
    bin -> bout
    ByteArray.convert (ByteString -> Digest SHA256
    forall a. HashAlgorithm a => ByteString -> Digest a
    CH.hashlazy ByteString
    bodyLBS :: CH.Digest CH.SHA256)

            -- for some reason AWS doesn't want the x-amz-security-token in the canonical request
            amzHeaders :: RequestHeaders
    amzHeaders = [ (CI ByteString
    "x-amz-date", ByteString
    sigTime)
                         , (CI ByteString
    "x-amz-target", ByteString
    dyApiVersion ByteString -> ByteString -> ByteString
    forall a. Semigroup a => a -> a -> a
    Sem.<> ByteString
    target)
                         ]

            canonicalHeaders :: RequestHeaders
    canonicalHeaders = ((CI ByteString, ByteString)
     -> (CI ByteString, ByteString) -> Ordering)
    -> RequestHeaders -> RequestHeaders
    forall a. (a -> a -> Ordering) -> [a] -> [a]
    sortBy (CI ByteString -> CI ByteString -> Ordering
    forall a. Ord a => a -> a -> Ordering
    compare (CI ByteString -> CI ByteString -> Ordering)
    -> ((CI ByteString, ByteString) -> CI ByteString)
    -> (CI ByteString, ByteString)
    -> (CI ByteString, ByteString)
    -> Ordering
    forall b c a. (b -> b -> c) -> (a -> b) -> a -> a -> c
    `on` (CI ByteString, ByteString) -> CI ByteString
    forall a b. (a, b) -> a
    fst) (RequestHeaders -> RequestHeaders)
    -> RequestHeaders -> RequestHeaders
    forall a b. (a -> b) -> a -> b
    $ RequestHeaders
    amzHeaders RequestHeaders -> RequestHeaders -> RequestHeaders
    forall a. [a] -> [a] -> [a]
    ++
                               [(CI ByteString
    "host", ByteString
    host),
                                (CI ByteString
    "content-type", ByteString
    "application/x-amz-json-1.0")]

            canonicalRequest :: ByteString
    canonicalRequest = [ByteString] -> ByteString
    B.concat ([ByteString] -> ByteString) -> [ByteString] -> ByteString
    forall a b. (a -> b) -> a -> b
    $ [ByteString] -> [[ByteString]] -> [ByteString]
    forall a. [a] -> [[a]] -> [a]
    intercalate [ByteString
    "\n"] (
                                        [ [ByteString
    "POST"]
                                        , [ByteString
    "/"]
                                        , [] -- query string
                                        ] [[ByteString]] -> [[ByteString]] -> [[ByteString]]
    forall a. [a] -> [a] -> [a]
    ++
                                        ((CI ByteString, ByteString) -> [ByteString])
    -> RequestHeaders -> [[ByteString]]
    forall a b. (a -> b) -> [a] -> [b]
    map (\(CI ByteString
    a,ByteString
    b) -> [CI ByteString -> ByteString
    forall s. CI s -> s
    CI.foldedCase CI ByteString
    a,ByteString
    ":",ByteString
    b]) RequestHeaders
    canonicalHeaders [[ByteString]] -> [[ByteString]] -> [[ByteString]]
    forall a. [a] -> [a] -> [a]
    ++
                                        [ [] -- end headers
                                        , ByteString -> [ByteString] -> [ByteString]
    forall a. a -> [a] -> [a]
    intersperse ByteString
    ";" (((CI ByteString, ByteString) -> ByteString)
    -> RequestHeaders -> [ByteString]
    forall a b. (a -> b) -> [a] -> [b]
    map (CI ByteString -> ByteString
    forall s. CI s -> s
    CI.foldedCase (CI ByteString -> ByteString)
    -> ((CI ByteString, ByteString) -> CI ByteString)
    -> (CI ByteString, ByteString)
    -> ByteString
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . (CI ByteString, ByteString) -> CI ByteString
    forall a b. (a, b) -> a
    fst) RequestHeaders
    canonicalHeaders)
                                        , [ByteString
    bodyHash]
                                        ])

            auth :: IO ByteString
    auth = SignatureData
    -> AuthorizationHash
    -> ByteString
    -> ByteString
    -> ByteString
    -> ByteString
    -> IO ByteString
    authorizationV4 SignatureData
    sd AuthorizationHash
    HmacSHA256 ByteString
    rName ByteString
    "dynamodb"
                                   ByteString
    "content-type;host;x-amz-date;x-amz-target"
                                   ByteString
    canonicalRequest

    data AmazonError = AmazonError {
          AmazonError -> Text
    aeType    :: T.Text
        , AmazonError -> Maybe Text
    aeMessage :: Maybe T.Text
        }

    instance FromJSON AmazonError where
        parseJSON :: Value -> Parser AmazonError
    parseJSON (Object Object
    v) = Text -> Maybe Text -> AmazonError
    AmazonError
            (Text -> Maybe Text -> AmazonError)
    -> Parser Text -> Parser (Maybe Text -> AmazonError)
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Object
    v Object -> Key -> Parser Text
    forall a. FromJSON a => Object -> Key -> Parser a
    .: Key
    "__type"
            Parser (Maybe Text -> AmazonError)
    -> Parser (Maybe Text) -> Parser AmazonError
    forall a b. Parser (a -> b) -> Parser a -> Parser b
    forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
    <*> (Text -> Maybe Text
    forall a. a -> Maybe a
    Just (Text -> Maybe Text) -> Parser Text -> Parser (Maybe Text)
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> (Object
    v Object -> Key -> Parser Text
    forall a. FromJSON a => Object -> Key -> Parser a
    .: Key
    "message" Parser Text -> Parser Text -> Parser Text
    forall a. Parser a -> Parser a -> Parser a
    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
    <|> Object
    v Object -> Key -> Parser Text
    forall a. FromJSON a => Object -> Key -> Parser a
    .: Key
    "Message") Parser (Maybe Text) -> Parser (Maybe Text) -> Parser (Maybe Text)
    forall a. Parser a -> Parser a -> Parser a
    forall (f :: * -> *) a. Alternative f => f a -> f a -> f a
    <|> Maybe Text -> Parser (Maybe Text)
    forall a. a -> Parser a
    forall (f :: * -> *) a. Applicative f => a -> f a
    pure Maybe Text
    forall a. Maybe a
    Nothing)
        parseJSON Value
    _ = String -> Parser AmazonError
    forall a. HasCallStack => String -> a
    error (String -> Parser AmazonError) -> String -> Parser AmazonError
    forall a b. (a -> b) -> a -> b
    $ String
    "aws: unexpected AmazonError message"

    -------------------------------------------------------------------------------
    ddbResponseConsumer :: A.FromJSON a => IORef DdbResponse -> HTTPResponseConsumer a
    ddbResponseConsumer :: forall a. FromJSON a => IORef DdbResponse -> HTTPResponseConsumer a
    ddbResponseConsumer IORef DdbResponse
    ref Response (ConduitM () ByteString (ResourceT IO) ())
    resp = do
        val <- ConduitT () Void (ResourceT IO) Value -> ResourceT IO Value
    forall (m :: * -> *) r. Monad m => ConduitT () Void m r -> m r
    runConduit (ConduitT () Void (ResourceT IO) Value -> ResourceT IO Value)
    -> ConduitT () Void (ResourceT IO) Value -> ResourceT IO Value
    forall a b. (a -> b) -> a -> b
    $ Response (ConduitM () ByteString (ResourceT IO) ())
    -> ConduitM () ByteString (ResourceT IO) ()
    forall body. Response body -> body
    HTTP.responseBody Response (ConduitM () ByteString (ResourceT IO) ())
    resp ConduitM () ByteString (ResourceT IO) ()
    -> ConduitT ByteString Void (ResourceT IO) Value
    -> ConduitT () Void (ResourceT IO) Value
    forall (m :: * -> *) a b c r.
    Monad m =>
    ConduitT a b m () -> ConduitT b c m r -> ConduitT a c m r
    .| Parser ByteString Value
    -> ConduitT ByteString Void (ResourceT IO) Value
    forall a (m :: * -> *) b o.
    (AttoparsecInput a, MonadThrow m) =>
    Parser a b -> ConduitT a o m b
    sinkParser (Parser ByteString Value
    A.json' Parser ByteString Value
    -> Parser ByteString () -> Parser ByteString Value
    forall a b.
    Parser ByteString a -> Parser ByteString b -> Parser ByteString a
    forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
    <* Parser ByteString ()
    forall t. Chunk t => Parser t ()
    AttoB.endOfInput)
        case statusCode of
          Int
    200 -> Value -> ResourceT IO a
    rSuccess Value
    val
          Int
    _   -> Value -> ResourceT IO a
    rError Value
    val
      where

        header :: CI ByteString -> Maybe Text
    header = (ByteString -> Text) -> Maybe ByteString -> Maybe Text
    forall a b. (a -> b) -> Maybe a -> Maybe b
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    fmap ByteString -> Text
    T.decodeUtf8 (Maybe ByteString -> Maybe Text)
    -> (CI ByteString -> Maybe ByteString)
    -> CI ByteString
    -> Maybe Text
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . (CI ByteString -> RequestHeaders -> Maybe ByteString)
    -> RequestHeaders -> CI ByteString -> Maybe ByteString
    forall a b c. (a -> b -> c) -> b -> a -> c
    flip CI ByteString -> RequestHeaders -> Maybe ByteString
    forall a b. Eq a => a -> [(a, b)] -> Maybe b
    lookup (Response (ConduitM () ByteString (ResourceT IO) ())
    -> RequestHeaders
    forall body. Response body -> RequestHeaders
    HTTP.responseHeaders Response (ConduitM () ByteString (ResourceT IO) ())
    resp)
        amzId :: Maybe Text
    amzId = CI ByteString -> Maybe Text
    header CI ByteString
    "x-amzn-RequestId"
        amzCrc :: Maybe Text
    amzCrc = CI ByteString -> Maybe Text
    header CI ByteString
    "x-amz-crc32"
        meta :: DdbResponse
    meta = Maybe Text -> Maybe Text -> DdbResponse
    DdbResponse Maybe Text
    amzCrc Maybe Text
    amzId
        tellMeta :: ResourceT IO ()
    tellMeta = IO () -> ResourceT IO ()
    forall a. IO a -> ResourceT IO a
    forall (m :: * -> *) a. MonadIO m => IO a -> m a
    liftIO (IO () -> ResourceT IO ()) -> IO () -> ResourceT IO ()
    forall a b. (a -> b) -> a -> b
    $ IORef DdbResponse -> DdbResponse -> IO ()
    forall m. Monoid m => IORef m -> m -> IO ()
    tellMetadataRef IORef DdbResponse
    ref DdbResponse
    meta

        rSuccess :: Value -> ResourceT IO a
    rSuccess Value
    val =
          case Value -> Result a
    forall a. FromJSON a => Value -> Result a
    A.fromJSON Value
    val of
            A.Success a
    a -> a -> ResourceT IO a
    forall a. a -> ResourceT IO a
    forall (m :: * -> *) a. Monad m => a -> m a
    return a
    a
            A.Error String
    err -> do
                ResourceT IO ()
    tellMeta
                DdbLibraryError -> ResourceT IO a
    forall e a. (HasCallStack, Exception e) => e -> ResourceT IO a
    forall (m :: * -> *) e a.
    (MonadThrow m, HasCallStack, Exception e) =>
    e -> m a
    throwM (DdbLibraryError -> ResourceT IO a)
    -> DdbLibraryError -> ResourceT IO a
    forall a b. (a -> b) -> a -> b
    $ Value -> Text -> DdbLibraryError
    JsonProtocolError Value
    val (String -> Text
    T.pack String
    err)

        rError :: Value -> ResourceT IO a
    rError Value
    val = do
          ResourceT IO ()
    tellMeta
          case (Value -> Parser AmazonError) -> Value -> Either String AmazonError
    forall a b. (a -> Parser b) -> a -> Either String b
    parseEither Value -> Parser AmazonError
    forall a. FromJSON a => Value -> Parser a
    parseJSON Value
    val of
            Left String
    e ->
              DdbLibraryError -> ResourceT IO a
    forall e a. (HasCallStack, Exception e) => e -> ResourceT IO a
    forall (m :: * -> *) e a.
    (MonadThrow m, HasCallStack, Exception e) =>
    e -> m a
    throwM (DdbLibraryError -> ResourceT IO a)
    -> DdbLibraryError -> ResourceT IO a
    forall a b. (a -> b) -> a -> b
    $ Value -> Text -> DdbLibraryError
    JsonProtocolError Value
    val (String -> Text
    T.pack String
    e)

            Right AmazonError
    err'' -> do
              let e :: Text
    e = Int -> Text -> Text
    T.drop Int
    1 (Text -> Text) -> (Text -> Text) -> Text -> Text
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . (Text, Text) -> Text
    forall a b. (a, b) -> b
    snd ((Text, Text) -> Text) -> (Text -> (Text, Text)) -> Text -> Text
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . HasCallStack => Text -> Text -> (Text, Text)
    Text -> Text -> (Text, Text)
    T.breakOn Text
    "#" (Text -> Text) -> Text -> Text
    forall a b. (a -> b) -> a -> b
    $ AmazonError -> Text
    aeType AmazonError
    err''
              errCode <- Text -> ResourceT IO DdbErrCode
    forall {a} {m :: * -> *}. (Read a, MonadThrow m) => Text -> m a
    readErrCode Text
    e
              throwM $ DdbError statusCode errCode (fromMaybe "" $ aeMessage err'')

        readErrCode :: Text -> m a
    readErrCode Text
    txt =
            let txt' :: String
    txt' = Text -> String
    T.unpack Text
    txt
            in case String -> Maybe a
    forall a. Read a => String -> Maybe a
    readMay String
    txt' of
                 Just a
    e -> a -> m a
    forall a. a -> m a
    forall (m :: * -> *) a. Monad m => a -> m a
    return (a -> m a) -> a -> m a
    forall a b. (a -> b) -> a -> b
    $ a
    e
                 Maybe a
    Nothing -> DdbLibraryError -> m a
    forall e a. (HasCallStack, Exception e) => e -> m a
    forall (m :: * -> *) e a.
    (MonadThrow m, HasCallStack, Exception e) =>
    e -> m a
    throwM (Text -> DdbLibraryError
    UnknownDynamoErrCode Text
    txt)

        HTTP.Status{Int
    ByteString
    statusCode :: Int
    statusMessage :: ByteString
    statusMessage :: Status -> ByteString
    statusCode :: Status -> Int
    ..} = Response (ConduitM () ByteString (ResourceT IO) ()) -> Status
    forall body. Response body -> Status
    HTTP.responseStatus Response (ConduitM () ByteString (ResourceT IO) ())
    resp

    -- | Conditions used by mutation operations ('PutItem', 'UpdateItem',
    -- etc.). The default 'def' instance is empty (no condition).
    data Conditions = Conditions CondMerge [Condition]
        deriving (Conditions -> Conditions -> Bool
    (Conditions -> Conditions -> Bool)
    -> (Conditions -> Conditions -> Bool) -> Eq Conditions
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: Conditions -> Conditions -> Bool
    == :: Conditions -> Conditions -> Bool
    $c/= :: Conditions -> Conditions -> Bool
    /= :: Conditions -> Conditions -> Bool
    Eq,Int -> Conditions -> ShowS
    [Conditions] -> ShowS
    Conditions -> String
    (Int -> Conditions -> ShowS)
    -> (Conditions -> String)
    -> ([Conditions] -> ShowS)
    -> Show Conditions
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> Conditions -> ShowS
    showsPrec :: Int -> Conditions -> ShowS
    $cshow :: Conditions -> String
    show :: Conditions -> String
    $cshowList :: [Conditions] -> ShowS
    showList :: [Conditions] -> ShowS
    Show,ReadPrec [Conditions]
    ReadPrec Conditions
    Int -> ReadS Conditions
    ReadS [Conditions]
    (Int -> ReadS Conditions)
    -> ReadS [Conditions]
    -> ReadPrec Conditions
    -> ReadPrec [Conditions]
    -> Read Conditions
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS Conditions
    readsPrec :: Int -> ReadS Conditions
    $creadList :: ReadS [Conditions]
    readList :: ReadS [Conditions]
    $creadPrec :: ReadPrec Conditions
    readPrec :: ReadPrec Conditions
    $creadListPrec :: ReadPrec [Conditions]
    readListPrec :: ReadPrec [Conditions]
    Read,Eq Conditions
    Eq Conditions =>
    (Conditions -> Conditions -> Ordering)
    -> (Conditions -> Conditions -> Bool)
    -> (Conditions -> Conditions -> Bool)
    -> (Conditions -> Conditions -> Bool)
    -> (Conditions -> Conditions -> Bool)
    -> (Conditions -> Conditions -> Conditions)
    -> (Conditions -> Conditions -> Conditions)
    -> Ord Conditions
    Conditions -> Conditions -> Bool
    Conditions -> Conditions -> Ordering
    Conditions -> Conditions -> Conditions
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: Conditions -> Conditions -> Ordering
    compare :: Conditions -> Conditions -> Ordering
    $c< :: Conditions -> Conditions -> Bool
    < :: Conditions -> Conditions -> Bool
    $c<= :: Conditions -> Conditions -> Bool
    <= :: Conditions -> Conditions -> Bool
    $c> :: Conditions -> Conditions -> Bool
    > :: Conditions -> Conditions -> Bool
    $c>= :: Conditions -> Conditions -> Bool
    >= :: Conditions -> Conditions -> Bool
    $cmax :: Conditions -> Conditions -> Conditions
    max :: Conditions -> Conditions -> Conditions
    $cmin :: Conditions -> Conditions -> Conditions
    min :: Conditions -> Conditions -> Conditions
    Ord,Typeable)

    instance Default Conditions where
        def :: Conditions
    def = CondMerge -> [Condition] -> Conditions
    Conditions CondMerge
    CondAnd []

    expectsJson :: Conditions -> [A.Pair]
    expectsJson :: Conditions -> [Pair]
    expectsJson = Text -> Conditions -> [Pair]
    conditionsJson Text
    "Expected"

    -- | JSON encoding of conditions parameter in various contexts.
    conditionsJson :: T.Text -> Conditions -> [A.Pair]
    conditionsJson :: Text -> Conditions -> [Pair]
    conditionsJson Text
    key (Conditions CondMerge
    op [Condition]
    es) = [Pair]
    b [Pair] -> [Pair] -> [Pair]
    forall a. [a] -> [a] -> [a]
    ++ [Pair]
    a
        where
          a :: [Pair]
    a = if [Condition] -> Bool
    forall a. [a] -> Bool
    forall (t :: * -> *) a. Foldable t => t a -> Bool
    null [Condition]
    es
              then []
              else [Text -> Key
    AK.fromText Text
    key Key -> Value -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= [Pair] -> Value
    object ((Condition -> Pair) -> [Condition] -> [Pair]
    forall a b. (a -> b) -> [a] -> [b]
    map Condition -> Pair
    conditionJson [Condition]
    es)]

          b :: [Pair]
    b = if [Condition] -> Int
    forall a. [a] -> Int
    forall (t :: * -> *) a. Foldable t => t a -> Int
    length (Int -> [Condition] -> [Condition]
    forall a. Int -> [a] -> [a]
    take Int
    2 [Condition]
    es) Int -> Int -> Bool
    forall a. Ord a => a -> a -> Bool
    > Int
    1
              then [Key
    "ConditionalOperator" Key -> Value -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Text -> Value
    String (CondMerge -> Text
    rendCondOp CondMerge
    op) ]
              else []

    -------------------------------------------------------------------------------
    rendCondOp :: CondMerge -> T.Text
    rendCondOp :: CondMerge -> Text
    rendCondOp CondMerge
    CondAnd = Text
    "AND"
    rendCondOp CondMerge
    CondOr = Text
    "OR"

    -------------------------------------------------------------------------------
    -- | How to merge multiple conditions.
    data CondMerge = CondAnd | CondOr
        deriving (CondMerge -> CondMerge -> Bool
    (CondMerge -> CondMerge -> Bool)
    -> (CondMerge -> CondMerge -> Bool) -> Eq CondMerge
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: CondMerge -> CondMerge -> Bool
    == :: CondMerge -> CondMerge -> Bool
    $c/= :: CondMerge -> CondMerge -> Bool
    /= :: CondMerge -> CondMerge -> Bool
    Eq,Int -> CondMerge -> ShowS
    [CondMerge] -> ShowS
    CondMerge -> String
    (Int -> CondMerge -> ShowS)
    -> (CondMerge -> String)
    -> ([CondMerge] -> ShowS)
    -> Show CondMerge
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> CondMerge -> ShowS
    showsPrec :: Int -> CondMerge -> ShowS
    $cshow :: CondMerge -> String
    show :: CondMerge -> String
    $cshowList :: [CondMerge] -> ShowS
    showList :: [CondMerge] -> ShowS
    Show,ReadPrec [CondMerge]
    ReadPrec CondMerge
    Int -> ReadS CondMerge
    ReadS [CondMerge]
    (Int -> ReadS CondMerge)
    -> ReadS [CondMerge]
    -> ReadPrec CondMerge
    -> ReadPrec [CondMerge]
    -> Read CondMerge
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS CondMerge
    readsPrec :: Int -> ReadS CondMerge
    $creadList :: ReadS [CondMerge]
    readList :: ReadS [CondMerge]
    $creadPrec :: ReadPrec CondMerge
    readPrec :: ReadPrec CondMerge
    $creadListPrec :: ReadPrec [CondMerge]
    readListPrec :: ReadPrec [CondMerge]
    Read,Eq CondMerge
    Eq CondMerge =>
    (CondMerge -> CondMerge -> Ordering)
    -> (CondMerge -> CondMerge -> Bool)
    -> (CondMerge -> CondMerge -> Bool)
    -> (CondMerge -> CondMerge -> Bool)
    -> (CondMerge -> CondMerge -> Bool)
    -> (CondMerge -> CondMerge -> CondMerge)
    -> (CondMerge -> CondMerge -> CondMerge)
    -> Ord CondMerge
    CondMerge -> CondMerge -> Bool
    CondMerge -> CondMerge -> Ordering
    CondMerge -> CondMerge -> CondMerge
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: CondMerge -> CondMerge -> Ordering
    compare :: CondMerge -> CondMerge -> Ordering
    $c< :: CondMerge -> CondMerge -> Bool
    < :: CondMerge -> CondMerge -> Bool
    $c<= :: CondMerge -> CondMerge -> Bool
    <= :: CondMerge -> CondMerge -> Bool
    $c> :: CondMerge -> CondMerge -> Bool
    > :: CondMerge -> CondMerge -> Bool
    $c>= :: CondMerge -> CondMerge -> Bool
    >= :: CondMerge -> CondMerge -> Bool
    $cmax :: CondMerge -> CondMerge -> CondMerge
    max :: CondMerge -> CondMerge -> CondMerge
    $cmin :: CondMerge -> CondMerge -> CondMerge
    min :: CondMerge -> CondMerge -> CondMerge
    Ord,Typeable)

    -- | A condition used by mutation operations ('PutItem', 'UpdateItem', etc.).
    data Condition = Condition {
          Condition -> Text
    condAttr :: T.Text
        -- ^ Attribute to use as the basis for this conditional
        , Condition -> CondOp
    condOp   :: CondOp
        -- ^ Operation on the selected attribute
        } deriving (Condition -> Condition -> Bool
    (Condition -> Condition -> Bool)
    -> (Condition -> Condition -> Bool) -> Eq Condition
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: Condition -> Condition -> Bool
    == :: Condition -> Condition -> Bool
    $c/= :: Condition -> Condition -> Bool
    /= :: Condition -> Condition -> Bool
    Eq,Int -> Condition -> ShowS
    [Condition] -> ShowS
    Condition -> String
    (Int -> Condition -> ShowS)
    -> (Condition -> String)
    -> ([Condition] -> ShowS)
    -> Show Condition
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> Condition -> ShowS
    showsPrec :: Int -> Condition -> ShowS
    $cshow :: Condition -> String
    show :: Condition -> String
    $cshowList :: [Condition] -> ShowS
    showList :: [Condition] -> ShowS
    Show,ReadPrec [Condition]
    ReadPrec Condition
    Int -> ReadS Condition
    ReadS [Condition]
    (Int -> ReadS Condition)
    -> ReadS [Condition]
    -> ReadPrec Condition
    -> ReadPrec [Condition]
    -> Read Condition
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS Condition
    readsPrec :: Int -> ReadS Condition
    $creadList :: ReadS [Condition]
    readList :: ReadS [Condition]
    $creadPrec :: ReadPrec Condition
    readPrec :: ReadPrec Condition
    $creadListPrec :: ReadPrec [Condition]
    readListPrec :: ReadPrec [Condition]
    Read,Eq Condition
    Eq Condition =>
    (Condition -> Condition -> Ordering)
    -> (Condition -> Condition -> Bool)
    -> (Condition -> Condition -> Bool)
    -> (Condition -> Condition -> Bool)
    -> (Condition -> Condition -> Bool)
    -> (Condition -> Condition -> Condition)
    -> (Condition -> Condition -> Condition)
    -> Ord Condition
    Condition -> Condition -> Bool
    Condition -> Condition -> Ordering
    Condition -> Condition -> Condition
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: Condition -> Condition -> Ordering
    compare :: Condition -> Condition -> Ordering
    $c< :: Condition -> Condition -> Bool
    < :: Condition -> Condition -> Bool
    $c<= :: Condition -> Condition -> Bool
    <= :: Condition -> Condition -> Bool
    $c> :: Condition -> Condition -> Bool
    > :: Condition -> Condition -> Bool
    $c>= :: Condition -> Condition -> Bool
    >= :: Condition -> Condition -> Bool
    $cmax :: Condition -> Condition -> Condition
    max :: Condition -> Condition -> Condition
    $cmin :: Condition -> Condition -> Condition
    min :: Condition -> Condition -> Condition
    Ord,Typeable)

    -------------------------------------------------------------------------------
    -- | Conditional operation to perform on a field.
    data CondOp
        = DEq DValue
        | NotEq DValue
        | DLE DValue
        | DLT DValue
        | DGE DValue
        | DGT DValue
        | NotNull
        | IsNull
        | Contains DValue
        | NotContains DValue
        | Begins DValue
        | In [DValue]
        | Between DValue DValue
        deriving (CondOp -> CondOp -> Bool
    (CondOp -> CondOp -> Bool)
    -> (CondOp -> CondOp -> Bool) -> Eq CondOp
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: CondOp -> CondOp -> Bool
    == :: CondOp -> CondOp -> Bool
    $c/= :: CondOp -> CondOp -> Bool
    /= :: CondOp -> CondOp -> Bool
    Eq,Int -> CondOp -> ShowS
    [CondOp] -> ShowS
    CondOp -> String
    (Int -> CondOp -> ShowS)
    -> (CondOp -> String) -> ([CondOp] -> ShowS) -> Show CondOp
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> CondOp -> ShowS
    showsPrec :: Int -> CondOp -> ShowS
    $cshow :: CondOp -> String
    show :: CondOp -> String
    $cshowList :: [CondOp] -> ShowS
    showList :: [CondOp] -> ShowS
    Show,ReadPrec [CondOp]
    ReadPrec CondOp
    Int -> ReadS CondOp
    ReadS [CondOp]
    (Int -> ReadS CondOp)
    -> ReadS [CondOp]
    -> ReadPrec CondOp
    -> ReadPrec [CondOp]
    -> Read CondOp
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS CondOp
    readsPrec :: Int -> ReadS CondOp
    $creadList :: ReadS [CondOp]
    readList :: ReadS [CondOp]
    $creadPrec :: ReadPrec CondOp
    readPrec :: ReadPrec CondOp
    $creadListPrec :: ReadPrec [CondOp]
    readListPrec :: ReadPrec [CondOp]
    Read,Eq CondOp
    Eq CondOp =>
    (CondOp -> CondOp -> Ordering)
    -> (CondOp -> CondOp -> Bool)
    -> (CondOp -> CondOp -> Bool)
    -> (CondOp -> CondOp -> Bool)
    -> (CondOp -> CondOp -> Bool)
    -> (CondOp -> CondOp -> CondOp)
    -> (CondOp -> CondOp -> CondOp)
    -> Ord CondOp
    CondOp -> CondOp -> Bool
    CondOp -> CondOp -> Ordering
    CondOp -> CondOp -> CondOp
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: CondOp -> CondOp -> Ordering
    compare :: CondOp -> CondOp -> Ordering
    $c< :: CondOp -> CondOp -> Bool
    < :: CondOp -> CondOp -> Bool
    $c<= :: CondOp -> CondOp -> Bool
    <= :: CondOp -> CondOp -> Bool
    $c> :: CondOp -> CondOp -> Bool
    > :: CondOp -> CondOp -> Bool
    $c>= :: CondOp -> CondOp -> Bool
    >= :: CondOp -> CondOp -> Bool
    $cmax :: CondOp -> CondOp -> CondOp
    max :: CondOp -> CondOp -> CondOp
    $cmin :: CondOp -> CondOp -> CondOp
    min :: CondOp -> CondOp -> CondOp
    Ord,Typeable)

    -------------------------------------------------------------------------------
    getCondValues :: CondOp -> [DValue]
    getCondValues :: CondOp -> [DValue]
    getCondValues CondOp
    c = case CondOp
    c of
        DEq DValue
    v -> [DValue
    v]
        NotEq DValue
    v -> [DValue
    v]
        DLE DValue
    v -> [DValue
    v]
        DLT DValue
    v -> [DValue
    v]
        DGE DValue
    v -> [DValue
    v]
        DGT DValue
    v -> [DValue
    v]
        CondOp
    NotNull -> []
        CondOp
    IsNull -> []
        Contains DValue
    v -> [DValue
    v]
        NotContains DValue
    v -> [DValue
    v]
        Begins DValue
    v -> [DValue
    v]
        In [DValue]
    v -> [DValue]
    v
        Between DValue
    a DValue
    b -> [DValue
    a,DValue
    b]

    -------------------------------------------------------------------------------
    renderCondOp :: CondOp -> T.Text
    renderCondOp :: CondOp -> Text
    renderCondOp CondOp
    c = case CondOp
    c of
        DEq{} -> Text
    "EQ"
        NotEq{} -> Text
    "NE"
        DLE{} -> Text
    "LE"
        DLT{} -> Text
    "LT"
        DGE{} -> Text
    "GE"
        DGT{} -> Text
    "GT"
        CondOp
    NotNull -> Text
    "NOT_NULL"
        CondOp
    IsNull -> Text
    "NULL"
        Contains{} -> Text
    "CONTAINS"
        NotContains{} -> Text
    "NOT_CONTAINS"
        Begins{} -> Text
    "BEGINS_WITH"
        In{} -> Text
    "IN"
        Between{} -> Text
    "BETWEEN"

    conditionJson :: Condition -> Pair
    conditionJson :: Condition -> Pair
    conditionJson Condition{Text
    CondOp
    condAttr :: Condition -> Text
    condOp :: Condition -> CondOp
    condAttr :: Text
    condOp :: CondOp
    ..} = Text -> Key
    AK.fromText Text
    condAttr Key -> CondOp -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= CondOp
    condOp

    instance ToJSON CondOp where
        toJSON :: CondOp -> Value
    toJSON CondOp
    c = [Pair] -> Value
    object ([Pair] -> Value) -> [Pair] -> Value
    forall a b. (a -> b) -> a -> b
    $ (Key
    "ComparisonOperator" Key -> Value -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Text -> Value
    String (CondOp -> Text
    renderCondOp CondOp
    c)) Pair -> [Pair] -> [Pair]
    forall a. a -> [a] -> [a]
    : [Pair]
    valueList
          where
            valueList :: [Pair]
    valueList =
              let vs :: [DValue]
    vs = CondOp -> [DValue]
    getCondValues CondOp
    c in
                if [DValue] -> Bool
    forall a. [a] -> Bool
    forall (t :: * -> *) a. Foldable t => t a -> Bool
    null [DValue]
    vs
                then []
                else [Key
    "AttributeValueList" Key -> [DValue] -> Pair
    forall v. ToJSON v => Key -> v -> Pair
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= [DValue]
    vs]

    -------------------------------------------------------------------------------
    dyApiVersion :: B.ByteString
    dyApiVersion :: ByteString
    dyApiVersion = ByteString
    "DynamoDB_20120810."

    -------------------------------------------------------------------------------
    -- | The standard response metrics on capacity consumption.
    data ConsumedCapacity = ConsumedCapacity {
          ConsumedCapacity -> Int64
    capacityUnits       :: Int64
        , ConsumedCapacity -> [(Text, Int64)]
    capacityGlobalIndex :: [(T.Text, Int64)]
        , ConsumedCapacity -> [(Text, Int64)]
    capacityLocalIndex  :: [(T.Text, Int64)]
        , ConsumedCapacity -> Maybe Int64
    capacityTableUnits  :: Maybe Int64
        , ConsumedCapacity -> Text
    capacityTable       :: T.Text
        } deriving (ConsumedCapacity -> ConsumedCapacity -> Bool
    (ConsumedCapacity -> ConsumedCapacity -> Bool)
    -> (ConsumedCapacity -> ConsumedCapacity -> Bool)
    -> Eq ConsumedCapacity
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: ConsumedCapacity -> ConsumedCapacity -> Bool
    == :: ConsumedCapacity -> ConsumedCapacity -> Bool
    $c/= :: ConsumedCapacity -> ConsumedCapacity -> Bool
    /= :: ConsumedCapacity -> ConsumedCapacity -> Bool
    Eq,Int -> ConsumedCapacity -> ShowS
    [ConsumedCapacity] -> ShowS
    ConsumedCapacity -> String
    (Int -> ConsumedCapacity -> ShowS)
    -> (ConsumedCapacity -> String)
    -> ([ConsumedCapacity] -> ShowS)
    -> Show ConsumedCapacity
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> ConsumedCapacity -> ShowS
    showsPrec :: Int -> ConsumedCapacity -> ShowS
    $cshow :: ConsumedCapacity -> String
    show :: ConsumedCapacity -> String
    $cshowList :: [ConsumedCapacity] -> ShowS
    showList :: [ConsumedCapacity] -> ShowS
    Show,ReadPrec [ConsumedCapacity]
    ReadPrec ConsumedCapacity
    Int -> ReadS ConsumedCapacity
    ReadS [ConsumedCapacity]
    (Int -> ReadS ConsumedCapacity)
    -> ReadS [ConsumedCapacity]
    -> ReadPrec ConsumedCapacity
    -> ReadPrec [ConsumedCapacity]
    -> Read ConsumedCapacity
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS ConsumedCapacity
    readsPrec :: Int -> ReadS ConsumedCapacity
    $creadList :: ReadS [ConsumedCapacity]
    readList :: ReadS [ConsumedCapacity]
    $creadPrec :: ReadPrec ConsumedCapacity
    readPrec :: ReadPrec ConsumedCapacity
    $creadListPrec :: ReadPrec [ConsumedCapacity]
    readListPrec :: ReadPrec [ConsumedCapacity]
    Read,Eq ConsumedCapacity
    Eq ConsumedCapacity =>
    (ConsumedCapacity -> ConsumedCapacity -> Ordering)
    -> (ConsumedCapacity -> ConsumedCapacity -> Bool)
    -> (ConsumedCapacity -> ConsumedCapacity -> Bool)
    -> (ConsumedCapacity -> ConsumedCapacity -> Bool)
    -> (ConsumedCapacity -> ConsumedCapacity -> Bool)
    -> (ConsumedCapacity -> ConsumedCapacity -> ConsumedCapacity)
    -> (ConsumedCapacity -> ConsumedCapacity -> ConsumedCapacity)
    -> Ord ConsumedCapacity
    ConsumedCapacity -> ConsumedCapacity -> Bool
    ConsumedCapacity -> ConsumedCapacity -> Ordering
    ConsumedCapacity -> ConsumedCapacity -> ConsumedCapacity
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: ConsumedCapacity -> ConsumedCapacity -> Ordering
    compare :: ConsumedCapacity -> ConsumedCapacity -> Ordering
    $c< :: ConsumedCapacity -> ConsumedCapacity -> Bool
    < :: ConsumedCapacity -> ConsumedCapacity -> Bool
    $c<= :: ConsumedCapacity -> ConsumedCapacity -> Bool
    <= :: ConsumedCapacity -> ConsumedCapacity -> Bool
    $c> :: ConsumedCapacity -> ConsumedCapacity -> Bool
    > :: ConsumedCapacity -> ConsumedCapacity -> Bool
    $c>= :: ConsumedCapacity -> ConsumedCapacity -> Bool
    >= :: ConsumedCapacity -> ConsumedCapacity -> Bool
    $cmax :: ConsumedCapacity -> ConsumedCapacity -> ConsumedCapacity
    max :: ConsumedCapacity -> ConsumedCapacity -> ConsumedCapacity
    $cmin :: ConsumedCapacity -> ConsumedCapacity -> ConsumedCapacity
    min :: ConsumedCapacity -> ConsumedCapacity -> ConsumedCapacity
    Ord,Typeable)

    instance FromJSON ConsumedCapacity where
        parseJSON :: Value -> Parser ConsumedCapacity
    parseJSON (Object Object
    o) = Int64
    -> [(Text, Int64)]
    -> [(Text, Int64)]
    -> Maybe Int64
    -> Text
    -> ConsumedCapacity
    ConsumedCapacity
          (Int64
     -> [(Text, Int64)]
     -> [(Text, Int64)]
     -> Maybe Int64
     -> Text
     -> ConsumedCapacity)
    -> Parser Int64
    -> Parser
         ([(Text, Int64)]
          -> [(Text, Int64)] -> Maybe Int64 -> Text -> ConsumedCapacity)
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Object
    o Object -> Key -> Parser Int64
    forall a. FromJSON a => Object -> Key -> Parser a
    .: Key
    "CapacityUnits"
          Parser
      ([(Text, Int64)]
       -> [(Text, Int64)] -> Maybe Int64 -> Text -> ConsumedCapacity)
    -> Parser [(Text, Int64)]
    -> Parser
         ([(Text, Int64)] -> Maybe Int64 -> Text -> ConsumedCapacity)
    forall a b. Parser (a -> b) -> Parser a -> Parser b
    forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
    <*> (((Key, Int64) -> (Text, Int64))
    -> [(Key, Int64)] -> [(Text, Int64)]
    forall a b. (a -> b) -> [a] -> [b]
    map (\(Key
    k, Int64
    v) -> (Key -> Text
    AK.toText Key
    k, Int64
    v)) ([(Key, Int64)] -> [(Text, Int64)])
    -> (KeyMap Int64 -> [(Key, Int64)])
    -> KeyMap Int64
    -> [(Text, Int64)]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . KeyMap Int64 -> [(Key, Int64)]
    forall v. KeyMap v -> [(Key, v)]
    KM.toList (KeyMap Int64 -> [(Text, Int64)])
    -> Parser (KeyMap Int64) -> Parser [(Text, Int64)]
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Object
    o Object -> Key -> Parser (Maybe (KeyMap Int64))
    forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
    .:? Key
    "GlobalSecondaryIndexes" Parser (Maybe (KeyMap Int64))
    -> KeyMap Int64 -> Parser (KeyMap Int64)
    forall a. Parser (Maybe a) -> a -> Parser a
    .!= KeyMap Int64
    forall a. Monoid a => a
    mempty)
          Parser ([(Text, Int64)] -> Maybe Int64 -> Text -> ConsumedCapacity)
    -> Parser [(Text, Int64)]
    -> Parser (Maybe Int64 -> Text -> ConsumedCapacity)
    forall a b. Parser (a -> b) -> Parser a -> Parser b
    forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
    <*> (((Key, Int64) -> (Text, Int64))
    -> [(Key, Int64)] -> [(Text, Int64)]
    forall a b. (a -> b) -> [a] -> [b]
    map (\(Key
    k, Int64
    v) -> (Key -> Text
    AK.toText Key
    k, Int64
    v)) ([(Key, Int64)] -> [(Text, Int64)])
    -> (KeyMap Int64 -> [(Key, Int64)])
    -> KeyMap Int64
    -> [(Text, Int64)]
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . KeyMap Int64 -> [(Key, Int64)]
    forall v. KeyMap v -> [(Key, v)]
    KM.toList (KeyMap Int64 -> [(Text, Int64)])
    -> Parser (KeyMap Int64) -> Parser [(Text, Int64)]
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Object
    o Object -> Key -> Parser (Maybe (KeyMap Int64))
    forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
    .:? Key
    "LocalSecondaryIndexes" Parser (Maybe (KeyMap Int64))
    -> KeyMap Int64 -> Parser (KeyMap Int64)
    forall a. Parser (Maybe a) -> a -> Parser a
    .!= KeyMap Int64
    forall a. Monoid a => a
    mempty)
          Parser (Maybe Int64 -> Text -> ConsumedCapacity)
    -> Parser (Maybe Int64) -> Parser (Text -> ConsumedCapacity)
    forall a b. Parser (a -> b) -> Parser a -> Parser b
    forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
    <*> (Object
    o Object -> Key -> Parser (Maybe Object)
    forall a. FromJSON a => Object -> Key -> Parser (Maybe a)
    .:? Key
    "Table" Parser (Maybe Object)
    -> (Maybe Object -> Parser (Maybe Int64)) -> Parser (Maybe Int64)
    forall a b. Parser a -> (a -> Parser b) -> Parser b
    forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
    >>= Parser (Maybe Int64)
    -> (Object -> Parser (Maybe Int64))
    -> Maybe Object
    -> Parser (Maybe Int64)
    forall b a. b -> (a -> b) -> Maybe a -> b
    maybe (Maybe Int64 -> Parser (Maybe Int64)
    forall a. a -> Parser a
    forall (m :: * -> *) a. Monad m => a -> m a
    return Maybe Int64
    forall a. Maybe a
    Nothing) (Object -> Key -> Parser (Maybe Int64)
    forall a. FromJSON a => Object -> Key -> Parser a
    .: Key
    "CapacityUnits"))
          Parser (Text -> ConsumedCapacity)
    -> Parser Text -> Parser ConsumedCapacity
    forall a b. Parser (a -> b) -> Parser a -> Parser b
    forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
    <*> Object
    o Object -> Key -> Parser Text
    forall a. FromJSON a => Object -> Key -> Parser a
    .: Key
    "TableName"
        parseJSON Value
    _ = String -> Parser ConsumedCapacity
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail String
    "ConsumedCapacity must be an Object."

    data ReturnConsumption = RCIndexes | RCTotal | RCNone
        deriving (ReturnConsumption -> ReturnConsumption -> Bool
    (ReturnConsumption -> ReturnConsumption -> Bool)
    -> (ReturnConsumption -> ReturnConsumption -> Bool)
    -> Eq ReturnConsumption
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: ReturnConsumption -> ReturnConsumption -> Bool
    == :: ReturnConsumption -> ReturnConsumption -> Bool
    $c/= :: ReturnConsumption -> ReturnConsumption -> Bool
    /= :: ReturnConsumption -> ReturnConsumption -> Bool
    Eq,Int -> ReturnConsumption -> ShowS
    [ReturnConsumption] -> ShowS
    ReturnConsumption -> String
    (Int -> ReturnConsumption -> ShowS)
    -> (ReturnConsumption -> String)
    -> ([ReturnConsumption] -> ShowS)
    -> Show ReturnConsumption
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> ReturnConsumption -> ShowS
    showsPrec :: Int -> ReturnConsumption -> ShowS
    $cshow :: ReturnConsumption -> String
    show :: ReturnConsumption -> String
    $cshowList :: [ReturnConsumption] -> ShowS
    showList :: [ReturnConsumption] -> ShowS
    Show,ReadPrec [ReturnConsumption]
    ReadPrec ReturnConsumption
    Int -> ReadS ReturnConsumption
    ReadS [ReturnConsumption]
    (Int -> ReadS ReturnConsumption)
    -> ReadS [ReturnConsumption]
    -> ReadPrec ReturnConsumption
    -> ReadPrec [ReturnConsumption]
    -> Read ReturnConsumption
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS ReturnConsumption
    readsPrec :: Int -> ReadS ReturnConsumption
    $creadList :: ReadS [ReturnConsumption]
    readList :: ReadS [ReturnConsumption]
    $creadPrec :: ReadPrec ReturnConsumption
    readPrec :: ReadPrec ReturnConsumption
    $creadListPrec :: ReadPrec [ReturnConsumption]
    readListPrec :: ReadPrec [ReturnConsumption]
    Read,Eq ReturnConsumption
    Eq ReturnConsumption =>
    (ReturnConsumption -> ReturnConsumption -> Ordering)
    -> (ReturnConsumption -> ReturnConsumption -> Bool)
    -> (ReturnConsumption -> ReturnConsumption -> Bool)
    -> (ReturnConsumption -> ReturnConsumption -> Bool)
    -> (ReturnConsumption -> ReturnConsumption -> Bool)
    -> (ReturnConsumption -> ReturnConsumption -> ReturnConsumption)
    -> (ReturnConsumption -> ReturnConsumption -> ReturnConsumption)
    -> Ord ReturnConsumption
    ReturnConsumption -> ReturnConsumption -> Bool
    ReturnConsumption -> ReturnConsumption -> Ordering
    ReturnConsumption -> ReturnConsumption -> ReturnConsumption
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: ReturnConsumption -> ReturnConsumption -> Ordering
    compare :: ReturnConsumption -> ReturnConsumption -> Ordering
    $c< :: ReturnConsumption -> ReturnConsumption -> Bool
    < :: ReturnConsumption -> ReturnConsumption -> Bool
    $c<= :: ReturnConsumption -> ReturnConsumption -> Bool
    <= :: ReturnConsumption -> ReturnConsumption -> Bool
    $c> :: ReturnConsumption -> ReturnConsumption -> Bool
    > :: ReturnConsumption -> ReturnConsumption -> Bool
    $c>= :: ReturnConsumption -> ReturnConsumption -> Bool
    >= :: ReturnConsumption -> ReturnConsumption -> Bool
    $cmax :: ReturnConsumption -> ReturnConsumption -> ReturnConsumption
    max :: ReturnConsumption -> ReturnConsumption -> ReturnConsumption
    $cmin :: ReturnConsumption -> ReturnConsumption -> ReturnConsumption
    min :: ReturnConsumption -> ReturnConsumption -> ReturnConsumption
    Ord,Typeable)

    instance ToJSON ReturnConsumption where
        toJSON :: ReturnConsumption -> Value
    toJSON ReturnConsumption
    RCIndexes = Text -> Value
    String Text
    "INDEXES"
        toJSON ReturnConsumption
    RCTotal = Text -> Value
    String Text
    "TOTAL"
        toJSON ReturnConsumption
    RCNone = Text -> Value
    String Text
    "NONE"

    instance Default ReturnConsumption where
        def :: ReturnConsumption
    def = ReturnConsumption
    RCNone

    data ReturnItemCollectionMetrics = RICMSize | RICMNone
        deriving (ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    (ReturnItemCollectionMetrics
     -> ReturnItemCollectionMetrics -> Bool)
    -> (ReturnItemCollectionMetrics
        -> ReturnItemCollectionMetrics -> Bool)
    -> Eq ReturnItemCollectionMetrics
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    == :: ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    $c/= :: ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    /= :: ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    Eq,Int -> ReturnItemCollectionMetrics -> ShowS
    [ReturnItemCollectionMetrics] -> ShowS
    ReturnItemCollectionMetrics -> String
    (Int -> ReturnItemCollectionMetrics -> ShowS)
    -> (ReturnItemCollectionMetrics -> String)
    -> ([ReturnItemCollectionMetrics] -> ShowS)
    -> Show ReturnItemCollectionMetrics
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> ReturnItemCollectionMetrics -> ShowS
    showsPrec :: Int -> ReturnItemCollectionMetrics -> ShowS
    $cshow :: ReturnItemCollectionMetrics -> String
    show :: ReturnItemCollectionMetrics -> String
    $cshowList :: [ReturnItemCollectionMetrics] -> ShowS
    showList :: [ReturnItemCollectionMetrics] -> ShowS
    Show,ReadPrec [ReturnItemCollectionMetrics]
    ReadPrec ReturnItemCollectionMetrics
    Int -> ReadS ReturnItemCollectionMetrics
    ReadS [ReturnItemCollectionMetrics]
    (Int -> ReadS ReturnItemCollectionMetrics)
    -> ReadS [ReturnItemCollectionMetrics]
    -> ReadPrec ReturnItemCollectionMetrics
    -> ReadPrec [ReturnItemCollectionMetrics]
    -> Read ReturnItemCollectionMetrics
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS ReturnItemCollectionMetrics
    readsPrec :: Int -> ReadS ReturnItemCollectionMetrics
    $creadList :: ReadS [ReturnItemCollectionMetrics]
    readList :: ReadS [ReturnItemCollectionMetrics]
    $creadPrec :: ReadPrec ReturnItemCollectionMetrics
    readPrec :: ReadPrec ReturnItemCollectionMetrics
    $creadListPrec :: ReadPrec [ReturnItemCollectionMetrics]
    readListPrec :: ReadPrec [ReturnItemCollectionMetrics]
    Read,Eq ReturnItemCollectionMetrics
    Eq ReturnItemCollectionMetrics =>
    (ReturnItemCollectionMetrics
     -> ReturnItemCollectionMetrics -> Ordering)
    -> (ReturnItemCollectionMetrics
        -> ReturnItemCollectionMetrics -> Bool)
    -> (ReturnItemCollectionMetrics
        -> ReturnItemCollectionMetrics -> Bool)
    -> (ReturnItemCollectionMetrics
        -> ReturnItemCollectionMetrics -> Bool)
    -> (ReturnItemCollectionMetrics
        -> ReturnItemCollectionMetrics -> Bool)
    -> (ReturnItemCollectionMetrics
        -> ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics)
    -> (ReturnItemCollectionMetrics
        -> ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics)
    -> Ord ReturnItemCollectionMetrics
    ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    ReturnItemCollectionMetrics
    -> ReturnItemCollectionMetrics -> Ordering
    ReturnItemCollectionMetrics
    -> ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: ReturnItemCollectionMetrics
    -> ReturnItemCollectionMetrics -> Ordering
    compare :: ReturnItemCollectionMetrics
    -> ReturnItemCollectionMetrics -> Ordering
    $c< :: ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    < :: ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    $c<= :: ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    <= :: ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    $c> :: ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    > :: ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    $c>= :: ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    >= :: ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics -> Bool
    $cmax :: ReturnItemCollectionMetrics
    -> ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics
    max :: ReturnItemCollectionMetrics
    -> ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics
    $cmin :: ReturnItemCollectionMetrics
    -> ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics
    min :: ReturnItemCollectionMetrics
    -> ReturnItemCollectionMetrics -> ReturnItemCollectionMetrics
    Ord,Typeable)

    instance ToJSON ReturnItemCollectionMetrics where
        toJSON :: ReturnItemCollectionMetrics -> Value
    toJSON ReturnItemCollectionMetrics
    RICMSize = Text -> Value
    String Text
    "SIZE"
        toJSON ReturnItemCollectionMetrics
    RICMNone = Text -> Value
    String Text
    "NONE"

    instance Default ReturnItemCollectionMetrics where
        def :: ReturnItemCollectionMetrics
    def = ReturnItemCollectionMetrics
    RICMNone

    data ItemCollectionMetrics = ItemCollectionMetrics {
          ItemCollectionMetrics -> (Text, DValue)
    icmKey      :: (T.Text, DValue)
        , ItemCollectionMetrics -> [Double]
    icmEstimate :: [Double]
        } deriving (ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    (ItemCollectionMetrics -> ItemCollectionMetrics -> Bool)
    -> (ItemCollectionMetrics -> ItemCollectionMetrics -> Bool)
    -> Eq ItemCollectionMetrics
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    == :: ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    $c/= :: ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    /= :: ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    Eq,Int -> ItemCollectionMetrics -> ShowS
    [ItemCollectionMetrics] -> ShowS
    ItemCollectionMetrics -> String
    (Int -> ItemCollectionMetrics -> ShowS)
    -> (ItemCollectionMetrics -> String)
    -> ([ItemCollectionMetrics] -> ShowS)
    -> Show ItemCollectionMetrics
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> ItemCollectionMetrics -> ShowS
    showsPrec :: Int -> ItemCollectionMetrics -> ShowS
    $cshow :: ItemCollectionMetrics -> String
    show :: ItemCollectionMetrics -> String
    $cshowList :: [ItemCollectionMetrics] -> ShowS
    showList :: [ItemCollectionMetrics] -> ShowS
    Show,ReadPrec [ItemCollectionMetrics]
    ReadPrec ItemCollectionMetrics
    Int -> ReadS ItemCollectionMetrics
    ReadS [ItemCollectionMetrics]
    (Int -> ReadS ItemCollectionMetrics)
    -> ReadS [ItemCollectionMetrics]
    -> ReadPrec ItemCollectionMetrics
    -> ReadPrec [ItemCollectionMetrics]
    -> Read ItemCollectionMetrics
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS ItemCollectionMetrics
    readsPrec :: Int -> ReadS ItemCollectionMetrics
    $creadList :: ReadS [ItemCollectionMetrics]
    readList :: ReadS [ItemCollectionMetrics]
    $creadPrec :: ReadPrec ItemCollectionMetrics
    readPrec :: ReadPrec ItemCollectionMetrics
    $creadListPrec :: ReadPrec [ItemCollectionMetrics]
    readListPrec :: ReadPrec [ItemCollectionMetrics]
    Read,Eq ItemCollectionMetrics
    Eq ItemCollectionMetrics =>
    (ItemCollectionMetrics -> ItemCollectionMetrics -> Ordering)
    -> (ItemCollectionMetrics -> ItemCollectionMetrics -> Bool)
    -> (ItemCollectionMetrics -> ItemCollectionMetrics -> Bool)
    -> (ItemCollectionMetrics -> ItemCollectionMetrics -> Bool)
    -> (ItemCollectionMetrics -> ItemCollectionMetrics -> Bool)
    -> (ItemCollectionMetrics
        -> ItemCollectionMetrics -> ItemCollectionMetrics)
    -> (ItemCollectionMetrics
        -> ItemCollectionMetrics -> ItemCollectionMetrics)
    -> Ord ItemCollectionMetrics
    ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    ItemCollectionMetrics -> ItemCollectionMetrics -> Ordering
    ItemCollectionMetrics
    -> ItemCollectionMetrics -> ItemCollectionMetrics
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: ItemCollectionMetrics -> ItemCollectionMetrics -> Ordering
    compare :: ItemCollectionMetrics -> ItemCollectionMetrics -> Ordering
    $c< :: ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    < :: ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    $c<= :: ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    <= :: ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    $c> :: ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    > :: ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    $c>= :: ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    >= :: ItemCollectionMetrics -> ItemCollectionMetrics -> Bool
    $cmax :: ItemCollectionMetrics
    -> ItemCollectionMetrics -> ItemCollectionMetrics
    max :: ItemCollectionMetrics
    -> ItemCollectionMetrics -> ItemCollectionMetrics
    $cmin :: ItemCollectionMetrics
    -> ItemCollectionMetrics -> ItemCollectionMetrics
    min :: ItemCollectionMetrics
    -> ItemCollectionMetrics -> ItemCollectionMetrics
    Ord,Typeable)

    instance FromJSON ItemCollectionMetrics where
        parseJSON :: Value -> Parser ItemCollectionMetrics
    parseJSON (Object Object
    o) = (Text, DValue) -> [Double] -> ItemCollectionMetrics
    ItemCollectionMetrics
          ((Text, DValue) -> [Double] -> ItemCollectionMetrics)
    -> Parser (Text, DValue)
    -> Parser ([Double] -> ItemCollectionMetrics)
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> (do m <- Object
    o Object -> Key -> Parser (KeyMap DValue)
    forall a. FromJSON a => Object -> Key -> Parser a
    .: Key
    "ItemCollectionKey"
                  return $ (\(Key
    k, DValue
    v) -> (Key -> Text
    AK.toText Key
    k, DValue
    v)) $ head $ KM.toList m)
          Parser ([Double] -> ItemCollectionMetrics)
    -> Parser [Double] -> Parser ItemCollectionMetrics
    forall a b. Parser (a -> b) -> Parser a -> Parser b
    forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
    <*> Object
    o Object -> Key -> Parser [Double]
    forall a. FromJSON a => Object -> Key -> Parser a
    .: Key
    "SizeEstimateRangeGB"
        parseJSON Value
    _ = String -> Parser ItemCollectionMetrics
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail String
    "ItemCollectionMetrics must be an Object."

    -------------------------------------------------------------------------------
    -- | What to return from the current update operation
    data UpdateReturn
        = URNone                    -- ^ Return nothing
        | URAllOld                  -- ^ Return old values
        | URUpdatedOld              -- ^ Return old values with a newer replacement
        | URAllNew                  -- ^ Return new values
        | URUpdatedNew              -- ^ Return new values that were replacements
        deriving (UpdateReturn -> UpdateReturn -> Bool
    (UpdateReturn -> UpdateReturn -> Bool)
    -> (UpdateReturn -> UpdateReturn -> Bool) -> Eq UpdateReturn
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: UpdateReturn -> UpdateReturn -> Bool
    == :: UpdateReturn -> UpdateReturn -> Bool
    $c/= :: UpdateReturn -> UpdateReturn -> Bool
    /= :: UpdateReturn -> UpdateReturn -> Bool
    Eq,Int -> UpdateReturn -> ShowS
    [UpdateReturn] -> ShowS
    UpdateReturn -> String
    (Int -> UpdateReturn -> ShowS)
    -> (UpdateReturn -> String)
    -> ([UpdateReturn] -> ShowS)
    -> Show UpdateReturn
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> UpdateReturn -> ShowS
    showsPrec :: Int -> UpdateReturn -> ShowS
    $cshow :: UpdateReturn -> String
    show :: UpdateReturn -> String
    $cshowList :: [UpdateReturn] -> ShowS
    showList :: [UpdateReturn] -> ShowS
    Show,ReadPrec [UpdateReturn]
    ReadPrec UpdateReturn
    Int -> ReadS UpdateReturn
    ReadS [UpdateReturn]
    (Int -> ReadS UpdateReturn)
    -> ReadS [UpdateReturn]
    -> ReadPrec UpdateReturn
    -> ReadPrec [UpdateReturn]
    -> Read UpdateReturn
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS UpdateReturn
    readsPrec :: Int -> ReadS UpdateReturn
    $creadList :: ReadS [UpdateReturn]
    readList :: ReadS [UpdateReturn]
    $creadPrec :: ReadPrec UpdateReturn
    readPrec :: ReadPrec UpdateReturn
    $creadListPrec :: ReadPrec [UpdateReturn]
    readListPrec :: ReadPrec [UpdateReturn]
    Read,Eq UpdateReturn
    Eq UpdateReturn =>
    (UpdateReturn -> UpdateReturn -> Ordering)
    -> (UpdateReturn -> UpdateReturn -> Bool)
    -> (UpdateReturn -> UpdateReturn -> Bool)
    -> (UpdateReturn -> UpdateReturn -> Bool)
    -> (UpdateReturn -> UpdateReturn -> Bool)
    -> (UpdateReturn -> UpdateReturn -> UpdateReturn)
    -> (UpdateReturn -> UpdateReturn -> UpdateReturn)
    -> Ord UpdateReturn
    UpdateReturn -> UpdateReturn -> Bool
    UpdateReturn -> UpdateReturn -> Ordering
    UpdateReturn -> UpdateReturn -> UpdateReturn
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: UpdateReturn -> UpdateReturn -> Ordering
    compare :: UpdateReturn -> UpdateReturn -> Ordering
    $c< :: UpdateReturn -> UpdateReturn -> Bool
    < :: UpdateReturn -> UpdateReturn -> Bool
    $c<= :: UpdateReturn -> UpdateReturn -> Bool
    <= :: UpdateReturn -> UpdateReturn -> Bool
    $c> :: UpdateReturn -> UpdateReturn -> Bool
    > :: UpdateReturn -> UpdateReturn -> Bool
    $c>= :: UpdateReturn -> UpdateReturn -> Bool
    >= :: UpdateReturn -> UpdateReturn -> Bool
    $cmax :: UpdateReturn -> UpdateReturn -> UpdateReturn
    max :: UpdateReturn -> UpdateReturn -> UpdateReturn
    $cmin :: UpdateReturn -> UpdateReturn -> UpdateReturn
    min :: UpdateReturn -> UpdateReturn -> UpdateReturn
    Ord,Typeable)

    instance ToJSON UpdateReturn where
        toJSON :: UpdateReturn -> Value
    toJSON UpdateReturn
    URNone = Value -> Value
    forall a. ToJSON a => a -> Value
    toJSON (Text -> Value
    String Text
    "NONE")
        toJSON UpdateReturn
    URAllOld = Value -> Value
    forall a. ToJSON a => a -> Value
    toJSON (Text -> Value
    String Text
    "ALL_OLD")
        toJSON UpdateReturn
    URUpdatedOld = Value -> Value
    forall a. ToJSON a => a -> Value
    toJSON (Text -> Value
    String Text
    "UPDATED_OLD")
        toJSON UpdateReturn
    URAllNew = Value -> Value
    forall a. ToJSON a => a -> Value
    toJSON (Text -> Value
    String Text
    "ALL_NEW")
        toJSON UpdateReturn
    URUpdatedNew = Value -> Value
    forall a. ToJSON a => a -> Value
    toJSON (Text -> Value
    String Text
    "UPDATED_NEW")

    instance Default UpdateReturn where
        def :: UpdateReturn
    def = UpdateReturn
    URNone

    -------------------------------------------------------------------------------
    -- | What to return from a 'Query' or 'Scan' query.
    data QuerySelect
        = SelectSpecific [T.Text]
        -- ^ Only return selected attributes
        | SelectCount
        -- ^ Return counts instead of attributes
        | SelectProjected
        -- ^ Return index-projected attributes
        | SelectAll
        -- ^ Default. Return everything.
        deriving (QuerySelect -> QuerySelect -> Bool
    (QuerySelect -> QuerySelect -> Bool)
    -> (QuerySelect -> QuerySelect -> Bool) -> Eq QuerySelect
    forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
    $c== :: QuerySelect -> QuerySelect -> Bool
    == :: QuerySelect -> QuerySelect -> Bool
    $c/= :: QuerySelect -> QuerySelect -> Bool
    /= :: QuerySelect -> QuerySelect -> Bool
    Eq,Int -> QuerySelect -> ShowS
    [QuerySelect] -> ShowS
    QuerySelect -> String
    (Int -> QuerySelect -> ShowS)
    -> (QuerySelect -> String)
    -> ([QuerySelect] -> ShowS)
    -> Show QuerySelect
    forall a.
    (Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
    $cshowsPrec :: Int -> QuerySelect -> ShowS
    showsPrec :: Int -> QuerySelect -> ShowS
    $cshow :: QuerySelect -> String
    show :: QuerySelect -> String
    $cshowList :: [QuerySelect] -> ShowS
    showList :: [QuerySelect] -> ShowS
    Show,ReadPrec [QuerySelect]
    ReadPrec QuerySelect
    Int -> ReadS QuerySelect
    ReadS [QuerySelect]
    (Int -> ReadS QuerySelect)
    -> ReadS [QuerySelect]
    -> ReadPrec QuerySelect
    -> ReadPrec [QuerySelect]
    -> Read QuerySelect
    forall a.
    (Int -> ReadS a)
    -> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
    $creadsPrec :: Int -> ReadS QuerySelect
    readsPrec :: Int -> ReadS QuerySelect
    $creadList :: ReadS [QuerySelect]
    readList :: ReadS [QuerySelect]
    $creadPrec :: ReadPrec QuerySelect
    readPrec :: ReadPrec QuerySelect
    $creadListPrec :: ReadPrec [QuerySelect]
    readListPrec :: ReadPrec [QuerySelect]
    Read,Eq QuerySelect
    Eq QuerySelect =>
    (QuerySelect -> QuerySelect -> Ordering)
    -> (QuerySelect -> QuerySelect -> Bool)
    -> (QuerySelect -> QuerySelect -> Bool)
    -> (QuerySelect -> QuerySelect -> Bool)
    -> (QuerySelect -> QuerySelect -> Bool)
    -> (QuerySelect -> QuerySelect -> QuerySelect)
    -> (QuerySelect -> QuerySelect -> QuerySelect)
    -> Ord QuerySelect
    QuerySelect -> QuerySelect -> Bool
    QuerySelect -> QuerySelect -> Ordering
    QuerySelect -> QuerySelect -> QuerySelect
    forall a.
    Eq a =>
    (a -> a -> Ordering)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> Bool)
    -> (a -> a -> a)
    -> (a -> a -> a)
    -> Ord a
    $ccompare :: QuerySelect -> QuerySelect -> Ordering
    compare :: QuerySelect -> QuerySelect -> Ordering
    $c< :: QuerySelect -> QuerySelect -> Bool
    < :: QuerySelect -> QuerySelect -> Bool
    $c<= :: QuerySelect -> QuerySelect -> Bool
    <= :: QuerySelect -> QuerySelect -> Bool
    $c> :: QuerySelect -> QuerySelect -> Bool
    > :: QuerySelect -> QuerySelect -> Bool
    $c>= :: QuerySelect -> QuerySelect -> Bool
    >= :: QuerySelect -> QuerySelect -> Bool
    $cmax :: QuerySelect -> QuerySelect -> QuerySelect
    max :: QuerySelect -> QuerySelect -> QuerySelect
    $cmin :: QuerySelect -> QuerySelect -> QuerySelect
    min :: QuerySelect -> QuerySelect -> QuerySelect
    Ord,Typeable)

    instance Default QuerySelect where def :: QuerySelect
    def = QuerySelect
    SelectAll

    -------------------------------------------------------------------------------
    querySelectJson :: KeyValue A.Value t => QuerySelect -> [t]
    querySelectJson :: forall t. KeyValue Value t => QuerySelect -> [t]
    querySelectJson (SelectSpecific [Text]
    as) =
        [ Key
    "Select" Key -> Value -> t
    forall v. ToJSON v => Key -> v -> t
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Text -> Value
    String Text
    "SPECIFIC_ATTRIBUTES"
        , Key
    "AttributesToGet" Key -> [Text] -> t
    forall v. ToJSON v => Key -> v -> t
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= [Text]
    as]
    querySelectJson QuerySelect
    SelectCount = [Key
    "Select" Key -> Value -> t
    forall v. ToJSON v => Key -> v -> t
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Text -> Value
    String Text
    "COUNT"]
    querySelectJson QuerySelect
    SelectProjected = [Key
    "Select" Key -> Value -> t
    forall v. ToJSON v => Key -> v -> t
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Text -> Value
    String Text
    "ALL_PROJECTED_ATTRIBUTES"]
    querySelectJson QuerySelect
    SelectAll = [Key
    "Select" Key -> Value -> t
    forall v. ToJSON v => Key -> v -> t
    forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
    .= Text -> Value
    String Text
    "ALL_ATTRIBUTES"]

    -------------------------------------------------------------------------------
    -- | A class to help predict DynamoDb size of values, attributes and
    -- entire items. The result is given in number of bytes.
    class DynSize a where
        dynSize :: a -> Int

    instance DynSize DValue where
        dynSize :: DValue -> Int
    dynSize DValue
    DNull = Int
    8
        dynSize (DBool Bool
    _) = Int
    8
        dynSize (DBoolSet Set Bool
    s) = [Int] -> Int
    forall a. Num a => [a] -> a
    forall (t :: * -> *) a. (Foldable t, Num a) => t a -> a
    sum ([Int] -> Int) -> [Int] -> Int
    forall a b. (a -> b) -> a -> b
    $ (Bool -> Int) -> [Bool] -> [Int]
    forall a b. (a -> b) -> [a] -> [b]
    map (DValue -> Int
    forall a. DynSize a => a -> Int
    dynSize (DValue -> Int) -> (Bool -> DValue) -> Bool -> Int
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Bool -> DValue
    DBool) ([Bool] -> [Int]) -> [Bool] -> [Int]
    forall a b. (a -> b) -> a -> b
    $ Set Bool -> [Bool]
    forall a. Set a -> [a]
    S.toList Set Bool
    s
        dynSize (DNum Scientific
    _) = Int
    8
        dynSize (DString Text
    a) = Text -> Int
    T.length Text
    a
        dynSize (DBinary ByteString
    bs) = Text -> Int
    T.length (Text -> Int) -> (ByteString -> Text) -> ByteString -> Int
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ByteString -> Text
    T.decodeUtf8 (ByteString -> Int) -> ByteString -> Int
    forall a b. (a -> b) -> a -> b
    $ ByteString -> ByteString
    Base64.encode ByteString
    bs
        dynSize (DNumSet Set Scientific
    s) = Int
    8 Int -> Int -> Int
    forall a. Num a => a -> a -> a
    * Set Scientific -> Int
    forall a. Set a -> Int
    S.size Set Scientific
    s
        dynSize (DStringSet Set Text
    s) = [Int] -> Int
    forall a. Num a => [a] -> a
    forall (t :: * -> *) a. (Foldable t, Num a) => t a -> a
    sum ([Int] -> Int) -> [Int] -> Int
    forall a b. (a -> b) -> a -> b
    $ (Text -> Int) -> [Text] -> [Int]
    forall a b. (a -> b) -> [a] -> [b]
    map (DValue -> Int
    forall a. DynSize a => a -> Int
    dynSize (DValue -> Int) -> (Text -> DValue) -> Text -> Int
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . Text -> DValue
    DString) ([Text] -> [Int]) -> [Text] -> [Int]
    forall a b. (a -> b) -> a -> b
    $ Set Text -> [Text]
    forall a. Set a -> [a]
    S.toList Set Text
    s
        dynSize (DBinSet Set ByteString
    s) = [Int] -> Int
    forall a. Num a => [a] -> a
    forall (t :: * -> *) a. (Foldable t, Num a) => t a -> a
    sum ([Int] -> Int) -> [Int] -> Int
    forall a b. (a -> b) -> a -> b
    $ (ByteString -> Int) -> [ByteString] -> [Int]
    forall a b. (a -> b) -> [a] -> [b]
    map (DValue -> Int
    forall a. DynSize a => a -> Int
    dynSize (DValue -> Int) -> (ByteString -> DValue) -> ByteString -> Int
    forall b c a. (b -> c) -> (a -> b) -> a -> c
    . ByteString -> DValue
    DBinary) ([ByteString] -> [Int]) -> [ByteString] -> [Int]
    forall a b. (a -> b) -> a -> b
    $ Set ByteString -> [ByteString]
    forall a. Set a -> [a]
    S.toList Set ByteString
    s
        dynSize (DList Vector DValue
    s) = [Int] -> Int
    forall a. Num a => [a] -> a
    forall (t :: * -> *) a. (Foldable t, Num a) => t a -> a
    sum ([Int] -> Int) -> [Int] -> Int
    forall a b. (a -> b) -> a -> b
    $ (DValue -> Int) -> [DValue] -> [Int]
    forall a b. (a -> b) -> [a] -> [b]
    map DValue -> Int
    forall a. DynSize a => a -> Int
    dynSize ([DValue] -> [Int]) -> [DValue] -> [Int]
    forall a b. (a -> b) -> a -> b
    $ Vector DValue -> [DValue]
    forall a. Vector a -> [a]
    V.toList Vector DValue
    s
        dynSize (DMap Map Text DValue
    s) = [Int] -> Int
    forall a. Num a => [a] -> a
    forall (t :: * -> *) a. (Foldable t, Num a) => t a -> a
    sum ([Int] -> Int) -> [Int] -> Int
    forall a b. (a -> b) -> a -> b
    $ (DValue -> Int) -> [DValue] -> [Int]
    forall a b. (a -> b) -> [a] -> [b]
    map DValue -> Int
    forall a. DynSize a => a -> Int
    dynSize ([DValue] -> [Int]) -> [DValue] -> [Int]
    forall a b. (a -> b) -> a -> b
    $ Map Text DValue -> [DValue]
    forall k a. Map k a -> [a]
    M.elems Map Text DValue
    s

    instance DynSize Attribute where
        dynSize :: Attribute -> Int
    dynSize (Attribute Text
    k DValue
    v) = Text -> Int
    T.length Text
    k Int -> Int -> Int
    forall a. Num a => a -> a -> a
    + DValue -> Int
    forall a. DynSize a => a -> Int
    dynSize DValue
    v

    instance DynSize Item where
        dynSize :: Map Text DValue -> Int
    dynSize Map Text DValue
    m = [Int] -> Int
    forall a. Num a => [a] -> a
    forall (t :: * -> *) a. (Foldable t, Num a) => t a -> a
    sum ([Int] -> Int) -> [Int] -> Int
    forall a b. (a -> b) -> a -> b
    $ (Attribute -> Int) -> [Attribute] -> [Int]
    forall a b. (a -> b) -> [a] -> [b]
    map Attribute -> Int
    forall a. DynSize a => a -> Int
    dynSize ([Attribute] -> [Int]) -> [Attribute] -> [Int]
    forall a b. (a -> b) -> a -> b
    $ Map Text DValue -> [Attribute]
    attributes Map Text DValue
    m

    instance DynSize a => DynSize [a] where
        dynSize :: [a] -> Int
    dynSize [a]
    as = [Int] -> Int
    forall a. Num a => [a] -> a
    forall (t :: * -> *) a. (Foldable t, Num a) => t a -> a
    sum ([Int] -> Int) -> [Int] -> Int
    forall a b. (a -> b) -> a -> b
    $ (a -> Int) -> [a] -> [Int]
    forall a b. (a -> b) -> [a] -> [b]
    map a -> Int
    forall a. DynSize a => a -> Int
    dynSize [a]
    as

    instance DynSize a => DynSize (Maybe a) where
        dynSize :: Maybe a -> Int
    dynSize = Int -> (a -> Int) -> Maybe a -> Int
    forall b a. b -> (a -> b) -> Maybe a -> b
    maybe Int
    0 a -> Int
    forall a. DynSize a => a -> Int
    dynSize

    instance (DynSize a, DynSize b) => DynSize (Either a b) where
        dynSize :: Either a b -> Int
    dynSize = (a -> Int) -> (b -> Int) -> Either a b -> Int
    forall a c b. (a -> c) -> (b -> c) -> Either a b -> c
    either a -> Int
    forall a. DynSize a => a -> Int
    dynSize b -> Int
    forall a. DynSize a => a -> Int
    dynSize

    -------------------------------------------------------------------------------
    -- | Will an attribute be considered empty by DynamoDb?
    --
    -- A 'PutItem' (or similar) with empty attributes will be rejected
    -- with a 'ValidationException'.
    nullAttr :: Attribute -> Bool
    nullAttr :: Attribute -> Bool
    nullAttr (Attribute Text
    _ DValue
    val) =
        case DValue
    val of
          DString Text
    "" -> Bool
    True
          DBinary ByteString
    "" -> Bool
    True
          DNumSet Set Scientific
    s | Set Scientific -> Bool
    forall a. Set a -> Bool
    S.null Set Scientific
    s -> Bool
    True
          DStringSet Set Text
    s | Set Text -> Bool
    forall a. Set a -> Bool
    S.null Set Text
    s -> Bool
    True
          DBinSet Set ByteString
    s | Set ByteString -> Bool
    forall a. Set a -> Bool
    S.null Set ByteString
    s -> Bool
    True
          DValue
    _ -> Bool
    False

    -------------------------------------------------------------------------------
    --
    -- | Item Parsing
    --
    -------------------------------------------------------------------------------

    -- | Failure continuation.
    type Failure f r   = String -> f r

    -- | Success continuation.
    type Success a f r = a -> f r

    -- | A continuation-based parser type.
    newtype Parser a = Parser {
          forall a.
    Parser a
    -> forall (f :: * -> *) r. Failure f r -> Success a f r -> f r
    runParser :: forall f r.
                       Failure f r
                    -> Success a f r
                    -> f r
        }

    instance Monad Parser where
        Parser a
    m >>= :: forall a b. Parser a -> (a -> Parser b) -> Parser b
    >>= a -> Parser b
    g = (forall (f :: * -> *) r. Failure f r -> Success b f r -> f r)
    -> Parser b
    forall a.
    (forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
    -> Parser a
    Parser ((forall (f :: * -> *) r. Failure f r -> Success b f r -> f r)
     -> Parser b)
    -> (forall (f :: * -> *) r. Failure f r -> Success b f r -> f r)
    -> Parser b
    forall a b. (a -> b) -> a -> b
    $ \Failure f r
    kf Success b f r
    ks -> let ks' :: a -> f r
    ks' a
    a = Parser b
    -> forall (f :: * -> *) r. Failure f r -> Success b f r -> f r
    forall a.
    Parser a
    -> forall (f :: * -> *) r. Failure f r -> Success a f r -> f r
    runParser (a -> Parser b
    g a
    a) Failure f r
    kf Success b f r
    ks
                                     in Parser a
    -> forall (f :: * -> *) r. Failure f r -> Success a f r -> f r
    forall a.
    Parser a
    -> forall (f :: * -> *) r. Failure f r -> Success a f r -> f r
    runParser Parser a
    m Failure f r
    kf a -> f r
    ks'
        {-# INLINE (>>=) #-}
        return :: forall a. a -> Parser a
    return a
    a = (forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
    -> Parser a
    forall a.
    (forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
    -> Parser a
    Parser ((forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
     -> Parser a)
    -> (forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
    -> Parser a
    forall a b. (a -> b) -> a -> b
    $ \Failure f r
    _kf Success a f r
    ks -> Success a f r
    ks a
    a
        {-# INLINE return #-}
    #if !(MIN_VERSION_base(4,13,0))
        fail msg = Parser $ \kf _ks -> kf msg
        {-# INLINE fail #-}
    #endif

    #if MIN_VERSION_base(4,9,0)
    instance Fail.MonadFail Parser where
        fail :: forall a. String -> Parser a
    fail String
    msg = (forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
    -> Parser a
    forall a.
    (forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
    -> Parser a
    Parser ((forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
     -> Parser a)
    -> (forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
    -> Parser a
    forall a b. (a -> b) -> a -> b
    $ \Failure f r
    kf Success a f r
    _ks -> Failure f r
    kf String
    msg
        {-# INLINE fail #-}
    #endif

    instance Functor Parser where
        fmap :: forall a b. (a -> b) -> Parser a -> Parser b
    fmap a -> b
    f Parser a
    m = (forall (f :: * -> *) r. Failure f r -> Success b f r -> f r)
    -> Parser b
    forall a.
    (forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
    -> Parser a
    Parser ((forall (f :: * -> *) r. Failure f r -> Success b f r -> f r)
     -> Parser b)
    -> (forall (f :: * -> *) r. Failure f r -> Success b f r -> f r)
    -> Parser b
    forall a b. (a -> b) -> a -> b
    $ \Failure f r
    kf Success b f r
    ks -> let ks' :: a -> f r
    ks' a
    a = Success b f r
    ks (a -> b
    f a
    a)
                                      in Parser a
    -> forall (f :: * -> *) r. Failure f r -> Success a f r -> f r
    forall a.
    Parser a
    -> forall (f :: * -> *) r. Failure f r -> Success a f r -> f r
    runParser Parser a
    m Failure f r
    kf a -> f r
    ks'
        {-# INLINE fmap #-}

    instance Applicative Parser where
        pure :: forall a. a -> Parser a
    pure  = a -> Parser a
    forall a. a -> Parser a
    forall (m :: * -> *) a. Monad m => a -> m a
    return
        {-# INLINE pure #-}
        <*> :: forall a b. Parser (a -> b) -> Parser a -> Parser b
    (<*>) = Parser (a -> b) -> Parser a -> Parser b
    forall a b. Parser (a -> b) -> Parser a -> Parser b
    apP
        {-# INLINE (<*>) #-}

    instance Alternative Parser where
        empty :: forall a. Parser a
    empty = String -> Parser a
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail String
    "empty"
        {-# INLINE empty #-}
        <|> :: forall a. Parser a -> Parser a -> Parser a
    (<|>) = Parser a -> Parser a -> Parser a
    forall a. Parser a -> Parser a -> Parser a
    forall (m :: * -> *) a. MonadPlus m => m a -> m a -> m a
    mplus
        {-# INLINE (<|>) #-}

    instance MonadPlus Parser where
        mzero :: forall a. Parser a
    mzero = String -> Parser a
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail String
    "mzero"
        {-# INLINE mzero #-}
        mplus :: forall a. Parser a -> Parser a -> Parser a
    mplus Parser a
    a Parser a
    b = (forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
    -> Parser a
    forall a.
    (forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
    -> Parser a
    Parser ((forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
     -> Parser a)
    -> (forall (f :: * -> *) r. Failure f r -> Success a f r -> f r)
    -> Parser a
    forall a b. (a -> b) -> a -> b
    $ \Failure f r
    kf Success a f r
    ks -> let kf' :: Failure f r
    kf' String
    _ = Parser a
    -> forall (f :: * -> *) r. Failure f r -> Success a f r -> f r
    forall a.
    Parser a
    -> forall (f :: * -> *) r. Failure f r -> Success a f r -> f r
    runParser Parser a
    b Failure f r
    kf Success a f r
    ks
                                       in Parser a
    -> forall (f :: * -> *) r. Failure f r -> Success a f r -> f r
    forall a.
    Parser a
    -> forall (f :: * -> *) r. Failure f r -> Success a f r -> f r
    runParser Parser a
    a Failure f r
    kf' Success a f r
    ks
        {-# INLINE mplus #-}

    instance Sem.Semigroup (Parser a) where
        <> :: Parser a -> Parser a -> Parser a
    (<>) = Parser a -> Parser a -> Parser a
    forall a. Parser a -> Parser a -> Parser a
    forall (m :: * -> *) a. MonadPlus m => m a -> m a -> m a
    mplus
        {-# INLINE (<>) #-}

    instance Monoid (Parser a) where
        mempty :: Parser a
    mempty  = String -> Parser a
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail String
    "mempty"
        {-# INLINE mempty #-}
        mappend :: Parser a -> Parser a -> Parser a
    mappend = Parser a -> Parser a -> Parser a
    forall a. Semigroup a => a -> a -> a
    (Sem.<>)
        {-# INLINE mappend #-}

    apP :: Parser (a -> b) -> Parser a -> Parser b
    apP :: forall a b. Parser (a -> b) -> Parser a -> Parser b
    apP Parser (a -> b)
    d Parser a
    e = do
      b <- Parser (a -> b)
    d
      a <- e
      return (b a)
    {-# INLINE apP #-}

    -------------------------------------------------------------------------------
    -- | Types convertible to DynamoDb 'Item' collections.
    --
    -- Use 'attr' and 'attrAs' combinators to conveniently define instances.
    class ToDynItem a where
        toItem :: a -> Item

    -------------------------------------------------------------------------------
    -- | Types parseable from DynamoDb 'Item' collections.
    --
    -- User 'getAttr' family of functions to applicatively or monadically
    -- parse into your custom types.
    class FromDynItem a where
        parseItem :: Item -> Parser a

    instance ToDynItem Item where toItem :: Map Text DValue -> Map Text DValue
    toItem = Map Text DValue -> Map Text DValue
    forall a. a -> a
    id

    instance FromDynItem Item where parseItem :: Map Text DValue -> Parser (Map Text DValue)
    parseItem = Map Text DValue -> Parser (Map Text DValue)
    forall a. a -> Parser a
    forall (m :: * -> *) a. Monad m => a -> m a
    return

    instance DynVal a => ToDynItem [(T.Text, a)] where
        toItem :: [(Text, a)] -> Map Text DValue
    toItem [(Text, a)]
    as = [Attribute] -> Map Text DValue
    item ([Attribute] -> Map Text DValue) -> [Attribute] -> Map Text DValue
    forall a b. (a -> b) -> a -> b
    $ ((Text, a) -> Attribute) -> [(Text, a)] -> [Attribute]
    forall a b. (a -> b) -> [a] -> [b]
    map ((Text -> a -> Attribute) -> (Text, a) -> Attribute
    forall a b c. (a -> b -> c) -> (a, b) -> c
    uncurry Text -> a -> Attribute
    forall a. DynVal a => Text -> a -> Attribute
    attr) [(Text, a)]
    as

    instance (Typeable a, DynVal a) => FromDynItem [(T.Text, a)] where
        parseItem :: Map Text DValue -> Parser [(Text, a)]
    parseItem Map Text DValue
    i = ((Text, DValue) -> Parser (Text, a))
    -> [(Text, DValue)] -> Parser [(Text, a)]
    forall (t :: * -> *) (m :: * -> *) a b.
    (Traversable t, Monad m) =>
    (a -> m b) -> t a -> m (t b)
    forall (m :: * -> *) a b. Monad m => (a -> m b) -> [a] -> m [b]
    mapM (Text, DValue) -> Parser (Text, a)
    f ([(Text, DValue)] -> Parser [(Text, a)])
    -> [(Text, DValue)] -> Parser [(Text, a)]
    forall a b. (a -> b) -> a -> b
    $ Map Text DValue -> [(Text, DValue)]
    forall k a. Map k a -> [(k, a)]
    M.toList Map Text DValue
    i
            where
              f :: (Text, DValue) -> Parser (Text, a)
    f (Text
    k,DValue
    v) = do
                  v' <- Parser a -> (a -> Parser a) -> Maybe a -> Parser a
    forall b a. b -> (a -> b) -> Maybe a -> b
    maybe (String -> Parser a
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail (Tagged a DValue -> String
    forall a. Typeable a => Tagged a DValue -> String
    valErr (DValue -> Tagged a DValue
    forall {k} (s :: k) b. b -> Tagged s b
    Tagged DValue
    v :: Tagged a DValue))) a -> Parser a
    forall a. a -> Parser a
    forall (m :: * -> *) a. Monad m => a -> m a
    return (Maybe a -> Parser a) -> Maybe a -> Parser a
    forall a b. (a -> b) -> a -> b
    $
                        DValue -> Maybe a
    forall a. DynVal a => DValue -> Maybe a
    fromValue DValue
    v
                  return (k, v')

    instance DynVal a => ToDynItem (M.Map T.Text a) where
        toItem :: Map Text a -> Map Text DValue
    toItem Map Text a
    m = [(Text, a)] -> Map Text DValue
    forall a. ToDynItem a => a -> Map Text DValue
    toItem ([(Text, a)] -> Map Text DValue) -> [(Text, a)] -> Map Text DValue
    forall a b. (a -> b) -> a -> b
    $ Map Text a -> [(Text, a)]
    forall k a. Map k a -> [(k, a)]
    M.toList Map Text a
    m

    instance (Typeable a, DynVal a) => FromDynItem (M.Map T.Text a) where
        parseItem :: Map Text DValue -> Parser (Map Text a)
    parseItem Map Text DValue
    i = [(Text, a)] -> Map Text a
    forall k a. Ord k => [(k, a)] -> Map k a
    M.fromList ([(Text, a)] -> Map Text a)
    -> Parser [(Text, a)] -> Parser (Map Text a)
    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
    <$> Map Text DValue -> Parser [(Text, a)]
    forall a. FromDynItem a => Map Text DValue -> Parser a
    parseItem Map Text DValue
    i

    valErr :: forall a. Typeable a => Tagged a DValue -> String
    valErr :: forall a. Typeable a => Tagged a DValue -> String
    valErr (Tagged DValue
    dv) = String
    "Can't convert DynamoDb value " String -> ShowS
    forall a. Semigroup a => a -> a -> a
    Sem.<> DValue -> String
    forall a. Show a => a -> String
    show DValue
    dv String -> ShowS
    forall a. Semigroup a => a -> a -> a
    Sem.<>
                  String
    " into type " String -> ShowS
    forall a. Semigroup a => a -> a -> a
    Sem.<> (TypeRep -> String
    forall a. Show a => a -> String
    show (a -> TypeRep
    forall a. Typeable a => a -> TypeRep
    typeOf (a
    forall a. HasCallStack => a
    undefined :: a)))

    -- | Convenience combinator for parsing fields from an 'Item' returned
    -- by DynamoDb.
    getAttr
        :: forall a. (Typeable a, DynVal a)
        => T.Text
        -- ^ Attribute name
        -> Item
        -- ^ Item from DynamoDb
        -> Parser a
    getAttr :: forall a.
    (Typeable a, DynVal a) =>
    Text -> Map Text DValue -> Parser a
    getAttr Text
    k Map Text DValue
    m = do
        case Text -> Map Text DValue -> Maybe DValue
    forall k a. Ord k => k -> Map k a -> Maybe a
    M.lookup Text
    k Map Text DValue
    m of
          Maybe DValue
    Nothing -> String -> Parser a
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail (String
    "Key " String -> ShowS
    forall a. Semigroup a => a -> a -> a
    Sem.<> Text -> String
    T.unpack Text
    k String -> ShowS
    forall a. Semigroup a => a -> a -> a
    Sem.<> String
    " not found")
          Just DValue
    dv -> Parser a -> (a -> Parser a) -> Maybe a -> Parser a
    forall b a. b -> (a -> b) -> Maybe a -> b
    maybe (String -> Parser a
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail (Tagged a DValue -> String
    forall a. Typeable a => Tagged a DValue -> String
    valErr (DValue -> Tagged a DValue
    forall {k} (s :: k) b. b -> Tagged s b
    Tagged DValue
    dv :: Tagged a DValue))) a -> Parser a
    forall a. a -> Parser a
    forall (m :: * -> *) a. Monad m => a -> m a
    return (Maybe a -> Parser a) -> Maybe a -> Parser a
    forall a b. (a -> b) -> a -> b
    $ DValue -> Maybe a
    forall a. DynVal a => DValue -> Maybe a
    fromValue DValue
    dv

    -- | Parse attribute if it's present in the 'Item'. Fail if attribute
    -- is present but conversion fails.
    getAttr'
        :: forall a. (DynVal a)
        => T.Text
        -- ^ Attribute name
        -> Item
        -- ^ Item from DynamoDb
        -> Parser (Maybe a)
    getAttr' :: forall a. DynVal a => Text -> Map Text DValue -> Parser (Maybe a)
    getAttr' Text
    k Map Text DValue
    m = do
        case Text -> Map Text DValue -> Maybe DValue
    forall k a. Ord k => k -> Map k a -> Maybe a
    M.lookup Text
    k Map Text DValue
    m of
          Maybe DValue
    Nothing -> Maybe a -> Parser (Maybe a)
    forall a. a -> Parser a
    forall (m :: * -> *) a. Monad m => a -> m a
    return Maybe a
    forall a. Maybe a
    Nothing
          Just DValue
    dv -> Maybe a -> Parser (Maybe a)
    forall a. a -> Parser a
    forall (m :: * -> *) a. Monad m => a -> m a
    return (Maybe a -> Parser (Maybe a)) -> Maybe a -> Parser (Maybe a)
    forall a b. (a -> b) -> a -> b
    $ DValue -> Maybe a
    forall a. DynVal a => DValue -> Maybe a
    fromValue DValue
    dv

    -- | Combinator for parsing an attribute into a 'FromDynItem'.
    parseAttr
        :: FromDynItem a
        => T.Text
        -- ^ Attribute name
        -> Item
        -- ^ Item from DynamoDb
        -> Parser a
    parseAttr :: forall a. FromDynItem a => Text -> Map Text DValue -> Parser a
    parseAttr Text
    k Map Text DValue
    m =
      case Text -> Map Text DValue -> Maybe DValue
    forall k a. Ord k => k -> Map k a -> Maybe a
    M.lookup Text
    k Map Text DValue
    m of
        Maybe DValue
    Nothing -> String -> Parser a
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail (String
    "Key " String -> ShowS
    forall a. Semigroup a => a -> a -> a
    Sem.<> Text -> String
    T.unpack Text
    k String -> ShowS
    forall a. Semigroup a => a -> a -> a
    Sem.<> String
    " not found")
        Just (DMap Map Text DValue
    dv) -> (String -> Parser a)
    -> (a -> Parser a) -> Either String a -> Parser a
    forall a c b. (a -> c) -> (b -> c) -> Either a b -> c
    either (Parser a -> String -> Parser a
    forall a b. a -> b -> a
    const (String -> Parser a
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail String
    "...")) a -> Parser a
    forall a. a -> Parser a
    forall (m :: * -> *) a. Monad m => a -> m a
    return (Either String a -> Parser a) -> Either String a -> Parser a
    forall a b. (a -> b) -> a -> b
    $ Map Text DValue -> Either String a
    forall a. FromDynItem a => Map Text DValue -> Either String a
    fromItem Map Text DValue
    dv
        Maybe DValue
    _       -> String -> Parser a
    forall a. String -> Parser a
    forall (m :: * -> *) a. MonadFail m => String -> m a
    fail (String
    "Key " String -> ShowS
    forall a. Semigroup a => a -> a -> a
    Sem.<> Text -> String
    T.unpack Text
    k String -> ShowS
    forall a. Semigroup a => a -> a -> a
    Sem.<> String
    " is not a map!")

    -------------------------------------------------------------------------------
    -- | Parse an 'Item' into target type using the 'FromDynItem'
    -- instance.
    fromItem :: FromDynItem a => Item -> Either String a
    fromItem :: forall a. FromDynItem a => Map Text DValue -> Either String a
    fromItem Map Text DValue
    i = Parser a
    -> forall (f :: * -> *) r. Failure f r -> Success a f r -> f r
    forall a.
    Parser a
    -> forall (f :: * -> *) r. Failure f r -> Success a f r -> f r
    runParser (Map Text DValue -> Parser a
    forall a. FromDynItem a => Map Text DValue -> Parser a
    parseItem Map Text DValue
    i) Failure (Either String) a
    forall a b. a -> Either a b
    Left Success a (Either String) a
    forall a b. b -> Either a b
    Right