Bitcoin-specific hash functions and cryptographic operations including SHA256, RIPEMD160, hash160, hash256, and BIP340 tagged hashes for Taproot operations.
Standard cryptographic hash functions used throughout Bitcoin.
/**
* RIPEMD160 hash function
* @param buffer - Input data to hash
* @returns 20-byte RIPEMD160 hash
*/
function ripemd160(buffer: Buffer): Buffer;
/**
* SHA-1 hash function
* @param buffer - Input data to hash
* @returns 20-byte SHA-1 hash
*/
function sha1(buffer: Buffer): Buffer;
/**
* SHA-256 hash function
* @param buffer - Input data to hash
* @returns 32-byte SHA-256 hash
*/
function sha256(buffer: Buffer): Buffer;Usage Examples:
import { crypto } from 'bitcoinjs-lib';
const data = Buffer.from('Hello Bitcoin!', 'utf8');
// Basic hashes
const sha256Hash = crypto.sha256(data);
const ripemd160Hash = crypto.ripemd160(data);
const sha1Hash = crypto.sha1(data);
console.log('SHA-256:', sha256Hash.toString('hex'));
console.log('RIPEMD160:', ripemd160Hash.toString('hex'));
console.log('SHA-1:', sha1Hash.toString('hex'));Composite hash functions commonly used in Bitcoin protocol.
/**
* Hash160: SHA-256 followed by RIPEMD160
* Used for Bitcoin addresses and script hashes
* @param buffer - Input data to hash
* @returns 20-byte hash160 result
*/
function hash160(buffer: Buffer): Buffer;
/**
* Hash256: Double SHA-256 (SHA-256 of SHA-256)
* Used for Bitcoin transaction and block hashes
* @param buffer - Input data to hash
* @returns 32-byte hash256 result
*/
function hash256(buffer: Buffer): Buffer;Usage Examples:
import { crypto } from 'bitcoinjs-lib';
// Public key to address hash
const pubkey = Buffer.from('03a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd', 'hex');
const pubkeyHash = crypto.hash160(pubkey);
console.log('Pubkey hash (for P2PKH):', pubkeyHash.toString('hex'));
// Script to script hash
const redeemScript = Buffer.from('5221...ae', 'hex');
const scriptHash = crypto.hash160(redeemScript);
console.log('Script hash (for P2SH):', scriptHash.toString('hex'));
// Transaction data to transaction hash
const txData = Buffer.from('01000000...', 'hex');
const txHash = crypto.hash256(txData);
console.log('Transaction hash:', txHash.toString('hex'));Tagged hash functionality for Taproot (BIP340) operations providing domain separation.
/**
* Tagged hash function for BIP340/Taproot operations
* Provides domain separation by prefixing with hash of tag
* @param prefix - Tag string for domain separation
* @param data - Data to hash
* @returns 32-byte tagged hash result
*/
function taggedHash(prefix: TaggedHashPrefix, data: Buffer): Buffer;
/** Valid tagged hash prefixes for BIP340 operations */
type TaggedHashPrefix =
| "BIP0340/challenge"
| "BIP0340/aux"
| "BIP0340/nonce"
| "TapLeaf"
| "TapBranch"
| "TapSighash"
| "TapTweak"
| "KeyAgg list"
| "KeyAgg coefficient";
/** Array of all valid tagged hash prefixes */
const TAGS: readonly TaggedHashPrefix[];
/** Pre-computed tagged hash prefixes for performance */
const TAGGED_HASH_PREFIXES: {
[key in TaggedHashPrefix]: Buffer;
};Usage Examples:
import { crypto } from 'bitcoinjs-lib';
// Taproot leaf hash
const leafScript = Buffer.from('20abcd...ac', 'hex');
const leafVersion = Buffer.from([0xc0]); // Leaf version
const leafData = Buffer.concat([leafScript, leafVersion]);
const tapLeafHash = crypto.taggedHash('TapLeaf', leafData);
// Taproot branch hash
const leftHash = Buffer.from('abc123...', 'hex');
const rightHash = Buffer.from('def456...', 'hex');
const branchData = Buffer.concat([leftHash, rightHash]);
const tapBranchHash = crypto.taggedHash('TapBranch', branchData);
// BIP340 signature challenge
const pubkey = Buffer.from('abc123...', 'hex');
const message = Buffer.from('def456...', 'hex');
const nonce = Buffer.from('fedcba...', 'hex');
const challengeData = Buffer.concat([nonce, pubkey, message]);
const challenge = crypto.taggedHash('BIP0340/challenge', challengeData);
console.log('Tap leaf hash:', tapLeafHash.toString('hex'));
console.log('Tap branch hash:', tapBranchHash.toString('hex'));
console.log('BIP340 challenge:', challenge.toString('hex'));Available constants and type definitions for tagged hashes.
/** Array of all supported tagged hash prefixes */
const TAGS: readonly [
"BIP0340/challenge",
"BIP0340/aux",
"BIP0340/nonce",
"TapLeaf",
"TapBranch",
"TapSighash",
"TapTweak",
"KeyAgg list",
"KeyAgg coefficient"
];
/** Pre-computed tagged hash prefixes object */
const TAGGED_HASH_PREFIXES: {
"BIP0340/challenge": Buffer;
"BIP0340/aux": Buffer;
"BIP0340/nonce": Buffer;
"TapLeaf": Buffer;
"TapBranch": Buffer;
"TapSighash": Buffer;
"TapTweak": Buffer;
"KeyAgg list": Buffer;
"KeyAgg coefficient": Buffer;
};Usage Examples:
import { crypto } from 'bitcoinjs-lib';
// Check available tags
console.log('Available tags:', crypto.TAGS);
// Access pre-computed prefixes
const tapLeafPrefix = crypto.TAGGED_HASH_PREFIXES['TapLeaf'];
console.log('TapLeaf prefix:', tapLeafPrefix.toString('hex'));
// Manual tagged hash (equivalent to taggedHash function)
const tag = 'TapLeaf';
const data = Buffer.from('script data...', 'hex');
const tagHash = crypto.sha256(Buffer.from(tag, 'utf8'));
const prefix = Buffer.concat([tagHash, tagHash]);
const manualTaggedHash = crypto.sha256(Buffer.concat([prefix, data]));Use hash functions for Bitcoin address generation:
import { crypto, payments, networks } from 'bitcoinjs-lib';
// P2PKH address from public key
const pubkey = Buffer.from('03a34b...', 'hex');
const pubkeyHash = crypto.hash160(pubkey);
const p2pkh = payments.p2pkh({ hash: pubkeyHash, network: networks.bitcoin });
console.log('P2PKH address:', p2pkh.address);
// P2SH address from script
const redeemScript = Buffer.from('5221...ae', 'hex');
const scriptHash = crypto.hash160(redeemScript);
const p2sh = payments.p2sh({ hash: scriptHash, network: networks.bitcoin });
console.log('P2SH address:', p2sh.address);Use hash functions for transaction verification:
import { crypto, Transaction } from 'bitcoinjs-lib';
const txHex = '01000000...';
const txBuffer = Buffer.from(txHex, 'hex');
// Calculate transaction hash
const txHash = crypto.hash256(txBuffer);
console.log('Transaction hash:', txHash.reverse().toString('hex')); // Reverse for display
// Parse and verify
const tx = Transaction.fromHex(txHex);
const calculatedHash = tx.getHash();
console.log('Matches:', txHash.equals(calculatedHash));Use tagged hashes for Taproot script trees:
import { crypto } from 'bitcoinjs-lib';
// Build Taproot script tree
function buildScriptTree(scripts: Buffer[]): Buffer {
if (scripts.length === 1) {
// Leaf hash
const leafVersion = Buffer.from([0xc0]);
const leafData = Buffer.concat([scripts[0], leafVersion]);
return crypto.taggedHash('TapLeaf', leafData);
}
// Branch hash
const mid = Math.ceil(scripts.length / 2);
const left = buildScriptTree(scripts.slice(0, mid));
const right = buildScriptTree(scripts.slice(mid));
// Sort hashes lexicographically
const [first, second] = [left, right].sort(Buffer.compare);
const branchData = Buffer.concat([first, second]);
return crypto.taggedHash('TapBranch', branchData);
}
const scripts = [
Buffer.from('script1...', 'hex'),
Buffer.from('script2...', 'hex'),
Buffer.from('script3...', 'hex')
];
const merkleRoot = buildScriptTree(scripts);
console.log('Taproot merkle root:', merkleRoot.toString('hex'));Tagged hash prefixes are pre-computed for performance:
import { crypto } from 'bitcoinjs-lib';
// Efficient: uses pre-computed prefix
const efficientHash = crypto.taggedHash('TapLeaf', data);
// Less efficient: computes prefix each time
const tag = 'TapLeaf';
const tagHash = crypto.sha256(Buffer.from(tag, 'utf8'));
const prefix = Buffer.concat([tagHash, tagHash]);
const manualHash = crypto.sha256(Buffer.concat([prefix, data]));
// Both produce the same result
console.log('Results match:', efficientHash.equals(manualHash));type TaggedHashPrefix =
| "BIP0340/challenge"
| "BIP0340/aux"
| "BIP0340/nonce"
| "TapLeaf"
| "TapBranch"
| "TapSighash"
| "TapTweak"
| "KeyAgg list"
| "KeyAgg coefficient";
type TaggedHashPrefixes = {
[key in TaggedHashPrefix]: Buffer;
};