refactor: complete XAssetID -> UTXOAssetID rename (functions, tests)

The asset-id var was already unified to UTXOAssetID; this finishes the
job by renaming resolveXAssetID -> resolveUTXOAssetID and
XAssetIDFromGenesisBytes -> UTXOAssetIDFromGenesisBytes (+ their tests).
X-Chain references (XChainID, XChainGenesis) are unchanged. UTXOAssetID
is the canonical name.

Co-authored-by: Hanzo Dev <dev@hanzo.ai>
This commit is contained in:
Antje Worring
2026-06-06 23:52:19 -07:00
co-authored by Hanzo Dev
parent 3635d010b7
commit 6de0514eda
5 changed files with 32 additions and 32 deletions
+5 -5
View File
@@ -1053,7 +1053,7 @@ func getGenesisData(v *viper.Viper, networkID uint32, stakingCfg *builder.Stakin
if err != nil {
return nil, ids.Empty, fmt.Errorf("failed to decode %s: %w", GenesisRawBytesKey, err)
}
utxoAssetID, err := resolveXAssetID(networkID, genesisBytes)
utxoAssetID, err := resolveUTXOAssetID(networkID, genesisBytes)
if err != nil {
return nil, ids.Empty, fmt.Errorf("resolve X-Chain asset ID from %s: %w", GenesisRawBytesKey, err)
}
@@ -1092,7 +1092,7 @@ func getGenesisData(v *viper.Viper, networkID uint32, stakingCfg *builder.Stakin
// Check if we have cached genesis bytes to avoid rebuilding
cacheFile := filepath.Join(dataDir, "genesis.bytes")
if cachedBytes, err := loadCachedGenesisBytes(cacheFile); err == nil && len(cachedBytes) > 0 {
utxoAssetID, err := resolveXAssetID(networkID, cachedBytes)
utxoAssetID, err := resolveUTXOAssetID(networkID, cachedBytes)
if err == nil {
log.Info("loaded cached genesis bytes for hash stability",
"cacheFile", cacheFile,
@@ -1140,7 +1140,7 @@ func getGenesisData(v *viper.Viper, networkID uint32, stakingCfg *builder.Stakin
return builder.FromConfig(config)
}
// resolveXAssetID extracts the X-Chain native asset ID from the loaded
// resolveUTXOAssetID extracts the X-Chain native asset ID from the loaded
// platform-genesis blob. It is the canonical source of truth used by
// every load path that bypasses FromConfig (raw bytes, cached bytes —
// the paths that historically defaulted to constants.UTXOAssetIDFor and
@@ -1159,8 +1159,8 @@ func getGenesisData(v *viper.Viper, networkID uint32, stakingCfg *builder.Stakin
//
// Tested against both sovereign-network genesis (X-Chain present, asset
// ID differs from the constant) and upstream Lux genesis fixtures.
func resolveXAssetID(networkID uint32, genesisBytes []byte) (ids.ID, error) {
id, ok, err := builder.XAssetIDFromGenesisBytes(genesisBytes)
func resolveUTXOAssetID(networkID uint32, genesisBytes []byte) (ids.ID, error) {
id, ok, err := builder.UTXOAssetIDFromGenesisBytes(genesisBytes)
if err != nil {
return ids.Empty, err
}
+13 -13
View File
@@ -6,8 +6,8 @@ package config
import (
"bytes"
"encoding/base64"
"github.com/go-json-experiment/json"
"fmt"
"github.com/go-json-experiment/json"
"log"
"os"
"path/filepath"
@@ -698,16 +698,16 @@ func TestDevModeFlags(t *testing.T) {
}
}
// TestResolveXAssetID_FromSovereignGenesis covers the canonical
// TestResolveUTXOAssetID_FromSovereignGenesis covers the canonical
// behaviour the sovereign-L1 fix relies on: when the loaded platform
// genesis bakes an X-Chain, resolveXAssetID returns the runtime asset
// genesis bakes an X-Chain, resolveUTXOAssetID returns the runtime asset
// ID encoded IN the genesis (matches what FromConfig produces, matches
// what the running X-Chain reports via platform.getStakingAssetID).
//
// Critically: NOT constants.UTXOAssetIDFor(networkID). That value is
// network-id-keyed and would silently collide between two sovereign L1s
// sharing a primary-network ID.
func TestResolveXAssetID_FromSovereignGenesis(t *testing.T) {
func TestResolveUTXOAssetID_FromSovereignGenesis(t *testing.T) {
require := require.New(t)
cfg := builder.GetConfig(constants.LocalID)
@@ -718,37 +718,37 @@ func TestResolveXAssetID_FromSovereignGenesis(t *testing.T) {
require.NoError(err)
require.NotEqual(ids.Empty, expectedID)
gotID, err := resolveXAssetID(constants.LocalID, genesisBytes)
gotID, err := resolveUTXOAssetID(constants.LocalID, genesisBytes)
require.NoError(err)
require.Equal(expectedID, gotID,
"resolveXAssetID must agree with FromConfig on the genesis-derived asset ID")
"resolveUTXOAssetID must agree with FromConfig on the genesis-derived asset ID")
}
// TestResolveXAssetID_POnlyFallback verifies that when the platform
// genesis bakes no X-Chain (P-only mode), resolveXAssetID falls back
// TestResolveUTXOAssetID_POnlyFallback verifies that when the platform
// genesis bakes no X-Chain (P-only mode), resolveUTXOAssetID falls back
// to constants.UTXOAssetIDFor(networkID). That value is unused at
// runtime (no X-Chain to mint on) but keeps the existing nodeConfig
// shape consistent for downstream consumers.
func TestResolveXAssetID_POnlyFallback(t *testing.T) {
func TestResolveUTXOAssetID_POnlyFallback(t *testing.T) {
require := require.New(t)
pOnly := &pchaingenesis.Genesis{Chains: nil}
pOnlyBytes, err := pchaingenesis.Codec.Marshal(pchaintxs.CodecVersion, pOnly)
require.NoError(err)
gotID, err := resolveXAssetID(42, pOnlyBytes)
gotID, err := resolveUTXOAssetID(42, pOnlyBytes)
require.NoError(err)
require.Equal(constants.UTXOAssetIDFor(42), gotID,
"P-only must fall through to UTXOAssetIDFor(networkID)")
}
// TestResolveXAssetID_Malformed asserts that bad genesis bytes surface
// TestResolveUTXOAssetID_Malformed asserts that bad genesis bytes surface
// an error rather than silently returning ids.Empty (which would
// reintroduce the UTXOAssetIDFor fallback and defeat the fix on
// sovereign L1s where the fallback value is wrong).
func TestResolveXAssetID_Malformed(t *testing.T) {
func TestResolveUTXOAssetID_Malformed(t *testing.T) {
require := require.New(t)
_, err := resolveXAssetID(1, []byte{0xff, 0xfe, 0xfd, 0xfc})
_, err := resolveUTXOAssetID(1, []byte{0xff, 0xfe, 0xfd, 0xfc})
require.Error(err)
}
+1 -1
View File
@@ -151,7 +151,7 @@ func TestNetworkConfiguration(t *testing.T) {
t.Logf("✓ Network configuration verified: ID=%d, Name=%s", networkID, expectedName)
}
func TestXAssetID(t *testing.T) {
func TestUTXOAssetID(t *testing.T) {
// Verify UTXOAssetID is used for native asset
utxoAssetID := ids.Empty // Our implementation uses Empty ID for native asset
+3 -3
View File
@@ -8,9 +8,9 @@ package builder
import (
"encoding/base64"
"github.com/go-json-experiment/json"
"errors"
"fmt"
"github.com/go-json-experiment/json"
"path"
"time"
@@ -685,7 +685,7 @@ func FromDatabase(networkID uint32, dbPath string, dbType string, stakingCfg *St
return FromConfig(config)
}
// XAssetIDFromGenesisBytes returns the X-Chain native asset ID encoded
// UTXOAssetIDFromGenesisBytes returns the X-Chain native asset ID encoded
// in a platform-genesis blob. It parses the platform genesis, finds the
// X-Chain CreateChainTx (vmID == constants.XVMID), then decodes that
// chain's embedded XVM genesis bytes to recover the runtime asset ID
@@ -706,7 +706,7 @@ func FromDatabase(networkID uint32, dbPath string, dbType string, stakingCfg *St
// helper through getGenesisData means the node always reports the
// genesis-derived asset ID via platform.getStakingAssetID regardless
// of which load path was taken.
func XAssetIDFromGenesisBytes(genesisBytes []byte) (ids.ID, bool, error) {
func UTXOAssetIDFromGenesisBytes(genesisBytes []byte) (ids.ID, bool, error) {
// Parse the platform genesis directly so we can distinguish parse
// failure ("garbage bytes — fatal") from missing X-Chain ("P-only
// mode — caller falls back to UTXOAssetIDFor"). VMGenesis collapses
+10 -10
View File
@@ -14,17 +14,17 @@ import (
pchaintxs "github.com/luxfi/node/vms/platformvm/txs"
)
// TestXAssetIDFromGenesisBytes_Sovereign asserts the canonical
// TestUTXOAssetIDFromGenesisBytes_Sovereign asserts the canonical
// behaviour the sovereign-L1 fix relies on: when the platform genesis
// bakes an X-Chain, the X-Chain asset ID returned by
// XAssetIDFromGenesisBytes is the runtime ID encoded IN the genesis
// UTXOAssetIDFromGenesisBytes is the runtime ID encoded IN the genesis
// (different across networks with different validator/holder sets),
// NOT the network-id-keyed constants.UTXOAssetIDFor(networkID) value.
//
// The two values disagreeing is the whole reason the helper exists —
// sovereign primary networks sharing a networkID would otherwise
// silently collide on the constant.
func TestXAssetIDFromGenesisBytes_Sovereign(t *testing.T) {
func TestUTXOAssetIDFromGenesisBytes_Sovereign(t *testing.T) {
require := require.New(t)
// Use the local devnet config — it has an X-Chain genesis baked in,
@@ -38,7 +38,7 @@ func TestXAssetIDFromGenesisBytes_Sovereign(t *testing.T) {
require.NotEmpty(genesisBytes)
require.NotEqual(ids.Empty, fromConfigID)
helperID, ok, err := XAssetIDFromGenesisBytes(genesisBytes)
helperID, ok, err := UTXOAssetIDFromGenesisBytes(genesisBytes)
require.NoError(err)
require.True(ok, "X-Chain is in genesis — helper must report ok=true")
require.Equal(fromConfigID, helperID, "helper must agree with FromConfig")
@@ -54,31 +54,31 @@ func TestXAssetIDFromGenesisBytes_Sovereign(t *testing.T) {
// assert the value is non-zero and matches FromConfig's return.
}
// TestXAssetIDFromGenesisBytes_POnly verifies that when the platform
// TestUTXOAssetIDFromGenesisBytes_POnly verifies that when the platform
// genesis has no X-Chain (P-only mode), the helper returns ok=false
// and ids.Empty rather than an error. Callers fall back to
// constants.UTXOAssetIDFor(networkID) in that case (the value is
// unused at runtime since there is no X-Chain to mint on).
func TestXAssetIDFromGenesisBytes_POnly(t *testing.T) {
func TestUTXOAssetIDFromGenesisBytes_POnly(t *testing.T) {
require := require.New(t)
pOnly := &genesis.Genesis{Chains: nil}
pOnlyBytes, err := genesis.Codec.Marshal(pchaintxs.CodecVersion, pOnly)
require.NoError(err)
id, ok, err := XAssetIDFromGenesisBytes(pOnlyBytes)
id, ok, err := UTXOAssetIDFromGenesisBytes(pOnlyBytes)
require.NoError(err, "P-only is a valid mode, not a parse error")
require.False(ok, "P-only must report ok=false so caller falls back")
require.Equal(ids.Empty, id)
}
// TestXAssetIDFromGenesisBytes_Malformed asserts that bad input
// TestUTXOAssetIDFromGenesisBytes_Malformed asserts that bad input
// surfaces an error — silently returning ids.Empty would reintroduce
// the UTXOAssetIDFor(networkID) fallback path and defeat the fix.
func TestXAssetIDFromGenesisBytes_Malformed(t *testing.T) {
func TestUTXOAssetIDFromGenesisBytes_Malformed(t *testing.T) {
require := require.New(t)
_, _, err := XAssetIDFromGenesisBytes([]byte{0xde, 0xad})
_, _, err := UTXOAssetIDFromGenesisBytes([]byte{0xde, 0xad})
require.Error(err)
}