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’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m 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’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve 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–ish.

Open Software & Tools

This site wouldn’t 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 – Pkg Stats / Ryan Hefner

@bsv/message-box-client

v2.4.2

Published

A client for P2P messaging and payments

Readme

@bsv/message-box-client

Authenticated, optionally encrypted store-and-forward messaging for BSV applications. The package supports browser and Node.js consumers, HTTP polling, live authenticated WebSockets, overlay-based host discovery, peer payments, token-settlement adapters, permissions, quotes, and push-device registration.

Install

npm install @bsv/message-box-client @bsv/sdk

@bsv/sdk is a required peer dependency. The package supports Node.js 22 and newer and publishes module-correct ESM and CommonJS entry points.

Basic messaging

import { MessageBoxClient } from '@bsv/message-box-client'
import { WalletClient } from '@bsv/sdk'

const wallet = new WalletClient()
const messages = new MessageBoxClient({
  walletClient: wallet,
  host: 'https://message-box-us-1.bsvb.tech'
})

const recipient = '025706528f0f6894b2ba505007267ccff1133e004452a1f6b72ac716f246216366'

await messages.sendMessage({
  recipient,
  messageBox: 'general_inbox',
  body: { text: 'Hello' }
})

const pending = await messages.listMessages({
  messageBox: 'general_inbox'
})

await messages.acknowledgeMessage({
  messageIds: pending.map(message => message.messageId)
})

TerraTestNet clients select the isolated overlay network and provide the dedicated TTN Message Box deployment explicitly:

const ttnMessages = new MessageBoxClient({
  walletClient: wallet,
  host: 'https://messagebox.ttn.example',
  networkPreset: 'teratestnet'
})

The explicit host is required until the dedicated TTN Message Box service has been deployed. This prevents TTN clients from silently using a testnet service.

listMessages() preserves its historical fetch-all behavior by following bounded server pages. Limit aggregate client memory when appropriate:

const firstTwoPages = await messages.listMessages({
  messageBox: 'general_inbox',
  pageSize: 250,
  maxPages: 2
})

const nextThousand = await messages.listMessages({
  messageBox: 'general_inbox',
  offset: 1000,
  limit: 1000
})

The client uses AuthFetch for BRC-105 challenges. It intentionally does not add a second Message Box-specific cost-approval mechanism because BRC-100 wallet permissions already govern payment authorization.

Explicit init() is optional. Public methods initialize the wallet identity when needed:

await messages.init()

Encryption is enabled by default through the wallet protocol. Plaintext is an explicit interoperability choice:

await messages.sendMessage({
  recipient,
  messageBox: 'public_payloads',
  body: 'This payload is intentionally plaintext.',
  skipEncryption: true
})

The server authenticates and routes ciphertext but does not hold the wallet keys required to decrypt it.

Live messages

await messages.listenForLiveMessages({
  messageBox: 'general_inbox',
  onMessage: message => {
    console.log(message.sender, message.body)
  }
})

await messages.sendLiveMessage({
  recipient,
  messageBox: 'general_inbox',
  body: 'Live when possible, store-and-forward when needed.'
})

sendLiveMessage() uses an authenticated WebSocket and falls back to the HTTP send route when the socket is unavailable or does not acknowledge delivery. Call disconnectWebSocket() when a long-lived client shuts down.

Host selection and public-service access

An explicitly configured host may use HTTP or HTTPS so local development and operator-controlled private networks remain possible. It must be an absolute URL without credentials, a query, or a fragment. Route prefixes are supported:

const messages = new MessageBoxClient({
  walletClient: wallet,
  host: 'https://messaging.example.com/api'
})

Overlay advertisements are untrusted network input. Discovered destinations must use public HTTPS addresses; loopback, private, link-local, reserved, and documentation-only hosts are rejected before a request is made. If no valid advertisement exists, the configured host is used.

Message Box is a public protocol service. Compatible servers should remain browser-accessible by default with credential-free wildcard CORS, including opaque Origin: null callers such as mobile webviews. Operators may opt into an exact-origin allowlist or disable browser CORS. CSP governs served documents and is not API authorization. BRC-103 authentication, recipient ownership, permissions, payments, quotas, and message encryption remain the security boundaries.

Permissions and delivery quotes

await messages.setMessageBoxPermission({
  messageBox: 'notifications',
  sender: recipient,
  recipientFee: 10
})

const quote = await messages.getMessageBoxQuote({
  recipient,
  messageBox: 'notifications'
})

Permission fees use these values:

  • -1: blocked
  • 0: allowed without a recipient fee
  • positive integer: required satoshi amount

Set checkPermissions: true on sendMessage() when the client should quote and construct the required payment before sending.

Peer payments

import { PeerPayClient } from '@bsv/message-box-client'

const payments = new PeerPayClient({ walletClient: wallet })

await payments.sendPayment({
  recipient,
  amount: 50_000
})

const incoming = await payments.listIncomingPayments()
for (const payment of incoming) {
  await payments.acceptPayment(payment)
}

PeerPayClient uses BRC-29 wallet-payment derivation and the same authenticated Message Box transport. It also supports live delivery, payment requests, responses, cancellations, and explicit rejection/refund flows. Its SDK peer accepts both historical number[] and binary Wallet Wire Uint8Array transaction results, while payment messages retain a portable JSON byte-array representation. Receipt remains compatible with pending messages whose typed-array bytes were already serialized as contiguous numeric keys. The same compatibility contract covers paid-message fees, batch delivery, token settlements, live-message fallback, and generic remittance transport. Malformed, sparse, or out-of-range byte records are rejected before wallet internalization and the source message remains available for retry or recovery.

Token settlement

PeerTokenClient routes token transfers and requests through Message Box while delegating token-standard-specific transaction work to registered TokenSettlementAdapter implementations:

import { PeerTokenClient } from '@bsv/message-box-client'

const tokens = new PeerTokenClient({
  walletClient: wallet,
  adapters: [myTokenAdapter]
})

The library does not assume a token wire format. Adapters own construction, acceptance, termination, and receipt data for their protocol.

RemittanceAdapter exposes Message Box as an SDK remittance communication layer.

HTTP and WebSocket contract

The client uses these authenticated HTTP routes:

| Method | Route | Purpose | | ------ | --------------------- | ---------------------------------------------------- | | POST | /sendMessage | Send to one or up to 100 recipients | | POST | /listMessages | Read a named box owned by the authenticated identity | | POST | /acknowledgeMessage | Delete acknowledged messages owned by the identity | | POST | /registerDevice | Register a Firebase push token | | GET | /devices | List the identity's registered devices | | POST | /permissions/set | Set a sender-specific or box-wide permission | | GET | /permissions/get | Read a permission | | GET | /permissions/list | List permissions | | GET | /permissions/quote | Quote one or up to 100 recipients |

The corresponding OpenAPI source is specs/messaging/message-box-http.yaml. Live delivery uses authenticated Socket.IO events and identity-owned rooms.

Public exports

  • MessageBoxClient
  • PeerPayClient
  • PeerTokenClient
  • RemittanceAdapter
  • TokenSettlementAdapter and its supporting types
  • messaging, payment, token, device, permission, quote, and batch-send types
  • standard message-box name constants

Development

From the repository root:

pnpm --filter @bsv/message-box-client typecheck
pnpm --filter @bsv/message-box-client lint
pnpm --filter @bsv/message-box-client test
pnpm --filter @bsv/message-box-client test:coverage
pnpm --filter @bsv/message-box-client pack:check
pnpm --filter @bsv/message-box-client test:browser

The unit suite is deterministic and does not contact a deployed service. test:integration is explicitly opt-in because it requires configured wallet, Message Box, database, WebSocket, and overlay services:

MESSAGE_BOX_RUN_INTEGRATION=true \
MESSAGE_BOX_INTEGRATION_HOST=http://127.0.0.1:8080 \
MESSAGE_BOX_WALLET_ORIGINATOR=localhost \
pnpm --filter @bsv/message-box-client test:integration

Targets under *.bsvb.tech require an additional explicit MESSAGE_BOX_ALLOW_PRODUCTION_INTEGRATION=true acknowledgement because the suite creates and acknowledges real messages.

The release tarball contains compiled ESM/CommonJS JavaScript, matching declarations and source maps, the UMD browser bundle, this README, and the license. It does not publish TypeScript source, tests, coverage, editor files, or package-manager locks.

License

TS Stack first-party material is under the Open BSV License Version 6. The UMD bundle incorporates separately licensed SDK material; keep THIRD_PARTY_NOTICES.md and LICENSES/ with the bundle.