Remove concept of ownership from folders by removing the user field.

"Ownership" now is now determined by ACL of a folder, like the rest of the objects in the system.
This commit is contained in:
Roberto Rosario
2016-03-08 01:20:10 -04:00
parent 74fd47d86e
commit 1c65b389ee
11 changed files with 91 additions and 134 deletions

View File

@@ -8,5 +8,4 @@ from .models import Folder
@admin.register(Folder)
class FolderAdmin(admin.ModelAdmin):
filter_horizontal = ('documents',)
list_display = ('label', 'user', 'datetime_created')
list_filter = ('user',)
list_display = ('label', 'datetime_created')

View File

@@ -67,7 +67,6 @@ class FoldersApp(MayanAppConfig):
SourceColumn(
source=Folder, label=_('Created'), attribute='datetime_created'
)
SourceColumn(source=Folder, label=_('User'), attribute='user')
SourceColumn(
source=Folder, label=_('Documents'),
func=lambda context: context['object'].get_document_count(

View File

@@ -0,0 +1,23 @@
# -*- coding: utf-8 -*-
from __future__ import unicode_literals
from django.db import migrations
def merge_label_and_user(apps, schema_editor):
Folder = apps.get_model('folders', 'Folder')
for folder in Folder.objects.all():
folder.label = '{}-{}'.format(folder.user.username, folder.label)
folder.save()
class Migration(migrations.Migration):
dependencies = [
('folders', '0004_documentfolder'),
]
operations = [
migrations.RunPython(merge_label_and_user),
]

View File

@@ -0,0 +1,22 @@
# -*- coding: utf-8 -*-
from __future__ import unicode_literals
from django.db import migrations
class Migration(migrations.Migration):
dependencies = [
('folders', '0005_auto_20160308_0437'),
]
operations = [
migrations.AlterUniqueTogether(
name='folder',
unique_together=set([('label',)]),
),
migrations.RemoveField(
model_name='folder',
name='user',
),
]

View File

@@ -1,6 +1,5 @@
from __future__ import absolute_import, unicode_literals
from django.contrib.auth.models import User
from django.core.exceptions import PermissionDenied
from django.core.urlresolvers import reverse
from django.db import models
@@ -20,7 +19,6 @@ class Folder(models.Model):
label = models.CharField(
db_index=True, max_length=128, verbose_name=_('Label')
)
user = models.ForeignKey(User, verbose_name=_('User'))
datetime_created = models.DateTimeField(
auto_now_add=True, verbose_name=_('Datetime created')
)
@@ -42,7 +40,7 @@ class Folder(models.Model):
class Meta:
ordering = ('label',)
unique_together = ('label', 'user')
unique_together = ('label', )
verbose_name = _('Folder')
verbose_name_plural = _('Folders')

View File

@@ -18,16 +18,14 @@ class FolderSerializer(serializers.HyperlinkedModelSerializer):
view_name='rest_api:folder-document-list'
)
documents_count = serializers.SerializerMethodField()
user = UserSerializer(read_only=True)
class Meta:
extra_kwargs = {
'url': {'view_name': 'rest_api:folder-detail'},
'user': {'view_name': 'rest_api:user-detail'}
}
fields = (
'datetime_created', 'documents', 'documents_count', 'id', 'label',
'url', 'user'
'url'
)
model = Folder
@@ -41,7 +39,6 @@ class NewFolderSerializer(serializers.Serializer):
def create(self, validated_data):
try:
data = validated_data.copy()
data.update({'user': self.context['request'].user})
return Folder.objects.create(**data)
except Exception as exception:
raise ValidationError(exception)

View File

@@ -42,12 +42,9 @@ class FolderAPITestCase(APITestCase):
self.assertEqual(Folder.objects.count(), 1)
self.assertEqual(folder.label, TEST_FOLDER_LABEL)
self.assertEqual(folder.user, self.admin_user)
def test_folder_delete(self):
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.admin_user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
self.client.delete(
reverse('rest_api:folder-detail', args=(folder.pk,))
@@ -56,9 +53,7 @@ class FolderAPITestCase(APITestCase):
self.assertEqual(Folder.objects.count(), 0)
def test_folder_edit(self):
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.admin_user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
self.client.put(
reverse('rest_api:folder-detail', args=(folder.pk,)),
@@ -71,9 +66,7 @@ class FolderAPITestCase(APITestCase):
@override_settings(OCR_AUTO_OCR=False)
def test_folder_add_document(self):
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.admin_user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
document_type = DocumentType.objects.create(
label=TEST_DOCUMENT_TYPE
@@ -93,9 +86,7 @@ class FolderAPITestCase(APITestCase):
@override_settings(OCR_AUTO_OCR=False)
def test_folder_remove_document(self):
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.admin_user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
document_type = DocumentType.objects.create(
label=TEST_DOCUMENT_TYPE

View File

@@ -12,6 +12,8 @@ from user_management.tests.literals import (
from ..models import Folder
from .literals import TEST_FOLDER_LABEL
class FolderTestCase(TestCase):
def setUp(self):
@@ -32,23 +34,21 @@ class FolderTestCase(TestCase):
def tearDown(self):
self.document_type.delete()
def test_creation_of_folder(self):
folder = Folder.objects.create(label='test', user=self.user)
def test_folder_creation(self):
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
self.assertEqual(Folder.objects.all().count(), 1)
self.assertEqual(list(Folder.objects.all()), [folder])
folder.delete()
def test_addition_of_documents(self):
folder = Folder.objects.create(label='test', user=self.user)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
folder.documents.add(self.document)
self.assertEqual(folder.documents.count(), 1)
self.assertEqual(list(folder.documents.all()), [self.document])
folder.delete()
def test_addition_and_deletion_of_documents(self):
folder = Folder.objects.create(label='test', user=self.user)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
folder.documents.add(self.document)
self.assertEqual(folder.documents.count(), 1)
@@ -58,5 +58,3 @@ class FolderTestCase(TestCase):
self.assertEqual(folder.documents.count(), 0)
self.assertEqual(list(folder.documents.all()), [])
folder.delete()

View File

@@ -43,12 +43,9 @@ class FolderViewTestCase(GenericDocumentViewTestCase):
self.assertContains(response, text='created', status_code=200)
self.assertEqual(Folder.objects.count(), 1)
self.assertEqual(Folder.objects.first().label, TEST_FOLDER_LABEL)
self.assertEqual(Folder.objects.first().user, self.user)
def test_folder_create_duplicate_view_with_permission(self):
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
self.login(username=TEST_USER_USERNAME, password=TEST_USER_PASSWORD)
@@ -62,16 +59,14 @@ class FolderViewTestCase(GenericDocumentViewTestCase):
}
)
self.assertContains(response, text='Error', status_code=200)
self.assertContains(response, text='exists', status_code=200)
self.assertEqual(Folder.objects.count(), 1)
self.assertEqual(Folder.objects.first().pk, folder.pk)
def test_folder_delete_view_no_permission(self):
self.login(username=TEST_USER_USERNAME, password=TEST_USER_PASSWORD)
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.admin_user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
response = self.post('folders:folder_delete', args=(folder.pk,))
self.assertEqual(response.status_code, 403)
@@ -84,9 +79,7 @@ class FolderViewTestCase(GenericDocumentViewTestCase):
permission_folder_delete.stored_permission
)
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.admin_user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
response = self.post(
'folders:folder_delete', args=(folder.pk,), follow=True
@@ -98,9 +91,7 @@ class FolderViewTestCase(GenericDocumentViewTestCase):
def test_folder_edit_view_no_permission(self):
self.login(username=TEST_USER_USERNAME, password=TEST_USER_PASSWORD)
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
response = self.post(
'folders:folder_edit', args=(folder.pk,), data={
@@ -118,9 +109,7 @@ class FolderViewTestCase(GenericDocumentViewTestCase):
permission_folder_edit.stored_permission
)
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
response = self.post(
'folders:folder_edit', args=(folder.pk,), data={
@@ -129,7 +118,7 @@ class FolderViewTestCase(GenericDocumentViewTestCase):
)
folder = Folder.objects.get(pk=folder.pk)
self.assertContains(response, text='saved', status_code=200)
self.assertContains(response, text='update', status_code=200)
self.assertEqual(folder.label, TEST_FOLDER_EDITED_LABEL)
def test_folder_add_document_view_no_permission(self):
@@ -137,9 +126,7 @@ class FolderViewTestCase(GenericDocumentViewTestCase):
self.role.permissions.add(permission_folder_view.stored_permission)
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.admin_user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
response = self.post(
'folders:folder_add_document', args=(self.document.pk,), data={
@@ -163,9 +150,7 @@ class FolderViewTestCase(GenericDocumentViewTestCase):
permission_document_view.stored_permission
)
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.admin_user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
response = self.post(
'folders:folder_add_document', args=(self.document.pk,), data={
@@ -185,9 +170,7 @@ class FolderViewTestCase(GenericDocumentViewTestCase):
self.role.permissions.add(permission_folder_view.stored_permission)
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.admin_user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
response = self.post(
'folders:folder_add_multiple_documents', data={
@@ -207,9 +190,7 @@ class FolderViewTestCase(GenericDocumentViewTestCase):
permission_folder_add_document.stored_permission
)
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.admin_user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
response = self.post(
'folders:folder_add_multiple_documents', data={
@@ -227,9 +208,7 @@ class FolderViewTestCase(GenericDocumentViewTestCase):
def test_folder_remove_document_view_no_permission(self):
self.login(username=TEST_USER_USERNAME, password=TEST_USER_PASSWORD)
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
folder.documents.add(self.document)
@@ -254,9 +233,7 @@ class FolderViewTestCase(GenericDocumentViewTestCase):
permission_folder_remove_document.stored_permission
)
folder = Folder.objects.create(
label=TEST_FOLDER_LABEL, user=self.user
)
folder = Folder.objects.create(label=TEST_FOLDER_LABEL)
folder.documents.add(self.document)
self.assertEqual(folder.documents.count(), 1)

View File

@@ -7,8 +7,8 @@ from .api_views import (
APIFolderDocumentView, APIFolderListView, APIFolderView
)
from .views import (
DocumentFolderListView, FolderCreateView, FolderDetailView, FolderEditView,
FolderListView
DocumentFolderListView, FolderCreateView, FolderDeleteView,
FolderDetailView, FolderEditView, FolderListView
)
urlpatterns = patterns(
@@ -17,7 +17,8 @@ urlpatterns = patterns(
url(r'^create/$', FolderCreateView.as_view(), name='folder_create'),
url(r'^(?P<pk>\d+)/edit/$', FolderEditView.as_view(), name='folder_edit'),
url(
r'^(?P<folder_id>\d+)/delete/$', 'folder_delete', name='folder_delete'
r'^(?P<pk>\d+)/delete/$', FolderDeleteView.as_view(),
name='folder_delete'
),
url(r'^(?P<pk>\d+)/$', FolderDetailView.as_view(), name='folder_view'),
url(

View File

@@ -13,7 +13,8 @@ from django.utils.translation import ugettext_lazy as _, ungettext
from acls.models import AccessControlList
from common.views import (
SingleObjectCreateView, SingleObjectEditView, SingleObjectListView
SingleObjectCreateView, SingleObjectDeleteView, SingleObjectEditView,
SingleObjectListView
)
from documents.permissions import permission_document_view
from documents.models import Document
@@ -40,11 +41,13 @@ class FolderEditView(SingleObjectEditView):
def get_extra_context(self):
return {
'object': self.get_object(),
'object_name': _('Folder'),
'title': _('Edit folder: %s') % self.get_object(),
}
class FolderListView(SingleObjectListView):
model = Folder
object_permission = permission_folder_view
def get_extra_context(self):
@@ -53,81 +56,30 @@ class FolderListView(SingleObjectListView):
'title': _('Folders'),
}
def get_folder_queryset(self):
return Folder.objects.all()
def get_queryset(self):
self.queryset = self.get_folder_queryset()
return super(FolderListView, self).get_queryset()
class FolderCreateView(SingleObjectCreateView):
fields = ('label',)
model = Folder
view_permission = permission_folder_create
def form_valid(self, form):
try:
Folder.objects.get(
label=form.cleaned_data['label'], user=self.request.user
)
except Folder.DoesNotExist:
instance = form.save(commit=False)
instance.user = self.request.user
instance.save()
return super(FolderCreateView, self).form_valid(form)
else:
messages.error(
self.request,
_(
'A folder named: %s, already exists.'
) % form.cleaned_data['label']
)
return super(FolderCreateView, self).form_invalid(form)
def get_extra_context(self):
return {
'object_name': _('Folder'),
'title': _('Create folder'),
}
def folder_delete(request, folder_id):
folder = get_object_or_404(Folder, pk=folder_id)
class FolderDeleteView(SingleObjectDeleteView):
model = Folder
object_permission = permission_folder_delete
post_action_redirect = reverse_lazy('folders:folder_list')
try:
Permission.check_permissions(request.user, (permission_folder_delete,))
except PermissionDenied:
AccessControlList.objects.check_access(
permission_folder_delete, request.user, folder
)
post_action_redirect = reverse('folders:folder_list')
previous = request.POST.get('previous', request.GET.get('previous', request.META.get('HTTP_REFERER', reverse(settings.LOGIN_REDIRECT_URL))))
next = request.POST.get('next', request.GET.get('next', post_action_redirect if post_action_redirect else request.META.get('HTTP_REFERER', reverse(settings.LOGIN_REDIRECT_URL))))
if request.method == 'POST':
try:
folder.delete()
messages.success(request, _('Folder: %s deleted successfully.') % folder)
except Exception as exception:
messages.error(request, _('Folder: %(folder)s delete error: %(error)s') % {
'folder': folder, 'error': exception})
return HttpResponseRedirect(next)
context = {
'delete_view': True,
'previous': previous,
'next': next,
'object': folder,
'title': _('Delete the folder: %s?') % folder,
}
return render_to_response(
'appearance/generic_confirm.html', context,
context_instance=RequestContext(request)
)
def get_extra_context(self):
return {
'object_name': _('Folder'),
'object': self.get_object(),
'title': _('Delete the folder: %s?') % self.get_object(),
}
class FolderDetailView(DocumentListView):
@@ -260,7 +212,7 @@ class DocumentFolderListView(FolderListView):
'title': _('Folders containing document: %s') % self.document,
}
def get_folder_queryset(self):
def get_queryset(self):
return self.document.document_folders().all()