Firebase Firestore implementation for Micropython.
Firebase implementation based on REST API, based on micropython-firebase-realtime-database from ckoever.
You can use uPip to install library from PyPi
import upip
upip.install("micropython-firebase-firestore")
or you can just upload ufirestore/ufirestore.py
to your microcontroller:
python pyboard.py -d PORT -f cp ufirestore.py :
- set_project_id
- set_access_token
- patch
- create
- get
- getfile
- delete
- list
- list_collection_ids
- run_query
ujson, urequests, _thread
import time
import network
wlan = network.WLAN(network.STA_IF)
wlan.active(True)
if not wlan.isconnected():
wlan.connect("ssid", "pass")
print("Waiting for Wi-Fi connection", end="...")
while not wlan.isconnected():
print(".", end="")
time.sleep(1)
print()
Reads a field from a stored document
import ufirestore
ufirestore.set_project_id("INSERT_PROJECT_ID")
ufirestore.set_access_token("INSERT_ACCESS_TOKEN")
raw_doc = ufirestore.get("DOCUMENT_PATH")
doc = FirebaseJson.from_raw(raw_doc)
if doc["fields"].exists("FIELD"):
print("The field value is: %s" % doc["fields"].get("FIELD"))
The project ID is required, read about it here
or you can find it at Project Settings > General
in your project's console
The access token is obtained from the Firebase Auth API, which can be harnessed with my auth library, or reading can be done here
ufirestore.set_project_id("INSERT_PROJECT_ID")
Set the ID of your Firebase project
ufirestore.set_access_token("INSERT_ACCESS_TOKEN")
Sets the access token to use for authentication
ufirestore.patch(PATH, DOC, update_mask=[], bg=True, cb=None)
Updates or inserts a document DOC
at the location PATH
- Set the fields to update with
update_mask
- Optional run in the background with
bg
- Set a callback function after getting data with
cb
doc = FirebaseJson()
doc.set("age/integerValue", 21)
response = ufirestore.patch("users/234", doc, ["age"], False)
print(response)
ufirestore.create(PATH, DOC, document_id=None, bg=True, cb=None)
Creates a new document DOC
at the collection at location PATH
document_id
- The document ID to use for the document. If not specified, an ID will be generated- Optional run in the background with
bg
- Set a callback function after getting data with
cb
doc = FirebaseJson()
doc.set("name/stringValue", "Jane Doe")
doc.set("age/integerValue", 25)
doc.set("height/integerValue", 165)
response = ufirestore.create("users", doc, bg=False)
print(response)
ufirestore.get(PATH, mask=None, bg=True, cb=None)
Gets a single document at location PATH
document_id
- The document ID to use for the document. If not specified, an ID will be generatedmask
- The fields to return- Optional run in the background with
bg
- Set a callback function after getting data with
cb
response = ufirestore.get("users/129", bg=False)
doc = FirebaseJson.from_raw(response)
if doc.exists("fields/name"):
print("Hello, %s" % doc.get("fields/name"))
ufirestore.getfile(PATH, FILENAME, mask=None, bg=True, cb=None)
Gets a single document at location PATH
and writes it to file FILENAME
document_id
- The document ID to use for the document. If not specified, an ID will be generatedmask
- The fields to return- Optional run in the background with
bg
- Set a callback function after getting data with
cb
ufirestore.getfile("users/129", "user.json")
ufirestore.delete(PATH, bg=True, cb=None)
Deletes a document at location PATH
- Optional run in the background with
bg
- Set a callback function after getting data with
cb
success = ufirestore.delete("users/129")
if success:
print("User data successfully deleted.")
ufirestore.list(PATH, page_size=None, page_token=None, order_by=None, mask=None, show_missing=None, bg=True, cb=None)
Lists documents at location PATH
page_size
- The number of documents to returnpage_token
- Thenext_page_token
returned from a previouslist
optionorder_by
- The order to sort results by. For example:priority desc, name
mask
- The fields to return. If not set, return all fieldsshow_missing
- If the list should show missing documents- Optional run in the background with
bg
- Set a callback function after getting data with
cb
documents, next_page_token = ufirestore.list("users", bg=False)
for document in documents:
doc = FirebaseJson.from_raw(document)
if doc.exists("fields/age"):
print("Age: %s" % doc.get("fields/age"))
ufirestore.list_collection_ids(PATH, page_size=None, page_token=None, bg=True, cb=None)
Lists all the collection IDs underneath a document at PATH
page_size
- The maximum number of results to returnpage_token
- A page token- Optional run in the background with
bg
- Set a callback function after getting data with
cb
collection_ids, next_page_token = ufirestore.list_collection_ids("rooms/28", bg=False)
for collection_id in collection_ids:
print("ID: %s" % collection_id)
ufirestore.run_query(PATH, query, bg=True, cb=None)
Runs a query at location PATH
- Optional run in the background with
bg
- Set a callback function after getting data with
cb
from ufirestore.json import FirebaseJson, Query
query = Query().from_("users").where("age", ">=", 18)
raw_doc = ufirestore.run_query("", query, bg=False)
doc = FirebaseJson.from_raw(raw_doc)
if doc.exists("fields/name"):
print("Resulted with user named %s" % doc.get("fields/name"))
A simple helper class for Firebase document JSON data
doc.set(path, value, with_type=False)
Edit, overwrite or create new node at the specified path
with_type
- If set toTrue
, the value's type will be inferred and applied accordingly, as per a Firestore Document Value
doc.get(path, default=None)
Get the node value at a given path, returning default
if the path does not exist
doc.add(path, name, value)
Add a new node at the path, with name name
and contents value
doc.add_item(path, value)
Adds an array item to the node at the path
doc.remove(path)
Removes the node at the path
doc.exists(path)
Checks whether a node exists at the path
doc.process(resource_name)
Processes json instance into a dict
for usage with Firestore API
NOTE: All the functions in this library that require a document actually require the FirebaseJon
instance and runs process
behind the scenes
FirebaseJson.from_raw(raw_doc)
Parses a raw document object from the Firestore API into a FirebaseJson
instance
FirebaseJson.to_value_type(value)
Infers the type of value
and returns a dict
in the format of a Firestore Document Value
value = 35
data = FirebaseJson.to_value_type(value)
print(data) # Returns {"integerValue": "35"}
FirebaseJson.from_value_type(value)
Takes a Firestore Document Value object and returns its value, casted to the correct type
# Example data from API
data = {
"arrayValue": {
"values": [
{"stringValue": "a"},
{"stringValue": "b"},
{"integerValue": "3"}
]
}
}
print(value) # Returns ["a", "b", 3]
Wrapper over FirebaseJson
to easily create document queries
Extends all FirebaseJson
methods
query.from_(collection_id, all_descendants=False)
collection_id
- When set, selects only collections with this IDall_descendants
- WhenTrue
, selects all descendant collections, whenFalse
, selects collections that are immediate children of theparent
the query will be run on
query.select(field)
Adds a document field to return
query.order_by(field, direction="DESCENDING")
field
- The field to order bydirection
- The direction to order by (ASCENDING
orDESCENDING
)
query.limit(value)
The maximum number of results to return, value
must be >= 0
query.where(field, op, value)
Applies a filter on a specific field.
field
- The field to filter byop
- The operation to filter by, is one of<
,<=
,>
,>=
,==
,!=
,array-contains
,in
,array-contains-any
,not-in
value
- The value to compare to, type is inferred withFirebaseJson.to_value_type
query.process()
Returns dict
data of query for use with Firestore API
NOTE: This function is already used in the run_query
function