Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[ISSUE #6551] Minor review of the current advanced resource workflow implementation… #6552

Merged
merged 23 commits into from
Oct 25, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
23 commits
Select commit Hold shift + click to select a range
2a30a32
Minor review of the current advanced resource workflow implementation…
Oct 20, 2020
c7f651c
Fix tests on Travis
Oct 20, 2020
7a3d5d0
Fix logical errors on approval workflow
Oct 21, 2020
36cdccb
Fix tests on Travis
Oct 21, 2020
e7c8ee7
Advanced workflow: remove change_permissions to the owner if not a ma…
Oct 21, 2020
c08b189
Advanced workflow: remove change_permissions to the owner if not a ma…
Oct 22, 2020
b22998f
Advanced workflow: remove change_permissions to the owner if not a ma…
Oct 22, 2020
b9f5b0f
Advanced workflow: remove change_permissions to the owner if not a ma…
Oct 22, 2020
7380906
Advanced workflow: filter actions stream returned to the users accord…
Oct 22, 2020
e2522fd
Advanced workflow: filter actions stream returned to the users accord…
Oct 22, 2020
00f4be1
Add new settings from django-allauth 0.43.0
Oct 22, 2020
d4ac5cb
Code styling alerts: remove unnecessary pass
Oct 22, 2020
e1425b7
Refreshing static libs
Oct 22, 2020
6e5a177
Refreshing static libs
Oct 22, 2020
7ce0d0e
Merge branch 'master' of https://github.com/GeoNode/geonode into adv_…
Oct 22, 2020
beda3d2
Merge branch 'master' of https://github.com/GeoNode/geonode into adv_…
Oct 23, 2020
da39fe6
Advanced Workflow: Make sure the APIs counters are coherent with the …
Oct 23, 2020
dd3d81d
Advanced Workflow: fix "request editing" action when published
Oct 23, 2020
c3b1d78
Advanced Workflow: fix "request editing" action when published -> sen…
Oct 23, 2020
97fec58
Fix test on travis
Oct 23, 2020
6d9d456
Merge branch 'master' into adv_workflow_improvements
Oct 23, 2020
8509bf2
Merge branch 'master' into adv_workflow_improvements
Oct 24, 2020
f9edc03
Merge branch 'master' into adv_workflow_improvements
Oct 24, 2020
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 8 additions & 7 deletions geonode/api/api.py
Original file line number Diff line number Diff line change
Expand Up @@ -330,9 +330,8 @@ def dehydrate_member_count(self, bundle):
def dehydrate(self, bundle):
"""Provide additional resource counts"""
request = bundle.request
_user = request.user
counts = _get_resource_counts(
_user,
request,
resourcebase_filter_kwargs={
'group__groupprofile__categories': bundle.obj
}
Expand Down Expand Up @@ -408,11 +407,11 @@ class Meta:
def dehydrate(self, bundle):
"""Provide additional resource counts"""
request = bundle.request
_user = request.user
counts = _get_resource_counts(
_user,
request,
resourcebase_filter_kwargs={'group': bundle.obj}
)

bundle.data.update(resource_counts=counts)
return bundle

Expand Down Expand Up @@ -835,15 +834,15 @@ class StyleResource(GeoserverStyleResource):
pass


def _get_resource_counts(user, resourcebase_filter_kwargs):
def _get_resource_counts(request, resourcebase_filter_kwargs):
"""Return a dict with counts of resources of various types

The ``resourcebase_filter_kwargs`` argument should be a dict with a suitable
queryset filter that can be applied to select only the relevant
``ResourceBase`` objects to use when retrieving counts. For example::

_get_resource_counts(
user,
request,
{
'group__slug': 'my-group',
}
Expand All @@ -855,10 +854,12 @@ def _get_resource_counts(user, resourcebase_filter_kwargs):
"""
resources = get_visible_resources(
ResourceBase.objects.filter(**resourcebase_filter_kwargs),
user,
request.user,
request=request,
admin_approval_required=settings.ADMIN_MODERATE_UPLOADS,
unpublished_not_visible=settings.RESOURCE_PUBLISHING,
private_groups_not_visibile=settings.GROUP_PRIVATE_RESOURCES)

values = resources.values(
'polymorphic_ctype__model',
'is_approved',
Expand Down
4 changes: 2 additions & 2 deletions geonode/api/tests.py
Original file line number Diff line number Diff line change
Expand Up @@ -113,15 +113,15 @@ def test_layer_get_list_layer_private_to_one_user(self):
# with resource publishing
with self.settings(RESOURCE_PUBLISHING=True):
resp = self.api_client.get(self.list_url)
self.assertEqual(len(self.deserialize(resp)['objects']), 8)
self.assertEqual(len(self.deserialize(resp)['objects']), 0)

self.api_client.client.login(username='bobby', password='bob')
resp = self.api_client.get(self.list_url)
self.assertEqual(len(self.deserialize(resp)['objects']), 2)

self.api_client.client.login(username=self.user, password=self.passwd)
resp = self.api_client.get(self.list_url)
self.assertEqual(len(self.deserialize(resp)['objects']), 8)
self.assertEqual(len(self.deserialize(resp)['objects']), 0)

def test_layer_get_detail_unauth_layer_not_public(self):
"""
Expand Down
8 changes: 8 additions & 0 deletions geonode/base/models.py
Original file line number Diff line number Diff line change
Expand Up @@ -879,6 +879,10 @@ def save(self, notify=False, *args, **kwargs):
if settings.ADMIN_MODERATE_UPLOADS:
if self.is_approved and not self.is_published and \
self.__is_approved != self.is_approved:
# Set "approved" workflow permissions
self.set_workflow_perms(approved=True)

# Send "approved" notification
notice_type_label = '%s_approved' % self.class_name.lower()
recipients = get_notification_recipients(notice_type_label)
send_notification(recipients, notice_type_label, {'resource': self})
Expand All @@ -888,6 +892,10 @@ def save(self, notify=False, *args, **kwargs):
if not _notification_sent and settings.RESOURCE_PUBLISHING:
if self.is_approved and self.is_published and \
self.__is_published != self.is_published:
# Set "published" workflow permissions
self.set_workflow_perms(published=True)

# Send "published" notification
notice_type_label = '%s_published' % self.class_name.lower()
recipients = get_notification_recipients(notice_type_label)
send_notification(recipients, notice_type_label, {'resource': self})
Expand Down
29 changes: 17 additions & 12 deletions geonode/base/templatetags/base_tags.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,15 +19,15 @@
#########################################################################

from django import template

from pinax.ratings.models import Rating
from django.db.models import Q
from django.conf import settings
from django.db.models import Count
from django.utils.translation import ugettext
from django.contrib.contenttypes.models import ContentType
from django.contrib.auth import get_user_model
from django.db.models import Count
from django.conf import settings
from django.utils.translation import ugettext_lazy as _
from django.contrib.contenttypes.models import ContentType

from pinax.ratings.models import Rating
from guardian.shortcuts import get_objects_for_user

from geonode.base.models import ResourceBase
Expand All @@ -45,11 +45,11 @@
register = template.Library()

FACETS = {
'raster': 'Raster Layer',
'vector': 'Vector Layer',
'vector_time': 'Vector Temporal Serie',
'remote': 'Remote Layer',
'wms': 'WMS Cascade Layer'
'raster': _('Raster Layer'),
'vector': _('Vector Layer'),
'vector_time': _('Vector Temporal Serie'),
'remote': _('Remote Layer'),
'wms': _('WMS Cascade Layer')
}


Expand Down Expand Up @@ -344,8 +344,13 @@ def get_visibile_resources(user):
@register.simple_tag
def display_edit_request_button(resource, user, perms):
def _has_owner_his_permissions():
return (set(resource.BASE_PERMISSIONS.get('owner') + resource.BASE_PERMISSIONS.get('write')) - set(
perms)) == set()
_owner_set = set(resource.BASE_PERMISSIONS.get('owner') +
resource.BASE_PERMISSIONS.get('read') +
resource.BASE_PERMISSIONS.get('write') +
resource.BASE_PERMISSIONS.get('download')) - \
set(perms)
return _owner_set == set() or \
_owner_set == set(['change_resourcebase_permissions', 'publish_resourcebase'])

if not _has_owner_his_permissions() and resource.owner.pk == user.pk:
return True
Expand Down
4 changes: 2 additions & 2 deletions geonode/base/tests.py
Original file line number Diff line number Diff line change
Expand Up @@ -775,12 +775,12 @@ def test_get_concrete_resource(self):
@override_settings(ADMIN_MODERATE_UPLOADS=True)
def test_msg_recipients_admin_mode(self):
users_count = 1
self.assertEqual(users_count, OwnerRightsRequestViewUtils.get_message_recipients().count())
self.assertEqual(users_count, OwnerRightsRequestViewUtils.get_message_recipients(self.user).count())

@override_settings(ADMIN_MODERATE_UPLOADS=False)
def test_msg_recipients_workflow_off(self):
users_count = 0
self.assertEqual(users_count, OwnerRightsRequestViewUtils.get_message_recipients().count())
self.assertEqual(users_count, OwnerRightsRequestViewUtils.get_message_recipients(self.user).count())


class TestGetVisibleResource(TestCase):
Expand Down
36 changes: 31 additions & 5 deletions geonode/base/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -138,11 +138,28 @@ def configuration_session_cache(session):
class OwnerRightsRequestViewUtils:

@staticmethod
def get_message_recipients():
def get_message_recipients(owner):
User = get_user_model()
allowed_users = User.objects.none()
if OwnerRightsRequestViewUtils.is_admin_publish_mode():
allowed_users |= User.objects.filter(is_superuser=True)
allowed_users |= User.objects.filter(is_superuser=True).exclude(pk=owner.pk)
try:
from geonode.groups.models import GroupProfile
groups = owner.groups.all()
obj_group_managers = []
for group in groups:
try:
group_profile = GroupProfile.objects.get(slug=group.name)
managers = group_profile.get_managers()
for manager in managers:
if manager not in obj_group_managers and not manager.is_superuser:
obj_group_managers.append(manager)
except GroupProfile.DoesNotExist:
pass
allowed_users |= User.objects.filter(id__in=[_u.id for _u in obj_group_managers])
except Exception:
pass

return allowed_users

@staticmethod
Expand Down Expand Up @@ -180,14 +197,23 @@ def _disable_owner_write_permissions(self):
remove_perm(perm, self.resource.owner, self.resource)

for perm in self.resource.BASE_PERMISSIONS.get('read') + self.resource.BASE_PERMISSIONS.get('download'):
assign_perm(perm, self.resource.owner, self.resource.get_self_resource())
if not settings.RESOURCE_PUBLISHING and not settings.ADMIN_MODERATE_UPLOADS:
assign_perm(perm, self.resource.owner, self.resource.get_self_resource())
elif perm not in ['change_resourcebase_permissions', 'publish_resourcebase']:
assign_perm(perm, self.resource.owner, self.resource.get_self_resource())

def _restore_owner_permissions(self):

for perm_list in self.resource.BASE_PERMISSIONS.values():
for perm in perm_list:
assign_perm(perm, self.resource.owner, self.resource.get_self_resource())
if not settings.RESOURCE_PUBLISHING and not settings.ADMIN_MODERATE_UPLOADS:
assign_perm(perm, self.resource.owner, self.resource.get_self_resource())
elif perm not in ['change_resourcebase_permissions', 'publish_resourcebase']:
assign_perm(perm, self.resource.owner, self.resource.get_self_resource())

for perm_list in self.resource.PERMISSIONS.values():
for perm in perm_list:
assign_perm(perm, self.resource.owner, self.resource)
if not settings.RESOURCE_PUBLISHING and not settings.ADMIN_MODERATE_UPLOADS:
assign_perm(perm, self.resource.owner, self.resource)
elif perm not in ['change_resourcebase_permissions', 'publish_resourcebase']:
assign_perm(perm, self.resource.owner, self.resource)
8 changes: 4 additions & 4 deletions geonode/base/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -248,17 +248,17 @@ def post(self, request, *args, **kwargs):
if form.is_valid():
reason = form.cleaned_data['reason']
notice_type_label = 'request_resource_edit'
recipients = OwnerRightsRequestViewUtils.get_message_recipients()
recipients = OwnerRightsRequestViewUtils.get_message_recipients(self.resource.owner)

Message.objects.new_message(
from_user=request.user,
to_users=recipients,
subject=_('System message: A request to modify resource'),
content=_('The resource owner has requested to modify the resource') + '.'
content=_('The resource owner has requested to modify the resource') + '.\n'
' ' +
_('Resource title') + ': ' + self.resource.title + '.'
_('Resource title') + ': ' + self.resource.title + '.\n'
' ' +
_('Reason for the request') + ': "' + reason + '".' +
_('Reason for the request') + ': "' + reason + '".\n' +
' ' +
_('To allow the change, set the resource to not "Approved" under the metadata settings' +
'and write message to the owner to notify him') + '.'
Expand Down
7 changes: 3 additions & 4 deletions geonode/documents/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -549,10 +549,6 @@ def document_metadata(

if settings.ADMIN_MODERATE_UPLOADS:
if not request.user.is_superuser:
if settings.RESOURCE_PUBLISHING:
document_form.fields['is_published'].widget.attrs.update(
{'disabled': 'true'})

can_change_metadata = request.user.has_perm(
'change_resourcebase_metadata',
document.get_self_resource())
Expand All @@ -561,6 +557,9 @@ def document_metadata(
except Exception:
is_manager = False
if not is_manager or not can_change_metadata:
if settings.RESOURCE_PUBLISHING:
document_form.fields['is_published'].widget.attrs.update(
{'disabled': 'true'})
document_form.fields['is_approved'].widget.attrs.update(
{'disabled': 'true'})

Expand Down
13 changes: 10 additions & 3 deletions geonode/geoserver/createlayer/utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,12 +17,12 @@
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#
#########################################################################

import requests
import json
import uuid
import logging
import json
import requests

from django.conf import settings
from django.contrib.auth import get_user_model
from django.contrib.gis.geos import Polygon
from django.template.defaultfilters import slugify
Expand Down Expand Up @@ -77,6 +77,13 @@ def create_gn_layer(workspace, datastore, name, title, owner_name):
bbox_polygon=Polygon.from_bbox(BBOX),
data_quality_statement=DATA_QUALITY_MESSAGE,
)

if settings.ADMIN_MODERATE_UPLOADS:
layer.is_approved = False
if settings.RESOURCE_PUBLISHING:
layer.is_published = False

layer.save()
return layer


Expand Down
2 changes: 1 addition & 1 deletion geonode/geoserver/createlayer/views.py
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ def layer_create(request, template='createlayer/layer_create.html'):
attributes = form.cleaned_data['attributes']
permissions = form.cleaned_data["permissions"]
layer = create_layer(name, title, request.user.username, geometry_type, attributes)
layer.set_permissions(json.loads(permissions))
layer.set_permissions(json.loads(permissions), created=True)
return redirect(layer)
except Exception as e:
error = '%s (%s)' % (e, type(e))
Expand Down
Loading