Skip to main content
Skill — Copyable reference implementation. Use as-is or customize. See Skills Philosophy.
Sign arbitrary messages with private keys and verify signatures to authenticate users. This guide covers EIP-191 personal messages, the standard used by wallets like MetaMask for off-chain authentication.

EIP-191 Personal Sign

EIP-191 defines a standard format for signed data that prevents signed messages from being valid transactions. The format prepends \x19Ethereum Signed Message:\n{length} to your message before hashing.

Hash Prefixing Convention

The EIP-191 personal message format:
For example, signing “Hello” produces:
This prefix ensures:
  1. Signed messages cannot be valid transactions
  2. Users know they are signing a message, not a transaction
  3. Cross-application signature reuse is prevented

Verifying Signatures

Verify that a signature was created by a specific address:

Recovering the Signer Address

Recover the signer’s address from a signature without knowing it beforehand:

Complete Example

Full sign-and-verify flow:

EIP-191 Version Bytes

EIP-191 defines three version bytes for different use cases:

Security Considerations

Always validate signatures server-side. Client-side validation can be bypassed.
  • Use EIP-191 prefix: Raw message signing allows transaction replay attacks
  • Include context: Add domain, timestamp, or nonce to prevent cross-site signature reuse
  • Verify v value: Must be 27 or 28 (or 0/1 in some libraries)
  • Check address format: Recovered addresses are checksummed differently per library
  • Time-bound signatures: Include expiration timestamps in signed messages