| Crates.io | beeper-desktop-api |
| lib.rs | beeper-desktop-api |
| version | 0.1.1 |
| created_at | 2025-12-12 10:40:35.846017+00 |
| updated_at | 2025-12-12 10:56:18.256427+00 |
| description | Rust API wrapper for Beeper Desktop API |
| homepage | |
| repository | https://github.com/ErdemGKSL/beeper-desktop-api |
| max_upload_size | |
| id | 1981342 |
| size | 131,641 |
A type-safe, ergonomic Rust client library for the Beeper Desktop API. Manage chats, messages, and accounts across multiple messaging networks (WhatsApp, Telegram, Signal, Matrix, and more) through a unified interface.
Add this to your Cargo.toml:
[dependencies]
beeper_desktop_api = { version = "0.1.1" }
tokio = { version = "1", features = ["full"] }
use beeper_desktop_api::BeeperClient;
#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
// Create client with token and default URL (http://localhost:23373)
let client = BeeperClient::new("your-token-here", "http://localhost:23373");
Ok(())
}
// List all connected messaging accounts
let accounts = client.get_accounts().await?;
for account in accounts {
println!("Account: {} ({})", account.user.full_name.unwrap_or_default(), account.network);
println!(" User ID: {}", account.user.id);
println!(" Account ID: {}", account.account_id);
}
// List all chats
let chats_response = client.list_chats(None, None).await?;
for chat in &chats_response.items {
println!("Chat: {} ({} type)", chat.title, chat.chat_type);
println!(" Unread: {}", chat.unread_count);
println!(" Last Activity: {:?}", chat.last_activity);
}
// Get first chat
if let Some(chat) = chats_response.items.first() {
// Fetch messages from this chat
let messages_response = client.list_messages(&chat.id, None, None).await?;
for message in &messages_response.items {
println!("[{}] {}: {}",
message.timestamp,
message.sender_name.as_deref().unwrap_or("Unknown"),
message.text.as_deref().unwrap_or("[No text]")
);
}
}
Ready-to-run examples are provided in the examples/ directory:
Set environment variables and run:
export BEEPER_TOKEN="your-token-here"
export BEEPER_API_URL="http://localhost:23373" # optional, uses this by default
# Fetch and display all accounts
cargo run --example fetch_accounts
# Fetch and display all chats
cargo run --example fetch_chats
# Fetch and display messages from the first chat
cargo run --example fetch_messages
# Search chats and messages
cargo run --example search "your-search-query"
# Or use default search term
cargo run --example search
fetch_accountsπ€ Fetching connected accounts...
β
Successfully retrieved 3 account(s):
1. Beeper (Matrix) Account
ββ User: Erdem GΓΆksel
ββ Account ID: hungryserv
ββ User ID: @erdemdev:beeper.com
ββ Phone: +905325965386
ββ Email: zahrakon06@gmail.com
2. Instagram Account
ββ User: myinsta
ββ Account ID: instagramgo
ββ User ID: 17842413400511926
3. WhatsApp Account
ββ User: erdem
ββ Account ID: whatsapp
ββ User ID: 905325965386
fetch_chatsπ Fetching chats from Beeper...
β
Successfully retrieved 25 chats:
1. Beeper Developer Community
2. DM: Annem
3. DM: umut
4. DM: ozgen
...
fetch_messages㪠Fetching messages from first chat: 'Beeper Developer Community'
β
Successfully retrieved 20 messages:
1. [2025-12-12T09:36:18.075Z] erdemdev: i will send its link when its finished
2. [2025-12-12T09:36:10.876Z] erdemdev: also i am currently making and api wrapper for rust
3. [2025-12-12T09:33:26.464Z] erdemdev: i just want to setup main beeper communication at my server
...
searchSearching for: "api"
π Searching chats...
β
Found 50 matching chat(s):
1. Beeper Developer Community (group)
ββ Network: Beeper (Matrix)
ββ Participants: 345
ββ Unread: 0
2. @erdemdev:beeper.com (single)
ββ Network: WhatsApp
ββ Participants: 2
ββ Unread: 0
3. Annem (single)
ββ Network: WhatsApp
ββ Participants: 2
ββ Unread: 0
π¨ Searching messages...
β
Found 20 matching message(s):
Chat: Beeper Developer Community
ββ 8 message(s) found:
1. [2025-12-12T09:36:18.075Z] erdemdev: i will send its link when its finished
2. [2025-12-12T09:36:10.876Z] erdemdev: also i am currently making and api wrapper for rust
3. [2025-12-12T09:33:26.464Z] erdemdev: i just want to setup main beeper communication...
π Search Summary for "api":
β’ Chats: 50
β’ Messages: 20
β’ Total Results: 70
Represents a connected messaging account.
pub struct Account {
pub account_id: String, // e.g., "whatsapp", "telegram"
pub network: String, // Display name (e.g., "WhatsApp")
pub user: User, // User info
}
Represents a conversation (direct message or group).
pub struct Chat {
pub id: String, // Unique chat ID
pub account_id: String, // Account this chat belongs to
pub title: String, // Chat name/display title
pub chat_type: String, // "single" or "group"
pub participants: Participants, // Chat members
pub unread_count: u32, // Unread message count
pub last_activity: Option<String>, // ISO 8601 timestamp
pub is_archived: bool,
pub is_muted: bool,
pub is_pinned: bool,
}
Represents a message in a chat.
pub struct Message {
pub id: String, // Message ID
pub chat_id: String, // Which chat this is in
pub sender_id: String, // Who sent it
pub sender_name: Option<String>, // Display name
pub text: Option<String>, // Message content
pub timestamp: String, // ISO 8601 timestamp
pub attachments: Option<Vec<Attachment>>, // Media files
pub reactions: Option<Vec<Reaction>>, // Emoji reactions
pub is_sender: Option<bool>, // True if current user sent it
pub is_unread: Option<bool>, // Unread status
}
Represents a person on the messaging platform.
pub struct User {
pub id: String, // Stable user ID
pub username: Option<String>, // Handle (e.g., "@alice")
pub phone_number: Option<String>, // E.164 format
pub email: Option<String>,
pub full_name: Option<String>, // Display name
pub img_url: Option<String>, // Avatar URL
pub is_self: Option<bool>, // True if current user
pub cannot_message: Option<bool>, // Can't initiate messages
}
// Get all connected accounts
let accounts: Vec<Account> = client.get_accounts().await?;
// List all chats with pagination
let chats = client.list_chats(cursor: Option<&str>, direction: Option<&str>).await?;
// Get a specific chat
let chat: Chat = client.get_chat(chat_id: &str).await?;
// Create a new chat
let input = CreateChatInput {
account_id: "whatsapp".to_string(),
participant_ids: vec!["user-id-1".to_string()],
title: Some("My Chat".to_string()),
};
let output = client.create_chat(input).await?;
// Archive/unarchive a chat
let chat = client.archive_chat(chat_id: &str, archived: true).await?;
// Search chats
let results = client.search_chats(query: &str).await?;
// List messages in a chat with pagination
let messages = client.list_messages(
chat_id: &str,
cursor: Option<&str>,
direction: Option<&str>
).await?;
// Send a message
let input = SendMessageInput {
text: "Hello!".to_string(),
reply_to_id: None,
};
let output = client.send_message(chat_id: &str, input).await?;
// Search for messages with pagination
let results = client.search_messages(
query: &str,
cursor: Option<&str>,
direction: Option<&str>
).await?;
// Search for chats with pagination
let results = client.search_chats(
query: &str,
cursor: Option<&str>,
direction: Option<&str>
).await?;
Get a token from Beeper Desktop (Settings > API) and use it:
let client = BeeperClient::new("your-token", "http://localhost:23373");
For MCP servers and applications requiring user authorization:
GET http://localhost:23373/oauth/authorize?
client_id=your-client-id&
response_type=code&
scope=read%20write&
redirect_uri=http://localhost:3000/callback
Exchange authorization code for token:
POST http://localhost:23373/oauth/token
code=authorization-code&
client_id=your-client-id&
grant_type=authorization_code&
redirect_uri=http://localhost:3000/callback
Many list endpoints support pagination:
// Get first page
let page1 = client.list_chats(None, None).await?;
// Use cursor and direction for next page
if page1.has_more {
let page2 = client.list_chats(
Some(&page1.newest_cursor.unwrap()),
Some("after")
).await?;
}
For messages, use message.sort_key as the cursor:
let messages = client.list_messages(chat_id, None, None).await?;
if messages.has_more {
let older_messages = client.list_messages(
chat_id,
Some(&messages.items.last().unwrap().sort_key),
Some("before")
).await?;
}
All operations return Result<T, BeeperError>:
match client.list_chats(None, None).await {
Ok(chats) => println!("Got {} chats", chats.items.len()),
Err(BeeperError::Unauthorized) => eprintln!("Invalid token"),
Err(BeeperError::NotFound) => eprintln!("Resource not found"),
Err(e) => eprintln!("Error: {}", e),
}
# Build library
cargo build
# Build with optimizations
cargo build --release
# Build examples
cargo build --examples
# Run all tests
cargo test
# Run with output
cargo test -- --nocapture
# Run integration tests (requires BEEPER_TEST_TOKEN env var)
BEEPER_TEST_TOKEN="token" cargo test --test integration_tests
The library follows Rust best practices:
Beeper Desktop API provides access to these messaging networks:
For detailed API documentation, see:
MIT License - See LICENSE file for details
Contributions are welcome! Please ensure:
cargo test)cargo fmt)cargo clippy)/docs folder and inline code comments