Description
The issue
There are use-cases where we need or could want to generate a random string:
- Creating a validation link for an email
- Generating a unique identifier for a conference call room (like Google Meet)
- Other use-cases ? (if anyone has some it could be nice to drop them in the comments)
For now neither math/rand
nor crypto/rand
provide a straightforward solution.
Proposal
Add a String
function to any/both of the rand packages, with only a length parameter to generate a random string of any length.
package main
import (
"math/rand"
)
func main() {
id := rand.String(10) // djfrtyusao
}
The method would only take a size parameter, that would determine the length of the final string (and possibly panic if this size is negative or too big?).
I think it should also generate a url-safe string, or even only alphanumerics/latin alphabet characters.
StringAlphabet
For a greater coverage, we could also include a more sophisticated method, that would accept an "alphabet" (a user generated set of elements to pick up as runes). Maybe the method could be named StringAlphabet
? (I'm not the best at naming xD)
package main
import (
"math/rand"
)
const alphabet = "1234567890" // here it would only generate a numeric string, but whatever
func main() {
id := rand.StringAlphabet(alphabet, 10) // 2834753819
}
Where the alphabet argument would be a string of allowed runes to pick up. Could be used for example to generate uuids, where alphabet would look like "0123456789abcdef"
.
package main
import (
"fmt"
"math/rand"
)
const alphabet = "0123456789abcdef" // for uuids
func GenerateUUID() string {
a := rand.StringAlphabet(alphabet, 8)
b := rand.StringAlphabet(alphabet, 4)
c := rand.StringAlphabet(alphabet, 4)
d := rand.StringAlphabet(alphabet, 4)
e := rand.StringAlphabet(alphabet, 12)
return fmt.Sprintf("%s-%s-%s-%s-%s",a, b, c, d, e)
}
Conclusion
I use some working examples I wrote in my packages, so the concept seems to work. However I don't know anything about pseudo-random generators and my solution may be far from optimized.
For the String
method at least, I found this stackoverflow post that provides a very pleasant solution.