Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 5 additions & 6 deletions packages/portalnetwork/src/networks/beacon/beacon.ts
Original file line number Diff line number Diff line change
Expand Up @@ -695,14 +695,13 @@ export class BeaconNetwork extends BaseNetwork {
// TODO: Decide whether it ever makes sense to accept a HistoricalSummaries object if we don't already have a finality update to verify against
// return
} else {
// TODO: Make this future proof with forkConfig
const reconstructedStateMerkleTree = ssz.capella.BeaconState.createFromProof({
const forkName = this.beaconConfig.forkDigest2ForkName(value.slice(0, 4)) as LightClientForkName
const reconstructedStateMerkleTree = ssz[ForkName[forkName]].BeaconState.createFromProof({
type: ProofType.single,
gindex: ssz.capella.BeaconState.getPathInfo(['historicalSummaries']).gindex,
gindex: ssz[ForkName[forkName]].BeaconState.getPathInfo(['historicalSummaries']).gindex,
witnesses: summaries.proof,
leaf: ssz.capella.BeaconState.fields.historicalSummaries
.toView(summaries.historicalSummaries)
.hashTreeRoot(),
leaf: (ssz[ForkName[forkName]].BeaconState.fields as any).historicalSummaries
.hashTreeRoot(summaries.historicalSummaries)
})
if (
equalsBytes(
Expand Down
2 changes: 1 addition & 1 deletion packages/portalnetwork/src/networks/beacon/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ export const LightClientOptimisticUpdateKey = new ContainerType({

export const HistoricalSummariesKey = new ContainerType({ epoch: new UintBigintType(8) })

export const HistoricalSummariesStateProof = new VectorCompositeType(Bytes32Type, 5)
export const HistoricalSummariesStateProof = new VectorCompositeType(Bytes32Type, 6)

export const HistoricalSummariesWithProof = new ContainerType<{
epoch: UintBigintType
Expand Down
37 changes: 18 additions & 19 deletions packages/portalnetwork/test/integration/beacon.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -766,16 +766,16 @@ describe('beacon light client sync tests', () => {
describe('historicalSummaries verification', () => {
it('should sync two light clients to present and then gossip HistoricalSummaries', async () => {
vi.useFakeTimers({ shouldAdvanceTime: true, shouldClearNativeTimers: true })
vi.setSystemTime(1722959051100)
vi.setSystemTime(1747332119000)
const bootstrapJson =
require('./testdata/historicalSummaries/bootstrap0xb7918b28a8e9c6be29467a0771d0ab2693d5061f43d214b6056e8c6a12a5b9f3.json').data
const bootstrap = ssz.deneb.LightClientBootstrap.fromJson(bootstrapJson)
require('./testdata/historicalSummaries/bootstrap.json').data
const bootstrap = ssz.electra.LightClientBootstrap.fromJson(bootstrapJson)

const finalityUpdatejson = require('./testdata/historicalSummaries/finality_update.json').data
const finalityUpdate = ssz.deneb.LightClientFinalityUpdate.fromJson(finalityUpdatejson)
const finalityUpdatejson = require('./testdata/historicalSummaries/finalityUpdateSlot11708998.json').data
const finalityUpdate = ssz.electra.LightClientFinalityUpdate.fromJson(finalityUpdatejson)
const optimisticUpdateJson =
require('./testdata/historicalSummaries/optimistic_update.json').data
const optimisticUpdate = ssz.deneb.LightClientOptimisticUpdate.fromJson(optimisticUpdateJson)
require('./testdata/historicalSummaries/optimisticUpdateSlot11709008.json').data
const optimisticUpdate = ssz.electra.LightClientOptimisticUpdate.fromJson(optimisticUpdateJson)
const initMa: any = multiaddr('/ip4/127.0.0.1/udp/30027')
enr1.setLocationMultiaddr(initMa)
const initMa2: any = multiaddr('/ip4/127.0.0.1/udp/30028')
Expand Down Expand Up @@ -808,16 +808,16 @@ describe('historicalSummaries verification', () => {
const network1 = node1.networks.get(NetworkId.BeaconChainNetwork) as BeaconNetwork
const network2 = node2.networks.get(NetworkId.BeaconChainNetwork) as BeaconNetwork

const capellaForkDigest = network1.beaconConfig.forkName2ForkDigest(ForkName.deneb)

const capellaForkDigest = network1.beaconConfig.forkName2ForkDigest(ForkName.electra)
console.log(bytesToHex(ssz.phase0.BeaconBlockHeader.hashTreeRoot(bootstrap.header.beacon)))
await network1.store(
getBeaconContentKey(
BeaconNetworkContentType.LightClientBootstrap,
LightClientBootstrapKey.serialize({
blockHash: ssz.phase0.BeaconBlockHeader.hashTreeRoot(bootstrap.header.beacon),
}),
),
concatBytes(capellaForkDigest, ssz.deneb.LightClientBootstrap.serialize(bootstrap)),
concatBytes(capellaForkDigest, ssz.electra.LightClientBootstrap.serialize(bootstrap)),
)

await network1.store(
Expand All @@ -843,10 +843,10 @@ describe('historicalSummaries verification', () => {
)

await network1.initializeLightClient(
'0xb7918b28a8e9c6be29467a0771d0ab2693d5061f43d214b6056e8c6a12a5b9f3',
'0xee691ed0308c995e53203ca26fb68e652a172c4356d72002dd0c058d7489ca3a',
)
await network2.initializeLightClient(
'0xb7918b28a8e9c6be29467a0771d0ab2693d5061f43d214b6056e8c6a12a5b9f3',
'0xee691ed0308c995e53203ca26fb68e652a172c4356d72002dd0c058d7489ca3a',
)

await network1.store(
Expand All @@ -868,24 +868,23 @@ describe('historicalSummaries verification', () => {
'light client synced to latest epoch successfully',
)

const epoch = BigInt(Math.floor(9677824 / 8192))
const historicalSummariesJson = require('./testdata/historicalSummaries/historicalSummaries_slot_9677824.json')
const historicalSummariesProofJson = require('./testdata/historicalSummaries/historicalSummariesStateProof_slot_9677824.json')
const historicalSummariesJson = require('./testdata/historicalSummaries/historicalSummariesSlot11708928.json')
const epoch = BigInt(Math.floor(Number(historicalSummariesJson.data.slot) / 8192))
const hsWProof = HistoricalSummariesWithProof.fromJson({
epoch: bigIntToHex(epoch),
historical_summaries: historicalSummariesJson,
proof: historicalSummariesProofJson,
historical_summaries: historicalSummariesJson.data.historical_summaries,
proof: historicalSummariesJson.data.proof,
})
await network1.store(
getBeaconContentKey(
BeaconNetworkContentType.HistoricalSummaries,
HistoricalSummariesKey.serialize({ epoch }),
),
concatBytes(network1.forkDigest, HistoricalSummariesWithProof.serialize(hsWProof)),
concatBytes(network1.beaconConfig.forkName2ForkDigest(ForkName.electra), HistoricalSummariesWithProof.serialize(hsWProof)),
)
while (network2.historicalSummaries.length === 0) {
await new Promise((r) => setTimeout(r, 1000))
}
assert.equal(network2.historicalSummariesEpoch, 1181n)
assert.equal(network2.historicalSummariesEpoch, 1429n)
}, 15000)
})
Original file line number Diff line number Diff line change
Expand Up @@ -10,28 +10,27 @@ import { ssz } from '@lodestar/types'
import { multiaddr } from '@multiformats/multiaddr'
import { assert, describe, it, vi } from 'vitest'
import {
type BeaconNetwork,
BeaconNetworkContentType,
BlockHeaderWithProof,
HistoricalSummariesBlockProof,
HistoricalSummariesKey,
HistoricalSummariesWithProof,
HistoryNetworkContentType,
LightClientBootstrapKey,
NetworkId,
createPortalNetwork,
getBeaconContentKey,
getContentKey,
getContentKey
} from '../../src/index.js'

describe('Block Bridge Data Test', () => {
it('should store and retrieve block header data', async () => {
vi.useFakeTimers({ shouldAdvanceTime: true, shouldClearNativeTimers: true })
vi.setSystemTime(1737151319000)
vi.setSystemTime(1747332119000)
const privateKeys = [
'0x0a2700250802122102273097673a2948af93317235d2f02ad9cf3b79a34eeb37720c5f19e09f11783c12250802122102273097673a2948af93317235d2f02ad9cf3b79a34eeb37720c5f19e09f11783c1a2408021220aae0fff4ac28fdcdf14ee8ecb591c7f1bc78651206d86afe16479a63d9cb73bd',
'0x0a27002508021221039909a8a7e81dbdc867480f0eeb7468189d1e7a1dd7ee8a13ee486c8cbd743764122508021221039909a8a7e81dbdc867480f0eeb7468189d1e7a1dd7ee8a13ee486c8cbd7437641a2408021220c6eb3ae347433e8cfe7a0a195cc17fc8afcd478b9fb74be56d13bccc67813130',
]
const pk1 = keys.privateKeyFromProtobuf(hexToBytes(privateKeys[0]).slice(-36))
const pk1 = keys.privateKeyFromProtobuf(hexToBytes(privateKeys[0] as `0x${string}`).slice(-36))
const enr1 = SignableENR.createFromPrivateKey(pk1)
const initMa: any = multiaddr('/ip4/127.0.0.1/udp/5033')

Expand All @@ -44,57 +43,52 @@ describe('Block Bridge Data Test', () => {
})
await client.start()

const bootstrapHex = JSON.parse(
readFileSync('./test/integration/testdata/postCapellaData/bootstrap.json', 'utf8'),
)
const historicalSummariesJson = JSON.parse(
readFileSync('./test/integration/testdata/postCapellaData/historical_summaries.json', 'utf8'),
)
const bootstrapJson = await import('./testdata/historicalSummaries/bootstrap.json')
const historicalSummariesJson = await import('./testdata/historicalSummaries/historicalSummariesSlot11708928.json')
const fullBlock = JSON.parse(
readFileSync('./test/integration/testdata/postCapellaData/full_block.json', 'utf8'),
)
const headerWithProof = JSON.parse(
readFileSync('./test/integration/testdata/postCapellaData/header_with_proof.json', 'utf8'),
)

const bootstrap = ssz.deneb.LightClientBootstrap.deserialize(hexToBytes(bootstrapHex.bootstrap))
const bootstrapRoot = '0x47a956b9cd45c73a60dac4c89dc869a5faa46a9d5d802486f31025c74d41ef39'

const bootstrap = ssz.electra.LightClientBootstrap.fromJson((bootstrapJson.data))
const bootstrapRoot = ssz.phase0.BeaconBlockHeader.hashTreeRoot(bootstrap.header.beacon)
// Get fork info
const forkConfig = getChainForkConfigFromNetwork('mainnet')
const bootstrapSlot = bootstrap.header.beacon.slot
const forkName = forkConfig.getForkName(bootstrapSlot)
const forkDigest = createBeaconConfig(
mainnetChainConfig,
hexToBytes(genesisData.mainnet.genesisValidatorsRoot),
hexToBytes(genesisData.mainnet.genesisValidatorsRoot as `0x${string}`),
).forkName2ForkDigest(forkName)

// Store bootstrap

const bootstrapKey = getBeaconContentKey(
BeaconNetworkContentType.LightClientBootstrap,
LightClientBootstrapKey.serialize({ blockHash: hexToBytes(bootstrapRoot) }),
LightClientBootstrapKey.serialize({ blockHash: bootstrapRoot }),
)
const bootstrapValue = concatBytes(
forkDigest,
ssz.deneb.LightClientBootstrap.serialize(bootstrap),
ssz.electra.LightClientBootstrap.serialize(bootstrap),
)

const beacon = client.network()['0x500c']
const beacon = client.network()['0x500c'] as BeaconNetwork
const history = client.network()['0x500b']

await beacon?.store(bootstrapKey, bootstrapValue)

// Start light client
await beacon?.initializeLightClient(bootstrapRoot)
await beacon?.initializeLightClient(bytesToHex(bootstrapRoot))

const historicalSummariesEpoch = computeEpochAtSlot(bootstrapSlot)

// Store historical summaries
const historicalSummariesObj = HistoricalSummariesWithProof.fromJson({
epoch: historicalSummariesEpoch,
historical_summaries: historicalSummariesJson.historical_summaries,
proof: historicalSummariesJson.proof,
historical_summaries: historicalSummariesJson.data.historical_summaries,
proof: historicalSummariesJson.data.proof,
})
const summariesKey = getBeaconContentKey(
BeaconNetworkContentType.HistoricalSummaries,
Expand Down
Loading