Skip to main content

SHA-256 Generator

sha256

Computes the SHA-256 hash of a UTF-8 string and returns it as a lowercase hexadecimal string.

Overview

The sha256 function provides a convenient way to compute SHA-256 cryptographic hashes from strings. It's a pure JavaScript implementation that works in any environment (browser, Node.js, Deno, etc.) without relying on platform-specific crypto APIs.

Function Signature

sha256(msg: string): string

Parameters

ParameterTypeRequiredDescription
msgstringYesThe input string to hash (supports UTF-8 characters)

Returns

  • Type: string
  • Format: 64-character lowercase hexadecimal string
  • Example: "2cf24dba5fb0a30e26e83b2ac5b9e29e1b161e5c1fa7425e73043362938b9824"

Examples

Basic Usage

import { sha256 } from 'nhb-toolbox/hash';

// Hash a simple string
const hash = sha256('hello');
// Returns: '2cf24dba5fb0a30e26e83b2ac5b9e29e1b161e5c1fa7425e73043362938b9824'

// Hash an empty string
const emptyHash = sha256('');
// Returns: 'e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855'

// Hash with special characters
const specialHash = sha256('password123!@#');
// Returns: '8f6c1b0d58c9c22737dd3fcf15f5ec836a3a91d8dda3cb196213531cb3ae3e68'

Unicode Support

// ASCII characters
console.log(sha256('Hello'));
// '185f8db32271fe25f561a6fc938b2e264306ec304eda518007d1764826381969'

// Unicode characters
console.log(sha256('Hello 🌍'));
// '6e2de92e24e019c3d3e5df9f616b0472f0b9a98925b8e4e6e576172545160c4a'

// Non-Latin scripts
console.log(sha256('مرحبا بالعالم')); // Arabic
// '9262a0a791605071a500c1a15bef2d5efcc6c8f198567105e9ab364811377e9f'
console.log(sha256('হ্যালো পৃথিবী')); // Bangla
// 'ef5cd426d9c588e962c15c3d86d450bf8ff7d96bc2577a231aa117eca31ebcb4'
console.log(sha256('你好世界')); // Chinese
// beca6335b20ff57ccc47403ef4d9e0b8fccb4442b3151c2e7d50050673d43172

Data Integrity Verification

// Verify data hasn't been tampered with
function verifyData(originalData: string, receivedHash: string): boolean {
const computedHash = sha256(originalData);
return computedHash === receivedHash;
}

// Usage
const data = 'sensitive information';
const storedHash = sha256(data); // Store this

// Later, verify
const isIntact = verifyData(data, storedHash); // true

// If data changes
const tamperedData = 'sensitive informatioN';
const isStillIntact = verifyData(tamperedData, storedHash); // false

Implementation Details

Internal Process

The sha256 function is a convenience wrapper that combines three lower-level operations:

export function sha256(msg: string): string {
// 1. Convert UTF-8 string to bytes
const bytes = utf8ToBytes(msg);

// 2. Compute SHA-256 hash of bytes
const hashBytes = sha256Bytes(bytes);

// 3. Convert hash bytes to hex string
return bytesToHex(hashBytes);
}

Dependencies

  • utf8ToBytes: Converts the input string to UTF-8 encoded bytes
  • sha256Bytes: Pure JavaScript SHA-256 implementation operating on bytes
  • bytesToHex: Converts the resulting hash bytes to hexadecimal string

Common Use Cases

1. Password Hashing (Simplified)

// Note: For actual passwords, use proper key derivation functions (PBKDF2, bcrypt, scrypt)
// This is for demonstration only

function createPasswordHash(password: string, salt: string): string {
return sha256(password + salt);
}

// Usage
const password = 'userPassword123';
const salt = 'unique-salt-per-user';
const passwordHash = createPasswordHash(password, salt);
// Store passwordHash and salt in database

2. Cache Key Generation

function generateCacheKey(endpoint: string, params: Record<string, any>): string {
const paramString = JSON.stringify(params);
const keyBase = `${endpoint}:${paramString}`;
return `cache:${sha256(keyBase)}`;
}

// Usage
const cacheKey = generateCacheKey('/api/users', { page: 1, limit: 20 });
// Result: cache:8f7b4e3a... (deterministic, fixed length)

3. File/Data Fingerprinting

async function createFileFingerprint(file: File): Promise<string> {
const fileContent = await file.text();
return sha256(fileContent);
}

// Usage with configuration objects
function fingerprintConfig(config: object): string {
const configString = JSON.stringify(config);
return sha256(configString);
}

4. Unique ID Generation

function generateUniqueId(data: string, timestamp: number = Date.now()): string {
const combined = `${data}:${timestamp}:${Math.random()}`;
return sha256(combined).substring(0, 16); // Use first 16 chars as ID
}

// Usage
const userId = generateUniqueId('user@example.com');
// Result: '2cf24dba5fb0a30e' (collision resistant)

Comparison with Alternatives

Built-in Web Crypto API

// Web Crypto API (browser only, async)
async function sha256WebCrypto(message: string): Promise<string> {
const encoder = new TextEncoder();
const data = encoder.encode(message);
const hash = await crypto.subtle.digest('SHA-256', data);
return Array.from(new Uint8Array(hash))
.map(b => b.toString(16).padStart(2, '0'))
.join('');
}

// nhb-toolbox sha256 (synchronous, works everywhere)
const hash = sha256(message);

Advantages of sha256:

  • Synchronous (no async/await needed)
  • Works in Node.js, browsers, Deno, etc.
  • No external dependencies
  • Consistent behavior across platforms

Node.js Crypto Module

// Node.js crypto (Node.js only)
import { createHash } from 'crypto';

function sha256Node(message: string): string {
return createHash('sha256').update(message).digest('hex');
}

// nhb-toolbox sha256 (works cross-platform)
const hash = sha256(message);

Advantages of sha256:

  • Works outside Node.js
  • Same API across environments
  • Can be tree-shaken

Performance Considerations

Speed

  • Pure JavaScript: Slower than native implementations but portable
  • Optimized: The underlying sha256Bytes is optimized for JavaScript execution
  • Adequate for most use cases: Suitable for hashing passwords, generating cache keys, etc.

Memory

  • Minimal allocations: Processes data in chunks
  • No large buffers: Handles large strings efficiently
  • Garbage collection: Clean memory management

Security Notes

Cryptographic Properties

SHA-256 provides:

  • Pre-image resistance: Cannot retrieve original input from hash
  • Second pre-image resistance: Cannot find another input with same hash
  • Collision resistance: Hard to find two different inputs with same hash

Important Warnings

  1. Not for passwords alone: Use with proper key derivation functions (PBKDF2, bcrypt, scrypt)
  2. No salting: This function doesn't add salts; add your own if needed
  3. Deterministic: Same input always produces same output
  4. Not encryption: Hashes are one-way; cannot be "decrypted"

Proper Usage

// ✅ Correct: Data integrity checking
const configHash = sha256(JSON.stringify(config));
storeHashForVerification(configHash);

// ✅ Correct: Cache keys
const cacheKey = sha256(`user:${userId}:${resource}`);

// ❌ Incorrect: Password storage (without proper KDF)
const passwordHash = sha256(password); // Vulnerable!

Error Handling

The function is designed to be robust:

// All of these work without throwing
sha256(''); // Empty string
sha256('a'.repeat(1000000)); // Very long string
sha256('特殊字符🎉'); // Unicode characters
sha256(String.fromCharCode(0)); // Null character

// Invalid input types will cause issues
sha256(null as any); // Runtime error
sha256(undefined as any); // Runtime error
sha256(123 as any); // Runtime error

For type safety, use with TypeScript or validate inputs:

function safeSha256(input: unknown): string | null {
if (typeof input !== 'string') {
return null;
}
return sha256(input);
}

Examples in Context

API Request Signing

function signRequest(apiKey: string, secret: string, payload: object): string {
const timestamp = Date.now();
const payloadString = JSON.stringify(payload);
const dataToSign = `${apiKey}:${timestamp}:${payloadString}`;
const signature = sha256(dataToSign + secret);

return `${apiKey}:${timestamp}:${signature}`;
}

Content-Based Routing

function getStorageShard(content: string, totalShards: number): number {
const hash = sha256(content);
const hashValue = parseInt(hash.substring(0, 8), 16);
return hashValue % totalShards;
}

// Consistent hashing: same content always goes to same shard
const shard = getStorageShard(userData, 10); // Returns 0-9

Change Detection

class ConfigManager {
private lastHash: string = '';

hasConfigChanged(newConfig: object): boolean {
const newHash = sha256(JSON.stringify(newConfig));
const changed = newHash !== this.lastHash;
this.lastHash = newHash;
return changed;
}
}

See Also