I want to generate a secure random number to use for bearer tokens in vapor swift.
I have looked at OpenCrypto but it doesn't seem to be able to generate random numbers.
How do I do this?
I want to generate a secure random number to use for bearer tokens in vapor swift.
I have looked at OpenCrypto but it doesn't seem to be able to generate random numbers.
How do I do this?
For Vapor you can generate a token like so:
[UInt8].random(count: 32).base64
That will be cryptographically secure to use. You can use it like in this repo
You may want to take a look at SecRandomCopyBytes(_:_:_:):
From Apple documentation:
Generates an array of cryptographically secure random bytes.
var bytes = [Int8](repeating: 0, count: 10)
let status = SecRandomCopyBytes(kSecRandomDefault, bytes.count, &bytes)
if status == errSecSuccess { // Always test the status.
print(bytes)
// Prints something different every time you run.
}
In general (but keep reading), you'll want SystemRandomNumberGenerator for this. As documented:
SystemRandomNumberGenerator is automatically seeded, is safe to use in multiple threads, and uses a cryptographically secure algorithm whenever possible.
The "whenever possible" may give you pause depending on how this is going to be deployed. If it's on an enumerated list of platforms, you can check that they use a CSPRNG. "Almost" (see below) all current platforms do:
Apple platforms use arc4random_buf(3).
Linux platforms use getrandom(2) when available; otherwise, they read from /dev/urandom.
Windows uses BCryptGenRandom.
On Linux, getrandom is explicitly appropriate for cryptographic purposes, and blocks if it cannot yet provide good entropy. See the source for its implementation. Specifically, if the entropy pool is not initialized yet, it will block:
if (!(flags & GRND_INSECURE) && !crng_ready()) {
if (flags & GRND_NONBLOCK)
return -EAGAIN;
ret = wait_for_random_bytes();
if (unlikely(ret))
return ret;
}
On systems without getrandom, I believe swift_stdlib_random, which SystemRandomNumberGenerator uses, may read /dev/urandom before it's initialized. This is a rare situation (typically immediately after boot, though possibly due to other processes rapidly consuming entropy), but it can reduce the randomness of your values. Of currently supported Swift platforms, I believe this only impacts CentOS 7.
On Windows, BCryptGenRandom is documented to be appropriate for cryptographic random numbers:
The default random number provider implements an algorithm for generating random numbers that complies with the NIST SP800-90 standard, specifically the CTR_DRBG portion of that standard.
SP800-90 covers both the algorithm and entropy requirements.