Skip to main content

Provides object-level commit hooks for SQLAlchemy

Project description

Overview

sqlalchemy_commithooks allows actions to be deferred until commit time. It also allows for objects to take action if a commit fails.

This is useful for maintaining consistency with external systems, for example:

  • sending events
  • s3 synchronization
  • redis queue synchronization

sqlalchemy_commithooks requires Python >=3.6. This would be hard (impossible?) to get around without changing the API or modifying sqlalchemy.

There is no overhead if a commit hook is unused.

Getting Started

Use sqlalchemy_commithooks.Session instead of sqlalchemy.orm.Session. SessionMixin is also defined, if you are already subclassing Session:

session = sqlalchemy_commithooks.Session()

Add sqlalchemy_commithooks.CommitMixin to your mapped class and use any of 9 hooks:

class Data(Base, sqlalchemy_commithooks.CommitMixin):
    def before_commit_from_insert(self):
        pass

The hooks are available for all combinations of (before, after, failed) and (insert, update, delete).

Simply override methods like before_commit_from_insert, failed_commit_from_insert, after_commit_from_delete etc.

Usage Notes

before_commit_* will always fire, and one of after_commit_* or failed_commit_* will fire, assuming two conditions are met.

  1. You handle your own exceptions in your *_commit_from_* handlers.
  2. You are using sqlalchemy's recommended transaction semantics (commit/rollback).

If an object is inserted (flushed), updated (flushed), deleted (flushed) and then commit is called, insert/update/delete methods will execute (in that order) even though the object will not persist after the commit.

Updates in before_commit_* will be applied, but will not cascade/trigger any *_commit_from_* calls.

Limitations

sqlalchemy_commithooks cannot solve all problems. As an example, it is not perfectly robust against network outages:

DB.add(mapped_object)
DB.commit()
#  before_commit_from_insert is run, puts an object into s3
#  network outage occurs now
#  actual commit to DB fails (network outage)
#  failed_commit_from_insert is run, fails to remove object from s3

For each use case, you must determine what has priority.

Should an notification be sent if the DB commit fails (notification is sent, then network outage preventing full commit)? Or should an event notification possibly not be sent if the commit succeeds (transaction is committed, network outage prevents notification)?

TODO

  • add session.nested_transaction support
  • add cascade option
  • make it easy to see which hooks will run in the debugger

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

sqlalchemy_commithooks-1.2.8.tar.gz (9.1 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

sqlalchemy_commithooks-1.2.8-py2.py3-none-any.whl (7.9 kB view details)

Uploaded Python 2Python 3

File details

Details for the file sqlalchemy_commithooks-1.2.8.tar.gz.

File metadata

File hashes

Hashes for sqlalchemy_commithooks-1.2.8.tar.gz
Algorithm Hash digest
SHA256 14536617d66f08c095f9abd629f205451e8d105d551f6537d0e98c5d5665eb75
MD5 2b39d0c3a3647cfb420c7a6971740f00
BLAKE2b-256 8feb74a2fde687c8335419ddfa8239a56c7433a4df30bee1a60c1721594351a3

See more details on using hashes here.

File details

Details for the file sqlalchemy_commithooks-1.2.8-py2.py3-none-any.whl.

File metadata

File hashes

Hashes for sqlalchemy_commithooks-1.2.8-py2.py3-none-any.whl
Algorithm Hash digest
SHA256 1fcb5746791b45cea2a2556b98860f31f8509926a84695a25260ec04e5ac6576
MD5 506f009b773a2bef84bcff630fe87661
BLAKE2b-256 66c302695f707e95740d9acfea4354a271d023c3d2a81195a3d7806807a0557f

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page