Skip to content

Conversation

@goran-ethernal
Copy link
Contributor

@goran-ethernal goran-ethernal commented Aug 7, 2025

🔄 Changes Summary

This PR introduces a new interface called CertificateQuerier which, for now, has only one function called GetLastSettledCertificateToBlock which calculates the last settled block from a previously settled certificate.

This will be used on the validator, to calculate what was the last settled block, so we can figure out from which block a new certificate that is being verified is built.

It will also be used on startup from scratch, when aggsender syncs its state with agglayer, so we can save the ToBlock of the last settled certificate in the db.

The motivation behind this PR is to not use the Metadata field on the certificate, since it will not be signed by the proposer and validators, hence, it can be faked, but deduce the block range from other certificate data.

How the last settled block is calculated

The last settled block in the CertificateQuerier is calculated like this:

  • First it will check the NewLocalExitRoot field on the certificate, if it is not the first empty LER, meaning, there were some bridge exits in the certificate, or in certificates before it, it will get the block num on which the NewLocalExitRoot hash was added on L2 by calling the L2 bridge syncer.
  • Secondly, it will call the agglayer endpoint to get the latest settled imported bridge exit. Note that this PR added only the endpoint sceleton, since this is not yet implemented on agglayer. This endpoint will return the GlobalIndex of the last settled imported bridge exit (claim), and we will use that to get the claim from the L2 bridge syncer since GlobalIndex is unique per claim.
  • Thirdly, it will ping the AggchainFEP rollup contract to get the last settled L2 block from it (which is gotten from the aggchain proof in the FEP certificates). If the network is not FEP this call will just return 0.
  • At the end, it will compare the 3 blocks gotten in previous steps, and choose the max value from it.

We need all three values because, PP certificates can either contain only bridge exits, or only imported bridge exits, and FEP certificates can be empty.

IMPORTANT NOTE: This code is not used anywhere. It will be used in subsequent PRs.

⚠️ Breaking Changes

NA

📋 Config Updates

NA

✅ Testing

  • 🤖 Automatic: aggkit CI

@goran-ethernal goran-ethernal self-assigned this Aug 7, 2025
@goran-ethernal goran-ethernal marked this pull request as ready for review August 7, 2025 10:02
@goran-ethernal goran-ethernal force-pushed the feat/compute-block-range-by-not-using-metadata branch from 7ae3acd to 1a71b93 Compare August 7, 2025 10:13
@goran-ethernal goran-ethernal added this to the AggKit - v0.8.0 milestone Aug 7, 2025
@goran-ethernal goran-ethernal requested a review from Copilot August 7, 2025 12:48
Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull Request Overview

This PR introduces a CertificateQuerier interface and implementation to calculate the last settled block from previously settled certificates without relying on the Metadata field. The implementation examines three sources of settlement data: bridge exits via NewLocalExitRoot, imported bridge exits from the agglayer, and FEP contract settlement data.

Key changes:

  • New CertificateQuerier interface with GetLastSettledCertificateToBlock method
  • AggchainFEPRollupQuerier interface and implementation for querying FEP contract data
  • Enhanced bridge syncer to support querying claims by global index and exit roots by hash
  • Moved EmptyLER constant to a shared location and updated references

Reviewed Changes

Copilot reviewed 24 out of 24 changed files in this pull request and generated 2 comments.

Show a summary per file
File Description
aggsender/query/certificate_query.go Implements the core CertificateQuerier logic to calculate last settled blocks from multiple sources
aggsender/query/aggchain_fep_rollup_query.go Provides FEP contract querying capabilities with no-op fallback for PP networks
bridgesync/processor.go Adds GetClaimByGlobalIndex method for retrieving claims by their global index
aggsender/types/interfaces.go Defines new interfaces for certificate querying and FEP contract interaction
agglayer/types/types.go Adds ToBigInt method to GlobalIndex for converting to big.Int representation

@goran-ethernal goran-ethernal force-pushed the feat/compute-block-range-by-not-using-metadata branch from a0a491d to acf7062 Compare August 8, 2025 11:08
@sonarqubecloud
Copy link

sonarqubecloud bot commented Aug 8, 2025

@goran-ethernal goran-ethernal merged commit ff90cf9 into feat/aggsender-multisig Aug 8, 2025
21 of 22 checks passed
@goran-ethernal goran-ethernal deleted the feat/compute-block-range-by-not-using-metadata branch August 8, 2025 11:46
goran-ethernal added a commit that referenced this pull request Aug 11, 2025
## 🔄 Changes Summary
This PR decouples `aggsender-validator` from using the `Metadata` field
in certificate to figure out block range.

The validator will now use the `certificate querier` interface to get
the `ToBlock` from the last settled certificate in order to figure out
if the new certificate is valid or not.

## ⚠️ Breaking Changes
NA

## 📋 Config Updates
NA

## ✅ Testing
- 🤖 **Automatic**: `aggkit` CI

## 🔗 Related PRs
- #838
- #839
goran-ethernal added a commit that referenced this pull request Aug 12, 2025
## 🔄 Changes Summary

This PR completely removes the logic around setting `Metadata` field on
certificates since it will no longer be used to determin block ranges on
`aggsender`.

`Metadata` field will still exist on certificates, but it will no longer
be used, and a `ZeroHash` will be enforced instead.

## ⚠️ Breaking Changes
NA

## 📋 Config Updates
NA

## ✅ Testing
- 🤖 **Automatic**: `aggkit` CI

## 🐞 Issues
#799

## 🔗 Related PRs
#838
#839
#846
Stefan-Ethernal added a commit that referenced this pull request Oct 10, 2025
## 🔄 Changes Summary

Enable the AggSender to work with multiple validator nodes in a
committee-based validation system. The implementation includes validator
services, multisig committee management, certificate validation
improvements, and enhanced gRPC communication protocols.

**Multisig Committee Support:** 
- Added `MultisigCommittee` type to manage signer sets and enforce
signature thresholds.
- Signers are represented as `SignerInfo` structs with both address and
URL for improved context and error reporting.
- Committee construction validates non-empty membership and non-zero
threshold, preventing misconfiguration.
- Dynamic signer management: methods for adding signers, duplicate
checks by address and URL.

**Aggsender Validator Refactor:**
- The Aggsender certificate validation flow was refactored to integrate
multisig logic.
- The multisig validation logic is applicable to both `PP` and `FEP`
certificates.
- Certificate validation now checks for contiguous certificates, last L2
block, and settlement status using new queries.
- Import bridge exit proof verification is handled via new logic using
`verifyClaimProofs`, ensuring only valid proofs pass.

**Certificate Metadata removal:**
- It is gone from the agglayer and therefore it is not sent anymore from
the aggsender either.
- Only thing worth noting is that, when calculating `CertificateID`,
instead of metadata field, which was used previously, we now use
`ZeroHash`.

**Smart contracts integration:**
- **AggchainFEP contract:** Removed querying of `TrustedSequencer`
address and rely on the signers committee instead
- **AggchainBase contract:** Retrieve the multisig committee from the
`AggchainBase` contract

**Agglayer integration:**
- Invoke the `GetNetworkState` API from agglayer to get the latest
settled imported bridge exit info.
- Multisig is populated into the certificate and sent to the Agglayer's
`SendCertificate` gRPC endpoint

## ⚠️ Breaking Changes
- 🛠️ **Config**: Make sure that `Mode` on the `Validator` and
`AggSender` are the same.
- 🔌 **API/CLI**: `aggkit` version (`v0.7.0`) that supports `multisig`
will now require updated contracts to run. At least version
`v12.1.0-rc.3` of `agglayer-contracts`, and a new version of `agglayer`
which supports `multisig`, which is the `v0.4.0` of `agglayer`.
- 🗑️ **Deprecated Features**: Aggsender Phase II validator signing logic

## 📋 Config Updates
- Added `AggSender.RequireCommitteeMembershipCheck = false` parameter,
which defines if a check on `aggsender proposer` startup will be
performed to see if the proposer is in the `multisig` committee.
- Added `Validator.RequireCommitteeMembershipCheck =
{{AggSender.RequireCommitteeMembershipCheck}}` parameter, which defines
if a check on `aggsender validator` startup will be performed to see if
the validator is in the `multisig` committee.
- Added `Validator.Mode = "PessimisticProof"` parameter, which acts the
same as the `AggSender.Mode`. It tells the validator that the network is
a `PP` network or an `FEP` network. It has to be the same as on
`aggsender proposer`.
- Added `Validator.FEPConfig.SovereignRollupAddr =
"{{AggSender.SovereignRollupAddr}}" parameter which is the address of
the `AggchainFEP` rollup on L1 for given network for which validator is
running.
- Added `Validator.FEPConfig.RequireNoBlockGap =
{{AggSender.RequireNoFEPBlockGap}}, which acts the same as the given
paremeter on `AggSender` (proposer) config, and tells the validator if
gaps in blocks in certificates are allowed in `FEP` network.

```toml
[AggSender]
RequireCommitteeMembershipCheck = false

[Validator]
# PessimisticProof or AggchainProof
Mode = "PessimisticProof"
RequireCommitteeMembershipCheck = {{AggSender.RequireCommitteeMembershipCheck}}
[Validator.FEPConfig]
	SovereignRollupAddr = "{{AggSender.SovereignRollupAddr}}"
	RequireNoBlockGap = "{{AggSender.RequireNoFEPBlockGap}}"
```

## ✅ Testing
- 🤖 **Automatic**: `aggkit` CI
- 🖱️ **Manual**: [Optional: Steps to verify]

## 🐞 Issues
- Closes #792 
## 🔗 Related PRs
- #814
- #832
- #838
- #839
- #843
- #842
- #846
- #858
- #847
- #865
- #861
- #863
- #875
- #876
- #881
- #877
- #898
- #920
- #913
- #926
- #945
- #951
- #954
- #957
- #955
- #974
- #978
- #985
- #989
- #984
- #998
- #1017
- #1028
- #1034
- #1024
- #1052
- #1067
- #1068
- #1050
- #1071
- #1072
- #1060
- #1087
- #1077
- #1073

---------

Co-authored-by: Goran Rojovic <[email protected]>
Co-authored-by: Goran Rojovic <[email protected]>
Co-authored-by: Joan Esteban <[email protected]>
Co-authored-by: Rachit Sonthalia <[email protected]>
Co-authored-by: Arpit Temani <[email protected]>
Co-authored-by: Copilot <[email protected]>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants