Skip to content

PLATFORM_VERSION_OVERRIDE is still pinned to 12, but testnet has been running protocol version 13 since late July #112

Description

@DashBot-0001

platformVersion.mjs pins the SDK to protocol version 12:

// TODO: Remove this pin once dashpay/platform#3809 lands in the consumed
// @dashevo/evo-sdk release; unpinned clients should then auto-detect the
// network protocol version safely.
export const PLATFORM_VERSION_OVERRIDE = 12;

That value was last bumped in chore: bump platform version override to 12 (2026-06-18). Since then testnet has moved to protocol version 13, and the pin appears not to have been bumped along with it.

Testnet is on PV 13. Consensus block headers show the switch happening between 2026-07-25 and 2026-07-28:

Block height version.app Block time
460000 12 2026-07-24
466000 12 2026-07-25
472000 13 2026-07-28
483354 13 2026-08-03

/consensus_params on testnet currently reports version.app_version: "13", i.e. the value in force on-chain rather than a node's desired version.

A pin disables auto-detection rather than acting as a floor. In rs-sdk/src/sdk.rs, the ratchet returns immediately when a version is pinned:

fn maybe_update_protocol_version(&self, received_version: u32) {
    if self.version_pinned {
        return;
    }
    ...

and Sdk::version() documents that "when pinned via SdkBuilder::with_version(), always returns the pinned version". So a pinned client stays at 12 silently — no error and no warning — even when every response carries protocol_version: 13.

Since createClient() in setupDashClient-core.mjs passes the constant to all three networks, this applies to testnetTrusted, mainnetTrusted and localTrusted alike, and the same constant is imported by the dashrate, dashnote and dashnote-starter example apps. (dashmint-lab's dashmint-lite.html doesn't import it, but carries a comment pointing back at the same pin, so it would likely want the same treatment.)

The TODO's removal condition already appears to be met. dashpay/platform#3809 merged on 2026-06-12, and it looks present in the consumed release: unpacking @dashevo/evo-sdk@4.1.0 and decompressing the inlined WASM, the binary contains the tracing string received unknown protocol version from network, which that PR introduced. So the "once #3809 lands in the consumed release" condition seems satisfied as of 4.0.0/4.1.0.

What the green CI does and doesn't cover. The read-only suite has been passing against a PV-13 testnet with the client pinned to 12, and since the tutorials use the *Trusted factories — which pre-fetch quorum keys for proof verification — that is real evidence that the read path stays compatible across this particular version gap. It is a genuine data point in favour of the pin being harmless, and I want to be clear that I am not reporting a known breakage.

The write path is the part with no coverage. test-tutorials.yml gates the read-write job on github.event_name == 'workflow_dispatch', so pushes and pull requests only ever run test:read-only. The two workflow_dispatch runs in the workflow's history are from 2026-03-12 and 2026-04-10 — both months before testnet moved to 13. So state transitions built by a version-12-pinned client have not been exercised against a PV-13 network in CI.

What I have not verified: whether a client pinned to 12 actually behaves any differently against a PV-13 network for state transitions. I did not run the write tutorials, so I am not claiming breakage. drive_state_transition_method_versions has a v3 entry associated with protocol version 13, which suggests the write surface is at least version-sensitive, but that is a reason to check rather than evidence of a fault.

Given that mainnet's PV-13 vote has already passed threshold, the same window will open for NETWORK=mainnet at the next epoch boundary, so it seemed worth reporting before then rather than after.

Suggested next steps, in whichever order makes sense:

  • Either bump the pin to 13 or drop it per the TODO, since #3809 appears to be in the consumed SDK release.
  • Trigger one workflow_dispatch run of the read-write suite — that would settle the open question above directly.
  • Optionally, consider whether the read-write suite should run on some schedule, since a version-sensitive regression is currently only observable by manual dispatch.

Reported with assistance from Claude (Anthropic).

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions