npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I鈥檝e always been into building performant and accessible sites, but lately I鈥檝e been taking it extremely seriously. So much so that I鈥檝e been building a tool to help me optimize and monitor the sites that I build to make sure that I鈥檓 making an attempt to offer the best experience to those who visit them. If you鈥檙e into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 馃憢, I鈥檓 Ryan Hefner聽 and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you鈥檙e interested in other things I鈥檓 working on, follow me on Twitter or check out the open source projects I鈥檝e been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon鈥搃sh.

Open Software & Tools

This site wouldn鈥檛 be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 馃檹

漏 2026 鈥撀燩kg Stats / Ryan Hefner

@askjo/wa_meow

v1.0.17

Published

WhatsApp bridge powered by whatsmeow 馃惐 路 OpenClaw plugin

Readme

WhatsApp Bridge

A lightweight, self-hosted WhatsApp gateway for AI assistants. Built for OpenClaw and similar personal AI agent projects.

Production-tested: This code is extracted from and powers the WhatsApp integration at askjo.ai.

Add to OpenClaw

openclaw plugins install @askjo/wa_meow

Or directly from GitHub:

openclaw plugins install https://github.com/jo-inc/wa_meow

Then configure:

channels:
  wa_meow:
    serverUrl: http://localhost:8090
    accounts:
      main:
        userId: 1
        enabled: true

Connect your AI assistant to WhatsApp in minutes. Send messages, receive events via SSE, and manage multiple sessions with a simple REST API.

Why This Exists

If you're running OpenClaw or building your own AI assistant, you need a way to connect to WhatsApp. This bridge:

  • Runs on your hardware - Your messages stay with you
  • Simple REST API - No complex protocols to learn
  • Real-time events - SSE streaming for instant message delivery
  • Multi-user support - One instance handles multiple WhatsApp accounts
  • Session persistence - Encrypted backup/restore across restarts
  • More stable than Baileys - Built on whatsmeow (Go), which has better memory management and fewer session logout issues than the popular Baileys library

Quick Start

Option 1: Docker (Recommended)

docker run -d \
  --name wa_meow \
  -p 8090:8090 \
  -v wa_meow-data:/data/whatsapp \
  ghcr.io/jo-inc/wa_meow:latest

Option 2: From Source

# Clone the repo
git clone https://github.com/jo-inc/wa_meow.git
cd wa_meow

# Run (requires Go 1.21+)
./run-server.sh

Connect to WhatsApp

# 1. Create a session
curl -X POST localhost:8090/sessions -d '{"user_id": 1}'

# 2. Get QR code (opens SSE stream)
curl localhost:8090/sessions/qr?user_id=1

# 3. Scan QR with your phone (WhatsApp > Linked Devices > Link a Device)

# 4. You're connected! Send a message:
curl -X POST localhost:8090/messages/send \
  -H "Content-Type: application/json" \
  -d '{"user_id": 1, "chat_jid": "[email protected]", "text": "Hello from my AI!"}'

API Reference

Sessions

| Endpoint | Method | Description | |----------|--------|-------------| | /sessions | POST | Create session ({"user_id": 123}) | | /sessions/qr?user_id=X | GET | SSE stream of QR codes for login | | /sessions/status?user_id=X | GET | Connection status | | /sessions/save?user_id=X | POST | Persist session (requires encryption key) | | /sessions/delete?user_id=X | DELETE | Disconnect and cleanup |

Messages

| Endpoint | Method | Description | |----------|--------|-------------| | /messages/send | POST | Send text message | | /messages/react | POST | React to a message with emoji | | /messages/typing | POST | Send typing indicator | | /chats?user_id=X | GET | List all chats (contacts + groups) | | /events?user_id=X | GET | SSE stream of incoming messages |

Health

| Endpoint | Method | Description | |----------|--------|-------------| | /health | GET | Health check |

Message Format

Send a Message

curl -X POST http://localhost:8090/messages/send \
  -H "Content-Type: application/json" \
  -d '{
    "user_id": 1,
    "chat_jid": "[email protected]",
    "text": "Hello!"
  }'

React to a Message

curl -X POST http://localhost:8090/messages/react \
  -H "Content-Type: application/json" \
  -d '{
    "user_id": 1,
    "chat_jid": "[email protected]",
    "message_id": "ABC123",
    "emoji": "thumbsup"
  }'

Listen for Incoming Messages

curl -N http://localhost:8090/events?user_id=1

Events are delivered as SSE:

event: message
data: {"type":"message","payload":{"id":"ABC123","chat_jid":"[email protected]","sender_jid":"[email protected]","sender_name":"John","text":"Hey there!","timestamp":1706745600,"is_from_me":false}}

Configuration

| Environment Variable | Default | Description | |---------------------|---------|-------------| | DATA_DIR | /data/whatsapp | SQLite database storage | | PORT | 8090 | HTTP server port | | WHATSAPP_SESSION_KEY | - | Base64 AES-256 key for encrypted session backup |

Session Encryption (Optional)

To persist sessions across container restarts or sync between instances:

# Generate a key
openssl rand -base64 32

# Set it as an environment variable
export WHATSAPP_SESSION_KEY="your-generated-key"

Deployment

Fly.io

fly apps create my-wa_meow
fly secrets set WHATSAPP_SESSION_KEY="$(openssl rand -base64 32)"
fly deploy

Docker Compose

version: '3.8'
services:
  wa_meow:
    image: ghcr.io/jo-inc/wa_meow:latest
    ports:
      - "8090:8090"
    volumes:
      - wa_meow-data:/data/whatsapp
    environment:
      - WHATSAPP_SESSION_KEY=your-secret-key
    restart: unless-stopped

volumes:
  wa_meow-data:

Architecture

Your AI Assistant
       |
       | REST API (JSON)
       v
+------------------+
| WhatsApp Bridge  |  <-- This project
+------------------+
       |
       | WhatsApp Web Protocol (via whatsmeow)
       v
+------------------+
| WhatsApp Servers |
+------------------+
  • One SQLite database per user - Sessions are isolated
  • whatsmeow - Battle-tested WhatsApp Web client library
  • Server-Sent Events - Real-time message streaming
  • AES-256-GCM - Optional session encryption for backup

Development

# Install air for live-reload
go install github.com/air-verse/air@latest

# Run with auto-reload
./run-server.sh

Troubleshooting

QR code not appearing?

  • Make sure you're using curl -N to disable buffering
  • The QR stream times out after 2 minutes

Session keeps disconnecting?

  • WhatsApp may disconnect linked devices after 14 days of phone inactivity
  • Keep your phone connected to the internet

Getting rate limited?

  • WhatsApp has sending limits. Space out your messages.
  • Don't spam or you'll get banned.

Security Notes

  • This connects to your personal WhatsApp account
  • Your session data is stored locally (or encrypted if WHATSAPP_SESSION_KEY is set)
  • Never expose this bridge to the public internet without authentication
  • Consider running behind a reverse proxy with auth

Current Limitations

  • No group chat support yet - You can list groups and send messages to group JIDs, but group-specific features (mentions, replies, admin actions) are not implemented
  • Text messages only - No media (images, audio, video, documents) support yet
  • No message history - Only receives messages while connected

Credits

This project is built on whatsmeow by @tulir - a robust, well-maintained Go library that handles all the WhatsApp Web protocol complexity. Without whatsmeow, this bridge wouldn't exist. If you find this project useful, consider starring whatsmeow on GitHub.

Inspired by the OpenClaw community and the growing ecosystem of self-hosted AI assistants.

License

MIT License - See LICENSE for details.