Getting Started
This guide walks you through creating a Rust library and packaging it for use in other languages.
Prerequisites
- Rust 1.70+ (rustup.rs)
- For Apple: Xcode 15+ with command line tools
- For Android: Android Studio with NDK
- For WASM: Node.js 18+ and wasm-pack (
cargo install wasm-pack)
Install BoltFFI
cargo install boltffi_cli
Create a Rust library
cargo new --lib mylib
cd mylib
Edit Cargo.toml:
[package]
name = "mylib"
version = "0.1.0"
edition = "2021"
[lib]
crate-type = ["staticlib", "cdylib"]
[dependencies]
boltffi = "0.1"
Write your code
Two attributes do most of the work:
#[data]marks a struct or enum as a record (value type, copied across the boundary)#[export]exposes a function or impl block to the target language
Replace src/lib.rs:
use boltffi::*;
#[data]
pub struct Point {
pub x: f64,
pub y: f64,
}
#[export]
pub fn distance(a: Point, b: Point) -> f64 {
((b.x - a.x).powi(2) + (b.y - a.y).powi(2)).sqrt()
}
Build and package
boltffi init # creates boltffi.toml
boltffi pack --release # builds for all platforms
This creates:
dist/apple/- XCFramework + Swift bindingsdist/android/- JNI libraries + Kotlin bindingsdist/wasm/- WASM module + TypeScript bindings
To build for a single platform:
boltffi pack apple --release
boltffi pack android --release
boltffi pack wasm --release
Use in Swift
Add the package to Xcode (File → Add Package Dependencies → local path to dist/apple), then:
import MyLib
let p1 = Point(x: 0, y: 0)
let p2 = Point(x: 3, y: 4)
print(distance(a: p1, b: p2)) // 5.0
Use in Kotlin
Copy dist/android into your Android project, then:
import com.example.mylib.*
val p1 = Point(0.0, 0.0)
val p2 = Point(3.0, 4.0)
println(distance(p1, p2)) // 5.0
Use in TypeScript
The WASM package works in bundlers, Node.js, and browsers.
With a Bundler (Vite, webpack)
Import directly - your bundler handles WASM loading:
import { Point, distance } from 'mylib';
const p1: Point = { x: 0, y: 0 };
const p2: Point = { x: 3, y: 4 };
console.log(distance(p1, p2)); // 5.0
In Node.js
Await initialization before calling functions:
import { initialized, Point, distance } from 'mylib';
await initialized;
const p1: Point = { x: 0, y: 0 };
const p2: Point = { x: 3, y: 4 };
console.log(distance(p1, p2)); // 5.0
In a Browser (no bundler)
Use the web entrypoint and call init():
<script type="module">
import init, { distance } from './pkg/web.js';
await init();
const p1 = { x: 0, y: 0 };
const p2 = { x: 3, y: 4 };
console.log(distance(p1, p2)); // 5.0
</script>
What you learned
#[data]creates records (value types)#[export]exposes functionsboltffi packhandles build, codegen, and packaging in one step