42 lines
1.0 KiB
JavaScript
42 lines
1.0 KiB
JavaScript
|
// @ts-check
|
||
|
|
||
|
import maybeJsonParse from "../common/maybeJsonParse.js";
|
||
|
import * as base64url from "../common/base64url.js";
|
||
|
|
||
|
/**
|
||
|
* Parse a location hash into `name` and `bytes`.
|
||
|
* @param {string} hash
|
||
|
* @returns {null | { name: string, bytes: Uint8Array }} The parsed data, or `null` if the hash can't be parsed.
|
||
|
*/
|
||
|
export default (hash) => {
|
||
|
const normalizedHash = decodeURI(hash.replace(/^#/, ""));
|
||
|
|
||
|
const parsed = maybeJsonParse(normalizedHash);
|
||
|
if (!parsed || typeof parsed !== "object") {
|
||
|
console.warn("Couldn't parse hash as JSON object");
|
||
|
return null;
|
||
|
}
|
||
|
|
||
|
if (
|
||
|
!("name" in parsed) || (typeof parsed.name !== "string") ||
|
||
|
!("bytes" in parsed) || (typeof parsed.bytes !== "string")
|
||
|
) {
|
||
|
console.warn("Hash fields missing or invalid type");
|
||
|
return null;
|
||
|
}
|
||
|
|
||
|
const { name } = parsed;
|
||
|
if (!name) {
|
||
|
console.warn("Name is empty");
|
||
|
return null;
|
||
|
}
|
||
|
|
||
|
const bytes = base64url.parse(parsed.bytes);
|
||
|
if (!bytes || !bytes.byteLength) {
|
||
|
console.warn("Bytes is empty");
|
||
|
return null;
|
||
|
}
|
||
|
|
||
|
return { name, bytes };
|
||
|
};
|