fire_api 1.5.6
fire_api: ^1.5.6 copied to clipboard
A stripped down interface for firestore databases which allows both dart servers using `fire_api_dart` and flutter apps using `fire_api_flutter` to use the same api.
Fire API #
fire_api is a shared Firestore and Firebase Storage wrapper that lets Flutter apps and Dart servers use the same API surface.
The shared package models a smaller common subset of Firestore so the same document, query, aggregate, atomic-update, and storage code can run against:
fire_api_flutterfor Flutter viacloud_firestoreandfirebase_storagefire_api_dartfor Dart servers via Google Cloud Firestore and Storage APIs
Firestore Support #
| Feature | Flutter | Dart |
|---|---|---|
| Get / Set / Add / Delete / Update documents | ✅ | ✅ |
| Query collections | ✅ | ✅ |
| Aggregate count queries | ✅ | ✅ |
| Aggregate sum queries | ✅ | ✅ |
FieldValue updates |
✅ | ✅ |
| Atomic get-then-set / get-then-update | ✅ | ✅ |
| Start / end at / after / before queries | ✅ | ✅ |
| Limit queries | ✅ | ✅ |
| Order queries | ✅ | ✅ |
Recursive VectorValue read / write conversion |
✅ | ✅ |
Nearest-neighbor vector query findNearest(...).get() |
✅ | ✅ |
CollectionReference.deleteAll() |
✅ | ✅ |
| Realtime document streams | ✅ | ❌ |
| Realtime collection streams | ✅ | ❌ |
| Cached document reads | ✅ | ❌ |
Cloud Storage Support #
| Feature | Flutter | Dart |
|---|---|---|
| Upload files | ✅ | ✅ |
| Download files | ✅ | ✅ |
| Delete files | ❌ | ❌ |
| Get file metadata | ✅ | ✅ |
| Set file metadata | ✅ | ✅ |
| List files | ❌ | ❌ |
| Stream files | ❌ | ❌ |
| Generate download URLs | ❌ | ❌ |
| Generate upload URLs | ❌ | ❌ |
Setup #
Flutter #
Current implementation: fire_api_flutter
Initialize after Firebase:
import 'package:fire_api_flutter/fire_api_flutter.dart';
void main() {
FirebaseFirestoreDatabase.create();
FirebaseFireStorage.create();
}
Dart Server #
Current implementation: fire_api_dart
To use Firestore, run on Google Cloud or provide service-account credentials.
Useful environment variables for local development:
GCP_PROJECT=<project_id>GOOGLE_APPLICATION_CREDENTIALS=<path_to_service_account_key.json>
If you need a custom database name or custom authenticated client, use GoogleCloudFirestoreDatabase.create(...).
import 'package:fire_api_dart/fire_api_dart.dart';
void main() async {
await GoogleCloudFirestoreDatabase.create();
await GoogleCloudFireStorage.create();
}
Usage #
Documents #
final dan = FirestoreDatabase.instance.collection("user").doc("dan");
final danDoc = await dan.get();
if (danDoc.exists) {
final data = danDoc.data!;
print(data["name"]);
}
await dan.set({
"name": "Dan",
"age": 21,
});
await dan.update({
"likes": FieldValue.arrayUnion(["cats", "dogs"]),
"age": FieldValue.increment(1),
});
await dan.setAtomic((current) {
current!["age"]++;
return current;
});
await dan.delete();
Queries #
final users = FirestoreDatabase.instance.collection("user");
final allUsers = await users.get();
final adults = await users
.whereGreaterThanOrEqual("age", 18)
.orderBy("name")
.limit(10)
.get();
final under18Count = await users
.whereLessThan("age", 18)
.limit(100)
.count();
Vector Values #
VectorValue is the shared vector type for both adapters. Reads and writes convert recursively through nested maps and lists.
await FirestoreDatabase.instance.collection("items").doc("one").set({
"title": "Example",
"embedding": const VectorValue([0.2, 0.4, 0.6]),
"nested": {
"history": [
const VectorValue([1, 2, 3]),
],
},
});
final doc = await FirestoreDatabase.instance.collection("items").doc("one").get();
final embedding = doc.data!["embedding"] as VectorValue;
Vector Search #
Vector search is explicit and get-only. It is not part of the normal realtime query chain.
final results = await FirestoreDatabase.instance
.collection("items")
.whereEqual("color", "red")
.findNearest(
vectorField: "embedding_field",
queryVector: const VectorValue([3, 1, 2]),
limit: 5,
distanceMeasure: VectorDistanceMeasure.euclidean,
distanceResultField: "vector_distance",
distanceThreshold: 4.5,
)
.get();
for (final doc in results) {
print(doc.id);
print(doc.data?["vector_distance"]);
}
Notes:
- Use the
limitparameter onfindNearest(...)rather than calling.limit(...)before it. - Vector queries currently support
.get()only, not realtime listeners.
Collection Deletes #
deleteAll() is implemented in the shared package and works by:
- Counting the remaining documents
- Fetching and deleting up to
batchSizedocuments at a time - Repeating until the collection is empty
await FirestoreDatabase.instance
.collection("users")
.doc("dan")
.collection("sessions")
.deleteAll();
await FirestoreDatabase.instance
.collection("items")
.deleteAll(
only: {"a", "b", "c"},
batchSize: 50,
);
Notes:
batchSizedefaults to100only:lets you target a known set of document IDs- if every ID in
only:is already gone, the operation finishes early
Streams #
Realtime streams are Flutter-only:
final danStream = FirestoreDatabase.instance
.collection("user")
.doc("dan")
.stream;
final usersStream = FirestoreDatabase.instance
.collection("user")
.whereEqual("age", 25)
.limit(50)
.stream;
Firebase Storage #
final ref = FireStorage.instance
.bucket("my_bucket")
.ref("some/file");
final bytes = await ref.read();
await ref.write(bytes);
Notes #
- This is an unofficial wrapper around Firebase / Google Cloud APIs.
- Test carefully before using in production.