Async MongoDB wrapper over motor with a raw escape hatch
Go to file
2026-06-29 18:07:41 -04:00
src/mongo fix: matched_count for idempotent updates; document drop-on-missing-key (v0.1.2) 2026-06-29 17:58:26 -04:00
.gitignore mongodb wrapper in py 2026-06-22 21:26:40 -04:00
pyproject.toml fix: matched_count for idempotent updates; document drop-on-missing-key (v0.1.2) 2026-06-29 17:58:26 -04:00
README.md docs: show unpinned install line; note tag-pinning for reproducibility 2026-06-29 18:07:41 -04:00

mongo

Async MongoDB wrapper over motor. Thin, opinionated helpers for the common paths, with a raw escape hatch for everything else.

Install

requirements.txt:

mongo @ git+ssh://git@git.rethinkstudios.io/rethink-public/mongo.git

Direct:

pip install "mongo @ git+ssh://git@git.rethinkstudios.io/rethink-public/mongo.git"

Requires motor and pymongo (pulled transitively).

Usage

Object (preferred) — one client per process:

from mongo import Mongo

db = Mongo(conn_string, database)          # attach as bot.db / app.db
users = await db.get_documents("users", {"active": True})
db.close()                                  # on shutdown (sync)

Module proxy (back-compat) — arm once, then call bare:

import mongo                                # NOT `from mongo import ...`
mongo.init(conn_string, database)
users = await mongo.get_documents("users", {"active": True})

Both styles share one client. The proxy exists so legacy call sites keep working after a one-line init(); new code should use the object.

Error contract

  • Wrapped methods log-and-swallow exceptions and return a safe default (False / [] / {} / 0 / None). Branch on the result.
  • db.collection(name) (or db[name]) returns the raw motor collection: full driver surface, no swallowing, raises. Use it for anything not wrapped (find_one_and_* beyond what's exposed, change streams, complex bulk ops).

API

See the module docstring and method docstrings in mongo.py — that's the source of truth. Grouped as: collection/index management, create, read, update, delete, bulk, checks. Atomic ops (find_one_and_update/replace/delete) and bulk_write are included.

Gotchas

  • from mongo import func won't see the proxy (resolved at import, before init). Use import mongo then mongo.func(...).
  • find_one_and_update returns the after image by default (return_after=True).
  • bulk_write takes pymongo ops the caller builds:
    from pymongo import UpdateOne
    ops = [UpdateOne({"_id": i}, {"$set": {...}}, upsert=True) for i in ids]
    await db.bulk_write("col", ops)
    

Versioning

Releases are tagged vX.Y.Z. The install line above is unpinned and tracks the latest on the default branch; append @vX.Y.Z to pin a specific release for reproducible installs.