Skip to content

BOBER3r/nokto-protocol

Repository files navigation

Nokto Protocol

Website: https://www.noktopay.com

EIP-5564 Stealth Addresses for Solana - Privacy-preserving transactions using unlinkable one-time addresses.

Overview

This project implements EIP-5564 stealth address protocol adapted for Solana. It enables senders to pay recipients without creating a public on-chain link between them.

How It Works

  1. Recipient generates a stealth meta-address (spending + viewing keypairs) and publishes it
  2. Sender uses the meta-address to derive a unique one-time stealth address for each payment
  3. Sender transfers funds to the stealth address and emits an announcement
  4. Recipient scans announcements using their viewing key to detect payments
  5. Recipient derives the private key to spend from their stealth address

Only the recipient can detect and spend from stealth addresses - observers see no connection between payments.

Architecture

sol-eip5564/
├── programs/sol-eip5564/    # Anchor program (Rust)
│   └── src/lib.rs           # On-chain program
├── sdk/                     # TypeScript SDK
│   ├── src/                 # Source code
│   │   ├── index.ts         # Public exports
│   │   ├── keys.ts          # Key generation
│   │   ├── stealth.ts       # Stealth address derivation
│   │   ├── scanning.ts      # Announcement scanning
│   │   └── utils.ts         # Utilities (hashing, encoding)
│   └── dist/                # Compiled output
├── tests/                   # Integration tests
└── scripts/                 # Demo scripts

Components

Solana Program

The Anchor program provides four instructions:

Instruction Description
register_stealth_meta_address Store spending/viewing pubkeys on-chain
announce Emit stealth announcement event
stealth_transfer_sol Transfer SOL + emit announcement atomically
stealth_transfer_token Transfer SPL tokens + create ATA + emit announcement

Program ID: 463ouCTiiJqyitwkcfwhtuS1vcDrPTEibiYKTQeVu62a (Mainnet & Devnet)

TypeScript SDK

The SDK handles all cryptographic operations client-side:

  • Key Generation: secp256k1 keypairs for spending/viewing
  • Stealth Address Derivation: ECDH + Ed25519 for spendable Solana addresses
  • Scanning: View tag filtering (99.6% early rejection) + full verification
  • Spending: Derive Ed25519 keypair from stealth secret
  • SPL Token Support: Token metadata encoding/decoding, ATA derivation

See sdk/README.md for full API documentation.

Quick Start

Installation

# Clone and install
git clone https://github.com/BOBER3r/nokto-protocol.git
cd nokto-protocol
yarn install

# Build program
anchor build

# Build SDK
cd sdk && npm run build

Run Tests

# Start local validator
solana-test-validator

# Run tests (in another terminal)
anchor test --skip-local-validator

Basic Usage

import {
  generateStealthMetaAddress,
  parseStealthMetaAddress,
  generateStealthAddress,
  deriveStealthKeypair,
  checkStealthAddress
} from 'sol-stealth-sdk';

// === RECIPIENT: Generate meta-address (once) ===
const metaAddress = generateStealthMetaAddress();
console.log(metaAddress.encoded); // Share this publicly
// Keep spending.privateKey and viewing.privateKey SECRET

// === SENDER: Send to stealth address ===
const recipientMeta = parseStealthMetaAddress("st:sol:1:02abc...:03xyz...");
const stealth = generateStealthAddress(recipientMeta);

// Transfer SOL to stealth.stealthAddress
// Store announcement: { ephemeralPubkey, viewTag, stealthAddress }

// === RECIPIENT: Scan and spend ===
const result = checkStealthAddress(
  announcement,
  myViewingPrivateKey,
  mySpendingPublicKey
);

if (result.isMine) {
  const keypair = deriveStealthKeypair(
    announcement.ephemeralPubkey,
    mySpendingPrivateKey,
    myViewingPrivateKey
  );
  // Sign transactions with keypair
}

Protocol Details

Cryptographic Flow

Recipient Setup:
  k_spend, K_spend = secp256k1 keypair (spending)
  k_view,  K_view  = secp256k1 keypair (viewing)
  meta-address = encode(K_spend, K_view)

Sender Derivation:
  r, R = ephemeral secp256k1 keypair
  S = r * K_view                          (ECDH shared secret)
  h = keccak256(S)                        (hash)
  viewTag = h[0]                          (first byte)
  P_combined = K_spend + h*G              (secp256k1 point)
  seed = sha256(P_combined)               (Ed25519 seed)
  stealthAddress = Ed25519(seed).publicKey

Recipient Recovery:
  S = k_view * R                          (ECDH shared secret)
  h = keccak256(S)
  P_combined = (k_spend + h) * G          (reconstruct point)
  seed = sha256(P_combined)
  keypair = Ed25519(seed)                 (can sign transactions)

View Tag Optimization

The view tag (first byte of hash) allows recipients to reject 255/256 (99.6%) of non-matching announcements with a single byte comparison, before expensive point operations.

Security Model

Key Who Holds Capability
Spending Private Recipient only Spend from stealth addresses
Viewing Private Recipient (or delegate) Detect incoming payments
Spending Public Anyone (in meta-address) Derive stealth addresses
Viewing Public Anyone (in meta-address) Derive stealth addresses

Key separation allows:

  • Delegating scanning to a service (share viewing key)
  • Service can detect payments but CANNOT spend
  • Only spending key holder can move funds

Development

Prerequisites

  • Rust 1.70+
  • Solana CLI 1.17+
  • Anchor 0.29+
  • Node.js 18+

Build

# Program
anchor build

# SDK
cd sdk && npm run build

Test

# Full test suite
anchor test

# With local validator already running
anchor test --skip-local-validator

Deploy

# Devnet
anchor deploy --provider.cluster devnet

# Mainnet (be careful!)
anchor deploy --provider.cluster mainnet

Limitations

  • Off-chain scanning: Recipients must scan announcements off-chain. An indexer service would improve UX.
  • No registry UI: Meta-addresses stored on-chain but no explorer integration yet.
  • Token-2022: Currently uses standard SPL Token. Token-2022 support via token_interface.

References

License

MIT License - see LICENSE

About

No description, website, or topics provided.

Resources

License

Stars

0 stars

Watchers

0 watching

Forks

Releases

No releases published

Packages

 
 
 

Contributors