The randomness worker processes pending randomness requests from the queue. It determines whether to use VRF (high-stakes) or PRNG (low-stakes), computes the seed and proof, and submits the result to the Soroban contract.
RandomnessRequested Event
↓
Queue Job
↓
RandomnessWorker.processRequest()
↓
┌───┴────────────────────────┐
│ 1. Check idempotency │
│ 2. Check contract status │
│ 3. Get prize amount │
│ 4. Determine VRF/PRNG │
│ 5. Compute randomness │
│ 6. Submit to contract │
└────────────────────────────┘
- Maintains in-memory cache of processed request IDs
- Skips duplicate events to prevent double-processing
- Queries contract to verify raffle not already finalized
- Prevents unnecessary computation if randomness already submitted
- Uses
prizeAmountfrom event payload if available - Falls back to
ContractService.getRaffleData()RPC call if not
- High-stakes (≥ 500 XLM): Uses VRF for cryptographic verifiability
- Low-stakes (< 500 XLM): Uses PRNG for instant, zero-cost randomness
- VrfService: Ed25519 VRF with proof generation
- PrngService: SHA-256 PRNG with timestamp + entropy
- Builds
receive_randomness(raffleId, seed, proof)transaction - Signs with oracle keypair
- Submits to Soroban RPC
- Polls for confirmation
Main processor that orchestrates the entire flow.
Key Methods:
processRequest(job: RandomnessRequest): Promise<void>- Processes a single jobclearProcessedCache(): void- Clears idempotency cache (testing/cleanup)
Interacts with Soroban contract for read operations.
Methods:
getRaffleData(raffleId): Promise<RaffleData>- Fetches raffle detailsisRandomnessSubmitted(raffleId): Promise<boolean>- Checks if already finalized
Generates verifiable random function output for high-stakes raffles.
Methods:
compute(requestId): Promise<RandomnessResult>- Computes VRF seed + proof
Generates pseudo-random output for low-stakes raffles.
Methods:
compute(requestId): Promise<RandomnessResult>- Computes PRNG seed
Submits randomness to the contract.
Methods:
submitRandomness(raffleId, randomness): Promise<SubmitResult>- Submits transaction
- Worker throws errors on failure to trigger queue retry mechanism
- Idempotency ensures safe retries (won't double-submit)
- Contract status check prevents submission to finalized raffles
Run unit tests:
npm testTest Coverage:
- ✅ Low-stakes PRNG path
- ✅ High-stakes VRF path
- ✅ Prize amount fetching from contract
- ✅ Duplicate request handling
- ✅ Already-finalized raffle handling
- ✅ Error handling and retry behavior
✅ Worker logic implemented
✅ VRF/PRNG branching
✅ Idempotency handling
✅ Unit tests with mocks
⏳ ContractService RPC calls need Stellar SDK integration
⏳ VrfService needs Ed25519 VRF library
⏳ TxSubmitterService needs Soroban transaction building
- Integrate Stellar SDK for contract RPC calls
- Implement Ed25519 VRF (e.g., using
@noble/curves) - Implement Soroban transaction building and signing
- Add Bull queue integration for job processing
- Add integration tests against Stellar testnet
- Configure oracle keypair management (HSM/secrets)