/// <summary> /// Given a Hash of parameters, normalize them (flatten and convert to a /// string), then generate the HMAC-SHA-256 signature using the provided key. /// </summary> /// <param name="params">the parameters to sign</param> /// <param name="key">the key to sign the params with</param> /// <returns>the resulting signature</returns> internal static string GetSignatureForParams(HashParams @params, string key) { byte[] keybytes = Encoding.UTF8.GetBytes(key); byte[] paramsbytes = Encoding.UTF8.GetBytes(@params.ToQueryString()); byte[] hashedbytes = new HMACSHA256(keybytes).ComputeHash(paramsbytes); return(BitConverter.ToString(hashedbytes).Replace("-", string.Empty).ToLower()); }
/// <summary> /// Toes the hash params. /// </summary> /// <param name="queryStringable">The query stringable.</param> /// <param name="hash">The hash.</param> /// <param name="prefix">The prefix.</param> /// <returns>HashParams object</returns> internal static HashParams ToHashParams( this object queryStringable, HashParams hash = null, string prefix = null) { Func <object, bool> isOfSimpleType = o => { var type = o.GetType(); return(type.IsPrimitive || type == typeof(string) || type == typeof(decimal) || type == typeof(DateTimeOffset)); }; PropertyInfo[] propertyInfos = queryStringable.GetType().GetProperties( BindingFlags.Public | BindingFlags.Instance); hash = hash ?? new HashParams(); foreach (PropertyInfo propertyInfo in propertyInfos) { if (propertyInfo.GetSetMethod(true) == null) { continue; } var value = propertyInfo.GetValue(queryStringable, null); if (value != null) { var propertyName = (prefix != null) ? prefix + "[" + propertyInfo.Name.ToUnderscoreCase() + "]" : propertyInfo.Name.ToUnderscoreCase(); if (value is Array) { foreach (var innerValue in (Array)value) { if (isOfSimpleType(innerValue)) { hash.Add(propertyName + "[]", innerValue); } else { innerValue.ToHashParams(hash, propertyName + "[]"); } } } else if (isOfSimpleType(value)) { hash.Add(propertyName, value); } else { value.ToHashParams(hash, propertyName); } } } return(hash); }
/// <summary> /// Toes the query string. /// </summary> /// <param name="hash">The hash.</param> /// <returns>Query String</returns> internal static string ToQueryString(this HashParams hash) { var s = new StringBuilder(); foreach (string key in hash.Select(x => x.Key).Distinct().OrderBy(x => x)) { string key1 = key; foreach (var value in hash[key1].OrderBy(x => x.ToString())) { s.Append("&"); s.Append(key.ToUrlString()); s.Append("="); s.Append(value.ToUrlString()); } } // TODO: percent_encoding // cut off the first & return(s.ToString().Substring(1)); }