direct editing
This commit is contained in:
parent
df19daf501
commit
1caa730fc4
4 changed files with 67 additions and 9 deletions
|
@ -9,7 +9,7 @@ from django.apps import apps
|
|||
from django.conf import settings
|
||||
from django.core.cache import cache
|
||||
from django.core.exceptions import FieldDoesNotExist
|
||||
from django.db import models, transaction
|
||||
from django.db import connection, models, transaction
|
||||
from django.db.models import Q
|
||||
from django.urls import reverse
|
||||
from django.utils.http import int_to_base36
|
||||
|
@ -69,6 +69,8 @@ class ChangeSet(models.Model):
|
|||
self._request = None
|
||||
self._original_state = self.state
|
||||
|
||||
self.direct_editing = False
|
||||
|
||||
"""
|
||||
Get Changesets for Request/Session/User
|
||||
"""
|
||||
|
@ -111,6 +113,8 @@ class ChangeSet(models.Model):
|
|||
|
||||
changeset = ChangeSet()
|
||||
changeset._request = request
|
||||
if request.session.get('direct_editing', False) and ChangeSet.can_direct_edit(request):
|
||||
changeset.direct_editing = True
|
||||
|
||||
if request.user.is_authenticated:
|
||||
changeset.author = request.user
|
||||
|
@ -124,10 +128,15 @@ class ChangeSet(models.Model):
|
|||
if isinstance(model, str):
|
||||
model = apps.get_model('mapdata', model)
|
||||
assert isinstance(model, type) and issubclass(model, models.Model)
|
||||
if self.direct_editing:
|
||||
model.EditorForm = ModelWrapper(self, model).EditorForm
|
||||
return model
|
||||
return ModelWrapper(self, model)
|
||||
|
||||
def wrap_instance(self, instance):
|
||||
assert isinstance(instance, models.Model)
|
||||
if self.direct_editing:
|
||||
return instance
|
||||
return self.wrap_model(instance.__class__).create_wrapped_model_class()(self, instance)
|
||||
|
||||
def relevant_changed_objects(self) -> typing.Iterable[ChangedObject]:
|
||||
|
@ -399,17 +408,24 @@ class ChangeSet(models.Model):
|
|||
@contextmanager
|
||||
def lock_to_edit(self, request=None):
|
||||
with transaction.atomic():
|
||||
user = request.user if request is not None and request.user.is_authenticated else None
|
||||
if self.pk is not None:
|
||||
changeset = ChangeSet.objects.select_for_update().get(pk=self.pk)
|
||||
|
||||
self._object_changed = False
|
||||
yield changeset
|
||||
user = request.user if request is not None and request.user.is_authenticated else None
|
||||
if self._object_changed:
|
||||
update = changeset.updates.create(user=user, objects_changed=True)
|
||||
changeset.last_update = update
|
||||
changeset.last_change = update
|
||||
changeset.save()
|
||||
elif self.direct_editing:
|
||||
with MapUpdate.lock():
|
||||
queries_before = len(connection.queries)
|
||||
yield self
|
||||
if any((q['sql'].startswith('UPDATE') or q['sql'].startswith('INSERT') or
|
||||
q['sql'].startswith('DELETE')) for q in connection.queries[queries_before:]):
|
||||
MapUpdate.objects.create(user=user, type='direct_edit')
|
||||
else:
|
||||
yield self
|
||||
|
||||
|
@ -433,6 +449,11 @@ class ChangeSet(models.Model):
|
|||
# todo implement permissions
|
||||
return self.is_author(request)
|
||||
|
||||
@classmethod
|
||||
def can_direct_edit(self, request):
|
||||
# todo implement permissions
|
||||
return request.user.is_authenticated
|
||||
|
||||
def can_start_review(self, request):
|
||||
return self.can_review(request) and self.state in ('proposed', 'reproposed')
|
||||
|
||||
|
@ -609,6 +630,8 @@ class ChangeSet(models.Model):
|
|||
Get “%d changed objects” display text.
|
||||
"""
|
||||
if self.pk is None:
|
||||
if self.direct_editing:
|
||||
return _('Direct editing active')
|
||||
return _('No objects changed')
|
||||
return (ungettext_lazy('%(num)d object changed', '%(num)d objects changed', 'num') %
|
||||
{'num': self.changed_objects_count})
|
||||
|
|
|
@ -1,7 +1,13 @@
|
|||
{% load i18n %}
|
||||
|
||||
<ul class="nav navbar-nav navbar-right">
|
||||
<li><a href="{{ request.changeset.get_absolute_url }}">{{ request.changeset.count_display }}</a></li>
|
||||
<li><a href="{{ request.changeset.get_absolute_url }}">
|
||||
{% if request.changeset.direct_editing %}
|
||||
<span class="text-warning">{{ request.changeset.count_display }}</span>
|
||||
{% else %}
|
||||
{{ request.changeset.count_display }}
|
||||
{% endif %}
|
||||
</a></li>
|
||||
{% if request.user.is_authenticated %}
|
||||
<li class="logged_in_user">
|
||||
<a href="{% url 'editor.users.detail' pk=request.user.pk %}">{{ request.user.username }}</a>
|
||||
|
|
|
@ -23,9 +23,26 @@
|
|||
<button type="submit" class="btn btn-xs btn-default" name="deactivate_changeset" value="1">{% trans 'Deactivate change set' %}</button>
|
||||
</form>
|
||||
{% endwith %}
|
||||
{% elif request.changeset.direct_editing %}
|
||||
<p>
|
||||
{% trans 'Direct editing is activated.' %}<br>
|
||||
{% trans 'Everything you do will be applied immediately.' %}
|
||||
</p>
|
||||
<form method="post" action="{{ request.path }}">
|
||||
{% csrf_token %}
|
||||
<button type="submit" class="btn btn-xs btn-warning" name="direct_editing" value="0">{% trans 'Deactivate direct editing' %}</button>
|
||||
</form>
|
||||
{% else %}
|
||||
{% trans 'You have currently no active change set.' %}<br>
|
||||
{% trans 'Just edit something to create one.' %}
|
||||
<p>
|
||||
{% trans 'You have currently no active change set.' %}<br>
|
||||
{% trans 'Just edit something to create one.' %}
|
||||
</p>
|
||||
{% if can_direct_edit %}
|
||||
<form method="post" action="{{ request.path }}">
|
||||
{% csrf_token %}
|
||||
<button type="submit" class="btn btn-xs btn-warning" name="direct_editing" value="1">{% trans 'Activate direct editing' %}</button>
|
||||
</form>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
|
||||
|
|
|
@ -14,13 +14,25 @@ def user_detail(request, pk):
|
|||
user = get_object_or_404(User, pk=pk)
|
||||
|
||||
if request.method == 'POST':
|
||||
if request.POST.get('deactivate_changeset') == '1' and request.user == user and 'changeset' in request.session:
|
||||
request.session.pop('changeset', None)
|
||||
messages.success(request, _('You deactivated your current changeset.'))
|
||||
return redirect(request.path)
|
||||
if request.user == user and 'changeset' in request.session:
|
||||
if request.POST.get('deactivate_changeset') == '1':
|
||||
request.session.pop('changeset', None)
|
||||
messages.success(request, _('You deactivated your current changeset.'))
|
||||
return redirect(request.path)
|
||||
|
||||
if request.changeset.pk is None and ChangeSet.can_direct_edit(request):
|
||||
if request.POST.get('direct_editing') == '1':
|
||||
request.session['direct_editing'] = True
|
||||
messages.success(request, _('You activated direct editing.'))
|
||||
return redirect(request.path)
|
||||
elif request.POST.get('direct_editing') == '0':
|
||||
request.session.pop('direct_editing', None)
|
||||
messages.success(request, _('You deactivated direct editing.'))
|
||||
return redirect(request.path)
|
||||
|
||||
ctx = {
|
||||
'user': user,
|
||||
'can_direct_edit': ChangeSet.can_direct_edit(request),
|
||||
'recent_changesets': ChangeSet.objects.filter(author=user).order_by('-last_update')[:10],
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue