Packages

@solana/kit

8.5.0 · 13 Oct 2026MIT1.3M / weekRepositoryHomepagenpmAtom feed

40 stable releases, newest first, by release line. Notes are quoted as the maintainers published them.

  1. 8.x · latest line
  2. 8.5.0

    13 Oct 2026
    • [@solana/addresses] #2115 e59ed8b Thanks @lorisleiva! - Allow getAddressEncoder() and getAddressCodec() to encode any address-bearing object (HasAddress) in addition to plain Address values, so that signers and framework wrapper classes can be encoded directly without unwrapping them first. Decoders still return a plain Address. As a result, the encoder input type of codecs composing an address codec (e.g. a struct with an address field) is now inferred as Address | HasAddress instead of Address.

      const addressEncoder = getAddressEncoder();
      addressEncoder.encode(signer); // Same bytes as `addressEncoder.encode(signer.address)`.
    • [@solana/codecs-data-structures, @solana/errors] #2089 de1c63f Thanks @latent-9! - Fix an infinite loop in the array, set, and map codecs' sentinel and remainder decoding strategies: a zero-byte item codec (e.g. getStructCodec()) can never advance past a sentinel boundary or the end of the byte array, so decoding used to push elements until the process ran out of memory. Zero-byte fixed-size item codecs are now rejected on both the encoding and decoding sides when used with the sentinel or remainder strategies, throwing a new error instead: SOLANA_ERROR__CODECS__UNEXPECTED_ZERO_FIXED_SIZE_ITEM_FOR_ARRAY_LIKE_SIZE_STRATEGY. They remain allowed when the collection size is explicit.

    • [@solana/errors] #2111 0be380e Thanks @mcintyre94! - Add the SOLANA_ERROR__WALLET__INVALID_MESSAGE_SIGNATURE and SOLANA_ERROR__WALLET__INVALID_SIGN_IN_OUTPUT error codes, thrown when a wallet returns a message signature or a sign-in output that fails verification. Their context carries the signing account's address and the walletName.

      Also add the SOLANA_ERROR__WALLET__INVALID_NUMBER_OF_OUTPUTS error code, thrown when a wallet feature returns a different number of outputs than the number of inputs it was given. Its context carries the expected and actual number of outputs, the featureName and the walletName.

  3. 8.4.0

    28 Sep 2026
    • [@solana/codecs-data-structures, @solana/errors] #2061 0e76741 Thanks @lorisleiva! - Add a sentinel size strategy to the array, set, and map codecs. Passing a { __kind: 'sentinel', sentinel, strategy? } object as the size option ends the collection when the bytes at the next item position match the given sentinel, compared at item boundaries only. The optional strategy ('required' by default, or 'optional' / 'omitted') controls whether the sentinel is written when encoding and required when decoding. This provides codec support for Codama's sentinelCountNode.

      Two new errors accompany this: SOLANA_ERROR__CODECS__SENTINEL_MISSING_AT_END_OF_BYTES (thrown under the 'required' strategy when the byte array ends without the sentinel) and SOLANA_ERROR__CODECS__SENTINEL_MUST_NOT_BE_EMPTY (thrown when constructing a codec with an empty sentinel).

    • [@solana/errors, @solana/instruction-plans] #2073 5be269c Thanks @lorisleiva! - Add helpers for writing custom message packers. resolveMaxInstructionsPerTransaction, assertMaxInstructionsPerTransaction and assertMessageCanAccommodateSize enforce the instruction-count and size limits the built-in packers rely on, and a new SOLANA_ERROR__INSTRUCTION_PLANS__MESSAGE_REJECTED_BY_PACKER error lets a packer refuse a transaction message for any other reason by providing a reason. The transaction planner treats this error like the existing capacity errors and opens a new transaction message. Use isMessagePackerErrorThatRequiresNewCandidate to identify every error that calls for a new transaction message.

    • [@solana/codecs-numbers] #2067 56b4960 Thanks @latent-9! - Fixed getShortU16Decoder() silently accepting malformed input: a truncated buffer decoded to garbage with an offset past the end of the byte array, and continuation chains longer than the documented three-byte encoding decoded to values outside the u16 domain. Malformed input now throws SOLANA_ERROR__CODECS__INVALID_BYTE_LENGTH, and decoded values above 65,535 now throw SOLANA_ERROR__CODECS__NUMBER_OUT_OF_RANGE, matching the guards every other number decoder already uses.

  4. 8.3.0

    9 Sep 2026
    • [@solana/addresses, @solana/transaction-messages] #2025 7a14614 Thanks @lorisleiva! - Add a new HasAddress type representing any object exposing a Solana address through an address property — e.g. a TransactionSigner, an AccountMeta or a framework's address wrapper class. The fee payer of a transaction message is now typed using HasAddress (a structurally identical change).

    • [@solana/codecs-core] #2030 a5267b3 Thanks @lorisleiva! - Add tap codec helpers for observing values and bytes without modifying them. The value family (tapEncoder/tapDecoder/tapCodec) observes the input value before encoding and the decoded value after decoding, whilst the bytes family (tapEncoderBytes/tapDecoderBytes/tapCodecBytes) observes the raw bytes after encoding and before decoding. Any tap may throw to abort the operation, making these helpers ideal for adding validation guards to existing codecs without an identity transformEncoder. For example, tapDecoderBytes(getBooleanDecoder(), (bytes, offset) => { if (bytes[offset] > 1) throw new Error('Expected a 0 or a 1 for booleans'); }).

    • [@solana/codecs-data-structures] #2042 cd2776e Thanks @lorisleiva! - Add a requireSizePrefix option to the array, map and set codecs. By default, decoding an exhausted byte array yields an empty collection so that collections can be appended to existing data layouts; with requireSizePrefix: true, a missing size prefix throws instead.

  5. 8.2.0

    29 Aug 2026
    • breaking

      [@solana/instruction-plans] #2013 26edd3b Thanks @mcintyre94! - Align createTransactionPlanExecutorWithConcurrentLeaves with createTransactionPlanExecutor by giving both the same TransactionPlanExecutorConfig. Its executeTransactionMessage callback now receives a mutable per-leaf context object and returns the context of a successful result, instead of building a whole SingleTransactionPlanResult itself. The executor builds the results: on success it merges the returned context over the stored one, and when the callback throws — or the abort signal fires before it settles — it preserves the stored context on the failed result, matching the partial-context behaviour of createTransactionPlanExecutor. The ConcurrentLeafTransactionPlanExecutorConfig type is removed. This is a breaking change to the createTransactionPlanExecutorWithConcurrentLeaves API introduced in 8.1.0.

    • [@solana/signers] #2006 d385ce3 Thanks @amilz! - Relaxed the parameter type of the signer type guards (isMessagePartialSigner, isTransactionSigner, isKeyPairSigner, their siblings, and the assertIs* variants) so that class instances implementing a signer interface can be passed without casts. The guards now accept any TValue extends { address: Address } and narrow to TValue & Signer, whereas the previous parameter type required an implicit index signature, which TypeScript never grants to class instances.

  6. 8.1.0

    27 Aug 2026
    • [@solana/errors, @solana/transaction-messages] #1972 7d56e29 Thanks @skyyycodes! - Validate compute unit limit and heap size when they are set on a transaction message

      setTransactionMessageComputeUnitLimit, setTransactionMessageHeapSize and setTransactionMessageConfig now reject values the runtime will not honor as written, throwing SOLANA_ERROR__TRANSACTION__COMPUTE_UNIT_LIMIT_OUT_OF_RANGE or SOLANA_ERROR__TRANSACTION__INVALID_HEAP_SIZE at the point the value is set. An invalid heap size fails the transaction on-chain; a compute unit limit above the maximum is instead clamped down by the runtime, so the transaction quietly runs with a budget other than the one requested. A compute unit limit must be an integer in the range [0, 1,400,000]; a heap size must be an integer multiple of 1 KiB between 32 KiB and 256 KiB inclusive.

      Decoding is unaffected: decompileTransactionMessage still returns messages carrying out-of-range values so that callers can inspect any transaction that reaches them.

    • [@solana/instruction-plans] #1995 95a2788 Thanks @mcintyre94! - Add createTransactionPlanExecutorWithConcurrentLeaves to concurrently transform every transaction plan leaf while preserving the plan's result shape.

    • [@solana/codecs-core] #1970 be30e32 Thanks @koriyoshi2041! - Fix toArrayBuffer slicing SharedArrayBuffer-backed views from a non-zero byte offset.

  7. 8.0.0

    21 Aug 2026
    • breaking

      [@solana/instruction-plans] #1913 80368eb Thanks @mcintyre94! - Stop writing to the execution context in createTransactionPlanExecutor

      The executeTransactionMessage callback can no longer return a Signature or a Transaction. Those return values were deprecated when the callback gained the ability to return the context that a successful result should carry, and they are now gone: that context, a complete TContext, is the only thing the callback returns. Nothing is written to it on your behalf.

      const transactionPlanExecutor = createTransactionPlanExecutor({
        executeTransactionMessage: async (context, message) => {
          const transaction = await signTransactionMessageWithSigners(message);
          context.transaction = transaction;
      +   const signature = getSignatureFromTransaction(transaction);
          await sendAndConfirmTransaction(transaction, { commitment: 'confirmed' });
      -   return transaction;
      +   return { signature, transaction };
        },
      });

      The mutable context argument is still there, and still serves the failure path: whatever the callback stores on it before it throws is preserved in the resulting FailedSingleTransactionPlanResult. The two channels differ only in which outcome they feed. Mutating the context makes a value available to a failed result; returning it makes a value available to a successful one. On success the two are merged, with the returned value taking precedence, so a property stored but not returned is still reported.

      Note that the callback cannot simply return the context it was given — every property on it is optional, so it does not satisfy TContext. Build the return value from the values you have instead. This is the point of the return type: a callback that declares a context with a required signature and never produces one now fails to compile, rather than yielding a successful result whose context.signature is typed but undefined at runtime.

      This unblocks executors that never obtain a fee payer signature. Previously the executor derived context.signature by calling getSignatureFromTransaction on a returned transaction, and on any transaction found on the context while handling a failure. That call throws SOLANA_ERROR__TRANSACTION__FEE_PAYER_SIGNATURE_MISSING when the fee payer slot is empty, so an executor that deliberately produces partially signed transactions — signed by an authority, to be paid for and submitted by a relayer later — could not succeed, and one that stored such a transaction before failing had its original error replaced by that one. Neither derivation exists any more, so both cases now work. Declare a context type that does not require a signature and store just the transaction:

      const transactionPlanExecutor = createTransactionPlanExecutor<{ transaction: Transaction }>({
          executeTransactionMessage: async (_context, message) => {
              return { transaction: await signTransactionMessageWithSigners(message) };
          },
      });

      Signatures are no longer added behind your back. An executor whose TContext requires a signature — including the default TransactionPlanResultContextWithSignature — must now produce one itself, and the compiler holds it to that. Failed results carry only what the callback stored on the context before it threw; a signature is no longer recovered from a stored transaction.

      BaseTransactionPlanResultContext is removed. It described the fields the executor used to write on your behalf, and nothing writes them any more — what a context holds is entirely TContext's business. Use TransactionPlanResultContextWithSignature where you want the signature guarantee, or declare the optional message / signature / transaction fields your own context actually needs.

      successfulSingleTransactionPlanResultFromTransaction is removed. It was the last place that derived a signature on your behalf — by calling getSignatureFromTransaction, with the same fee-payer-signature requirement described above — and the executor no longer uses it. Construct results with successfulSingleTransactionPlanResult instead, passing the context explicitly:

      - successfulSingleTransactionPlanResultFromTransaction(message, transaction);
      + successfulSingleTransactionPlanResult(message, {
      +   signature: getSignatureFromTransaction(transaction),
      +   transaction,
      + });
    • breaking

      [@solana/instruction-plans, @solana/kit, @solana/rpc-transformers, @solana/transactions] #1948 34568a9 Thanks @mcintyre94! - Remove APIs that were deprecated in previous versions: the compute-unit-limit estimation helpers in @solana/kit, the getBigIntDowncastRequestTransformer in @solana/rpc-transformers, the fixed transaction size constants in @solana/transactions, and the SuccessfulBaseTransactionPlanResultContext type in @solana/instruction-plans.

      BREAKING CHANGES

      estimateComputeUnitLimitFactory removed from @solana/kit. Use estimateResourceLimitsFactory instead. The resource-limits estimator returns both the compute unit limit and (for version 1 transactions) the loaded accounts data size limit from a single simulation call.

      - const estimateComputeUnitLimit = estimateComputeUnitLimitFactory({ rpc });
      - const computeUnitLimit = await estimateComputeUnitLimit(transactionMessage);
      + const estimateResourceLimits = estimateResourceLimitsFactory({ rpc });
      + const { computeUnitLimit } = await estimateResourceLimits(transactionMessage);

      estimateAndSetComputeUnitLimitFactory removed from @solana/kit. Use estimateAndSetResourceLimitsFactory instead, which additionally sets the loaded accounts data size limit for version 1 transactions.

      - const estimateAndSet = estimateAndSetComputeUnitLimitFactory(estimateComputeUnitLimitFactory({ rpc }));
      + const estimateAndSet = estimateAndSetResourceLimitsFactory(estimateResourceLimitsFactory({ rpc }));
        const updatedMessage = await estimateAndSet(transactionMessage);

      fillTransactionMessageProvisoryComputeUnitLimit removed from @solana/kit. Use fillTransactionMessageProvisoryResourceLimits instead, which additionally reserves space for the loaded accounts data size limit on version 1 transactions.

      - const filledMessage = fillTransactionMessageProvisoryComputeUnitLimit(transactionMessage);
      + const filledMessage = fillTransactionMessageProvisoryResourceLimits(transactionMessage);

      getBigIntDowncastRequestTransformer removed from @solana/rpc-transformers. This transformer was no longer used by the default Solana RPC request transformer. The Solana RPC transport serializes bigint values losslessly as large integer literals, and Agave parses JSON integers across the full u64 range without precision loss, so downcasting bigints to (potentially lossy) numbers is unnecessary. If you still need this behavior, recreate it with getTreeWalkerRequestTransformer.

      TRANSACTION_PACKET_SIZE, TRANSACTION_PACKET_HEADER, and TRANSACTION_SIZE_LIMIT removed from @solana/transactions. Transaction size is no longer constant, as version 1 transactions have a larger size limit. Use getTransactionSizeLimit to get the size limit for a specific transaction based on its version, or the LEGACY_TRANSACTION_SIZE_LIMIT and V1_TRANSACTION_SIZE_LIMIT constants for a specific version.

      - const numFreeBytes = TRANSACTION_SIZE_LIMIT - getTransactionSize(transaction);
      + const numFreeBytes = getTransactionSizeLimit(transaction) - getTransactionSize(transaction);

      SuccessfulBaseTransactionPlanResultContext removed from @solana/instruction-plans. Use TransactionPlanResultContextWithSignature instead as the context type argument.

      - function processResult(result: SuccessfulSingleTransactionPlanResult<SuccessfulBaseTransactionPlanResultContext>) {
      + function processResult(result: SuccessfulSingleTransactionPlanResult<TransactionPlanResultContextWithSignature>) {
    • breaking

      [@solana/instruction-plans] #1910 7b983ba Thanks @mcintyre94! - Let TContext decide what a transaction plan result context contains

      The context attached to a transaction plan result was never entirely controlled by the executor. SuccessfulSingleTransactionPlanResult hardcoded it as SuccessfulBaseTransactionPlanResultContext & TContext, and createTransactionPlanExecutor mixed further properties into both the callback's context and the executor's result type. Because intersections only ever narrow, no choice of TContext could relax the required signature — which made it impossible to type an executor that partially signs transactions for a relayer to submit later.

      TContext is now the only thing that says what a context contains. The signature guarantee moved out of the structure of the result types and into the default value of TContext, so every zero-type-argument spelling behaves exactly as it did before.

      A new context type. TransactionPlanResultContextWithSignature guarantees a signature and is the new default everywhere. SuccessfulBaseTransactionPlanResultContext is deprecated in favour of it.

      Explicit context types must be migrated. Intersect the new default to keep the signature guarantee:

      - SingleTransactionPlanResult<{ startedAt: number }>
      + SingleTransactionPlanResult<TransactionPlanResultContextWithSignature & { startedAt: number }>

      The executor callback now receives Partial<TContext>. A fresh, empty context is created for every transaction message and filling it in is the callback's job, but its properties used to be typed as required — so a callback could read one before writing it, be told a value was there, and get undefined at runtime. Everything is optional on entry now. Writing still narrows, so a read after context.custom = 'value' gives the non-optional type.

      One consequence is that a callback can no longer annotate its own parameter with required properties, which was a common way to infer a custom context. Use a type argument instead:

      - createTransactionPlanExecutor({
      -     executeTransactionMessage: async (context: { startedAt: number }) => { /* ... */ },
      - })
      + createTransactionPlanExecutor<TransactionPlanResultContextWithSignature & { startedAt: number }>({
      +     executeTransactionMessage: async context => { /* ... */ },
      + })

      A returned context no longer has to carry a signature. The executeTransactionMessage callback may return the context that a successful result should carry, and that context used to need a signature because the result type hardcoded one. TContext decides now: the default still requires it, and a custom TContext that omits it is accepted — which is what makes the relayer case above expressible end to end, rather than merely possible at runtime. Consequently the executor no longer tells a returned context apart from a returned Transaction by looking for a signature on it, since a context may not have one; it looks for the signatures map that only a Transaction has.

      Failed and canceled results type their context as Readonly<Partial<TContext>>. Those branches never guaranteed custom properties at runtime — the context is built incrementally and the callback may throw at any point — so the types now say so.

      Inference from object literals is narrower, since the result constructors no longer add properties you did not pass. successfulSingleTransactionPlanResult(message, { signature }) infers Readonly<{ signature: Signature }> rather than a context that also carried optional message and transaction fields plus an index signature, so reading result.context.message off it is now an error. On the failed and canceled constructors the Partial goes further: even a field you did pass comes back optional, so failedSingleTransactionPlanResult(message, error, { transaction }).context.transaction is Transaction | undefined. Pass an explicit type argument wherever you need a field to type as required. Relatedly, successfulSingleTransactionPlanResultFromTransaction's optional context parameter changes from Omit<BaseTransactionPlanResultContext, 'signature' | 'transaction'> & TContext to TContext; signature and transaction are still derived from the transaction argument and intersected into the result's context type.

      Helpers that consume results now accept any context. passthroughFailedTransactionPlanExecution, createFailedToSendTransactionError, createFailedToSendTransactionsError and createFailedToExecuteTransactionPlanError were non-generic, so they implicitly demanded the default signature-guaranteeing context and rejected results parameterised with anything else. They are now generic over TContext and preserve it. Where they read a signature to build an error message they narrow it at runtime, so a result without one simply omits it from the message.

      Execution behaviour is unchanged. The executor still populates context.signature from the signature or transaction your callback returns, and still recovers one for failed results from a transaction left on the context. Those writes just no longer show up in the result type unless your TContext asked for them. The behavioural changes are the two described above: an error message built from a context whose signature is absent, or is not a string, now omits it rather than interpolating whatever was there, and a returned context is recognised by the absence of a signatures map rather than the presence of a signature.

  8. 7.x
  9. 7.1.1

    18 Aug 2026
    • [@solana/codecs-strings] #1926 1d074ed Thanks @latent-9! - Fix getBaseXDecoder returning an offset of 0 instead of the buffer length when there are no bytes left to decode, which corrupted the offset of any decoder composed after it.

    • [@solana/instruction-plans] #1924 769da66 Thanks @mcintyre94! - Deprecate transaction plan result APIs being removed in v8

      Both of the following are deprecated and will be removed in the next major version.

      successfulSingleTransactionPlanResultFromTransaction derives the transaction signature on your behalf by calling getSignatureFromTransaction, which throws when the transaction's fee payer has not signed it. Construct results with successfulSingleTransactionPlanResult instead, passing the context explicitly:

      - successfulSingleTransactionPlanResultFromTransaction(message, transaction, context);
      + successfulSingleTransactionPlanResult(message, {
      +   ...context,
      +   signature: getSignatureFromTransaction(transaction),
      +   transaction,
      + });

      BaseTransactionPlanResultContext goes away together with the intersections that graft it onto every SingleTransactionPlanResult. The context of a result is becoming entirely caller-defined — it will be exactly the TContext you supply — so there will be no separate base shape to merge in. If you refer to this type, declare whichever of its fields you need on your own context type instead:

      type MyContext = {
          message?: TransactionMessage & TransactionMessageWithFeePayer;
          signature?: Signature;
          transaction?: Transaction;
      };
    • [@solana/rpc-spec, @solana/rpc-spec-types, @solana/rpc-subscriptions-spec] #1748 9f8e4d0 Thanks @ChargingFoxSec! - Avoid treating JavaScript protocol hooks and Object prototype properties as RPC method names in proxy-backed RPC objects.

  10. 7.1.0

    14 Aug 2026
    • [@solana/errors, @solana/kit, @solana/react, @solana/subscribable] #1811 7022c26 Thanks @mcintyre94! - Add bridgeStoreToAsyncIterable to @solana/subscribable

      bridgeStoreToAsyncIterable adapts a ReactiveStreamStore into the pull-based AsyncIterable contract that consumers like TanStack Query's experimental_streamedQuery expect. It is now a public export of @solana/subscribable (and re-exported from @solana/kit). It was previously an internal helper of @solana/react, but it is not React- or TanStack-specific and is useful to any consumer that needs to drive a stream store by for await-ing it.

      The bridge only observes the store — consistent with the rest of the ecosystem, the caller owns the store's lifecycle (connect() it yourself, bound to the same signal, and reset() it when done). The bridge subscribes, seeds from the store's current snapshot, yields values, and unsubscribes when iteration ends.

      It throws the new SOLANA_ERROR__SUBSCRIBABLE__STREAM_CLOSED_WITHOUT_ERROR when a store closes in an error state with a nullish payload. This is the error useSubscriptionQuery and useTrackedDataQuery now surface in that case; the SWR bridge is unaffected.

    • [@solana/errors, @solana/offchain-messages] #1888 14a3e5b Thanks @mcintyre94! - Add an assertOffchainMessageV1Equal helper that asserts that a version 1 offchain message you received from an untrusted signer (eg. a wallet) is the message you expected it to sign. Verifying a signature proves only that the signer produced it over the bytes it handed back, not that those bytes represent the message you asked for, so assert this before verifying signatures with verifyOffchainMessageEnvelope. The helper compares the content and the required signatories, and reports each kind of mismatch with its own error code: the new SOLANA_ERROR__OFFCHAIN_MESSAGE__CONTENT_DOES_NOT_MATCH_EXPECTED and SOLANA_ERROR__OFFCHAIN_MESSAGE__REQUIRED_SIGNATORIES_DO_NOT_MATCH_EXPECTED. Required signatories are compared without regard to order, since a decoded message lists them in the order the specification mandates while yours may be in any order. It accepts an OffchainMessageV1 rather than the OffchainMessage union that decoding produces, so narrow the decoded message to a version 1 message before calling it.

    • [@solana/instruction-plans] #1915 9e7daea Thanks @mcintyre94! - Let the createTransactionPlanExecutor callback return the context of a successful result

      The executeTransactionMessage callback may now return the context that a successful result should carry, instead of a Signature or a Transaction. When it does, that context is used as-is: nothing is derived from it, and in particular getSignatureFromTransaction is never called on your behalf.

      const transactionPlanExecutor = createTransactionPlanExecutor({
        executeTransactionMessage: async (context, message) => {
          const transaction = await signTransactionMessageWithSigners(message);
          context.transaction = transaction;
      +   const signature = getSignatureFromTransaction(transaction);
          await sendAndConfirmTransaction(transaction, { commitment: 'confirmed' });
      -   return transaction;
      +   return { signature, transaction };
        },
      });

      Since a successful result always carries a signature, a returned context must include one — a callback that declares a custom context and forgets a property of it now fails to compile, rather than producing a result whose context is typed but undefined at runtime. That signature is also how the executor tells a returned context apart from a returned Transaction, which keeps its signatures in a signatures map and therefore never has one.

      The mutable context argument is unchanged and still serves the failure path: whatever the callback stores on it before it throws is preserved in the resulting FailedSingleTransactionPlanResult. On success the two are merged, with the returned context taking precedence, so a property stored but not returned is still reported.

      Returning a Signature or a Transaction is deprecated. Both still behave exactly as before — a returned signature is stored as context.signature, and a returned transaction is stored as context.transaction with its signature derived from it — and IDEs now flag those call sites, because createTransactionPlanExecutor gained a deprecated overload that only matches callbacks returning those types. Note that a config declared as TransactionPlanExecutorConfig up front is not flagged, since that type permits either return style.

      Prefer returning a context, since deriving a signature from a transaction throws SOLANA_ERROR__TRANSACTION__FEE_PAYER_SIGNATURE_MISSING when the fee payer slot is empty. An executor that deliberately produces partially signed transactions — signed by an authority, to be paid for and submitted by a relayer later — can now succeed by returning its own signature alongside the transaction. Dropping the signature from a successful result's context altogether remains impossible, since SuccessfulSingleTransactionPlanResult guarantees one.

      Failure handling is unchanged, including the signature still derived from a transaction left on the context when the callback throws. Since the callback never returned anything in that case, there is nothing to bypass that derivation, so a callback working with fee-payer-unsigned transactions should avoid storing them on the context — otherwise deriving a signature from one replaces the error it meant to report.

  11. 7.0.0

    30 Jun 2026

    Reading the note…

  12. 6.x
  13. 6.10.0

    16 Jun 2026

    Reading the note…

  14. 6.9.0

    6 May 2026

    Reading the note…

  15. 6.8.0

    10 Apr 2026

    Reading the note…

  16. 6.7.0

    2 Apr 2026

    Reading the note…

  17. 6.6.0

    1 Apr 2026

    Reading the note…

  18. 6.5.0

    19 Mar 2026

    Reading the note…

  19. 6.4.0

    18 Mar 2026

    Reading the note…

  20. 6.3.1

    12 Mar 2026

    Reading the note…

  21. 6.3.0

    11 Mar 2026

    Reading the note…

  22. 6.2.0

    9 Mar 2026

    Reading the note…

  23. 6.1.0

    16 Feb 2026

    Reading the note…

  24. 6.0.1

    5 Feb 2026

    Reading the note…

  25. 6.0.0

    4 Feb 2026

    Reading the note…

  26. 5.x
  27. 5.5.1

    28 Jan 2026

    Reading the note…

  28. 5.5.0

    27 Jan 2026

    Reading the note…

  29. 5.4.0

    13 Jan 2026

    Reading the note…

  30. 5.3.0

    7 Jan 2026

    Reading the note…

  31. 5.2.0

    7 Jan 2026

    Reading the note…

  32. 5.1.0

    12 Dec 2025

    Reading the note…

  33. 5.0.0

    23 Oct 2025

    Reading the note…

  34. 4.x
  35. 4.0.0

    8 Oct 2025

    Reading the note…

  36. 3.x
  37. 3.0.3

    11 Sep 2025

    Reading the note…

  38. 3.0.2

    3 Sep 2025

    Reading the note…

  39. 3.0.1

    29 Aug 2025

    Reading the note…

  40. 3.0.0

    27 Aug 2025

    Reading the note…

  41. 2.x
  42. 2.3.0

    8 Jul 2025

    Reading the note…

  43. 2.2.1

    8 Jul 2025

    Reading the note…

  44. 2.2.0

    8 Jul 2025

    Reading the note…

  45. 2.1.1

    12 May 2025

    Reading the note…

  46. 2.1.0

    27 Feb 2025

    Reading the note…

  47. 0.0.x
  48. 0.0.0

    27 Feb 2025

    Reading the note…