Transactions

Overview

Transactions are cryptographically signed instructions from accounts that update the state of the Starknet network. Starknet supports only three types of transactions, with each type going through the same lifecycle to receive its execution and finality statuses. Every transaction that was executed successfully is issued a receipt, which includes its statuses, as well as other information about it.

Additional information

Transaction types

Starknet supports the following types of transactions:

DECLARE

Introduces a new contract class to Starknet, enabling other contracts to either deploy instances of it or use it via a library call

For more information about contract classes and instances, see the Cairo Book.

INVOKE

Invokes a function in an existing contract instance, undergoing validation and execution initiated by the caller account’s __validate__ and __execute__ functions (respectively).

The validation stage verifies that the caller account approves the transaction. Because an account’s __validate__ and __execute__ functions can contain any logic, the caller account ultimately determines how to handle the INVOKE transaction.

DEPLOY_ACCOUNT

Deploys a new account contract to Starknet.

For more information about deploying a new account, see Accounts.

The L1HandlerTransaction type is also a valid transaction type within Starknet, be it cannot be broadcast through the Starknet API like other transaction types, as it was specifically designed for internal Starknet operations (particularly, handling messages from L1 to L2).

The DEPLOY transaction type existed in Starknet for deploying account before being replaced by DEPLOY_ACCOUNT. DEPLOY only had one version (v0) and is now unsupported by Starknet.

Each transaction type is versioned, with versions increasing when the fields that comprise the transaction change, either with the addition of a new field or the removal of an existing field. The following table summarizes the current, deprecated, and unsupported versions of each transaction type:

Type Current version Deprecated versions Unsupported versions

INVOKE

v3

None

v1, v0

DECLARE

v3

None

v2, v1, v0

DEPLOY_ACCOUNT

v3

None

v1

Do not submit a transaction that uses an unsupported transaction type, as it cannot be included in a proof, and therefore cannot become part of a Starknet block.

Sending transaction that use deprecated versions is still supported, but support will be removed in an upcoming Starknet release.

Transaction lifecycle

The high-level steps in the Starknet transaction lifecycle are as follows:

  1. Transaction submission: A transaction is submitted to a sequencer by a full node.

  2. Mempool validation: The sequencer’s mempool performs preliminary validation of the transaction, such as ensuring that its invoker’s balance exceeds the transaction’s max_fee value, assuring the transaction’s calldata length is within the legal limit, and more. If the transaction is invalid, it does not proceed.

  3. Sequencer validation: The sequencer performs preliminary validation of the transaction before executing it to ensure that the transaction is still valid. If the transaction is invalid, it does not proceed.

  4. Execution: The sequencer batches all transactions that passed the preliminary validation into a block, and applies them to the state sequentially. If a transaction fails during execution, it is included in the block with as reverted.

  5. Proof generation and verification: The prover uses the Starknet operating system to computes the proof for the correct execution of all transactions in the block, and transmits it to the L1 verifier, which verifies it. At this point, the L1 state is updated to include the transaction.

Mempools

Up to and including Starknet v0.13.5, transactions were received and ordered by the sequencer in a first-in-first-out (FIFO) fashion. Starting from Starknet v0.14.0, each sequencer will instead maintain a mempool, decouping the transaction order of arrival from the transaction ordering in blocks, for which they are can decide their own policy.

The introduction of mempools will have the following implications on how transactions are processed:

  • Nonces: Transactions with a nonce greater than the sender’s current nonce + \(x\) will be rejected by the mempool, where:

    • A sender’s current nonce is the sender’s nonce in the latest finalized state at the time the transaction is received

    • \(50 \leq x \leq 100\) is still TBD for INVOKE and DEPLOY_ACCOUNT transactions and \(x = 0\) for DECLARE transactions (i.e., no declares with future nonces)

  • Fee escalation: A transaction in the mempool can be replaced by a transaction sent from the same account with the same nonce and both tip and max_l2_gas_price increased by at least 10%

    There are unlikely edge cases in which a transaction is not replaced despite submitting a valid transaction to replace it, such as the existing transaction entering a block while the new one is still processed in the gateway.

  • Transaction time-to-live (TTL): Transactions that cannot be included in a block and have exceeded their TTL, currently configured to be 5 mins, are periodically evicted from the mempool

  • DECLARE transactions time-to-mature (TTM): Before being inserted into the mempool, DECLARE transactions are sent to a "waiting room" until they exceed their TTM, where TTM < TTL but is still TBD. While in the "waiting room", DECLARE transactions can’t be replaced, and transactions sent with the same nonce as a transaction in the "waiting room" by the same account are rejected

Transaction statuses

A transaction’s state is represented by the following finality and execution statuses:

Type Status Description

Finality

NOT_RECEIVED

The transaction is not yet known to the sequencer.

RECEIVED

The transaction was received by the mempool. The transaction is now either executed successfully, rejected, or reverted.

REJECTED

The transaction was received by the mempool but failed the validation by the sequencer. Such transactions are not included in a block.

A rejected transaction is stored in the mempool. You cannot send another transaction with the same transaction hash.

ACCEPTED_ON_L2

The transaction was executed and included in a block.

ACCEPTED_ON_L1

The transaction was accepted on Ethereum.

Execution

REVERTED

The transaction passed validation but failed during the execution by the sequencer, and is included in a block as reverted.

Since the DEPLOY_ACCOUNT and DECLARE transactions don’t have an execution phase, they cannot be reverted.

SUCCEEDED

The transaction was successfully executed by the sequencer and is included in a block.

Starting from Starknet version 0.14.0, these statuses will change to the following:

Type Status Description

Finality

NOT_RECEIVED

The transaction is not yet known to any sequencer.

RECEIVED

A full node has successfully submitted the transaction to a sequencer.

As there is currently no P2P protocol between full nodes for updating on each other about received transactions, querying a different node than the one that submitted the transaction for its status will result in a Transaction hash not found error.

Therefore, relying on RECEIVED statuses requires initiating sticky HTTP sessions with your full node provider.

PRE-CONFIRMED

The transaction was written to the feeder gateway’s storage by a sequencer.

As the transaction hasn’t been executed yet, no execution information is available and only the transaction hash is written to the feeder gateway’s storage.

EXECUTED

The transaction was successfully executed by a sequencer and its receipt was written to the feeder gateway’s storage.

ACCEPTED_ON_L2

The transaction was included in a block finalized by the consensus protocol.

ACCEPTED_ON_L1

The Starknet state on L1 moved to a block height which is greater than or equal to the height of the block containing the transaction.

Execution

REVERTED

The transaction failed during execution by a sequencer, and was included in a block as reverted.

Since the DEPLOY_ACCOUNT and DECLARE transactions don’t have an execution phase, they cannot be reverted.

SUCCEEDED

The transaction was successfully executed by a sequencer and is included in a block.

State implications of reverted transactions

When a transaction is marked as REVERTED, the following state implications occur:

Nonce increases

The nonce value for the account of the failed transaction iterates despite the failure.

Fee charge

The sequencer charges a fee for the execution of the transaction up to the point of failure, and a respective Transfer event is emitted.

Partial reversion

All changes that occurred during the validation stage are not reverted. However, all changes that occurred during the execution stage are reverted, including all messages to L1 or any events that were emitted during this stage. Events might still be emitted from the validation stage or the fee charge stage.

Fee calculation

The fee charged for REVERTED transactions is the smaller of the following two values:

  • The maximum fee that the user is willing to pay, either max_fee (pre-v3 transactions) or \(\text{max_amount} \cdot \text{max_price_per_unit}\) (v3 transactions).

  • The total consumed resources.

    Consumed resources are resources used for the execution of the transaction up to the point of failure, including Cairo steps, builtins, syscalls, L1 messages, events, and state diffs during the validation and execution stages.

Transaction receipt

A transaction receipt can be obtained by using the Starknet API’s starknet_getTransactionReceipt endpoint and contains the following fields:

transaction_hash

The hash of the transaction.

actual_fee

The actual fee paid for the transaction.

finality_status

The finality status of the transaction.

execution_status

The execution status of the transaction.

block_hash

The hash of the block that includes the transaction

block_number

The sequential number of the block that includes the transaction

messages_sent

A list of messages sent to L1.

events

The events emitted.

execution_resource

A summary of the execution resources used by the transaction.

type

The type of the transaction.

The following is an example of a transaction receipt:

{
  "jsonrpc": "2.0",
  "result": {
    "actual_fee": "0x221db5dbf6db",
    "block_hash": "0x301fc0d09c5810600af7bb9610be10596ad6f4e6d28a60d397dd148f0962a88",
    "block_number": 906096,
    "events": [
      {
        "data": [
          "0x181de8b0cd32999a5cc962c5f724bc0f6a322f02957b80e1d5fef49a87588b7",
          "0x0",
          "0x9184e72a000",
          "0x0"
        ],
        "from_address": "0x49d36570d4e46f48e99674bd3fcc84644ddd6b96f7c741b1562b82f9e004dc7",
        "keys": [
          "0x99cd8bde557814842a3121e8ddfd433a539b8c9f14bf31ebf108d12e6196e9"
        ]
      },
      {
        "data": [
          "0x764da020183e28a48ee38a9474f84e7e5ff13194",
          "0x9184e72a000",
          "0x0",
          "0x181de8b0cd32999a5cc962c5f724bc0f6a322f02957b80e1d5fef49a87588b7"
        ],
        "from_address": "0x73314940630fd6dcda0d772d4c972c4e0a9946bef9dabf4ef84eda8ef542b82",
        "keys": [
          "0x194fc63c49b0f07c8e7a78476844837255213824bd6cb81e0ccfb949921aad1"
        ]
      },
      {
        "data": [
          "0x181de8b0cd32999a5cc962c5f724bc0f6a322f02957b80e1d5fef49a87588b7",
          "0x1176a1bd84444c89232ec27754698e5d2e7e1a7f1539f12027f28b23ec9f3d8",
          "0x221db5dbf6db",
          "0x0"
        ],
        "from_address": "0x49d36570d4e46f48e99674bd3fcc84644ddd6b96f7c741b1562b82f9e004dc7",
        "keys": [
          "0x99cd8bde557814842a3121e8ddfd433a539b8c9f14bf31ebf108d12e6196e9"
        ]
      }
    ],
    "execution_status": "SUCCEEDED",
    "finality_status": "ACCEPTED_ON_L2",
    "messages_sent": [
      {
        "from_address": "0x73314940630fd6dcda0d772d4c972c4e0a9946bef9dabf4ef84eda8ef542b82",
        "payload": [
          "0x0",
          "0x764da020183e28a48ee38a9474f84e7e5ff13194",
          "0x9184e72a000",
          "0x0"
        ],
        "to_address": "0xc3511006c04ef1d78af4c8e0e74ec18a6e64ff9e"
      }
    ],
    "transaction_hash": "0xdeadbeef",
    "type": "INVOKE"
  },
  "id": 1
}