Skip to content

Instantly share code, notes, and snippets.

View ardislu's full-sized avatar

Ardis Lu ardislu

View GitHub Profile
@ardislu
ardislu / eip-6963.js
Created July 10, 2024 04:16
The minimal JavaScript to select an EIP-6963 wallet as window.ethereum in the DevTools console for quick testing.
// EIP-6963: Multi Injected Provider Discovery
// https://eips.ethereum.org/EIPS/eip-6963
const wallets = [];
window.addEventListener('eip6963:announceProvider', e => wallets.push(e.detail));
window.dispatchEvent(new Event('eip6963:requestProvider'));
console.table(wallets.map(w => w.info.name));
console.log('Wallets have been collected in the \x1B[1;4mwallets\x1B[m object.');
console.log('Basic example to set window.ethereum:\n \x1B[1mwindow.ethereum = wallets[0].provider;\x1B[m');
@ardislu
ardislu / erc-7201.js
Created May 29, 2024 06:13
JavaScript implementation of ERC-7201 ("Namespaced Storage Layout") using noble-hashes.
// JavaScript implementation of ERC-7201 ("Namespaced Storage Layout") using noble-hashes
// https://ercs.ethereum.org/ERCS/erc-7201
// https://github.com/paulmillr/noble-hashes
// import { keccak_256 } from '@noble/hashes/sha3';
const { keccak_256 } = await import('https://esm.sh/@noble/[email protected]/esm/sha3.js');
function arrToBigInt(arr) {
const hex = `0x${[...arr].map(b => b.toString(16).padStart(2, '0')).join('')}`;
return BigInt(hex);
@ardislu
ardislu / rot13.js
Created May 8, 2024 04:26
Golfed ROT13 in JavaScript.
// Ignores input casing, output will be all lowercase.
const r=s=>s.replace(/[a-z]/gi,c=>(((parseInt(c,36)+3)%26)+10).toString(36));
// r('the quick brown fox jumps over the lazy dog')
// 'gur dhvpx oebja sbk whzcf bire gur ynml qbt'
// r('gur dhvpx oebja sbk whzcf bire gur ynml qbt')
// 'the quick brown fox jumps over the lazy dog'
@ardislu
ardislu / littleEndian64ToBigInt.js
Created April 21, 2024 05:43
Convert a hex string of 8 bytes into a BigInt.
// Converts a hex string of 8 bytes into a BigInt.
// Useful for converting Ethereum's Beacon Deposit Contract get_deposit_count().
// https://etherscan.io/address/0x00000000219ab540356cBB839Cbe05303d7705Fa
function littleEndian64ToBigInt(bytes) {
bytes = bytes.replace('0x', '').replaceAll(/\s/g, '');
return new DataView(Uint8Array.from(bytes.matchAll(/.{2}/g), b => parseInt(b, 16)).buffer).getBigUint64(0, true);
}
// Example:
// littleEndian64ToBigInt('0x0519160000000000')
@ardislu
ardislu / erc-7673.js
Last active June 19, 2024 07:14
Minimal JavaScript implementation of ERC-7673.
// Utility functions to convert an Ethereum hexadecimal address to base256emoji and vice versa.
// https://ercs.ethereum.org/ERCS/erc-7673
const toEmoji = [
'πŸš€', 'πŸͺ', 'β˜„', 'πŸ›°', '🌌', 'πŸŒ‘', 'πŸŒ’', 'πŸŒ“', 'πŸŒ”', 'πŸŒ•', 'πŸŒ–', 'πŸŒ—', '🌘', '🌍', '🌏', '🌎',
'πŸ‰', 'β˜€', 'πŸ’»', 'πŸ–₯', 'πŸ’Ύ', 'πŸ’Ώ', 'πŸ˜‚', '❀', '😍', '🀣', '😊', 'πŸ™', 'πŸ’•', '😭', '😘', 'πŸ‘',
'πŸ˜…', 'πŸ‘', '😁', 'πŸ”₯', 'πŸ₯°', 'πŸ’”', 'πŸ’–', 'πŸ’™', '😒', 'πŸ€”', 'πŸ˜†', 'πŸ™„', 'πŸ’ͺ', 'πŸ˜‰', '☺', 'πŸ‘Œ',
'πŸ€—', 'πŸ’œ', 'πŸ˜”', '😎', 'πŸ˜‡', '🌹', '🀦', 'πŸŽ‰', 'πŸ’ž', '✌', '✨', '🀷', '😱', '😌', '🌸', 'πŸ™Œ',
'πŸ˜‹', 'πŸ’—', 'πŸ’š', '😏', 'πŸ’›', 'πŸ™‚', 'πŸ’“', '🀩', 'πŸ˜„', 'πŸ˜€', 'πŸ–€', 'πŸ˜ƒ', 'πŸ’―', 'πŸ™ˆ', 'πŸ‘‡', '🎢',
'πŸ˜’', '🀭', '❣', '😜', 'πŸ’‹', 'πŸ‘€', 'πŸ˜ͺ', 'πŸ˜‘', 'πŸ’₯', 'πŸ™‹', '😞', '😩', '😑', 'πŸ€ͺ', 'πŸ‘Š', 'πŸ₯³',
@ardislu
ardislu / minimal-endianness.js
Created March 27, 2024 06:27
This is the minimum amount of JavaScript (74 characters) to detect the endianness of a platform.
// The magic number 0xFEFF is selected for familiarity with the commonly-used
// byte-order mark (BOM) character (https://en.wikipedia.org/wiki/Byte_order_mark).
const isLE = new Uint8Array(new Uint16Array([0xFEFF]).buffer)[0] === 0xFF;
// Golfed (-12 characters; 62 total characters):
// const isLE=new Uint8Array(new Uint16Array([256]).buffer)[0]<1;
@ardislu
ardislu / copy-all-code.js
Created February 21, 2024 07:10
Simple script to copy all the code blocks at once from an Etherscan smart contract code page.
// Simple script to copy all the code blocks at once from an Etherscan smart contract code page
// (example: https://etherscan.io/address/0x43506849d7c04f9138d1a2050bbf3a0c054402dd#code).
// Uses a hardcoded CSS selector, must update if Etherscan updates its frontend markup
// (this script was last updated February 2024).
// References:
// 1. Etherscan uses Ace for code blocks (https://ace.c9.io/)
// - API reference: https://ajaxorg.github.io/ace-api-docs/
// 2. Etherscan's "Copy source to clipboard" button is implemented in `copySourceCodeBtn`,
@ardislu
ardislu / erc-55.js
Last active May 29, 2024 05:42
JavaScript implementation of ERC-55 ("Mixed-case checksum address encoding") using noble-hashes.
// JavaScript implementation of ERC-55 ("Mixed-case checksum address encoding") using noble-hashes
// https://ercs.ethereum.org/ERCS/erc-55
// https://github.com/paulmillr/noble-hashes
// import { keccak_256 } from '@noble/hashes/sha3';
const { keccak_256 } = await import('https://esm.sh/@noble/[email protected]/esm/sha3.js');
function toChecksumAddress(address) {
address = address.toLowerCase().replace('0x', '');
// Hash the address (treat it as UTF-8) and return as a hex string
@ardislu
ardislu / ethereum-address-from-signature.js
Last active September 23, 2023 05:15
This is the minimum amount of JavaScript code to derive an Ethereum address from a signature, using the low-level noble-crypto libraries to minimize dependencies.
import { Signature } from '@noble/secp256k1';
import { keccak_256 } from '@noble/hashes/sha3';
// The message that will be signed
const message = 'Any arbitrary message here. πŸ΄β€β˜ οΈπŸ’―πŸ˜‚';
const encodedMessage = new TextEncoder().encode(message);
// Assuming "signature" has been acquired from the user and is in string hex form.
// Note that MetaMask and most other high-level tools will automatically inject the ERC-191 prefix to messages.
// For example, here's the minimal code to request a signature from MetaMask (assuming the below code is run in a frontend):
@ardislu
ardislu / camelCaseToTitleCase.js
Created June 2, 2023 04:35
Simple utility function to convert a camelCase string into Title Case With Spaces for human readability.
/**
* Converts a camelCase string into Title Case With Spaces for human readability.
* @param {string} str - A string in camelCase.
* @returns {string} The input string converted into Title Case With Spaces.
*/
function camelCaseToTitleCase(str) {
str = str[0].toLocaleUpperCase() + str.slice(1);
return str.replaceAll(/([A-Z]+)/g, ' $1').slice(1);
}