public ISimpleWebToken CreateToken(
string issuer, string audience, DateTime expiryTime, string signingKey,
IEnumerable<KeyValuePair<string, string>> values = null)
{
if (string.IsNullOrEmpty(issuer)) throw new ArgumentNullException(nameof(issuer));
if (string.IsNullOrEmpty(audience)) throw new ArgumentNullException(nameof(audience));
if (string.IsNullOrEmpty(signingKey)) throw new ArgumentNullException(nameof(signingKey));
if (expiryTime.Kind != DateTimeKind.Utc) throw new ArgumentOutOfRangeException(nameof(expiryTime), "Expiry time must be in UTC.");
if (expiryTime < _swtBaseTime) throw new ArgumentOutOfRangeException(nameof(expiryTime), "Expiry time must be after 1970.");
var signingKeyBytes = Convert.FromBase64String(signingKey);
if (signingKeyBytes.Length != 32) throw new ArgumentOutOfRangeException(nameof(signingKey), "Signing key must be 32 bytes.");
var token = new SimpleWebToken
{
Issuer = issuer,
Audience = audience,
ExpiresOn = expiryTime,
Properties = new Dictionary<string, string>()
};
var sb = new StringBuilder();
if (values != null)
{
foreach (var item in values)
{
token.Properties.Add(item.Key, item.Value);
sb.AppendFormat("{0}={1}&", WebUtility.UrlEncode(item.Key), WebUtility.UrlEncode(item.Value));
}
}
sb.AppendFormat("{0}={1}&", SimpleWebTokenConstants.Audience, WebUtility.UrlEncode(audience));
sb.AppendFormat("{0}={1}&", SimpleWebTokenConstants.ExpiresOn, GetSwtTime(expiryTime));
sb.AppendFormat("{0}={1}", SimpleWebTokenConstants.Issuer, WebUtility.UrlEncode(issuer));
token.Signature = GenerateSignature(sb.ToString(), signingKeyBytes);
sb.AppendFormat("&{0}={1}", SimpleWebTokenConstants.Signature, WebUtility.UrlEncode(token.Signature));
token.RawToken = sb.ToString();
return token;
}