-- | BlockIndex query parameter

module Blockfrost.Types.Shared.BlockIndex
  where

import qualified Data.Text
import GHC.Generics
import Servant.API (FromHttpApiData (..), QueryParam, ToHttpApiData (..))
import Servant.Docs
  ( DocQueryParam (..)
  , ParamKind (..)
  , ToParam (..)
  , ToSample (..)
  , samples
  )

-- | Block height (number) and optional index
data BlockIndex = BlockIndex {
    BlockIndex -> Integer
blockIndexHeight :: Integer
  , BlockIndex -> Maybe Integer
blockIndexIndex  :: Maybe Integer
  }
  deriving stock (BlockIndex -> BlockIndex -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
/= :: BlockIndex -> BlockIndex -> Bool
$c/= :: BlockIndex -> BlockIndex -> Bool
== :: BlockIndex -> BlockIndex -> Bool
$c== :: BlockIndex -> BlockIndex -> Bool
Eq, Int -> BlockIndex -> ShowS
[BlockIndex] -> ShowS
BlockIndex -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
showList :: [BlockIndex] -> ShowS
$cshowList :: [BlockIndex] -> ShowS
show :: BlockIndex -> String
$cshow :: BlockIndex -> String
showsPrec :: Int -> BlockIndex -> ShowS
$cshowsPrec :: Int -> BlockIndex -> ShowS
Show, forall x. Rep BlockIndex x -> BlockIndex
forall x. BlockIndex -> Rep BlockIndex x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cto :: forall x. Rep BlockIndex x -> BlockIndex
$cfrom :: forall x. BlockIndex -> Rep BlockIndex x
Generic)

instance ToHttpApiData BlockIndex where
  toUrlPiece :: BlockIndex -> Text
toUrlPiece BlockIndex
bi = String -> Text
Data.Text.pack forall a b. (a -> b) -> a -> b
$
       forall a. Show a => a -> String
show (BlockIndex -> Integer
blockIndexHeight BlockIndex
bi)
    forall a. Semigroup a => a -> a -> a
<> forall b a. b -> (a -> b) -> Maybe a -> b
maybe forall a. Monoid a => a
mempty ((Char
':'forall a. a -> [a] -> [a]
:) forall b c a. (b -> c) -> (a -> b) -> a -> c
.forall a. Show a => a -> String
show) (BlockIndex -> Maybe Integer
blockIndexIndex BlockIndex
bi)

instance FromHttpApiData BlockIndex where
  parseUrlPiece :: Text -> Either Text BlockIndex
parseUrlPiece Text
x = case Text -> Text -> [Text]
Data.Text.splitOn Text
":" Text
x of
    [Text
""] -> forall a b. a -> Either a b
Left Text
"Empty block index"
    [Text
bh] -> (Integer -> Maybe Integer -> BlockIndex
`BlockIndex` forall a. Maybe a
Nothing) forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromHttpApiData a => Text -> Either Text a
parseUrlPiece Text
bh
    [Text
bh, Text
idx] -> Integer -> Maybe Integer -> BlockIndex
BlockIndex forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromHttpApiData a => Text -> Either Text a
parseUrlPiece Text
bh forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> (forall a. a -> Maybe a
Just forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. FromHttpApiData a => Text -> Either Text a
parseUrlPiece Text
idx)
    [Text]
_ -> forall a b. a -> Either a b
Left Text
"Invalid block index"

instance ToParam (QueryParam "from" BlockIndex) where
  toParam :: Proxy (QueryParam "from" BlockIndex) -> DocQueryParam
toParam Proxy (QueryParam "from" BlockIndex)
_ =
    String -> [String] -> String -> ParamKind -> DocQueryParam
DocQueryParam
      String
"blockIndex"
      []
      String
"The block number and optionally also index from which (inclusive)\
      \ to start search for results, concatenated using colon.\
      \ Has to be lower than or equal to `to` parameter."
      ParamKind
Normal

instance ToParam (QueryParam "to" BlockIndex) where
  toParam :: Proxy (QueryParam "to" BlockIndex) -> DocQueryParam
toParam Proxy (QueryParam "to" BlockIndex)
_ =
    String -> [String] -> String -> ParamKind -> DocQueryParam
DocQueryParam
      String
"blockIndex"
      []
      String
"The block number and optionally also index from which (inclusive)\
      \ to end the search for results, concatenated using colon.\
      \ Has to be higher than or equal to `from` parameter."
      ParamKind
Normal

instance ToSample BlockIndex where
    toSamples :: Proxy BlockIndex -> [(Text, BlockIndex)]
toSamples = forall (f :: * -> *) a. Applicative f => a -> f a
pure forall a b. (a -> b) -> a -> b
$ forall a. [a] -> [(Text, a)]
samples [
        Integer -> Maybe Integer -> BlockIndex
BlockIndex Integer
892961 forall a. Maybe a
Nothing
      , Integer -> Maybe Integer -> BlockIndex
BlockIndex Integer
9999269 (forall a. a -> Maybe a
Just Integer
10)
      ]