Tuesday, November 25, 2014

Re: Preventing race conditions when submitting forms

+1 - conflict resolution is not an easy task, and really depends on your business logic/use case.

It's worth mentioning that the approach django-concurrency uses may not be suitable for your use case, and in my opinion implementing this restriction on a per model basis is not the best approach, especially when handling multiple model scenarios. Also the implementation of django-concurrency is "dumb", if you look at the example it blocks two save() calls despite no fields being changed on them, and I suspect it doesn't attempt to do any sort of checks to see if the updates would have conflicted. This in itself would be enough reason to stay away from the library (if I'm mistaken, let me know).

django-locking is even worse, it uses a shotgun approach of locking the entire model.. I've used systems (as a user) in the past which implement a similar locking system, and they are a UX anti pattern (imho).

Also remember that representing conflicts in the UI is quite important, having an error at the top of the page telling you that a field conflicted really is quite ghetto and doesn't give a good user experience.. Trello handles this nicely, but they put a lot of time/effort into making the whole process seamless.

The above doesn't really answer your original question of "what can I do", but I hope it gives you some insight into the downsides of those other options.

Cal

On Tue, Nov 25, 2014 at 9:10 PM, Simon Charette <charette.s@gmail.com> wrote:
I can't think of a generic way of solving conflict resolution. I'd say it's highly application specific.

Le mardi 25 novembre 2014 15:06:53 UTC-5, Paul Johnston a écrit :
Tim, Simon,

Thanks for the responses. Looks like django-concurrency is a good fit, and it works the way Tim suggested (so no need to write your own mixins!)

One follow-up question: do you have any ideas for conflict resolution? The django-concurrency resolution is pretty basic, but it would be a lot of work to do something better.

Paul


On Tuesday, November 25, 2014 6:59:15 PM UTC, Tim Chase wrote:
On 2014-11-25 07:57, Paul Johnston wrote:
> Consider an e-commerce site, where Alice and Bob are both editing
> the product listings. Alice is improving descriptions, while Bob is
> updating prices. They start editing the Acme Wonder Widget at the
> same time. Bob finishes first and saves the product with the new
> price. Alice takes a bit longer to update the description, and when
> she finishes, she saves the product with her new description.
> Unfortunately, she also overwrites the price with the old price,
> which was not intended.

The common solution in this case your model would have something like
a "last_modified_timestamp" or "last_modified_counter".  This would
be sent with the form and then resubmitted back.  If the
timestamp/counter is the same, you know it's safe to update the
timestamp or increment the counter (done within the transaction to
ensure atomicity).  If it's *not* the same timestamp/counter as it was
when the form was created, you know that it's been modified in the
interim and you can present a conflict-resolution form.

I don't think Django has anything like this out of the box, but it's
fairly straightforward to implement.  I've done it enough times that
I should just create some model/form mixin to handle it for me.

-tkc



--
You received this message because you are subscribed to the Google Groups "Django users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to django-users+unsubscribe@googlegroups.com.
To post to this group, send email to django-users@googlegroups.com.
Visit this group at http://groups.google.com/group/django-users.
To view this discussion on the web visit https://groups.google.com/d/msgid/django-users/1c0c9322-65cc-4c1d-a3bb-e8c80428d0f2%40googlegroups.com.

For more options, visit https://groups.google.com/d/optout.

--
You received this message because you are subscribed to the Google Groups "Django users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to django-users+unsubscribe@googlegroups.com.
To post to this group, send email to django-users@googlegroups.com.
Visit this group at http://groups.google.com/group/django-users.
To view this discussion on the web visit https://groups.google.com/d/msgid/django-users/CAHKQagEaWY0ASiYsfxnqHadbCQvP12eomRJTtMzNaAfLVUqEaA%40mail.gmail.com.
For more options, visit https://groups.google.com/d/optout.

No comments:

Post a Comment