{-# LANGUAGE DeriveDataTypeable #-} {-# LANGUAGE DeriveGeneric #-} {-# LANGUAGE GeneralizedNewtypeDeriving #-} {-# LANGUAGE TemplateHaskell #-} -- | -- Module : Network.Ethereum.Web3.Types -- Copyright : Alexander Krupenkin 2016 -- License : BSD3 -- -- Maintainer : mail@akru.me -- Stability : experimental -- Portability : portable -- -- Commonly used types and instances. -- module Network.Ethereum.Web3.Types where import Control.Exception (Exception) import Control.Monad.IO.Class (MonadIO) import Data.Aeson import Data.Aeson.TH import Data.Monoid ((<>)) import Data.Text (Text) import qualified Data.Text.Lazy.Builder as B import qualified Data.Text.Lazy.Builder.Int as B import qualified Data.Text.Read as R import Data.Typeable (Typeable) import GHC.Generics import Network.Ethereum.Web3.Address (Address) import Network.Ethereum.Web3.Internal (toLowerFirst) -- | Any communication with Ethereum node wrapped with 'Web3' monad newtype Web3 a b = Web3 { unWeb3 :: IO b } deriving (Functor, Applicative, Monad, MonadIO) -- | Some peace of error response data Web3Error = JsonRpcFail !RpcError -- ^ JSON-RPC communication error | ParserFail !String -- ^ Error in parser state | UserFail !String -- ^ Common head for user errors deriving (Typeable, Show, Eq, Generic) instance Exception Web3Error -- | JSON-RPC error message data RpcError = RpcError { errCode :: !Int , errMessage :: !Text , errData :: !(Maybe Value) } deriving (Show, Eq, Generic) $(deriveJSON (defaultOptions { fieldLabelModifier = toLowerFirst . drop 3 }) ''RpcError) -- | Low-level event filter data structure data Filter = Filter { filterAddress :: !(Maybe Address) , filterTopics :: !(Maybe [Maybe Text]) , filterFromBlock :: !(Maybe Text) , filterToBlock :: !(Maybe Text) } deriving (Show, Generic) $(deriveJSON (defaultOptions { fieldLabelModifier = toLowerFirst . drop 6 }) ''Filter) -- | Event filter identifier newtype FilterId = FilterId Integer deriving (Show, Eq, Ord, Generic) instance FromJSON FilterId where parseJSON (String v) = case R.hexadecimal v of Right (x, "") -> return (FilterId x) _ -> fail "Unable to parse FilterId!" parseJSON _ = fail "The string is required!" instance ToJSON FilterId where toJSON (FilterId x) = let hexValue = B.toLazyText (B.hexadecimal x) in toJSON ("0x" <> hexValue) -- | Changes pulled by low-level call 'eth_getFilterChanges', 'eth_getLogs', -- and 'eth_getFilterLogs' data Change = Change { changeLogIndex :: !Text , changeTransactionIndex :: !Text , changeTransactionHash :: !Text , changeBlockHash :: !Text , changeBlockNumber :: !Text , changeAddress :: !Address , changeData :: !Text , changeTopics :: ![Text] } deriving (Show, Generic) $(deriveJSON (defaultOptions { fieldLabelModifier = toLowerFirst . drop 6 }) ''Change) -- | The contract call params data Call = Call { callFrom :: !(Maybe Address) , callTo :: !Address , callGas :: !(Maybe Text) , callGasPrice:: !(Maybe Text) , callValue :: !(Maybe Text) , callData :: !(Maybe Text) } deriving (Show, Generic) $(deriveJSON (defaultOptions { fieldLabelModifier = toLowerFirst . drop 4 , omitNothingFields = True }) ''Call) -- | The contract call mode describe used state: latest or pending data DefaultBlock = BlockNumberHex Text | Earliest | Latest | Pending deriving (Show, Eq) instance ToJSON DefaultBlock where toJSON (BlockNumberHex hex) = toJSON hex toJSON parameter = toJSON . toLowerFirst . show $ parameter -- TODO: Wrap -- | Transaction hash text string type TxHash = Text -- | Transaction information data Transaction = Transaction { txHash :: !TxHash -- ^ DATA, 32 Bytes - hash of the transaction. , txNonce :: !Text -- ^ QUANTITY - the number of transactions made by the sender prior to this one. , txBlockHash :: !Text -- ^ DATA, 32 Bytes - hash of the block where this transaction was in. null when its pending. , txBlockNumber :: !Text -- ^ QUANTITY - block number where this transaction was in. null when its pending. , txTransactionIndex :: !Text -- ^ QUANTITY - integer of the transactions index position in the block. null when its pending. , txFrom :: !Address -- ^ DATA, 20 Bytes - address of the sender. , txTo :: !(Maybe Address) -- ^ DATA, 20 Bytes - address of the receiver. null when its a contract creation transaction. , txValue :: !Text -- ^ QUANTITY - value transferred in Wei. , txGasPrice :: !Text -- ^ QUANTITY - gas price provided by the sender in Wei. , txGas :: !Text -- ^ QUANTITY - gas provided by the sender. , txInput :: !Text -- ^ DATA - the data send along with the transaction. } deriving (Show, Generic) $(deriveJSON (defaultOptions { fieldLabelModifier = toLowerFirst . drop 2 }) ''Transaction) -- | Block information data Block = Block { blockNumber :: !Text -- ^ QUANTITY - the block number. null when its pending block. , blockHash :: !Text -- ^ DATA, 32 Bytes - hash of the block. null when its pending block. , blockParentHash :: !Text -- ^ DATA, 32 Bytes - hash of the parent block. , blockNonce :: !(Maybe Text) -- ^ DATA, 8 Bytes - hash of the generated proof-of-work. null when its pending block. , blockSha3Uncles :: !Text -- ^ DATA, 32 Bytes - SHA3 of the uncles data in the block. , blockLogsBloom :: !Text -- ^ DATA, 256 Bytes - the bloom filter for the logs of the block. null when its pending block. , blockTransactionsRoot :: !Text -- ^ DATA, 32 Bytes - the root of the transaction trie of the block. , blockStateRoot :: !Text -- ^ DATA, 32 Bytes - the root of the final state trie of the block. , blockReceiptRoot :: !(Maybe Text) -- ^ DATA, 32 Bytes - the root of the receipts trie of the block. , blockMiner :: !Address -- ^ DATA, 20 Bytes - the address of the beneficiary to whom the mining rewards were given. , blockDifficulty :: !Text -- ^ QUANTITY - integer of the difficulty for this block. , blockTotalDifficulty :: !Text -- ^ QUANTITY - integer of the total difficulty of the chain until this block. , blockExtraData :: !Text -- ^ DATA - the "extra data" field of this block. , blockSize :: !Text -- ^ QUANTITY - integer the size of this block in bytes. , blockGasLimit :: !Text -- ^ QUANTITY - the maximum gas allowed in this block. , blockGasUsed :: !Text -- ^ QUANTITY - the total used gas by all transactions in this block. , blockTimestamp :: !Text -- ^ QUANTITY - the unix timestamp for when the block was collated. , blockTransactions :: ![Transaction] -- ^ Array of transaction objects. , blockUncles :: ![Text] -- ^ Array - Array of uncle hashes. } deriving (Show, Generic) $(deriveJSON (defaultOptions { fieldLabelModifier = toLowerFirst . drop 5 }) ''Block)