Skip to content

Instantly share code, notes, and snippets.

@clementi
Last active February 7, 2025 22:47
Show Gist options
  • Save clementi/8d639c521c3585633b3688f3e44888f3 to your computer and use it in GitHub Desktop.
Save clementi/8d639c521c3585633b3688f3e44888f3 to your computer and use it in GitHub Desktop.
SecureTokenGenerator
using System;
using System.Linq;
using (var generator = new SecureTokenGenerator(TokenAlphabet.All, 30))
foreach (string token in generator.Tokens.Take(40))
Console.WriteLine(token);
using System;
using System.Collections.Generic;
public class SecureTokenGenerator : IDisposable
{
private bool disposed = false;
private readonly CryptoRandom random;
private readonly string alphabet;
private readonly int size;
private const int DefaultSize = 16;
private static readonly string DefaultAlphabet = TokenAlphabet.AsciiLetters + TokenAlphabet.Digits;
internal SecureTokenGenerator(CryptoRandom random, string alphabet, int size)
{
this.random = random;
this.alphabet = alphabet;
this.size = size;
}
public SecureTokenGenerator(string alphabet, int size) : this(new CryptoRandom(), alphabet, size)
{
}
public SecureTokenGenerator(string alphabet) : this(alphabet, DefaultSize)
{
}
public SecureTokenGenerator(int size) : this(DefaultAlphabet, size)
{
}
public SecureTokenGenerator() : this(DefaultSize)
{
}
public string GetNextToken()
{
char[] chars = new char[this.size];
for (int i = 0; i < this.size; i++)
{
var index = this.random.Next(this.alphabet.Length);
chars[i] = this.alphabet[index];
}
return new string(chars);
}
public IEnumerable<string> Tokens
{
get
{
while (true)
yield return this.GetNextToken();
}
}
protected virtual void Dispose(bool disposing)
{
if (disposed)
return;
if (disposing)
this.random.Dispose();
this.disposed = true;
}
public void Dispose()
{
this.Dispose(true);
GC.SuppressFinalize(this);
}
}
public static class TokenAlphabet
{
public const string AsciiLowercase = "abcdefghijklmnopqrstuvwxyz";
public const string AsciiUppercase = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
public const string Digits = "0123456789";
public const string Symbols = "~!@#$%^&*()_+`-={}|[]\\:\"'<>?,./";
public static readonly string AsciiLetters = AsciiLowercase + AsciiUppercase;
public static readonly string All = AsciiLowercase + AsciiUppercase + Digits + Symbols;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment