Class TestKit

All Implemented Interfaces:
CloseableNativeProxy, AutoCloseable

public final class TestKit
extends AbstractCloseableNativeProxy
TestKit for testing blockchain services. It offers simple network configuration emulation (with no real network setup). Although it is possible to add several validator nodes to this network, only one node will create the service instances, execute their operations (e.g., Service.afterCommit(BlockCommittedEvent) method logic), and provide access to its state.

Only the emulated node has a pool of unconfirmed transactions where a service can submit new transaction messages through Node.submitTransaction(RawTransaction); or the test code through createBlockWithTransactions(TransactionMessage...). All transactions from the pool are committed when a new block is created with createBlock().

When TestKit is created, Exonum blockchain instance is initialized — service instances are initialized and genesis block is committed. Then the public API handlers are created.

See Also:
TestKit documentation, Pool of Unconfirmed Transactions
  • Field Details

    • MAX_VALIDATOR_COUNT_WITH_ENABLED_TIME_SERVICE

      public static final short MAX_VALIDATOR_COUNT_WITH_ENABLED_TIME_SERVICE
      The maximum number of validators supported by TestKit when a time oracle is enabled. The time oracle does not work in a TestKit with a higher number of validators because the time oracle requires the majority of those validators to submit transactions with time updates, but only a single emulated node submits them.
      See Also:
      Constant Field Values
  • Method Details

    • forService

      public static TestKit forService​(ServiceArtifactId artifactId, String artifactFilename, String serviceName, int serviceId, Path artifactsDirectory)
      Deploys and creates a single service with no configuration and with a single validator node in this TestKit network.
      Parameters:
      artifactId - the id of the artifact
      artifactFilename - a filename of the service artifact in the directory for artifacts
      serviceName - the name of the service
      serviceId - the id of the service, must be in range [0; 1023]
      artifactsDirectory - the directory from which the service runtime loads service artifacts
      Throws:
      IllegalArgumentException - if serviceId is not in range [0; 1023]
    • createBlockWithTransactions

      public Block createBlockWithTransactions​(TransactionMessage... transactions)
      Creates a block with the given transaction(s). Transactions are applied in the lexicographical order of their hashes. In-pool transactions will be ignored.
      Returns:
      created block
      Throws:
      IllegalArgumentException - if transactions are malformed or don't belong to this service
    • createBlockWithTransactions

      public Block createBlockWithTransactions​(Iterable<TransactionMessage> transactions)
      Creates a block with the given transactions. Transactions are applied in the lexicographical order of their hashes. In-pool transactions will be ignored.
      Returns:
      created block
      Throws:
      IllegalArgumentException - if transactions are malformed or don't belong to this service
    • createBlock

      public Block createBlock()
      Creates a block with all in-pool transactions. Transactions are applied in the lexicographical order of their hashes.
      Returns:
      created block
    • getTransactionPool

      public List<TransactionMessage> getTransactionPool()
      Returns a list of in-pool transactions. Please note that the order of transactions in pool does not necessarily match the order in which the clients submitted the messages.
    • findTransactionsInPool

      public List<TransactionMessage> findTransactionsInPool​(Predicate<TransactionMessage> predicate)
      Returns a list of in-pool transactions that match the given predicate.
    • withSnapshot

      public void withSnapshot​(Consumer<Snapshot> snapshotFunction)
      Performs the given function with a snapshot of the current database state (i.e., the one that corresponds to the latest committed block). In-pool (not yet processed) transactions are also accessible with it in blockchain.

      This method destroys the snapshot once the passed closure completes, compared to getSnapshot(), which disposes created snapshots only when TestKit is closed.

      Parameters:
      snapshotFunction - a function to execute
      See Also:
      applySnapshot(Function)
    • applySnapshot

      public <ResultT> ResultT applySnapshot​(Function<Snapshot,​ResultT> snapshotFunction)
      Performs the given function with a snapshot of the current database state (i.e., the one that corresponds to the latest committed block) and returns a result of its execution. In-pool (not yet processed) transactions are also accessible with it in blockchain.

      This method destroys the snapshot once the passed closure completes, compared to getSnapshot(), which disposes created snapshots only when TestKit is closed.

      Consider using withSnapshot(Consumer) when returning the result of given function is not needed.

      Type Parameters:
      ResultT - a type the function returns
      Parameters:
      snapshotFunction - a function to execute
      Returns:
      the result of applying the given function to the database state
    • getSnapshot

      public Snapshot getSnapshot()
      Returns a snapshot of the current database state (i.e., the one that corresponds to the latest committed block). In-pool (not yet processed) transactions are also accessible with it in blockchain.

      All created snapshots are deleted when this TestKit is closed. It is forbidden to access the snapshots once the TestKit is closed.

      If you need to create a large number (e.g. more than a hundred) of snapshots, it is recommended to use withSnapshot(Consumer) or applySnapshot(Function), which destroy the snapshots once the passed closure completes.

    • getEmulatedNode

      public EmulatedNode getEmulatedNode()
      Returns the context of the node that the TestKit emulates (i.e., on which it instantiates and executes services).
    • getPort

      public int getPort()
      Returns the TCP port on which the service REST API is mounted.
    • disposeInternal

      protected void disposeInternal()
      Description copied from class: AbstractCloseableNativeProxy
      Releases any resources owned by this proxy (e.g., the corresponding native object).

      This method is only called once from AbstractCloseableNativeProxy.close() for a valid proxy and shall not be called directly.

      Specified by:
      disposeInternal in class AbstractCloseableNativeProxy
    • builder

      public static TestKit.Builder builder()
      Creates a new builder for the TestKit. Note that this builder creates a single validator network by default.