文章目录

  • 背景
  • HMAC-SHA256
  • SHA256

背景

最近在一些前端低代码平台开发过程中,需要用到 sha256 加密算法,但是不会用低代码平台的导库,特意从网上找一些纯 js 实现的算法备用。

HMAC-SHA256

使用示例:

result = hex(sign(key, value))

算法源码:

// To ensure cross-browser support even without a proper SubtleCrypto
// impelmentation (or without access to the impelmentation, as is the case with
// Chrome loaded over HTTP instead of HTTPS), this library can create SHA-256
// HMAC signatures using nothing but raw JavaScript/* eslint-disable no-magic-numbers, id-length, no-param-reassign, new-cap */// By giving internal functions names that we can mangle, future calls to
// them are reduced to a single byte (minor space savings in minified file)
var uint8Array = Uint8Array;
var uint32Array = Uint32Array;
var pow = Math.pow;// Will be initialized below
// Using a Uint32Array instead of a simple array makes the minified code
// a bit bigger (we lose our `unshift()` hack), but comes with huge
// performance gains
var DEFAULT_STATE = new uint32Array(8);
var ROUND_CONSTANTS = [];// Reusable object for expanded message
// Using a Uint32Array instead of a simple array makes the minified code
// 7 bytes larger, but comes with huge performance gains
var M = new uint32Array(64);// After minification the code to compute the default state and round
// constants is smaller than the output. More importantly, this serves as a
// good educational aide for anyone wondering where the magic numbers come
// from. No magic numbers FTW!
function getFractionalBits(n) {return ((n - (n | 0)) * pow(2, 32)) | 0;
}var n = 2, nPrime = 0;
while (nPrime < 64) {// isPrime() was in-lined from its original function form to save// a few bytesvar isPrime = true;// Math.sqrt() was replaced with pow(n, 1/2) to save a few bytes// var sqrtN = pow(n, 1 / 2);// So technically to determine if a number is prime you only need to// check numbers up to the square root. However this function only runs// once and we're only computing the first 64 primes (up to 311), so on// any modern CPU this whole function runs in a couple milliseconds.// By going to n / 2 instead of sqrt(n) we net 8 byte savings and no// scaling performance costfor (var factor = 2; factor <= n / 2; factor++) {if (n % factor === 0) {isPrime = false;}}if (isPrime) {if (nPrime < 8) {DEFAULT_STATE[nPrime] = getFractionalBits(pow(n, 1 / 2));}ROUND_CONSTANTS[nPrime] = getFractionalBits(pow(n, 1 / 3));nPrime++;}n++;
}// For cross-platform support we need to ensure that all 32-bit words are
// in the same endianness. A UTF-8 TextEncoder will return BigEndian data,
// so upon reading or writing to our ArrayBuffer we'll only swap the bytes
// if our system is LittleEndian (which is about 99% of CPUs)
var LittleEndian = !!new uint8Array(new uint32Array([1]).buffer)[0];function convertEndian(word) {if (LittleEndian) {return (// byte 1 -> byte 4(word >>> 24) |// byte 2 -> byte 3(((word >>> 16) & 0xff) << 8) |// byte 3 -> byte 2((word & 0xff00) << 8) |// byte 4 -> byte 1(word << 24));}else {return word;}
}function rightRotate(word, bits) {return (word >>> bits) | (word << (32 - bits));
}function sha256(data) {// Copy default statevar STATE = DEFAULT_STATE.slice();// Caching this reduces occurrences of ".length" in minified JavaScript// 3 more byte savings! :Dvar legth = data.length;// Pad datavar bitLength = legth * 8;var newBitLength = (512 - ((bitLength + 64) % 512) - 1) + bitLength + 65;// "bytes" and "words" are stored BigEndianvar bytes = new uint8Array(newBitLength / 8);var words = new uint32Array(bytes.buffer);bytes.set(data, 0);// Append a 1bytes[legth] = 0b10000000;// Store length in BigEndianwords[words.length - 1] = convertEndian(bitLength);// Loop iterator (avoid two instances of "var") -- saves 2 bytesvar round;// Process blocks (512 bits / 64 bytes / 16 words at a time)for (var block = 0; block < newBitLength / 32; block += 16) {var workingState = STATE.slice();// Roundsfor (round = 0; round < 64; round++) {var MRound;// Expand messageif (round < 16) {// Convert to platform Endianness for later mathMRound = convertEndian(words[block + round]);}else {var gamma0x = M[round - 15];var gamma1x = M[round - 2];MRound =M[round - 7] + M[round - 16] + (rightRotate(gamma0x, 7) ^rightRotate(gamma0x, 18) ^(gamma0x >>> 3)) + (rightRotate(gamma1x, 17) ^rightRotate(gamma1x, 19) ^(gamma1x >>> 10));}// M array matches platform endiannessM[round] = MRound |= 0;// Computationvar t1 =(rightRotate(workingState[4], 6) ^rightRotate(workingState[4], 11) ^rightRotate(workingState[4], 25)) +((workingState[4] & workingState[5]) ^(~workingState[4] & workingState[6])) + workingState[7] + MRound + ROUND_CONSTANTS[round];var t2 =(rightRotate(workingState[0], 2) ^rightRotate(workingState[0], 13) ^rightRotate(workingState[0], 22)) +((workingState[0] & workingState[1]) ^(workingState[2] & (workingState[0] ^workingState[1])));for (var i = 7; i > 0; i--) {workingState[i] = workingState[i - 1];}workingState[0] = (t1 + t2) | 0;workingState[4] = (workingState[4] + t1) | 0;}// Update statefor (round = 0; round < 8; round++) {STATE[round] = (STATE[round] + workingState[round]) | 0;}}// Finally the state needs to be converted to BigEndian for output// And we want to return a Uint8Array, not a Uint32Arrayreturn new uint8Array(new uint32Array(STATE.map(function (val) { return convertEndian(val); })).buffer);
}function hmac(key, data) {if (key.length > 64)key = sha256(key);if (key.length < 64) {const tmp = new Uint8Array(64);tmp.set(key, 0);key = tmp;}// Generate inner and outer keysvar innerKey = new Uint8Array(64);var outerKey = new Uint8Array(64);for (var i = 0; i < 64; i++) {innerKey[i] = 0x36 ^ key[i];outerKey[i] = 0x5c ^ key[i];}// Append the innerKeyvar msg = new Uint8Array(data.length + 64);msg.set(innerKey, 0);msg.set(data, 64);// Has the previous message and append the outerKeyvar result = new Uint8Array(64 + 32);result.set(outerKey, 0);result.set(sha256(msg), 64);// Hash the previous messagereturn sha256(result);
}// Convert a string to a Uint8Array, SHA-256 it, and convert back to string
const encoder = new TextEncoder("utf-8");function sign(inputKey, inputData) {const key = typeof inputKey === "string" ? encoder.encode(inputKey) : inputKey;const data = typeof inputData === "string" ? encoder.encode(inputData) : inputData;return hmac(key, data);
}function hash(str) {return hex(sha256(encoder.encode(str)));
}function hex(bin) {return bin.reduce((acc, val) =>acc + ("00" + val.toString(16)).substr(-2), "");
}

SHA256

使用示例:

result = sha256(value)

算法源码:

function sha256(s) {const chrsz = 8const hexcase = 0function safe_add(x, y) {const lsw = (x & 0xFFFF) + (y & 0xFFFF)const msw = (x >> 16) + (y >> 16) + (lsw >> 16)return (msw << 16) | (lsw & 0xFFFF)}function S(X, n) {return (X >>> n) | (X << (32 - n))}function R(X, n) {return (X >>> n)}function Ch(x, y, z) {return ((x & y) ^ ((~x) & z))}function Maj(x, y, z) {return ((x & y) ^ (x & z) ^ (y & z))}function Sigma0256(x) {return (S(x, 2) ^ S(x, 13) ^ S(x, 22))}function Sigma1256(x) {return (S(x, 6) ^ S(x, 11) ^ S(x, 25))}function Gamma0256(x) {return (S(x, 7) ^ S(x, 18) ^ R(x, 3))}function Gamma1256(x) {return (S(x, 17) ^ S(x, 19) ^ R(x, 10))}function core_sha256(m, l) {const K = [0x428A2F98, 0x71374491, 0xB5C0FBCF, 0xE9B5DBA5, 0x3956C25B, 0x59F111F1, 0x923F82A4, 0xAB1C5ED5, 0xD807AA98, 0x12835B01, 0x243185BE, 0x550C7DC3, 0x72BE5D74, 0x80DEB1FE, 0x9BDC06A7, 0xC19BF174, 0xE49B69C1, 0xEFBE4786, 0xFC19DC6, 0x240CA1CC, 0x2DE92C6F, 0x4A7484AA, 0x5CB0A9DC, 0x76F988DA, 0x983E5152, 0xA831C66D, 0xB00327C8, 0xBF597FC7, 0xC6E00BF3, 0xD5A79147, 0x6CA6351, 0x14292967, 0x27B70A85, 0x2E1B2138, 0x4D2C6DFC, 0x53380D13, 0x650A7354, 0x766A0ABB, 0x81C2C92E, 0x92722C85, 0xA2BFE8A1, 0xA81A664B, 0xC24B8B70, 0xC76C51A3, 0xD192E819, 0xD6990624, 0xF40E3585, 0x106AA070, 0x19A4C116, 0x1E376C08, 0x2748774C, 0x34B0BCB5, 0x391C0CB3, 0x4ED8AA4A, 0x5B9CCA4F, 0x682E6FF3, 0x748F82EE, 0x78A5636F, 0x84C87814, 0x8CC70208, 0x90BEFFFA, 0xA4506CEB, 0xBEF9A3F7, 0xC67178F2]const HASH = [0x6A09E667, 0xBB67AE85, 0x3C6EF372, 0xA54FF53A, 0x510E527F, 0x9B05688C, 0x1F83D9AB, 0x5BE0CD19]const W = new Array(64)let a, b, c, d, e, f, g, h, i, jlet T1, T2m[l >> 5] |= 0x80 << (24 - l % 32)m[((l + 64 >> 9) << 4) + 15] = lfor (i = 0; i < m.length; i += 16) {a = HASH[0]b = HASH[1]c = HASH[2]d = HASH[3]e = HASH[4]f = HASH[5]g = HASH[6]h = HASH[7]for (j = 0; j < 64; j++) {if (j < 16) {W[j] = m[j + i]} else {W[j] = safe_add(safe_add(safe_add(Gamma1256(W[j - 2]), W[j - 7]), Gamma0256(W[j - 15])), W[j - 16])}T1 = safe_add(safe_add(safe_add(safe_add(h, Sigma1256(e)), Ch(e, f, g)), K[j]), W[j])T2 = safe_add(Sigma0256(a), Maj(a, b, c))h = gg = ff = ee = safe_add(d, T1)d = cc = bb = aa = safe_add(T1, T2)}HASH[0] = safe_add(a, HASH[0])HASH[1] = safe_add(b, HASH[1])HASH[2] = safe_add(c, HASH[2])HASH[3] = safe_add(d, HASH[3])HASH[4] = safe_add(e, HASH[4])HASH[5] = safe_add(f, HASH[5])HASH[6] = safe_add(g, HASH[6])HASH[7] = safe_add(h, HASH[7])}return HASH}function str2binb(str) {const bin = []const mask = (1 << chrsz) - 1for (let i = 0; i < str.length * chrsz; i += chrsz) {bin[i >> 5] |= (str.charCodeAt(i / chrsz) & mask) << (24 - i % 32)}return bin}function Utf8Encode(string) {string = string.replace(/\r\n/g, '\n')let utfText = ''for (let n = 0; n < string.length; n++) {const c = string.charCodeAt(n)if (c < 128) {utfText += String.fromCharCode(c)} else if ((c > 127) && (c < 2048)) {utfText += String.fromCharCode((c >> 6) | 192)utfText += String.fromCharCode((c & 63) | 128)} else {utfText += String.fromCharCode((c >> 12) | 224)utfText += String.fromCharCode(((c >> 6) & 63) | 128)utfText += String.fromCharCode((c & 63) | 128)}}return utfText}function binb2hex(binarray) {const hex_tab = hexcase ? '0123456789ABCDEF' : '0123456789abcdef'let str = ''for (let i = 0; i < binarray.length * 4; i++) {str += hex_tab.charAt((binarray[i >> 2] >> ((3 - i % 4) * 8 + 4)) & 0xF) +hex_tab.charAt((binarray[i >> 2] >> ((3 - i % 4) * 8)) & 0xF)}return str}s = Utf8Encode(s)return binb2hex(core_sha256(str2binb(s), s.length * chrsz))
}

使用 JavaScript 实现 SHA256 以及 HMAC-SHA256相关推荐

  1. js怎么实现hmacsha256_各种语言HMAC SHA256实现

    语言包含: Javascript ,PHP,Java,Groovy,C#,Objective C,Go,Ruby,Python,Perl,Dart,Swift,Rust,Powershell. Jav ...

  2. Http请求加密规则(3DES、Base64、HMAC SHA256)

    Http请求加密规则(3DES.Base64.HMAC SHA256) 如果使用了Https请求,那么大多数情况下就无需双方再制定一套加密规则,所以本人讲述的是使用Http请求时,对于一些安全性较高的 ...

  3. JavaScript:实现加密哈希SHA-256 算法(附完整源码)

    JavaScript:实现加密哈希SHA-256 算法 // main variables const CHAR_SIZE = 8const K = [0x428a2f98, 0x71374491, ...

  4. hmacsha256 c语言源码,纯C语言实现hmac sha256,可在单片机中使用_沃航科技

    这是小沃最近遇到的一个项目,由于百度云的所有接口都需要通过hmac sha256计算,所以小沃在网上找到了相关代码可以在单片机中实现,现在就分享给大家. SHA256.h#ifndef SHA256_ ...

  5. docker导入镜像报错:invalid diffID for layer xxx: expected “sha256:xxx“, got “sha256:xxx“(文件被更改过)

    参考文章:Invalid diffID error on loading docker image [root@ubuntu /home/yg/H7 HEOP]4# docker image load ...

  6. java sha256 实现_JAVA SHA256加密代码实现

    //这里对密码进行加密,再存到数据库 String password3=StringEncrypt.Encrypt(password); //SHA256加密算法     public static ...

  7. python HMAC SHA256 加密(python3 HmacSHA256加密)

    首先保证亲测可用,代码如下:from hashlib import sha256 import hmacdef get_sign(key, data):#sha256加密有2种# hsobj = sh ...

  8. hmac sha256安全吗_全面普及HTTPS有意义吗?

    记得小时候,敞篷卡车从果园拉着一车车的苹果,运到码头上,然后再装载到万吨货轮上运往上海.但运往码头的最后一公里,道路坑坑洼洼,卡车会放慢速度,这时就会有一些青少年爬上货车,从袋子里拿苹果吃,每次都会有 ...

  9. hmac sha256 php,PHP中的HMAC-SHA-256

    我必须从这个字符串构建一个autorisation哈希: kki98hkl-u5d0-w96i-62dp-xpmr6xlvfnjz:20151110171858:b2c13532-3416-47d9- ...

  10. php hmac sha256签名,HMAC-SHA256签名错误?

    #2.连接商户key: act_name=3333321ss&client_ip=118.89.65.223&mch_billno=a0000000000000000001&m ...

最新文章

  1. Kmeans、Kmeans++和KNN算法比较
  2. TortoiseSVN与VisualSVN Server搭建SVN版本控制系统【转】
  3. 在OpenShift上扩展Java EE微服务
  4. eclipse 工程中使用引入maven项目遇到maven-resources-plugin:2.6 找不到
  5. java中unicode显示乱码_Java 已知Java系统编码是GBK,jtextarea从一编码为Unicode的文本中读取数据,出现乱码,怎么正常显示?...
  6. 18C 也不能避免 SQL 解析的 Bug
  7. sql动态sql给变量复值_在动态SQL中使用变量
  8. 分享一个完整的Mybatis分页解决方案
  9. nagios监控服务短信报警开发及部署细节
  10. paip.HTML文本框INPUT无法输入的解决
  11. 电信网关-天翼网关-GPON-HS8145C设置桥接路由拨号认证
  12. 现代电工技术实训考核装置
  13. 如何用计算机校验信息,Win10如何校验文件哈希值(系统自带方法)?
  14. 桌面图标变白,任务栏图标变白
  15. 技术漫谈:反病毒技术的现状与未来
  16. 创始人李卉:麦客CRM2.0核心逻辑及其背后的思考
  17. C#中Get和Set的用法
  18. POSTGRESQL index advisor 4种方式 (国内,国外,远程,云)那个更好
  19. 很迷的SG??Berzerk - 787C
  20. 推荐视频:浙大郑强教授演讲《中国强大的真正希望》

热门文章

  1. 今天跟我薅当当羊毛!4 折买正版书了!!
  2. 《黑客大曝光:移动应用安全揭秘及防护措施》一3.3 越狱:发泄愤怒
  3. go语言ORM框架ent使用教程
  4. 星期四定律。散分!_星期四
  5. 一看就会的kafka多线程顺序消费【内附Demo哦】
  6. vac虚拟声卡我linux,Virtual Audio Cable
  7. java 中 webcam类,使用WebCam实现java拍照功能
  8. 百度人脸识别sdk图片转码的问题
  9. 几种常见的Shell:sh、bash、csh、tcsh、ash
  10. 我国超级计算机第一名是,中国蝉联超级计算机冠军,美国跌出前三