ethereum / ethereum/beacon-APIs
Gloas: add an endpoint to retrieve the PTC (Payload Timeliness Committee) for a slot
- Dominant language
- HTML
- Stars
- 389
- Forks
- 224
- Avg merge
- 8h 29m
- Merged PRs (30d)
- 3
Description
## Problem
In Gloas, on-chain PTC votes are recorded in block bodies as `PayloadAttestation` aggregates whose `aggregation_bits: Bitvector[PTC_SIZE]` are indexed by the PTC ordering — the proposer constructs them "with respect to the PTC that is obtained from `get_ptc(state, Slot(block_slot - 1))`" ([validator.md](https://github.com/ethereum/consensus-specs/blob/master/specs/gloas/validator.md)).
No API surface exposes that ordering — and none would expose PTC *membership* to observers either, once the duties endpoint rework lands:
- The current duties endpoint (`POST /eth/v1/validator/duties/ptc/{epoch}`, #552) returns membership for the requested validators only, with no position information (unlike `AttesterDuty.validator_committee_index`).
- #619 replaces it with a per-slot `GET` returning `{data, validator_indices}` for validators the beacon node tracks — the right call for the VC flow (duties must exist per branch), but it removes the last way to query PTC membership in advance, historically, or for arbitrary validators.
- `GET /eth/v1/beacon/pool/payload_attestations` (#552) exposes individual messages, but the pool is ephemeral — it cannot answer historical questions, while the durable on-chain record (the aggregates) is exactly what cannot be interpreted.
- Both analogous on-chain participation bitfields have ordering endpoints today: attestation `aggregation_bits` → `GET /eth/v1/beacon/states/{state_id}/committees`, and `sync_aggregate.sync_committee_bits` → `GET /eth/v1/beacon/states/{state_id}/sync_committees`. The PTC is the one participation bitfield without one.
As a result, an external observer (staking operators' monitoring, block explorers, analytics, PTC-liveness research) cannot attribute on-chain payload attestations to validators — i.e. per-validator PTC participation cannot be computed the way attestation and sync participation are computed today.
Note that a `position` field on the duty object alone would not suffice: [`compute_ptc`](https://github.com/ethereum/consensus-specs/blob/master/specs/gloas/beacon-chain.md#new-compute_ptc) returns the committee "with possible duplicates", so one validator can hold several seats (bits). Sync committees share this property, and `sync_committees` solves it by returning the full ordered list.
## Proposal
Mirror the existing committee endpoints:
```
GET /eth/v1/beacon/states/{state_id}/ptc?slot={slot}
```
- `slot` optional, defaulting to the state's slot; must be within the range computable from the requested state (same semantics as `committees?slot=`).
- `data.validators`: exactly `PTC_SIZE` validator indices, in `get_ptc(state, slot)` order, duplicates preserved.
```json
{
"execution_optimistic": false,
"finalized": false,
"data": { "validators": ["1021", "994", "1021", "..."] }
}
```
Serving cost is minimal for recent slots: `state.ptc_window` already caches the PTC for `(2 + MIN_SEED_LOOKAHEAD) * SLOTS_PER_EPOCH` slots, so this is a cache read; historical slots can be served from historical states exactly like `/committees`. And because it is state-scoped, it composes with the non-canonical-branch concern motivating #619: the PTC for a branch is queryable via that branch's state.
## Alternative considered
A `positions` array on the duty object would be a smaller change, but it only helps callers that already know which validators to ask about, cannot answer historical queries, and #619's direction (BN-tracked validators, in-slot fetch) moves the duties endpoint further away from being an observer surface. Happy to go either way — and happy to follow up with the spec PR once there's agreement on the shape.
## References
- [`compute_ptc` / `get_ptc` / `ptc_window`](https://github.com/ethereum/consensus-specs/blob/master/specs/gloas/beacon-chain.md)
- [`PayloadAttestation`](https://github.com/ethereum/consensus-specs/blob/master/specs/gloas/beacon-chain.md#payloadattestation)
- #552 (ePBS API surface), #619 (PTC duties rework)
- [`apis/beacon/states/sync_committees.yaml`](https://github.com/ethereum/beacon-APIs/blob/master/apis/beacon/states/sync_committees.yaml)
Contributor guide
No contributing guide indexed for this repository
Research direction
Start by comparing apis/beacon/states/sync_committees.yaml with the existing committees endpoint and review the linked #619 changes. Define the state-scoped PTC endpoint, response schema, and slot semantics described here; done means the OpenAPI specification exposes the ordered validator list with duplicates preserved and matches the established committee endpoint patterns.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- openapi
- Domain
- api
- Issue type
- Feature
- Difficulty
- 3/5
- Estimated time
- 1-2 days
- Activity status
- Active
- Clarity
- Mostly clear
- Newbie friendliness
- 66/100