Testing On-Chain Randomness
Testing randomness requires special attention to ensure fair distribution and proper behavior.
Setting Up Tests
- JavaScript (AVA)
- Rust
Loading...
Loading...
Testing Initial State
Verify players start with zero points:
- JavaScript
- Rust
Loading...
Loading...
Testing Randomness Distribution
Verify both outcomes occur with reasonable frequency:
- JavaScript
- Rust
Loading...
Loading...
Running Tests
- JavaScript
- Rust
# Run all tests
npm test
# Run with verbose output
npm test -- --verbose
# Run specific test file
npm test sandbox-test/main.ava.js
# Run all tests
cargo test
# Run with output
cargo test -- --nocapture
# Run specific test
cargo test test_points_are_correctly_computed
Test Best Practices
1. Test Edge Cases
test('handles minimum points correctly', async (t) => {
// Ensure points don't go below 0
const points = await contract.view('points_of', {
player: account.accountId
});
t.true(points >= 0);
});
2. Mock Randomness for Unit Tests
For deterministic testing, consider mocking:
#[cfg(test)]
fn mock_random_seed() -> [u8; 32] {
[42; 32] // Fixed seed for testing
}
3. Integration Testing
Test the full flow with multiple accounts:
test('multiple players maintain separate scores', async (t) => {
const { root, contract } = t.context.accounts;
const alice = await root.createSubAccount('alice');
// Play as root
await root.call(contract, 'flip_coin', { player_guess: 'heads' });
// Play as alice
await alice.call(contract, 'flip_coin', { player_guess: 'tails' });
// Check separate scores
const rootPoints = await contract.view('points_of', { player: root.accountId });
const alicePoints = await contract.view('points_of', { player: alice.accountId });
t.not(rootPoints, alicePoints); // Different players, different scores
});
With tests confirming our randomness works correctly, let's explore advanced patterns for more complex use cases.