0

I am currently encoding a SHA-256 hash in a browser extension like this:

var hash = "arbitraryString";
const hash2 = await crypto.subtle.digest("SHA-256", (hash));
const hashArray = await Array.from(new Uint8Array(hash2));
const hashHex = await hashArray.map(b => b.toString(16).padStart(2, '0')).join('');
var length = 32;
var hashHexString = hashHex.substring(0,length);

This yields a 32 digit string comprised of only lowercase letters and numbers. Is there a way to change the encoding, or something else, that will yield a string with lowercase, uppercase, numbers and special chars?

When trying anything like:

const hashHex = await hashArray.map(b => b.toString(64).padStart(2, '0')).join('');

I get this error: "RangeError: toString() radix argument must be between 2 and 36"

Does this mean I can't use such a simple encoding function to create the desired lower/upper/number/special chars string in javascript (within a browser extension) without the addition of other libraries?

metamonkey
  • 427
  • 7
  • 33
  • 1
    It looks as if you need a [binary-to-text-encoding](https://en.wikipedia.org/wiki/Binary-to-text_encoding). Since you are not comfortable with Base16 (hexadecimal), how about [Base64](https://en.wikipedia.org/wiki/Base64)? It doesn't have a lot of special characters, but it has upper/lower case letters and numbers and is widespread (e.g. [here](https://stackoverflow.com/a/42334410/9014097) for an array). More special characters has Base85 but is already more exotic and also less supported. I would recommend Base64 unless the presence of special characters is important for some reason. – Topaco Nov 26 '19 at 07:21
  • Thanks. I followed the guidance and link and used Base64 [ btoa(String.fromCharCode.apply(null, new Uint8Array(hashArray))); ] and raised the max length to 64 in order to assure I get all char types. The encoded string is unique, always has upper/lower/numbers and is always 44 chars long. The only thing that's odd to me is that the last character is always "=". This is a good thing for my purposes, as it assures that the string always has a special character, but it concerned me. Can you explain it? @Topaco – metamonkey Nov 26 '19 at 21:29
  • You should read the Base64 specification carefully, just to make sure that the encoding serves your purpose. Base64 is explained in more detail [here](https://en.wikipedia.org/wiki/Base64), including the used [alphabet](https://en.wikipedia.org/wiki/Base64#Base64_table). The only allowed special charackteres are /+= where the latter is used exclusively for the padding explained in these [examples](https://en.wikipedia.org/wiki/Base64#Examples). – Topaco Nov 26 '19 at 22:03

0 Answers0