Install Fireproof Database
use-fireproof package provides both the core API and React hooks. It is compatible with TypeScript and works across Deno, Bun, Node.js, and the browser.npm install use-fireproofwebsite·Indexed 33 days ago
https://use-fireproof.com/A lightweight embedded document database with encrypted live sync designed for browser applications.
use-fireproof package provides both the core API and React hooks. It is compatible with TypeScript and works across Deno, Bun, Node.js, and the browser.npm install use-fireproof_files property of the document object. When retrieving a document, the _files property contains metadata; call the .file() method on the attachment metadata to retrieve the actual File object as a Promise.// Saving files
function handleFiles(event) {
const fileList = event.target.files;
const doc = {
type: "files",
_files: {}
};
for (const file of fileList) {
doc._files[file.name] = file;
}
database.put(doc);
}
// Retrieving files
const doc = await database.get("my-doc-id");
for (const fileName in doc._files) {
const meta = doc._files[fileName];
if (meta.file) {
const fileObj = await meta.file();
console.log("Loaded file:", fileObj.name);
}
}position field and a composite index containing the list ID and the position. New items can be inserted between existing items by calculating the midpoint of the surrounding documents' positions.const { database, useLiveQuery } = useFireproof("my-ledger");
// Query items on list 'xyz' sorted by position
const queryResult = useLiveQuery(
(doc) => [doc.list, doc.position],
{ prefix: ["xyz"] }
);
async function insertBetween(beforeDoc, afterDoc) {
const newPosition = (beforeDoc.position + afterDoc.position) / 2;
await database.put({
list: "xyz",
position: newPosition
});
}The useFireproof hook provides a suite of tools for React integration, including useLiveQuery for real-time data fetching and useDocument for managing document state.
Critical State Management Rule: Do not use useState() for form data that will be persisted. Instead, use merge() to update the local draft and submit() to persist the document to the database. Use useState only for ephemeral UI state (e.g., active tabs, open panels).
import { useFireproof } from "use-fireproof";
export default function App() {
const { useLiveQuery, useDocument, database } = useFireproof("todo-list-db");
// Manage a document draft
const {
doc: newTodo,
merge: mergeNewTodo,
submit: submitNewTodo
} = useDocument({
todo: "",
type: "todo",
completed: false,
createdAt: Date.now()
});
// Query data in real-time
const { docs: todos } = useLiveQuery("type", {
key: "todo",
descending: true
});
const handleInputChange = (e) => {
mergeNewTodo({ todo: e.target.value });
};
const handleSubmit = (e) => {
e.preventDefault();
submitNewTodo();
};
return (
// ... JSX using newTodo.todo and todos.map()
);
}database.subscribe method to listen for real-time changes in the Fireproof database. The callback receives an array of changes, allowing you to trigger side effects (such as sending emails or updating UI) when specific data conditions are met.import { fireproof } from "use-firproof";
const database = fireproof("todo-list-db");
database.subscribe((changes) => {
console.log("Recent changes:", changes);
changes.forEach((change) => {
if (change.completed) {
sendEmail(change.email, "Todo completed", "You have completed a todo.");
}
});
}, true);useLiveQuery provides real-time updates for documents based on sorted indexes.
_id to get documents sorted by time.key to filter for specific values.range option (an array of two values) to filter numeric or sortable data.prefix option to group records (e.g., by date).// 1. Temporal sorting (most recent first)
const { docs } = useLiveQuery("_id", { descending: true, limit: 100 });
// 2. Filter by specific key
const { docs } = useLiveQuery("agentName", { key: "agent-1" });
// 3. Range query
const { docs } = useLiveQuery("agentRating", { range: [3, 5] });
// 4. Prefix query for grouping (e.g., November 2024)
const queryResult = useLiveQuery(
(doc) => [doc.date.getFullYear(), doc.date.getMonth(), doc.date.getDate()],
{ prefix: [2024, 11] }
);fireproof core API instead of hooks. The core API is asynchronous.import { fireproof } from "use-fireproof";
const database = fireproof("my-ledger");
// Put a document
const ok = await database.put({ text: "Sample Data" });
// Get a document by ID
const doc = await database.get(ok.id);
// Query documents
const latest = await database.query("_id", { limit: 10, descending: true });
console.log("Latest documents:", latest.docs);useLiveQuery to create a custom index. This is useful for normalizing legacy data types or creating complex sort keys. The index function is sandboxed and cannot access external variables.const { docs } = useLiveQuery(
(doc) => {
if (doc.type == 'listing_v1') {
return doc.sellerId;
} else if (doc.type == 'listing') {
return doc.userId;
}
},
{ key : routeParams.sellerId }
);The useDocument hook allows you to create, edit, and save JSON-style documents. Documents use an _id field; if not provided, one is auto-generated to avoid conflicts.
Available methods:
merge(updates): Updates the document with new fields.submit(e): Prevents default form behavior, saves the document, and resets it to the initial state.save(): Persists the current document state.reset(): Resets the document to its initial state.const { useDocument } = useFireproof("my-ledger");
// For a specific resource (e.g., user profile)
const { doc, merge, submit, save, reset } = useDocument({ _id: "user-profile:abc@example.com" });
// For a new document
const { doc, merge, submit } = useDocument({ text: "" });use-fireproof library in React, use the ImgFile component to render images stored in the _files property of a document.import { ImgFile } from "use-fireproof";
// Inside a map of documents
{doc._files?.uploaded && (
<ImgFile
file={doc._files.uploaded}
alt="Uploaded Image"
className="w-full h-auto rounded"
/>
)}
useFireproof hook to create or load a database. Databases are identified by a string name and serve as the unit of sharing for collaboration sessions. The hook returns the database instance and specialized hooks for querying and document management.import { useFireproof } from "use-fireproof";
const { database, useLiveQuery, useDocument } = useFireproof("my-ledger");