Skip to content

Commit

Permalink
Write TestRandom util (#976)
Browse files Browse the repository at this point in the history
Signed-off-by: litt3 <[email protected]>
  • Loading branch information
litt3 authored Dec 11, 2024
1 parent 431be82 commit 3eb67af
Show file tree
Hide file tree
Showing 3 changed files with 86 additions and 0 deletions.
55 changes: 55 additions & 0 deletions common/testutils/random/test_random.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
package random

import (
"fmt"
"math/rand"
"time"
)

// TestRandom provides all the functionality of math/rand.Rand, plus additional randomness functionality useful for testing
type TestRandom struct {
*rand.Rand
}

// NewTestRandom creates a new instance of TestRandom
// This method may either be seeded, or not seeded. If no seed is provided, then current unix nano time is used.
func NewTestRandom(fixedSeed ...int64) *TestRandom {
var seed int64
if len(fixedSeed) == 0 {
seed = time.Now().UnixNano()
} else if len(fixedSeed) == 1 {
seed = fixedSeed[0]
} else {
panic("too many arguments, expected exactly one seed")
}

fmt.Printf("Random seed: %d\n", seed)
return &TestRandom{
rand.New(rand.NewSource(seed)),
}
}

// RandomBytes generates a random byte slice of a given length.
func (r *TestRandom) RandomBytes(length int) []byte {
bytes := make([]byte, length)
_, err := r.Read(bytes)
if err != nil {
panic(err)
}
return bytes
}

// RandomTime generates a random time.
func (r *TestRandom) RandomTime() time.Time {
return time.Unix(r.Int63(), r.Int63())
}

// RandomString generates a random string out of printable ASCII characters.
func (r *TestRandom) RandomString(length int) string {
const charset = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
b := make([]byte, length)
for i := range b {
b[i] = charset[r.Intn(len(charset))]
}
return string(b)
}
27 changes: 27 additions & 0 deletions common/testutils/random/test_random_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
package random

import (
"github.com/stretchr/testify/assert"
"math/rand"
"testing"
)

// Tests that random seeding produces random results, and that consistent seeding produces consistent results
func TestSetup(t *testing.T) {
testRandom1 := NewTestRandom()
x := testRandom1.Int()

testRandom2 := NewTestRandom()
y := testRandom2.Int()

assert.NotEqual(t, x, y)

seed := rand.Int63()
testRandom3 := NewTestRandom(seed)
a := testRandom3.Int()

testRandom4 := NewTestRandom(seed)
b := testRandom4.Int()

assert.Equal(t, a, b)
}
4 changes: 4 additions & 0 deletions common/testutils/test_utils.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import (

// InitializeRandom initializes the random number generator. If no arguments are provided, then the seed is randomly
// generated. If a single argument is provided, then the seed is fixed to that value.
// Deprecated: use TestRandom instead
func InitializeRandom(fixedSeed ...uint64) {

var seed uint64
Expand Down Expand Up @@ -85,6 +86,7 @@ func ExecuteWithTimeout(f func(), duration time.Duration, debugInfo ...any) {
}

// RandomBytes generates a random byte slice of a given length.
// Deprecated: use TestRandom.RandomBytes instead
func RandomBytes(length int) []byte {
bytes := make([]byte, length)
_, err := rand.Read(bytes)
Expand All @@ -95,11 +97,13 @@ func RandomBytes(length int) []byte {
}

// RandomTime generates a random time.
// Deprecated: use TestRandom.RandomTime instead
func RandomTime() time.Time {
return time.Unix(int64(rand.Int31()), 0)
}

// RandomString generates a random string out of printable ASCII characters.
// Deprecated: use TestRandom.RandomString instead
func RandomString(length int) string {
const charset = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
b := make([]byte, length)
Expand Down

0 comments on commit 3eb67af

Please sign in to comment.