Skip to content

Commit 686e61a

Browse files
authored
Merge pull request #1 from jedib0t/optimization
passphrase: ahead of time capitalization
2 parents c0235a2 + db41472 commit 686e61a

File tree

3 files changed

+24
-16
lines changed

3 files changed

+24
-16
lines changed

README.md

+1-1
Original file line numberDiff line numberDiff line change
@@ -170,7 +170,7 @@ goos: linux
170170
goarch: amd64
171171
pkg: github.com/jedib0t/go-passwords/passphrase
172172
cpu: AMD Ryzen 9 5900X 12-Core Processor
173-
BenchmarkGenerator_Generate-12 3015926 392.7 ns/op 167 B/op 8 allocs/op
173+
BenchmarkGenerator_Generate-12 4030634 292.0 ns/op 144 B/op 5 allocs/op
174174
PASS
175175
ok github.com/jedib0t/go-passwords/passphrase 1.603s
176176

passphrase/errors.go

+2-1
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ import (
77

88
var (
99
ErrDictionaryTooSmall = errors.New(fmt.Sprintf("dictionary cannot have less than %d words after word-length restrictions are applied", MinWordsInDictionary))
10-
ErrNumWordsInvalid = errors.New(fmt.Sprintf("number of words cannot be less than %d", MinNumWords))
10+
ErrNumWordsTooSmall = errors.New(fmt.Sprintf("number of words cannot be less than %d", NumWordsMin))
11+
ErrNumWordsTooLarge = errors.New(fmt.Sprintf("number of words cannot be more than %d", NumWordsMax))
1112
ErrWordLengthInvalid = errors.New("word-length rule invalid")
1213
)

passphrase/generator.go

+21-14
Original file line numberDiff line numberDiff line change
@@ -11,8 +11,9 @@ import (
1111
)
1212

1313
const (
14-
MinNumWords = 2
1514
MinWordsInDictionary = 256
15+
NumWordsMin = 2
16+
NumWordsMax = 32
1617
)
1718

1819
type Generator interface {
@@ -48,23 +49,14 @@ func NewGenerator(rules ...Rule) (Generator, error) {
4849
func (g *generator) Generate() string {
4950
var words []string
5051

51-
// generate words
52+
// select words
5253
for idx := 0; idx < g.numWords; idx++ {
5354
var word string
5455
for word == "" || slices.Contains(words, word) {
5556
word = g.dictionary[g.rng.IntN(len(g.dictionary))]
5657
}
5758
words = append(words, word)
5859
}
59-
// capitalize all words
60-
if g.capitalize {
61-
for idx := range words {
62-
r, size := utf8.DecodeRuneInString(words[idx])
63-
if r != utf8.RuneError {
64-
words[idx] = string(unicode.ToUpper(r)) + words[idx][size:]
65-
}
66-
}
67-
}
6860
// inject a random number after one of the words
6961
if g.withNumber {
7062
idx := g.rng.IntN(len(words))
@@ -83,15 +75,30 @@ func (g *generator) sanitize() (Generator, error) {
8375
if g.wordLenMin < 1 || g.wordLenMin > g.wordLenMax {
8476
return nil, ErrWordLengthInvalid
8577
}
86-
// filter the dictionary and remove too-short or too-long words
78+
79+
// remove words that are too-short & too-long
8780
slices.DeleteFunc(g.dictionary, func(word string) bool {
8881
return len(word) < g.wordLenMin || len(word) > g.wordLenMax
8982
})
9083
if len(g.dictionary) < MinWordsInDictionary {
9184
return nil, ErrDictionaryTooSmall
9285
}
93-
if g.numWords < MinNumWords {
94-
return nil, ErrNumWordsInvalid
86+
87+
// capitalize all words in the dictionary ahead of time
88+
if g.capitalize {
89+
for idx := range g.dictionary {
90+
r, size := utf8.DecodeRuneInString(g.dictionary[idx])
91+
if r != utf8.RuneError {
92+
g.dictionary[idx] = string(unicode.ToUpper(r)) + g.dictionary[idx][size:]
93+
}
94+
}
95+
}
96+
97+
if g.numWords < NumWordsMin {
98+
return nil, ErrNumWordsTooSmall
99+
}
100+
if g.numWords > NumWordsMax {
101+
return nil, ErrNumWordsTooLarge
95102
}
96103
return g, nil
97104
}

0 commit comments

Comments
 (0)