# Approved Applicant Registry

`ApprovedApplicantRegistry` gives vetted node applicants an initial TrustFingerprint score and a grace period, so they can start operating.

It solves a bootstrap problem. Registering as a node operator needs a TrustFingerprint score, but a score can only be built by running a node. The registry lets the protocol grow its operator base in a controlled way. Its address is in [Contract Addresses](./contract-addresses.md).

## What it does

- **Pre-approval.** Admins with `APPROVER_ROLE` add applicants who were vetted offchain, for example through a Typeform application.
- **Initial score.** On claiming, an applicant gets an initial TrustFingerprint score for the tier they were approved for. Scores are set just above each tier's minimum threshold, so the operator can start at once.
- **Grace period.** A configurable grace period, 30 days by default, starts on claim. During it the operator is protected from certain penalties while setting up infrastructure and building an organic score.
- **Sybil resistance.** Each approval is tied to one wallet address and one application ID and can be claimed once. One entity cannot create several nodes this way.
- **Role control.** Roles decide who can approve applicants, update settings and extend grace periods.

## How it works

1. **Application.** A prospective operator applies through an offchain channel, for example a Typeform on the Noderr website.
2. **Vetting.** The Noderr team or a delegated committee reviews the application. Factors may include technical expertise, hardware specifications and commitment to the protocol.
3. **Approval.** An admin with `APPROVER_ROLE` calls `addApprovedApplicant()`. It records the applicant's wallet address, approved tier and a unique application ID onchain.
4. **Claim.** The applicant calls `claimApproval()` from the approved wallet. See below.
5. **Onboarding.** The operator registers a node in the `NodeRegistry`, stakes NODR and starts doing work on the network, building an organic TrustFingerprint score.
6. **Grace period end.** The operator is then subject to the same performance monitoring and slashing conditions as all other operators.

`claimApproval()` does four things:

- Verifies the approval status.
- Assigns an initial TrustFingerprint score for the three active components (Uptime, SuccessRate, Stake). The reserved fields (Governance, History, Peer) are initialised to zero.
- Starts the 30-day grace period.
- Marks the approval as claimed.

## Functions

### Approver

- `addApprovedApplicant(address wallet, UtilityNFT.NodeTier tier, string calldata applicationId)`: Adds a new applicant to the registry. (Requires `APPROVER_ROLE`)
- `batchAddApprovedApplicants(...)`: Adds multiple applicants in a single transaction for gas efficiency. (Requires `APPROVER_ROLE`)
- `revokeApproval(address wallet, string calldata reason)`: Revokes an existing, unclaimed approval. (Requires `APPROVER_ROLE`)

### Applicant

- `claimApproval()`: Called by the applicant to receive their initial score and start their grace period.

### Governance

- `extendGracePeriod(address operator, uint256 extension, string calldata reason)`: Extends the grace period for a specific operator. (Requires `APPROVER_ROLE`)
- `setInitialScores(...)`: Updates the default initial scores for each tier. (Requires `DEFAULT_ADMIN_ROLE`)
- `setGracePeriodDuration(uint256 newDuration)`: Adjusts the length of the grace period. (Requires `DEFAULT_ADMIN_ROLE`)

### View

- `isApproved(address wallet)`: Checks if a wallet is approved and has not yet claimed.
- `isInGracePeriod(address operator)`: Checks if an operator is currently within their grace period.
- `getRemainingGracePeriod(address operator)`: Returns the time remaining in an operator's grace period.

## Integration with other contracts

- **TrustFingerprint.sol**: The registry is granted `ORACLE_ROLE` on the `TrustFingerprint` contract, allowing it to set the initial scores for new operators.
- **NodeRegistry.sol**: After claiming approval, operators interact with the `NodeRegistry` to formally register their node.
- **UtilityNFT.sol**: The `approvedTier` parameter corresponds to the `NodeTier` enum in the `UtilityNFT` contract.
