Skip to content

Commit 416ae51

Browse files
authored
Merge pull request #8 from FishGoddess/develop
v0.5.2
2 parents 565a584 + 7be99d6 commit 416ae51

File tree

6 files changed

+106
-15
lines changed

6 files changed

+106
-15
lines changed

FUTURE.md

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,14 @@
11
## ✈️ 未来版本的新特性 (Features in future versions)
22

3-
### v0.6.x
3+
### v0.7.x
44

5-
* [ ] 增加 cmd 包,提供二进制 cli 使用
65
* [ ] 支持 SM3 国标算法
76
* [ ] 支持 SM4 国标算法
8-
* [ ] 支持更多的散列算法
7+
8+
### v0.6.x
9+
10+
* [ ] 增加 cmd 包,提供二进制 cli 使用
11+
* [ ] 支持 chacha20 相关算法
912

1013
### v0.5.x
1114

HISTORY.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,11 @@
11
## 📜 历史版本的特性介绍 (Features in old versions)
22

3+
### v0.5.2
4+
5+
> 此版本发布于 2025-12-09
6+
7+
* 随机函数默认使用 crypto 包,可选弱安全性的 math 包
8+
39
### v0.5.1-alpha
410

511
> 此版本发布于 2025-12-07

bytes/rand/options.go

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
// Copyright 2025 FishGoddess. All rights reserved.
2+
// Use of this source code is governed by a MIT style
3+
// license that can be found in the LICENSE file.
4+
5+
package rand
6+
7+
type Config struct {
8+
weak bool
9+
}
10+
11+
func newConfig() *Config {
12+
conf := &Config{
13+
weak: false,
14+
}
15+
16+
return conf
17+
}
18+
19+
func (c *Config) Apply(opts ...Option) *Config {
20+
for _, opt := range opts {
21+
opt(c)
22+
}
23+
24+
return c
25+
}
26+
27+
type Option func(conf *Config)
28+
29+
// WithWeak sets weak to config.
30+
func WithWeak() Option {
31+
return func(conf *Config) {
32+
conf.weak = true
33+
}
34+
}

bytes/rand/options_test.go

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
// Copyright 2025 FishGoddess. All rights reserved.
2+
// Use of this source code is governed by a MIT style
3+
// license that can be found in the LICENSE file.
4+
5+
package rand
6+
7+
import (
8+
"testing"
9+
)
10+
11+
// go test -v -cover -run=^TestConfig$
12+
func TestConfig(t *testing.T) {
13+
opts := []Option{
14+
WithWeak(),
15+
}
16+
17+
conf := newConfig().Apply(opts...)
18+
19+
if !conf.weak {
20+
t.Fatalf("got %v != expect %v", conf.weak, true)
21+
}
22+
}

bytes/rand/rand.go

Lines changed: 19 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -5,32 +5,40 @@
55
package rand
66

77
import (
8-
"math/rand/v2"
8+
crand "crypto/rand"
9+
"io"
10+
mrand "math/rand/v2"
911
"unsafe"
1012
)
1113

1214
var words = []byte("abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789")
1315

14-
func appendBytes(data []byte, n int) []byte {
15-
length := len(words)
16-
for i := 0; i < n; i++ {
17-
index := rand.IntN(length)
18-
data = append(data, words[index])
16+
func readFull(data []byte, n int) []byte {
17+
for i := 0; i < n && i < len(data); i++ {
18+
index := mrand.IntN(len(words))
19+
data[i] = words[index]
1920
}
2021

2122
return data
2223
}
2324

2425
// Bytes returns n bytes in random which can be used to generate an iv.
25-
func Bytes(n int) []byte {
26-
data := make([]byte, 0, n)
27-
data = appendBytes(data, n)
26+
func Bytes(n int, opts ...Option) []byte {
27+
conf := newConfig().Apply(opts...)
28+
29+
data := make([]byte, n)
30+
if conf.weak {
31+
readFull(data, n)
32+
} else {
33+
io.ReadFull(crand.Reader, data)
34+
}
35+
2836
return data
2937
}
3038

3139
// String returns a string including n bytes in random which can be used to generate an iv.
32-
func String(n int) string {
33-
data := Bytes(n)
40+
func String(n int, opts ...Option) string {
41+
data := Bytes(n, opts...)
3442
ptr := unsafe.SliceData(data)
3543
return unsafe.String(ptr, len(data))
3644
}

bytes/rand/rand_test.go

Lines changed: 19 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,15 @@ import (
1313
func TestBytes(t *testing.T) {
1414
for i := 1; i <= 64; i++ {
1515
data := Bytes(i)
16+
if len(data) != i {
17+
t.Fatalf("len(data) %d != i %d", len(data), i)
18+
}
19+
20+
t.Logf("%s\n", data)
21+
}
22+
23+
for i := 1; i <= 64; i++ {
24+
data := Bytes(i, WithWeak())
1625

1726
for _, b := range data {
1827
index := bytes.IndexByte(words, b)
@@ -29,11 +38,20 @@ func TestBytes(t *testing.T) {
2938
func TestString(t *testing.T) {
3039
for i := 1; i <= 64; i++ {
3140
str := String(i)
41+
if len(str) != i {
42+
t.Fatalf("len(str) %d != i %d", len(str), i)
43+
}
44+
45+
t.Logf("%s\n", str)
46+
}
47+
48+
for i := 1; i <= 64; i++ {
49+
str := String(i, WithWeak())
3250

3351
for _, r := range str {
3452
index := bytes.IndexRune(words, r)
3553
if index < 0 {
36-
t.Fatalf("b %+v not in words %+v", r, words)
54+
t.Fatalf("r %+v not in words %+v", r, words)
3755
}
3856
}
3957

0 commit comments

Comments
 (0)