K
K
kazmiruk2012-10-09 10:54:09
Python
kazmiruk, 2012-10-09 10:54:09

How to get around the lack of transactions in MongoDB?

There is a project, the main essence of which is e-commerce. The whole structure fits perfectly into mongodb, given its schemaless nature. But there are problems with understanding the implementation of transactionality in this project. Mongo does not support transactions. It is necessary to solve the following tasks:
- transfer of money from A to B with checks and rollbacks;
- purchase of goods (leaves the warehouse and comes to the user in orders, and so that 2 users do not buy the last product from the warehouse, and the owner of the product does not have time to change the price while the user was buying (relatively speaking, a lock on the product))
I searched the Internet and found several solutions to this problem:
1. Implementation of a two-phase commit at the application level (from Cookbook mongoDB). The method is good for everyone, but already for two entities, fancy checks are obtained, in which it is easy to get confused and the code turns out to be completely non-universal, since rollbacks have to be done manually.
2. Transfer everything that requires a transaction to the RDBMS. That is, there is a collection of products in mongo and there is a warehouse table that contains the id of the product from mongo and the quantity of this product (simplified). This option is repulsive because there will be a need to split entities into several parts and, moreover, store these entities in different DBMS. And keeping the DBMS zoo for one project does not seem to be the right decision.

Who faced similar problems and somehow solved it - share your experience.

Answer the question

In order to leave comments, you need to log in

3 answer(s)
A
Alexey Huseynov, 2012-10-09
@kibergus

- transfer of money from A to B with checks and kickbacks;

Just don't use mongodb for this. Will not work. mongo is written to store non -valuable data, the loss of which is of little interest to anyone. Therefore, for example, mongo by default returns success immediately, without waiting for a write to the database.
- purchase of goods (leaves the warehouse and comes to the user in orders, and so that 2 users do not buy the last product from the warehouse, and the owner of the product does not have time to change the price while the user was buying (relatively speaking, a lock on the product))

This can most likely be done with atomic operations. But if necessary, locks are organized using the "blocked until" field, a unique index on the product id and requests like
upsert("object with the blocking time field set", "blocking time is less than the current time")
If there is no lock yet, then it will be created . If the lock exists but is expired (the process that captured it has crashed), then the request will update such a record. If the lock is captured, then the query will try to create a new lock, but will fail due to a duplicate key in the index.

J
Juralis, 2012-10-09
@Juralis

As I understand it, mongodb is good here precisely in the sense that it is possible to set profile properties for different types of goods and not describe them in advance. And there is a certain set of properties inherent in all goods (like quantity, cost, etc.). In that sense, you would indeed be more comfortable removing these generic properties from the RDBMS, and this task is clearly not up to mongodb.
I didn’t use it myself, but judging by the announcement of PostgreSQL 9.2, it supports json field and it might be suitable for such a task.
But, it seems there are some difficulties with searching by the data of this field.
For example, here is a question (with a solution) on stackoverflow:
stackoverflow.com/questions/10560394/how-do-i-query-using-fields-inside-the-new-postgresql-json-datatype

S
Stdit, 2012-10-09
@Stdit

Yes, two-phase commits, storage and verification of transaction states or versions of objects (documents). MongoDB is not designed for such tasks, even the developers themselves say so. It's just a fast and scalable storage of objects of arbitrary structure with flexible search. Use an RDBMS. As Juralis correctly noted , the same PostgreSQL has rich and interesting features, such as table inheritance, working with arrays and other data types that are not typical for SQL. They may be suitable for your needs.

Didn't find what you were looking for?

Ask your question

Ask a Question

731 491 924 answers to any question