github.com/bloxroute-labs/bor@v0.1.4/graphql/graphql.go (about)

     1  // Copyright 2018 The go-ethereum Authors
     2  // This file is part of the go-ethereum library.
     3  //
     4  // The go-ethereum library is free software: you can redistribute it and/or modify
     5  // it under the terms of the GNU Lesser General Public License as published by
     6  // the Free Software Foundation, either version 3 of the License, or
     7  // (at your option) any later version.
     8  //
     9  // The go-ethereum library is distributed in the hope that it will be useful,
    10  // but WITHOUT ANY WARRANTY; without even the implied warranty of
    11  // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
    12  // GNU Lesser General Public License for more details.
    13  //
    14  // You should have received a copy of the GNU Lesser General Public License
    15  // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
    16  
    17  // Package graphql provides a GraphQL interface to Ethereum node data.
    18  package graphql
    19  
    20  import (
    21  	"context"
    22  	"errors"
    23  	"time"
    24  
    25  	"github.com/maticnetwork/bor"
    26  	"github.com/maticnetwork/bor/common"
    27  	"github.com/maticnetwork/bor/common/hexutil"
    28  	"github.com/maticnetwork/bor/core/rawdb"
    29  	"github.com/maticnetwork/bor/core/state"
    30  	"github.com/maticnetwork/bor/core/types"
    31  	"github.com/maticnetwork/bor/core/vm"
    32  	"github.com/maticnetwork/bor/eth/filters"
    33  	"github.com/maticnetwork/bor/internal/ethapi"
    34  	"github.com/maticnetwork/bor/rlp"
    35  	"github.com/maticnetwork/bor/rpc"
    36  )
    37  
    38  var OnlyOnMainChainError = errors.New("This operation is only available for blocks on the canonical chain.")
    39  var BlockInvariantError = errors.New("Block objects must be instantiated with at least one of num or hash.")
    40  
    41  // Account represents an Ethereum account at a particular block.
    42  type Account struct {
    43  	backend     ethapi.Backend
    44  	address     common.Address
    45  	blockNumber rpc.BlockNumber
    46  }
    47  
    48  // getState fetches the StateDB object for an account.
    49  func (a *Account) getState(ctx context.Context) (*state.StateDB, error) {
    50  	state, _, err := a.backend.StateAndHeaderByNumber(ctx, a.blockNumber)
    51  	return state, err
    52  }
    53  
    54  func (a *Account) Address(ctx context.Context) (common.Address, error) {
    55  	return a.address, nil
    56  }
    57  
    58  func (a *Account) Balance(ctx context.Context) (hexutil.Big, error) {
    59  	state, err := a.getState(ctx)
    60  	if err != nil {
    61  		return hexutil.Big{}, err
    62  	}
    63  
    64  	return hexutil.Big(*state.GetBalance(a.address)), nil
    65  }
    66  
    67  func (a *Account) TransactionCount(ctx context.Context) (hexutil.Uint64, error) {
    68  	state, err := a.getState(ctx)
    69  	if err != nil {
    70  		return 0, err
    71  	}
    72  
    73  	return hexutil.Uint64(state.GetNonce(a.address)), nil
    74  }
    75  
    76  func (a *Account) Code(ctx context.Context) (hexutil.Bytes, error) {
    77  	state, err := a.getState(ctx)
    78  	if err != nil {
    79  		return hexutil.Bytes{}, err
    80  	}
    81  
    82  	return hexutil.Bytes(state.GetCode(a.address)), nil
    83  }
    84  
    85  func (a *Account) Storage(ctx context.Context, args struct{ Slot common.Hash }) (common.Hash, error) {
    86  	state, err := a.getState(ctx)
    87  	if err != nil {
    88  		return common.Hash{}, err
    89  	}
    90  
    91  	return state.GetState(a.address, args.Slot), nil
    92  }
    93  
    94  // Log represents an individual log message. All arguments are mandatory.
    95  type Log struct {
    96  	backend     ethapi.Backend
    97  	transaction *Transaction
    98  	log         *types.Log
    99  }
   100  
   101  func (l *Log) Transaction(ctx context.Context) *Transaction {
   102  	return l.transaction
   103  }
   104  
   105  func (l *Log) Account(ctx context.Context, args BlockNumberArgs) *Account {
   106  	return &Account{
   107  		backend:     l.backend,
   108  		address:     l.log.Address,
   109  		blockNumber: args.Number(),
   110  	}
   111  }
   112  
   113  func (l *Log) Index(ctx context.Context) int32 {
   114  	return int32(l.log.Index)
   115  }
   116  
   117  func (l *Log) Topics(ctx context.Context) []common.Hash {
   118  	return l.log.Topics
   119  }
   120  
   121  func (l *Log) Data(ctx context.Context) hexutil.Bytes {
   122  	return hexutil.Bytes(l.log.Data)
   123  }
   124  
   125  // Transaction represents an Ethereum transaction.
   126  // backend and hash are mandatory; all others will be fetched when required.
   127  type Transaction struct {
   128  	backend ethapi.Backend
   129  	hash    common.Hash
   130  	tx      *types.Transaction
   131  	block   *Block
   132  	index   uint64
   133  }
   134  
   135  // resolve returns the internal transaction object, fetching it if needed.
   136  func (t *Transaction) resolve(ctx context.Context) (*types.Transaction, error) {
   137  	if t.tx == nil {
   138  		tx, blockHash, _, index := rawdb.ReadTransaction(t.backend.ChainDb(), t.hash)
   139  		if tx != nil {
   140  			t.tx = tx
   141  			t.block = &Block{
   142  				backend:   t.backend,
   143  				hash:      blockHash,
   144  				canonical: unknown,
   145  			}
   146  			t.index = index
   147  		} else {
   148  			t.tx = t.backend.GetPoolTransaction(t.hash)
   149  		}
   150  	}
   151  	return t.tx, nil
   152  }
   153  
   154  func (tx *Transaction) Hash(ctx context.Context) common.Hash {
   155  	return tx.hash
   156  }
   157  
   158  func (t *Transaction) InputData(ctx context.Context) (hexutil.Bytes, error) {
   159  	tx, err := t.resolve(ctx)
   160  	if err != nil || tx == nil {
   161  		return hexutil.Bytes{}, err
   162  	}
   163  	return hexutil.Bytes(tx.Data()), nil
   164  }
   165  
   166  func (t *Transaction) Gas(ctx context.Context) (hexutil.Uint64, error) {
   167  	tx, err := t.resolve(ctx)
   168  	if err != nil || tx == nil {
   169  		return 0, err
   170  	}
   171  	return hexutil.Uint64(tx.Gas()), nil
   172  }
   173  
   174  func (t *Transaction) GasPrice(ctx context.Context) (hexutil.Big, error) {
   175  	tx, err := t.resolve(ctx)
   176  	if err != nil || tx == nil {
   177  		return hexutil.Big{}, err
   178  	}
   179  	return hexutil.Big(*tx.GasPrice()), nil
   180  }
   181  
   182  func (t *Transaction) Value(ctx context.Context) (hexutil.Big, error) {
   183  	tx, err := t.resolve(ctx)
   184  	if err != nil || tx == nil {
   185  		return hexutil.Big{}, err
   186  	}
   187  	return hexutil.Big(*tx.Value()), nil
   188  }
   189  
   190  func (t *Transaction) Nonce(ctx context.Context) (hexutil.Uint64, error) {
   191  	tx, err := t.resolve(ctx)
   192  	if err != nil || tx == nil {
   193  		return 0, err
   194  	}
   195  	return hexutil.Uint64(tx.Nonce()), nil
   196  }
   197  
   198  func (t *Transaction) To(ctx context.Context, args BlockNumberArgs) (*Account, error) {
   199  	tx, err := t.resolve(ctx)
   200  	if err != nil || tx == nil {
   201  		return nil, err
   202  	}
   203  
   204  	to := tx.To()
   205  	if to == nil {
   206  		return nil, nil
   207  	}
   208  
   209  	return &Account{
   210  		backend:     t.backend,
   211  		address:     *to,
   212  		blockNumber: args.Number(),
   213  	}, nil
   214  }
   215  
   216  func (t *Transaction) From(ctx context.Context, args BlockNumberArgs) (*Account, error) {
   217  	tx, err := t.resolve(ctx)
   218  	if err != nil || tx == nil {
   219  		return nil, err
   220  	}
   221  
   222  	var signer types.Signer = types.FrontierSigner{}
   223  	if tx.Protected() {
   224  		signer = types.NewEIP155Signer(tx.ChainId())
   225  	}
   226  	from, _ := types.Sender(signer, tx)
   227  
   228  	return &Account{
   229  		backend:     t.backend,
   230  		address:     from,
   231  		blockNumber: args.Number(),
   232  	}, nil
   233  }
   234  
   235  func (t *Transaction) Block(ctx context.Context) (*Block, error) {
   236  	if _, err := t.resolve(ctx); err != nil {
   237  		return nil, err
   238  	}
   239  	return t.block, nil
   240  }
   241  
   242  func (t *Transaction) Index(ctx context.Context) (*int32, error) {
   243  	if _, err := t.resolve(ctx); err != nil {
   244  		return nil, err
   245  	}
   246  	if t.block == nil {
   247  		return nil, nil
   248  	}
   249  	index := int32(t.index)
   250  	return &index, nil
   251  }
   252  
   253  // getReceipt returns the receipt associated with this transaction, if any.
   254  func (t *Transaction) getReceipt(ctx context.Context) (*types.Receipt, error) {
   255  	if _, err := t.resolve(ctx); err != nil {
   256  		return nil, err
   257  	}
   258  
   259  	if t.block == nil {
   260  		return nil, nil
   261  	}
   262  
   263  	receipts, err := t.block.resolveReceipts(ctx)
   264  	if err != nil {
   265  		return nil, err
   266  	}
   267  
   268  	return receipts[t.index], nil
   269  }
   270  
   271  func (t *Transaction) Status(ctx context.Context) (*hexutil.Uint64, error) {
   272  	receipt, err := t.getReceipt(ctx)
   273  	if err != nil || receipt == nil {
   274  		return nil, err
   275  	}
   276  
   277  	ret := hexutil.Uint64(receipt.Status)
   278  	return &ret, nil
   279  }
   280  
   281  func (t *Transaction) GasUsed(ctx context.Context) (*hexutil.Uint64, error) {
   282  	receipt, err := t.getReceipt(ctx)
   283  	if err != nil || receipt == nil {
   284  		return nil, err
   285  	}
   286  
   287  	ret := hexutil.Uint64(receipt.GasUsed)
   288  	return &ret, nil
   289  }
   290  
   291  func (t *Transaction) CumulativeGasUsed(ctx context.Context) (*hexutil.Uint64, error) {
   292  	receipt, err := t.getReceipt(ctx)
   293  	if err != nil || receipt == nil {
   294  		return nil, err
   295  	}
   296  
   297  	ret := hexutil.Uint64(receipt.CumulativeGasUsed)
   298  	return &ret, nil
   299  }
   300  
   301  func (t *Transaction) CreatedContract(ctx context.Context, args BlockNumberArgs) (*Account, error) {
   302  	receipt, err := t.getReceipt(ctx)
   303  	if err != nil || receipt == nil || receipt.ContractAddress == (common.Address{}) {
   304  		return nil, err
   305  	}
   306  
   307  	return &Account{
   308  		backend:     t.backend,
   309  		address:     receipt.ContractAddress,
   310  		blockNumber: args.Number(),
   311  	}, nil
   312  }
   313  
   314  func (t *Transaction) Logs(ctx context.Context) (*[]*Log, error) {
   315  	receipt, err := t.getReceipt(ctx)
   316  	if err != nil || receipt == nil {
   317  		return nil, err
   318  	}
   319  
   320  	ret := make([]*Log, 0, len(receipt.Logs))
   321  	for _, log := range receipt.Logs {
   322  		ret = append(ret, &Log{
   323  			backend:     t.backend,
   324  			transaction: t,
   325  			log:         log,
   326  		})
   327  	}
   328  	return &ret, nil
   329  }
   330  
   331  type BlockType int
   332  
   333  const (
   334  	unknown BlockType = iota
   335  	isCanonical
   336  	notCanonical
   337  )
   338  
   339  // Block represents an Ethereum block.
   340  // backend, and either num or hash are mandatory. All other fields are lazily fetched
   341  // when required.
   342  type Block struct {
   343  	backend   ethapi.Backend
   344  	num       *rpc.BlockNumber
   345  	hash      common.Hash
   346  	header    *types.Header
   347  	block     *types.Block
   348  	receipts  []*types.Receipt
   349  	canonical BlockType // Indicates if this block is on the main chain or not.
   350  }
   351  
   352  func (b *Block) onMainChain(ctx context.Context) error {
   353  	if b.canonical == unknown {
   354  		header, err := b.resolveHeader(ctx)
   355  		if err != nil {
   356  			return err
   357  		}
   358  		canonHeader, err := b.backend.HeaderByNumber(ctx, rpc.BlockNumber(header.Number.Uint64()))
   359  		if err != nil {
   360  			return err
   361  		}
   362  		if header.Hash() == canonHeader.Hash() {
   363  			b.canonical = isCanonical
   364  		} else {
   365  			b.canonical = notCanonical
   366  		}
   367  	}
   368  	if b.canonical != isCanonical {
   369  		return OnlyOnMainChainError
   370  	}
   371  	return nil
   372  }
   373  
   374  // resolve returns the internal Block object representing this block, fetching
   375  // it if necessary.
   376  func (b *Block) resolve(ctx context.Context) (*types.Block, error) {
   377  	if b.block != nil {
   378  		return b.block, nil
   379  	}
   380  
   381  	var err error
   382  	if b.hash != (common.Hash{}) {
   383  		b.block, err = b.backend.GetBlock(ctx, b.hash)
   384  	} else {
   385  		b.block, err = b.backend.BlockByNumber(ctx, *b.num)
   386  	}
   387  	if b.block != nil {
   388  		b.header = b.block.Header()
   389  	}
   390  	return b.block, err
   391  }
   392  
   393  // resolveHeader returns the internal Header object for this block, fetching it
   394  // if necessary. Call this function instead of `resolve` unless you need the
   395  // additional data (transactions and uncles).
   396  func (b *Block) resolveHeader(ctx context.Context) (*types.Header, error) {
   397  	if b.num == nil && b.hash == (common.Hash{}) {
   398  		return nil, BlockInvariantError
   399  	}
   400  
   401  	if b.header == nil {
   402  		if _, err := b.resolve(ctx); err != nil {
   403  			return nil, err
   404  		}
   405  	}
   406  	return b.header, nil
   407  }
   408  
   409  // resolveReceipts returns the list of receipts for this block, fetching them
   410  // if necessary.
   411  func (b *Block) resolveReceipts(ctx context.Context) ([]*types.Receipt, error) {
   412  	if b.receipts == nil {
   413  		hash := b.hash
   414  		if hash == (common.Hash{}) {
   415  			header, err := b.resolveHeader(ctx)
   416  			if err != nil {
   417  				return nil, err
   418  			}
   419  			hash = header.Hash()
   420  		}
   421  
   422  		receipts, err := b.backend.GetReceipts(ctx, hash)
   423  		if err != nil {
   424  			return nil, err
   425  		}
   426  		b.receipts = []*types.Receipt(receipts)
   427  	}
   428  	return b.receipts, nil
   429  }
   430  
   431  func (b *Block) Number(ctx context.Context) (hexutil.Uint64, error) {
   432  	if b.num == nil || *b.num == rpc.LatestBlockNumber {
   433  		header, err := b.resolveHeader(ctx)
   434  		if err != nil {
   435  			return 0, err
   436  		}
   437  		num := rpc.BlockNumber(header.Number.Uint64())
   438  		b.num = &num
   439  	}
   440  	return hexutil.Uint64(*b.num), nil
   441  }
   442  
   443  func (b *Block) Hash(ctx context.Context) (common.Hash, error) {
   444  	if b.hash == (common.Hash{}) {
   445  		header, err := b.resolveHeader(ctx)
   446  		if err != nil {
   447  			return common.Hash{}, err
   448  		}
   449  		b.hash = header.Hash()
   450  	}
   451  	return b.hash, nil
   452  }
   453  
   454  func (b *Block) GasLimit(ctx context.Context) (hexutil.Uint64, error) {
   455  	header, err := b.resolveHeader(ctx)
   456  	if err != nil {
   457  		return 0, err
   458  	}
   459  	return hexutil.Uint64(header.GasLimit), nil
   460  }
   461  
   462  func (b *Block) GasUsed(ctx context.Context) (hexutil.Uint64, error) {
   463  	header, err := b.resolveHeader(ctx)
   464  	if err != nil {
   465  		return 0, err
   466  	}
   467  	return hexutil.Uint64(header.GasUsed), nil
   468  }
   469  
   470  func (b *Block) Parent(ctx context.Context) (*Block, error) {
   471  	// If the block hasn't been fetched, and we'll need it, fetch it.
   472  	if b.num == nil && b.hash != (common.Hash{}) && b.header == nil {
   473  		if _, err := b.resolve(ctx); err != nil {
   474  			return nil, err
   475  		}
   476  	}
   477  
   478  	if b.header != nil && b.block.NumberU64() > 0 {
   479  		num := rpc.BlockNumber(b.header.Number.Uint64() - 1)
   480  		return &Block{
   481  			backend:   b.backend,
   482  			num:       &num,
   483  			hash:      b.header.ParentHash,
   484  			canonical: unknown,
   485  		}, nil
   486  	}
   487  	if b.num != nil && *b.num != 0 {
   488  		num := *b.num - 1
   489  		return &Block{
   490  			backend:   b.backend,
   491  			num:       &num,
   492  			canonical: isCanonical,
   493  		}, nil
   494  	}
   495  	return nil, nil
   496  }
   497  
   498  func (b *Block) Difficulty(ctx context.Context) (hexutil.Big, error) {
   499  	header, err := b.resolveHeader(ctx)
   500  	if err != nil {
   501  		return hexutil.Big{}, err
   502  	}
   503  	return hexutil.Big(*header.Difficulty), nil
   504  }
   505  
   506  func (b *Block) Timestamp(ctx context.Context) (hexutil.Uint64, error) {
   507  	header, err := b.resolveHeader(ctx)
   508  	if err != nil {
   509  		return 0, err
   510  	}
   511  	return hexutil.Uint64(header.Time), nil
   512  }
   513  
   514  func (b *Block) Nonce(ctx context.Context) (hexutil.Bytes, error) {
   515  	header, err := b.resolveHeader(ctx)
   516  	if err != nil {
   517  		return hexutil.Bytes{}, err
   518  	}
   519  	return hexutil.Bytes(header.Nonce[:]), nil
   520  }
   521  
   522  func (b *Block) MixHash(ctx context.Context) (common.Hash, error) {
   523  	header, err := b.resolveHeader(ctx)
   524  	if err != nil {
   525  		return common.Hash{}, err
   526  	}
   527  	return header.MixDigest, nil
   528  }
   529  
   530  func (b *Block) TransactionsRoot(ctx context.Context) (common.Hash, error) {
   531  	header, err := b.resolveHeader(ctx)
   532  	if err != nil {
   533  		return common.Hash{}, err
   534  	}
   535  	return header.TxHash, nil
   536  }
   537  
   538  func (b *Block) StateRoot(ctx context.Context) (common.Hash, error) {
   539  	header, err := b.resolveHeader(ctx)
   540  	if err != nil {
   541  		return common.Hash{}, err
   542  	}
   543  	return header.Root, nil
   544  }
   545  
   546  func (b *Block) ReceiptsRoot(ctx context.Context) (common.Hash, error) {
   547  	header, err := b.resolveHeader(ctx)
   548  	if err != nil {
   549  		return common.Hash{}, err
   550  	}
   551  	return header.ReceiptHash, nil
   552  }
   553  
   554  func (b *Block) OmmerHash(ctx context.Context) (common.Hash, error) {
   555  	header, err := b.resolveHeader(ctx)
   556  	if err != nil {
   557  		return common.Hash{}, err
   558  	}
   559  	return header.UncleHash, nil
   560  }
   561  
   562  func (b *Block) OmmerCount(ctx context.Context) (*int32, error) {
   563  	block, err := b.resolve(ctx)
   564  	if err != nil || block == nil {
   565  		return nil, err
   566  	}
   567  	count := int32(len(block.Uncles()))
   568  	return &count, err
   569  }
   570  
   571  func (b *Block) Ommers(ctx context.Context) (*[]*Block, error) {
   572  	block, err := b.resolve(ctx)
   573  	if err != nil || block == nil {
   574  		return nil, err
   575  	}
   576  
   577  	ret := make([]*Block, 0, len(block.Uncles()))
   578  	for _, uncle := range block.Uncles() {
   579  		blockNumber := rpc.BlockNumber(uncle.Number.Uint64())
   580  		ret = append(ret, &Block{
   581  			backend:   b.backend,
   582  			num:       &blockNumber,
   583  			hash:      uncle.Hash(),
   584  			header:    uncle,
   585  			canonical: notCanonical,
   586  		})
   587  	}
   588  	return &ret, nil
   589  }
   590  
   591  func (b *Block) ExtraData(ctx context.Context) (hexutil.Bytes, error) {
   592  	header, err := b.resolveHeader(ctx)
   593  	if err != nil {
   594  		return hexutil.Bytes{}, err
   595  	}
   596  	return hexutil.Bytes(header.Extra), nil
   597  }
   598  
   599  func (b *Block) LogsBloom(ctx context.Context) (hexutil.Bytes, error) {
   600  	header, err := b.resolveHeader(ctx)
   601  	if err != nil {
   602  		return hexutil.Bytes{}, err
   603  	}
   604  	return hexutil.Bytes(header.Bloom.Bytes()), nil
   605  }
   606  
   607  func (b *Block) TotalDifficulty(ctx context.Context) (hexutil.Big, error) {
   608  	h := b.hash
   609  	if h == (common.Hash{}) {
   610  		header, err := b.resolveHeader(ctx)
   611  		if err != nil {
   612  			return hexutil.Big{}, err
   613  		}
   614  		h = header.Hash()
   615  	}
   616  
   617  	return hexutil.Big(*b.backend.GetTd(h)), nil
   618  }
   619  
   620  // BlockNumberArgs encapsulates arguments to accessors that specify a block number.
   621  type BlockNumberArgs struct {
   622  	Block *hexutil.Uint64
   623  }
   624  
   625  // Number returns the provided block number, or rpc.LatestBlockNumber if none
   626  // was provided.
   627  func (a BlockNumberArgs) Number() rpc.BlockNumber {
   628  	if a.Block != nil {
   629  		return rpc.BlockNumber(*a.Block)
   630  	}
   631  	return rpc.LatestBlockNumber
   632  }
   633  
   634  func (b *Block) Miner(ctx context.Context, args BlockNumberArgs) (*Account, error) {
   635  	block, err := b.resolve(ctx)
   636  	if err != nil {
   637  		return nil, err
   638  	}
   639  
   640  	return &Account{
   641  		backend:     b.backend,
   642  		address:     block.Coinbase(),
   643  		blockNumber: args.Number(),
   644  	}, nil
   645  }
   646  
   647  func (b *Block) TransactionCount(ctx context.Context) (*int32, error) {
   648  	block, err := b.resolve(ctx)
   649  	if err != nil || block == nil {
   650  		return nil, err
   651  	}
   652  	count := int32(len(block.Transactions()))
   653  	return &count, err
   654  }
   655  
   656  func (b *Block) Transactions(ctx context.Context) (*[]*Transaction, error) {
   657  	block, err := b.resolve(ctx)
   658  	if err != nil || block == nil {
   659  		return nil, err
   660  	}
   661  
   662  	ret := make([]*Transaction, 0, len(block.Transactions()))
   663  	for i, tx := range block.Transactions() {
   664  		ret = append(ret, &Transaction{
   665  			backend: b.backend,
   666  			hash:    tx.Hash(),
   667  			tx:      tx,
   668  			block:   b,
   669  			index:   uint64(i),
   670  		})
   671  	}
   672  	return &ret, nil
   673  }
   674  
   675  func (b *Block) TransactionAt(ctx context.Context, args struct{ Index int32 }) (*Transaction, error) {
   676  	block, err := b.resolve(ctx)
   677  	if err != nil || block == nil {
   678  		return nil, err
   679  	}
   680  
   681  	txes := block.Transactions()
   682  	if args.Index < 0 || int(args.Index) >= len(txes) {
   683  		return nil, nil
   684  	}
   685  
   686  	tx := txes[args.Index]
   687  	return &Transaction{
   688  		backend: b.backend,
   689  		hash:    tx.Hash(),
   690  		tx:      tx,
   691  		block:   b,
   692  		index:   uint64(args.Index),
   693  	}, nil
   694  }
   695  
   696  func (b *Block) OmmerAt(ctx context.Context, args struct{ Index int32 }) (*Block, error) {
   697  	block, err := b.resolve(ctx)
   698  	if err != nil || block == nil {
   699  		return nil, err
   700  	}
   701  
   702  	uncles := block.Uncles()
   703  	if args.Index < 0 || int(args.Index) >= len(uncles) {
   704  		return nil, nil
   705  	}
   706  
   707  	uncle := uncles[args.Index]
   708  	blockNumber := rpc.BlockNumber(uncle.Number.Uint64())
   709  	return &Block{
   710  		backend:   b.backend,
   711  		num:       &blockNumber,
   712  		hash:      uncle.Hash(),
   713  		header:    uncle,
   714  		canonical: notCanonical,
   715  	}, nil
   716  }
   717  
   718  // BlockFilterCriteria encapsulates criteria passed to a `logs` accessor inside
   719  // a block.
   720  type BlockFilterCriteria struct {
   721  	Addresses *[]common.Address // restricts matches to events created by specific contracts
   722  
   723  	// The Topic list restricts matches to particular event topics. Each event has a list
   724  	// of topics. Topics matches a prefix of that list. An empty element slice matches any
   725  	// topic. Non-empty elements represent an alternative that matches any of the
   726  	// contained topics.
   727  	//
   728  	// Examples:
   729  	// {} or nil          matches any topic list
   730  	// {{A}}              matches topic A in first position
   731  	// {{}, {B}}          matches any topic in first position, B in second position
   732  	// {{A}, {B}}         matches topic A in first position, B in second position
   733  	// {{A, B}}, {C, D}}  matches topic (A OR B) in first position, (C OR D) in second position
   734  	Topics *[][]common.Hash
   735  }
   736  
   737  // runFilter accepts a filter and executes it, returning all its results as
   738  // `Log` objects.
   739  func runFilter(ctx context.Context, be ethapi.Backend, filter *filters.Filter) ([]*Log, error) {
   740  	logs, err := filter.Logs(ctx)
   741  	if err != nil || logs == nil {
   742  		return nil, err
   743  	}
   744  
   745  	ret := make([]*Log, 0, len(logs))
   746  	for _, log := range logs {
   747  		ret = append(ret, &Log{
   748  			backend:     be,
   749  			transaction: &Transaction{backend: be, hash: log.TxHash},
   750  			log:         log,
   751  		})
   752  	}
   753  	return ret, nil
   754  }
   755  
   756  func (b *Block) Logs(ctx context.Context, args struct{ Filter BlockFilterCriteria }) ([]*Log, error) {
   757  	var addresses []common.Address
   758  	if args.Filter.Addresses != nil {
   759  		addresses = *args.Filter.Addresses
   760  	}
   761  
   762  	var topics [][]common.Hash
   763  	if args.Filter.Topics != nil {
   764  		topics = *args.Filter.Topics
   765  	}
   766  
   767  	hash := b.hash
   768  	if hash == (common.Hash{}) {
   769  		block, err := b.resolve(ctx)
   770  		if err != nil {
   771  			return nil, err
   772  		}
   773  		hash = block.Hash()
   774  	}
   775  
   776  	// Construct the range filter
   777  	filter := filters.NewBlockFilter(b.backend, hash, addresses, topics)
   778  
   779  	// Run the filter and return all the logs
   780  	return runFilter(ctx, b.backend, filter)
   781  }
   782  
   783  func (b *Block) Account(ctx context.Context, args struct {
   784  	Address common.Address
   785  }) (*Account, error) {
   786  	err := b.onMainChain(ctx)
   787  	if err != nil {
   788  		return nil, err
   789  	}
   790  
   791  	if b.num == nil {
   792  		_, err := b.resolveHeader(ctx)
   793  		if err != nil {
   794  			return nil, err
   795  		}
   796  	}
   797  
   798  	return &Account{
   799  		backend:     b.backend,
   800  		address:     args.Address,
   801  		blockNumber: *b.num,
   802  	}, nil
   803  }
   804  
   805  // CallData encapsulates arguments to `call` or `estimateGas`.
   806  // All arguments are optional.
   807  type CallData struct {
   808  	From     *common.Address // The Ethereum address the call is from.
   809  	To       *common.Address // The Ethereum address the call is to.
   810  	Gas      *hexutil.Uint64 // The amount of gas provided for the call.
   811  	GasPrice *hexutil.Big    // The price of each unit of gas, in wei.
   812  	Value    *hexutil.Big    // The value sent along with the call.
   813  	Data     *hexutil.Bytes  // Any data sent with the call.
   814  }
   815  
   816  // CallResult encapsulates the result of an invocation of the `call` accessor.
   817  type CallResult struct {
   818  	data    hexutil.Bytes  // The return data from the call
   819  	gasUsed hexutil.Uint64 // The amount of gas used
   820  	status  hexutil.Uint64 // The return status of the call - 0 for failure or 1 for success.
   821  }
   822  
   823  func (c *CallResult) Data() hexutil.Bytes {
   824  	return c.data
   825  }
   826  
   827  func (c *CallResult) GasUsed() hexutil.Uint64 {
   828  	return c.gasUsed
   829  }
   830  
   831  func (c *CallResult) Status() hexutil.Uint64 {
   832  	return c.status
   833  }
   834  
   835  func (b *Block) Call(ctx context.Context, args struct {
   836  	Data ethapi.CallArgs
   837  }) (*CallResult, error) {
   838  	err := b.onMainChain(ctx)
   839  	if err != nil {
   840  		return nil, err
   841  	}
   842  
   843  	if b.num == nil {
   844  		_, err := b.resolveHeader(ctx)
   845  		if err != nil {
   846  			return nil, err
   847  		}
   848  	}
   849  
   850  	result, gas, failed, err := ethapi.DoCall(ctx, b.backend, args.Data, *b.num, vm.Config{}, 5*time.Second, b.backend.RPCGasCap())
   851  	status := hexutil.Uint64(1)
   852  	if failed {
   853  		status = 0
   854  	}
   855  	return &CallResult{
   856  		data:    hexutil.Bytes(result),
   857  		gasUsed: hexutil.Uint64(gas),
   858  		status:  status,
   859  	}, err
   860  }
   861  
   862  func (b *Block) EstimateGas(ctx context.Context, args struct {
   863  	Data ethapi.CallArgs
   864  }) (hexutil.Uint64, error) {
   865  	err := b.onMainChain(ctx)
   866  	if err != nil {
   867  		return hexutil.Uint64(0), err
   868  	}
   869  
   870  	if b.num == nil {
   871  		_, err := b.resolveHeader(ctx)
   872  		if err != nil {
   873  			return hexutil.Uint64(0), err
   874  		}
   875  	}
   876  
   877  	gas, err := ethapi.DoEstimateGas(ctx, b.backend, args.Data, *b.num, b.backend.RPCGasCap())
   878  	return gas, err
   879  }
   880  
   881  type Pending struct {
   882  	backend ethapi.Backend
   883  }
   884  
   885  func (p *Pending) TransactionCount(ctx context.Context) (int32, error) {
   886  	txs, err := p.backend.GetPoolTransactions()
   887  	return int32(len(txs)), err
   888  }
   889  
   890  func (p *Pending) Transactions(ctx context.Context) (*[]*Transaction, error) {
   891  	txs, err := p.backend.GetPoolTransactions()
   892  	if err != nil {
   893  		return nil, err
   894  	}
   895  
   896  	ret := make([]*Transaction, 0, len(txs))
   897  	for i, tx := range txs {
   898  		ret = append(ret, &Transaction{
   899  			backend: p.backend,
   900  			hash:    tx.Hash(),
   901  			tx:      tx,
   902  			index:   uint64(i),
   903  		})
   904  	}
   905  	return &ret, nil
   906  }
   907  
   908  func (p *Pending) Account(ctx context.Context, args struct {
   909  	Address common.Address
   910  }) *Account {
   911  	return &Account{
   912  		backend:     p.backend,
   913  		address:     args.Address,
   914  		blockNumber: rpc.PendingBlockNumber,
   915  	}
   916  }
   917  
   918  func (p *Pending) Call(ctx context.Context, args struct {
   919  	Data ethapi.CallArgs
   920  }) (*CallResult, error) {
   921  	result, gas, failed, err := ethapi.DoCall(ctx, p.backend, args.Data, rpc.PendingBlockNumber, vm.Config{}, 5*time.Second, p.backend.RPCGasCap())
   922  	status := hexutil.Uint64(1)
   923  	if failed {
   924  		status = 0
   925  	}
   926  	return &CallResult{
   927  		data:    hexutil.Bytes(result),
   928  		gasUsed: hexutil.Uint64(gas),
   929  		status:  status,
   930  	}, err
   931  }
   932  
   933  func (p *Pending) EstimateGas(ctx context.Context, args struct {
   934  	Data ethapi.CallArgs
   935  }) (hexutil.Uint64, error) {
   936  	return ethapi.DoEstimateGas(ctx, p.backend, args.Data, rpc.PendingBlockNumber, p.backend.RPCGasCap())
   937  }
   938  
   939  // Resolver is the top-level object in the GraphQL hierarchy.
   940  type Resolver struct {
   941  	backend ethapi.Backend
   942  }
   943  
   944  func (r *Resolver) Block(ctx context.Context, args struct {
   945  	Number *hexutil.Uint64
   946  	Hash   *common.Hash
   947  }) (*Block, error) {
   948  	var block *Block
   949  	if args.Number != nil {
   950  		num := rpc.BlockNumber(uint64(*args.Number))
   951  		block = &Block{
   952  			backend:   r.backend,
   953  			num:       &num,
   954  			canonical: isCanonical,
   955  		}
   956  	} else if args.Hash != nil {
   957  		block = &Block{
   958  			backend:   r.backend,
   959  			hash:      *args.Hash,
   960  			canonical: unknown,
   961  		}
   962  	} else {
   963  		num := rpc.LatestBlockNumber
   964  		block = &Block{
   965  			backend:   r.backend,
   966  			num:       &num,
   967  			canonical: isCanonical,
   968  		}
   969  	}
   970  
   971  	// Resolve the block; if it doesn't exist, return nil.
   972  	b, err := block.resolve(ctx)
   973  	if err != nil {
   974  		return nil, err
   975  	} else if b == nil {
   976  		return nil, nil
   977  	}
   978  	return block, nil
   979  }
   980  
   981  func (r *Resolver) Blocks(ctx context.Context, args struct {
   982  	From hexutil.Uint64
   983  	To   *hexutil.Uint64
   984  }) ([]*Block, error) {
   985  	from := rpc.BlockNumber(args.From)
   986  
   987  	var to rpc.BlockNumber
   988  	if args.To != nil {
   989  		to = rpc.BlockNumber(*args.To)
   990  	} else {
   991  		to = rpc.BlockNumber(r.backend.CurrentBlock().Number().Int64())
   992  	}
   993  
   994  	if to < from {
   995  		return []*Block{}, nil
   996  	}
   997  
   998  	ret := make([]*Block, 0, to-from+1)
   999  	for i := from; i <= to; i++ {
  1000  		num := i
  1001  		ret = append(ret, &Block{
  1002  			backend:   r.backend,
  1003  			num:       &num,
  1004  			canonical: isCanonical,
  1005  		})
  1006  	}
  1007  	return ret, nil
  1008  }
  1009  
  1010  func (r *Resolver) Pending(ctx context.Context) *Pending {
  1011  	return &Pending{r.backend}
  1012  }
  1013  
  1014  func (r *Resolver) Transaction(ctx context.Context, args struct{ Hash common.Hash }) (*Transaction, error) {
  1015  	tx := &Transaction{
  1016  		backend: r.backend,
  1017  		hash:    args.Hash,
  1018  	}
  1019  
  1020  	// Resolve the transaction; if it doesn't exist, return nil.
  1021  	t, err := tx.resolve(ctx)
  1022  	if err != nil {
  1023  		return nil, err
  1024  	} else if t == nil {
  1025  		return nil, nil
  1026  	}
  1027  	return tx, nil
  1028  }
  1029  
  1030  func (r *Resolver) SendRawTransaction(ctx context.Context, args struct{ Data hexutil.Bytes }) (common.Hash, error) {
  1031  	tx := new(types.Transaction)
  1032  	if err := rlp.DecodeBytes(args.Data, tx); err != nil {
  1033  		return common.Hash{}, err
  1034  	}
  1035  	hash, err := ethapi.SubmitTransaction(ctx, r.backend, tx)
  1036  	return hash, err
  1037  }
  1038  
  1039  // FilterCriteria encapsulates the arguments to `logs` on the root resolver object.
  1040  type FilterCriteria struct {
  1041  	FromBlock *hexutil.Uint64   // beginning of the queried range, nil means genesis block
  1042  	ToBlock   *hexutil.Uint64   // end of the range, nil means latest block
  1043  	Addresses *[]common.Address // restricts matches to events created by specific contracts
  1044  
  1045  	// The Topic list restricts matches to particular event topics. Each event has a list
  1046  	// of topics. Topics matches a prefix of that list. An empty element slice matches any
  1047  	// topic. Non-empty elements represent an alternative that matches any of the
  1048  	// contained topics.
  1049  	//
  1050  	// Examples:
  1051  	// {} or nil          matches any topic list
  1052  	// {{A}}              matches topic A in first position
  1053  	// {{}, {B}}          matches any topic in first position, B in second position
  1054  	// {{A}, {B}}         matches topic A in first position, B in second position
  1055  	// {{A, B}}, {C, D}}  matches topic (A OR B) in first position, (C OR D) in second position
  1056  	Topics *[][]common.Hash
  1057  }
  1058  
  1059  func (r *Resolver) Logs(ctx context.Context, args struct{ Filter FilterCriteria }) ([]*Log, error) {
  1060  	// Convert the RPC block numbers into internal representations
  1061  	begin := rpc.LatestBlockNumber.Int64()
  1062  	if args.Filter.FromBlock != nil {
  1063  		begin = int64(*args.Filter.FromBlock)
  1064  	}
  1065  	end := rpc.LatestBlockNumber.Int64()
  1066  	if args.Filter.ToBlock != nil {
  1067  		end = int64(*args.Filter.ToBlock)
  1068  	}
  1069  
  1070  	var addresses []common.Address
  1071  	if args.Filter.Addresses != nil {
  1072  		addresses = *args.Filter.Addresses
  1073  	}
  1074  
  1075  	var topics [][]common.Hash
  1076  	if args.Filter.Topics != nil {
  1077  		topics = *args.Filter.Topics
  1078  	}
  1079  
  1080  	// Construct the range filter
  1081  	filter := filters.NewRangeFilter(filters.Backend(r.backend), begin, end, addresses, topics)
  1082  	return runFilter(ctx, r.backend, filter)
  1083  }
  1084  
  1085  func (r *Resolver) GasPrice(ctx context.Context) (hexutil.Big, error) {
  1086  	price, err := r.backend.SuggestPrice(ctx)
  1087  	return hexutil.Big(*price), err
  1088  }
  1089  
  1090  func (r *Resolver) ProtocolVersion(ctx context.Context) (int32, error) {
  1091  	return int32(r.backend.ProtocolVersion()), nil
  1092  }
  1093  
  1094  // SyncState represents the synchronisation status returned from the `syncing` accessor.
  1095  type SyncState struct {
  1096  	progress ethereum.SyncProgress
  1097  }
  1098  
  1099  func (s *SyncState) StartingBlock() hexutil.Uint64 {
  1100  	return hexutil.Uint64(s.progress.StartingBlock)
  1101  }
  1102  
  1103  func (s *SyncState) CurrentBlock() hexutil.Uint64 {
  1104  	return hexutil.Uint64(s.progress.CurrentBlock)
  1105  }
  1106  
  1107  func (s *SyncState) HighestBlock() hexutil.Uint64 {
  1108  	return hexutil.Uint64(s.progress.HighestBlock)
  1109  }
  1110  
  1111  func (s *SyncState) PulledStates() *hexutil.Uint64 {
  1112  	ret := hexutil.Uint64(s.progress.PulledStates)
  1113  	return &ret
  1114  }
  1115  
  1116  func (s *SyncState) KnownStates() *hexutil.Uint64 {
  1117  	ret := hexutil.Uint64(s.progress.KnownStates)
  1118  	return &ret
  1119  }
  1120  
  1121  // Syncing returns false in case the node is currently not syncing with the network. It can be up to date or has not
  1122  // yet received the latest block headers from its pears. In case it is synchronizing:
  1123  // - startingBlock: block number this node started to synchronise from
  1124  // - currentBlock:  block number this node is currently importing
  1125  // - highestBlock:  block number of the highest block header this node has received from peers
  1126  // - pulledStates:  number of state entries processed until now
  1127  // - knownStates:   number of known state entries that still need to be pulled
  1128  func (r *Resolver) Syncing() (*SyncState, error) {
  1129  	progress := r.backend.Downloader().Progress()
  1130  
  1131  	// Return not syncing if the synchronisation already completed
  1132  	if progress.CurrentBlock >= progress.HighestBlock {
  1133  		return nil, nil
  1134  	}
  1135  	// Otherwise gather the block sync stats
  1136  	return &SyncState{progress}, nil
  1137  }