Exemplo n.º 1
0
    async def attest(self, slot: Slot) -> Tuple[Attestation, ...]:
        attestations: Tuple[Attestation, ...] = ()
        head = self.chain.get_canonical_head()
        state_machine = self.chain.get_state_machine()
        state = self.chain.get_head_state()
        epoch = compute_epoch_of_slot(slot, self.slots_per_epoch)

        validator_assignments = {
            validator_index: self._get_this_epoch_assignment(
                validator_index,
                epoch,
            )
            for validator_index in self.validator_privkeys
        }
        attesting_validators = self._get_attesting_validator_and_shard(
            validator_assignments,
            slot,
            epoch,
        )
        if len(attesting_validators) == 0:
            return ()

        # Sort the attesting validators by shard
        sorted_attesting_validators = sorted(
            attesting_validators,
            key=itemgetter(1),
        )
        # Group the attesting validators by shard
        attesting_validators_groups = groupby(
            sorted_attesting_validators,
            key=itemgetter(1),
        )
        for shard, group in attesting_validators_groups:
            # Get the validator_index -> privkey map of the attesting validators
            attesting_validator_privkeys = {
                attesting_data[0]: self.validator_privkeys[attesting_data[0]]
                for attesting_data in group
            }
            attesting_validators_indices = tuple(
                attesting_validator_privkeys.keys())
            # Get one of the attesting validator's assignment in order to get the committee info
            assignment = self._get_this_epoch_assignment(
                attesting_validators_indices[0],
                epoch,
            )
            attestation = create_signed_attestation_at_slot(
                state,
                state_machine.config,
                state_machine,
                slot,
                head.signing_root,
                attesting_validator_privkeys,
                assignment.committee,
                shard,
            )
            self.logger.debug(
                bold_green("Validators=%s attest to block=%s  attestation=%s"),
                attesting_validators_indices,
                head,
                attestation,
            )
            for validator_index in attesting_validators_indices:
                self.latest_attested_epoch[validator_index] = epoch
            attestations = attestations + (attestation, )

        self.logger.debug("Brodcasting attestations %s", attestations)
        await self.p2p_node.broadcast_attestations(attestations)
        return attestations
Exemplo n.º 2
0
    async def attest(self, slot: Slot) -> Tuple[Attestation, ...]:
        """
        Attest the block at the given ``slot`` and broadcast them.
        """
        attestations: Tuple[Attestation, ...] = ()
        head = self.chain.get_canonical_head()
        state_machine = self.chain.get_state_machine()
        state = self.chain.get_head_state()
        epoch = compute_epoch_at_slot(slot, self.slots_per_epoch)

        attesting_committee_assignments_at_slot = self._get_attesting_assignments_at_slot(slot)

        for committee_assignment in attesting_committee_assignments_at_slot:
            committee_index = committee_assignment.committee_index
            committee = committee_assignment.committee

            attesting_validators_indices = tuple(
                filter(
                    lambda attester: self.latest_attested_epoch[attester] < epoch,
                    self._get_local_attesters_at_assignment(committee_assignment),
                )
            )
            # Get the validator_index -> privkey map of the attesting validators
            attesting_validator_privkeys = {
                index: self.validator_privkeys[index]
                for index in attesting_validators_indices
            }
            attestation = create_signed_attestation_at_slot(
                state,
                state_machine.config,
                state_machine,
                slot,
                head.signing_root,
                attesting_validator_privkeys,
                committee,
                committee_index,
                tuple(
                    CommitteeValidatorIndex(committee.index(index))
                    for index in attesting_validators_indices
                ),
            )
            self.logger.debug(
                bold_green("validators %s attesting to block %s with attestation %s"),
                attesting_validators_indices,
                head,
                attestation,
            )

            # await self.p2p_node.broadcast_attestation(attestation)
            subnet_id = SubnetId(committee_index % ATTESTATION_SUBNET_COUNT)

            # Import attestation to pool and then broadcast it
            self.import_attestation(attestation, False)
            await self.p2p_node.broadcast_attestation_to_subnet(attestation, subnet_id)

            # Log the last epoch that the validator attested
            for index in attesting_validators_indices:
                self.latest_attested_epoch[index] = epoch

            attestations = attestations + (attestation,)
        # TODO: Aggregate attestations

        return attestations