Skip to content
KroszborgPublic

About

Open-source SMS API and phone verification. Send through Android phones you already own, with delivery reports and signed webhooks. Hosted or self-hosted.

Topics

Resources

Code of conduct

Contributing

Security policy

Stars

2 stars

Watchers

0 watching

Forks

Latest commit

 

History

41 Commits

Folders and files

NameName
Last commit message
Last commit date
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Bridge

Open-source infrastructure for SMS and phone verification.

Connect Android devices or professional messaging providers through one developer API. Use hosted Bridge or run it on your own server.

Application
     |  POST /v1/messages
     v
  Bridge  --  queue, retries, delivery status, logs
     |
     v
Android phone + SIM   or   MSG91 / Twilio / Vonage / Plivo
     |
     v
    SMS

Your application talks to one stable API. What delivers the message underneath (your own Android phone, or a messaging provider as a fallback or instead) can change without rewriting your code.

Bridge 1.0 is the first stable release. Documentation: bridge.kroszborg.co/docs.

What you get

  • SMS through your own phones. The Android app pairs by QR code or by signing in, sends through the phone's SIM (dual-SIM aware), reports sent and delivered, and can forward the SMS it receives. Bridge paces each phone under Android's limit and a daily cap that keeps SIMs within their operator's allowance.
  • SMS providers. MSG91, Twilio, Vonage and Plivo, as a fallback when no phone can send or for everything, with delivery reports.
  • Delivery you can follow. Every message has a timeline from queued to the carrier's delivery report, retries that never send a code twice, and signed webhooks (Standard Webhooks) for deliveries and incoming SMS, plus a live event stream.
  • Verify. One-time passwords that Bridge generates, sends and checks, with Verify apps per product, failover to another route, fraud limits, Cloudflare Turnstile, and a drop-in widget or hosted page that returns a signed token.
  • Messaging tools. Broadcasts to up to 10,000 numbers with variables, scheduled and repeating messages in any time zone, and an opt-out list, keyword auto-replies and forwarding rules (to another phone, Telegram, Slack, Discord, a signed webhook or email).
  • A dashboard for the whole team. Messages, Send (one, bulk CSV, scheduled), Verify, Automation, Phones, Providers, Integrations, API keys, webhooks, request logs, a playground, usage charts, teams with roles and invite links, an audit log and a public status page.
  • Developer tools. A zero-dependency TypeScript SDK (npm install @kroszborg/bridge), the bridgectl CLI, and an MCP server for AI assistants.
  • Integrations. Supabase Auth (built-in Send SMS hook), Better Auth, Auth0, Firebase and Clerk, and n8n, Zapier or Make.
  • Secure by default. Hashed keys and tokens, argon2id passwords, encrypted provider credentials, SSRF-safe webhooks, rate limits, and message text erased after 30 days. See the security model.

Get started

Hosted Bridge

Create an account. You get a workspace and a default project on the Free plan (1 phone, 100 live SMS a month); test messages are always free and unlimited. Pro ($5/month) and Team ($15/month) add phones, SMS, projects and members; see plans and billing. The API is at https://api.bridge.kroszborg.co.

Self-hosted

You need Docker with Compose.

git clone https://github.com/kroszborg/bridge.git
cd bridge
docker compose up -d
Service URL
Dashboard http://localhost:3000
API http://localhost:8080
API reference http://localhost:8080/docs
Status page http://localhost:3000/status

This builds the images from source. To run a published release instead, set BRIDGE_IMAGE_PREFIX=ghcr.io/kroszborg/ and BRIDGE_VERSION=1.1.0 in .env (see Releases). Self-hosted servers have no plans or limits. For a public server, read the self-hosting guide; configuration lives in environment variables, see .env.example.

Send your first message

Create an API key under API keys, pair a phone under Phones (or add an SMS provider), then send:

export BRIDGE_URL="https://api.bridge.kroszborg.co"   # or http://localhost:8080
export BRIDGE_API_KEY="bk_test_..."

curl "$BRIDGE_URL/v1/messages" \
  -H "Authorization: Bearer $BRIDGE_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"to": "+919876543210", "message": "Your order has shipped."}'
{ "id": "msg_01ja8z3k5wq2v7c9e4r2n0w6yb", "status": "queued", "to": "+919876543210", "segments": 1, "...": "..." }

bk_test_ keys use the full API but never send a real SMS. bk_live_ keys send through your paired phones (or your SMS providers, if the project routes to them).

Follow the message under Messages, or with GET /v1/messages/{id}, which includes the full delivery timeline. To be told when it is delivered, or when a phone receives an SMS, add a webhook endpoint. See Sending messages and Webhooks. For login and sign-up codes, use Verify: POST /v1/otp, then POST /v1/otp/verify, or drop in the verification widget and check its signed token.

From TypeScript, use the SDK:

import { Bridge } from '@kroszborg/bridge';

const bridge = new Bridge({ apiKey: process.env.BRIDGE_API_KEY, baseUrl: process.env.BRIDGE_URL });
const msg = await bridge.messages.send({ to: '+919876543210', message: 'Your order has shipped.' });

From a terminal, use bridgectl: bridgectl send +919876543210 "Hello" --wait.

To check a key without sending anything:

curl "$BRIDGE_URL/v1/whoami" -H "Authorization: Bearer $BRIDGE_API_KEY"
{
  "project_id": "prj_01j9tq4m2xk3v8c7e5r2n0w6yb",
  "project_name": "Default",
  "organization_id": "org_01j9tq4m2xk3v8c7e5r2n0w6yb",
  "environment": "test",
  "api_key_id": "key_01j9tq4m2xk3v8c7e5r2n0w6yb",
  "api_key_name": "Local test"
}

What is inside

Path What
apps/api Go API, background worker and migrations in one binary (bridge serve, bridge worker, bridge migrate)
apps/dashboard Next.js dashboard, including the public status page and the hosted Verify page
apps/web Public website and documentation site
apps/api/cmd/bridgectl Command-line tool and MCP server: send, broadcast from CSV, opt-outs, follow, tail events, forward webhooks locally, see docs/cli
packages/sdk TypeScript SDK (MIT, zero dependencies), see its README
packages/api-types TypeScript types generated from the API's OpenAPI document
examples curl and Node.js examples
android/gateway Android gateway app (Kotlin, foss and gms builds), see docs/android
docs Guides (messages, broadcasts, schedules, automation, Verify, providers, integrations), security model, self-hosting, hosted plans, releasing

The stack is deliberately boring: Go, PostgreSQL (data and job queue), Next.js. Self-hosting needs one binary and one database. What changed in each release is in the changelog.

Responsible use

Bridge is not a marketing tool, and it does not help you bypass carrier rules, DLT registration or provider policies. Broadcasts are for messages people expect from you, are paced to your phones' send limits, and always honour opt-outs. Each phone sends at most its daily cap (100 SMS in any 24 hours by default), because operators limit SIMs and may block those that send far more. Throughput is limited by your SIM and carrier, and Bridge reports those limits rather than hiding them.

Contributing

Read CONTRIBUTING.md for local setup, tests and conventions. Report security issues privately as described in SECURITY.md.

License

The Bridge server, dashboard and Android app are licensed under AGPL-3.0. Client SDKs are MIT-licensed so you can embed them anywhere.

About

Open-source SMS API and phone verification. Send through Android phones you already own, with delivery reports and signed webhooks. Hosted or self-hosted.

Topics

Resources

Code of conduct

Contributing

Security policy

Stars

2 stars

Watchers

0 watching

Forks

Releases

Packages

Contributors

Languages