Does SQLite Work With Fly.io?

Partially CompatibleLast verified: 2026-02-26

SQLite works with Fly.io but requires careful architectural planning due to Fly's distributed, ephemeral filesystem.

Quick Facts

Compatibility
partial
Setup Difficulty
Moderate
Official Integration
No — community maintained
Confidence
high
Minimum Versions

How SQLite Works With Fly.io

SQLite can run on Fly.io, but the platform's architecture creates friction. Fly.io runs applications in ephemeral containers across multiple regions—meaning your local SQLite database file doesn't persist between deployments or survive machine restarts. This works fine for development or small hobby projects, but production use requires either committing your database to your Docker image (poor DX for dynamic data) or using Fly.io's persistent volumes.

The best approach is mounting a persistent volume to your Fly app and storing your SQLite database there. This gives you a single source of truth, but you lose the "close to users worldwide" benefit since all reads/writes go to one region. For geographically distributed apps, you should consider PostgreSQL on Fly or a purpose-built distributed database. SQLite truly shines with Fly when used read-only (embedded in your container) or for caching/temporary data on ephemeral storage.

Best Use Cases

Small hobby projects or MVPs where performance and global distribution aren't critical
Embedded SQLite databases shipped with your application image for read-only reference data
Local development and testing environments before deploying to production
Single-region applications with modest traffic that accept centralized data storage

Quick Setup with Persistent Volume

bash
npm install better-sqlite3
javascript
import Database from 'better-sqlite3';
import path from 'path';

// Use Fly's persistent volume mount at /data
const dbPath = process.env.NODE_ENV === 'production'
  ? '/data/app.db'
  : './app.db';

const db = new Database(dbPath);

// Initialize schema
db.exec(`
  CREATE TABLE IF NOT EXISTS users (
    id INTEGER PRIMARY KEY,
    name TEXT NOT NULL,
    created_at DATETIME DEFAULT CURRENT_TIMESTAMP
  )
`);

// Simple query
const insert = db.prepare('INSERT INTO users (name) VALUES (?)');
insert.run('Alice');

const select = db.prepare('SELECT * FROM users');
console.log(select.all());

db.close();

Known Issues & Gotchas

critical

Database file lost on deploy if not on persistent volume

Fix: Mount a Fly persistent volume and store your database there, or accept data loss and use ephemeral SQLite for caching only

warning

SQLite locks under concurrent writes cause request timeouts in multi-instance apps

Fix: Run a single Fly machine (no horizontal scaling) or switch to PostgreSQL for concurrent workloads

warning

Network latency to persistent volume impacts query performance

Fix: Cache frequently accessed data in memory or accept higher latency; consider PostgreSQL for performance-critical apps

info

Volume not available in all Fly regions, forcing single-region deployment

Fix: Plan for single-region architecture or migrate to a distributed database solution

Alternatives

  • PostgreSQL on Fly.io - fully managed relational database with better concurrency and distribution support
  • Turso (SQLite-compatible) - distributed SQLite with automatic replication across Fly regions
  • PlanetScale (MySQL) - serverless relational database optimized for Fly deployments

Resources

Related Compatibility Guides

Explore more compatibility guides