TxtFlow Logo TxtFlow Free
Public Beta First public release 🎉

Send & Receive SMS from Your Server

A no-frills Android SMS Gateway that connects your phone to your server. No additional hardware needed.

App preview

Sample API Integration

Easily connect your server to TxtFlow using our simple API. Choose your preferred language below to get started.

Important: TxtFlow must be set as the default messaging app on your Android device. If not, the app will not be able to send or receive SMS, making it only useful for calling the API and sending requests, but not for actual SMS operations.
<?php
// API to handle scheduled reminders and webhook POSTs for TxtFlow

header('Content-Type: application/json');

// Replace with your own authentication if needed
define('CRON_URL', 'https://yourdomain.com/api/reminders');
define('WEBHOOK_URL', 'https://yourdomain.com/api/webhook');

if ($_SERVER['REQUEST_METHOD'] === 'GET') {
// Example: Return scheduled reminders for the app to poll
// In production, fetch from your database
$reminders = [
[
    'sender' => '+1234567890',
    'message' => 'This is your scheduled SMS!',
],
// ... more reminders
];
echo json_encode($reminders);
exit;
}

if ($_SERVER['REQUEST_METHOD'] === 'POST') {
// Receive webhook from TxtFlow app
$data = json_decode(file_get_contents('php://input'), true);
$message = $data['message'] ?? '';
$sender = $data['sender'] ?? '';
$timestamp = $data['timestamp'] ?? '';

if ($message && $sender && $timestamp) {
// Process the incoming SMS (e.g., log, store, trigger action)
file_put_contents('sms.log', "Sender: $sender\nMessage: $message\nTimestamp: $timestamp\n\n", FILE_APPEND);
echo json_encode(['status' => 'received']);
} else {
http_response_code(400);
echo json_encode(['error' => 'Invalid payload']);
}
exit;
}

http_response_code(405);
echo json_encode(['error' => 'Method not allowed']);
?>
// Node.js (Express) API for scheduled reminders and webhook POSTs

const express = require('express');
const bodyParser = require('body-parser');
const app = express();
app.use(bodyParser.json());

const reminders = [
{
sender: '+1234567890',
message: 'This is your scheduled SMS!',
},
// ... more reminders
];

// GET /api/reminders - for the app to poll scheduled reminders
app.get('/api/reminders', (req, res) => {
res.json(reminders);
});

// POST /api/webhook - receive SMS from TxtFlow app
app.post('/api/webhook', (req, res) => {
const { message, sender, timestamp } = req.body;
if (message && sender && timestamp) {
// Process the incoming SMS (e.g., log, store, trigger action)
console.log(`Sender: ${sender}\nMessage: ${message}\nTimestamp: ${timestamp}`);
res.json({ status: 'received' });
} else {
res.status(400).json({ error: 'Invalid payload' });
}
});

// (Optional) Listen on port 3000
app.listen(3000, () => {
console.log('API server running on port 3000');
});
# FastAPI API for scheduled reminders and webhook POSTs

from fastapi import FastAPI, Request, Response, status
from fastapi.responses import JSONResponse

app = FastAPI()

# Example reminders (replace with DB in production)
reminders = [
{"sender": "+1234567890", "message": "This is your scheduled SMS!"},
# ... more reminders
]

@app.get("/api/reminders")
async def get_reminders():
return reminders

@app.post("/api/webhook")
async def receive_webhook(request: Request):
data = await request.json()
message = data.get("message")
sender = data.get("sender")
timestamp = data.get("timestamp")
if message and sender and timestamp:
print(f"Sender: {sender}\\nMessage: {message}\\nTimestamp: {timestamp}")
return JSONResponse(content={"status": "received"})
return JSONResponse(content={"error": "Invalid payload"}, status_code=400)
Example: Receive SMS webhook from TxtFlow