"use strict";
Object.defineProperty(exports, "__esModule", {
    value: true
});
function _export(target, all) {
    for(var name in all)Object.defineProperty(target, name, {
        enumerable: true,
        get: all[name]
    });
}
_export(exports, {
    HexStruct: function() {
        return HexStruct;
    },
    StrictHexStruct: function() {
        return StrictHexStruct;
    },
    HexAddressStruct: function() {
        return HexAddressStruct;
    },
    HexChecksumAddressStruct: function() {
        return HexChecksumAddressStruct;
    },
    isHexString: function() {
        return isHexString;
    },
    isStrictHexString: function() {
        return isStrictHexString;
    },
    assertIsHexString: function() {
        return assertIsHexString;
    },
    assertIsStrictHexString: function() {
        return assertIsStrictHexString;
    },
    isValidHexAddress: function() {
        return isValidHexAddress;
    },
    getChecksumAddress: function() {
        return getChecksumAddress;
    },
    isValidChecksumAddress: function() {
        return isValidChecksumAddress;
    },
    add0x: function() {
        return add0x;
    },
    remove0x: function() {
        return remove0x;
    }
});
const _sha3 = require("@noble/hashes/sha3");
const _superstruct = require("superstruct");
const _assert = require("./assert");
const _bytes = require("./bytes");
const HexStruct = (0, _superstruct.pattern)((0, _superstruct.string)(), /^(?:0x)?[0-9a-f]+$/iu);
const StrictHexStruct = (0, _superstruct.pattern)((0, _superstruct.string)(), /^0x[0-9a-f]+$/iu);
const HexAddressStruct = (0, _superstruct.pattern)((0, _superstruct.string)(), /^0x[0-9a-f]{40}$/u);
const HexChecksumAddressStruct = (0, _superstruct.pattern)((0, _superstruct.string)(), /^0x[0-9a-fA-F]{40}$/u);
function isHexString(value) {
    return (0, _superstruct.is)(value, HexStruct);
}
function isStrictHexString(value) {
    return (0, _superstruct.is)(value, StrictHexStruct);
}
function assertIsHexString(value) {
    (0, _assert.assert)(isHexString(value), 'Value must be a hexadecimal string.');
}
function assertIsStrictHexString(value) {
    (0, _assert.assert)(isStrictHexString(value), 'Value must be a hexadecimal string, starting with "0x".');
}
function isValidHexAddress(possibleAddress) {
    return (0, _superstruct.is)(possibleAddress, HexAddressStruct) || isValidChecksumAddress(possibleAddress);
}
function getChecksumAddress(address) {
    (0, _assert.assert)((0, _superstruct.is)(address, HexChecksumAddressStruct), 'Invalid hex address.');
    const unPrefixed = remove0x(address.toLowerCase());
    const unPrefixedHash = remove0x((0, _bytes.bytesToHex)((0, _sha3.keccak_256)(unPrefixed)));
    return `0x${unPrefixed.split('').map((character, nibbleIndex)=>{
        const hashCharacter = unPrefixedHash[nibbleIndex];
        (0, _assert.assert)((0, _superstruct.is)(hashCharacter, (0, _superstruct.string)()), 'Hash shorter than address.');
        return parseInt(hashCharacter, 16) > 7 ? character.toUpperCase() : character;
    }).join('')}`;
}
function isValidChecksumAddress(possibleChecksum) {
    if (!(0, _superstruct.is)(possibleChecksum, HexChecksumAddressStruct)) {
        return false;
    }
    return getChecksumAddress(possibleChecksum) === possibleChecksum;
}
function add0x(hexadecimal) {
    if (hexadecimal.startsWith('0x')) {
        return hexadecimal;
    }
    if (hexadecimal.startsWith('0X')) {
        return `0x${hexadecimal.substring(2)}`;
    }
    return `0x${hexadecimal}`;
}
function remove0x(hexadecimal) {
    if (hexadecimal.startsWith('0x') || hexadecimal.startsWith('0X')) {
        return hexadecimal.substring(2);
    }
    return hexadecimal;
}

//# sourceMappingURL=hex.js.map