owned this note
owned this note
Published
Linked with GitHub
# [WIP] Minimum validator interface
This document represents the minimum interface required for a validator to perform their duties while interfacing with an eth2.0 node.
This interface utilizes repeated polling to check for updates in the node's state. This unidirectional design is what is currently supported in eth1.0 via the RPC methods. Alternatively, nodes could emit events to validators (`new_slot`, `new_shuffling`, etc) via something like grpc streams. This API can be modified to event-response driven with minimal changes primarily to `API.Queuries.StateChangePolling`.
**brevity** -- These methods represent the minimum required for a validator. Many methods that we'll likely want to expose to users were left out for brevity.
**known issues**
* Validator's need to compute a proof of custody bit and store the related data independent of the node. Need to define an interface for the validator to query for this data from the node. Note: this data is on the order of 64 * 16kb that the validator needs to retrieve from the node every cycle. When a shard is dropped in the node, the validator continues to hold on to the data as part of their 'proof of custody'
[toc]
## API
### Queries
#### State change polling
* `current_slot() -> slot`
* Change signals for validator to perform duties
* `current_shuffling_seed() -> hash32`
* Change signals to validator to check committee and shard assignments
#### Validator Roles
##### Beacon Chain
* `committee_shard(validator_index) -> shard`
* `committee_slot(validator_index) -> slot`
* `beacon_proposer(slot) -> validator_index`
##### Shard Chains
* `current_persistent_shard(validator_index) -> shard_id`
* `next_persistent_shard(validator_index) -> shard_id`
* returns -1 if no `SHARD_REASSIGNMENT_RECORD` exists for `validator_index`
* `next_persistent_shard_start_slot(validator_index) -> slot`
* returns -1 if no `SHARD_REASSIGNMENT_RECORD` exists for `validator_index`
* `shard_proposer(slot, shard_id) -> validator_index`
#### Signing candidates
* `beacon_block_candidate(slot) -> beacon_block_data`
* `attestation_candidate(slot, shard_id) -> attestation_data`
* `shard_block_candidate(slot, shard_id) -> shard_block_data`
### Directives
#### Controls
* `sync_shard(shard_id) -> status`
* `drop_shard(shard_id) -> status`
* `join_subnet(shard_id) -> status`
* `drop_subnet(shard_id) -> status`
#### Submissions
* `submit_beacon_block(block_data, sig) -> status`
* `submit_attestation(attestation_data, validator_index, sig) -> status`
* `submit_shard_block(block_data, sig) -> status`
## Sample usage
### Beacon Proposer and Attester
* Validator checks if new slot
* calls `current_slot()`
* validator sees new slot
* Validator checks if state recalc
* calls`current_shuffling_seed()`
* validator sees that a state recalc has occurred
* Validator updates local knowledge of duties if state recalc occurred
* calls `committee_shard(validator_index)`
* stores this `shard_id` for future attestation use
* calls `sync_shard(shard_id)` with `shard_id` from previous call
* calls `committee_slot(validator_index)`
* stores this slot number for future attestation trigger
* calls `beacon_proposer(slot)` on the committee slot
* notes if is the beacon proposer as well as attester at that slot
* Validator continues to check for slot updates with `current_slot()`...
* Validator reaches committee slot previous noted
* Proposer
* calls `beacon_proposer(current_slot)`
* sees that is the proposer
* calls `beacon_block_candidate(current_slot)`
* checks that `beacon_block_data` is not slashable wrt previously signed data
* signs `beacon_block_data` to create `block_sig`
* calls `submit_beacon_block(beacon_block_data, block_sig)`
* Attester
* calls `attestation_candidate(current_slot, shard_id)`
* uses previously stored `shard_id` from call to `committee_shard`
* node knows about block just proposed so this will be the block in the attestation data
* checks that `attestation_data` is not slashable wrt to previous signed data
* signs `attestation_data` to create `attestation_sig`
* calls `submit_attestation(attestation_data, validator_index, attestation_sig)`
---
# Workspace
## hwwhww feedback 20181129
1. `status` need to be defined. I think it at least contains:
1. `code`: success or error code
2. `slot`: for the validator to check if the node is falling behind locally.
2. Actually, all API should return the `code` message. But the details probably depend on which API scheme we will use.
3. To sync with current beacon chain spec, change `shard_id` to `shard`?
4. Maybe add more description for "Signing candidates"? Does that mean the proposal?
5. It’s unclear to me what’s the difference between `join_subnet(shard_id)` and `sync_shard(shard_id)`, or `drop_shard(shard_id)` and `drop_subnet(shard_id)`.
6. > Alternatively, nodes could emit events to validators (new_slot, new_state_recalc, etc) via something like grpc streams.
1. I’ve only just read some basic material of gRPC streaming, do you mean especially gRPC bidirectional streaming RPC? I see the benefit of bidirectional streaming RPC is that the client can send multiple requests to the server at the same time. Does it also enable the server to emit the notifications actively?
2. Besides unidirectional v.s. bidirectional, would polling v.s. pub/sub scheme be more accurate in case of API design high-level speaking?
7. What’s the reasonable polling frequency? 1 request/second?
8. `current_slot()` and `last_state_recalculation_slot()`
1. I thought slot increment also means state update, no?
2. Maybe change to `last_state_recalculation_slot() -> (state_root, slot)`, so that the validator can verify if the beacon chain reorgs?
9. It will be nice to clarify:
1. What are the data that need to be maintained in validator side? (the "local knowledge")
2. Shard proposer and attester. I think we don't *need* them right now but you defined the APIs... or just remove them for now?
3. System architecture diagram
10. Nice to have
1. Slashing notification: the validators need to know if they're losing deposit.