From daca9dd53951a81b95ec1a914e79de4c30b0b0df Mon Sep 17 00:00:00 2001 From: Roberto Rosario Date: Sat, 6 Apr 2019 02:08:22 -0400 Subject: [PATCH 1/8] Fix multiple tag selection wizard step Signed-off-by: Roberto Rosario --- HISTORY.rst | 4 + docs/releases/3.1.11.rst | 85 ++++++++++++++++++++++ docs/releases/index.rst | 1 + mayan/apps/tags/tests/literals.py | 2 + mayan/apps/tags/tests/test_wizard_steps.py | 28 ++++++- mayan/apps/tags/wizard_steps.py | 2 +- 6 files changed, 117 insertions(+), 5 deletions(-) create mode 100644 docs/releases/3.1.11.rst diff --git a/HISTORY.rst b/HISTORY.rst index 38802a82cf..7a43061f5b 100644 --- a/HISTORY.rst +++ b/HISTORY.rst @@ -1,3 +1,7 @@ +3.1.11 (2019-04-XX) +=================== +* Fix multiple tag selection wizard step. + 3.1.10 (2019-04-04) =================== * Backport test case improvements from the development branch. Add random diff --git a/docs/releases/3.1.11.rst b/docs/releases/3.1.11.rst new file mode 100644 index 0000000000..e7d593f49d --- /dev/null +++ b/docs/releases/3.1.11.rst @@ -0,0 +1,85 @@ +Version 3.1.11 +============== + +Released: April XX, 2019 + + +Changes +------- + +Other changes +^^^^^^^^^^^^^ + +* Fix multiple tag selection wizard step. + +Removals +-------- + +* None + + +Upgrading from a previous version +--------------------------------- + +If installed via Python's PIP +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Remove deprecated requirements:: + + $ curl https://gitlab.com/mayan-edms/mayan-edms/raw/master/removals.txt | pip uninstall -r /dev/stdin + +Type in the console:: + + $ pip install mayan-edms==3.1.11 + +the requirements will also be updated automatically. + + +Using Git +^^^^^^^^^ + +If you installed Mayan EDMS by cloning the Git repository issue the commands:: + + $ git reset --hard HEAD + $ git pull + +otherwise download the compressed archived and uncompress it overriding the +existing installation. + +Remove deprecated requirements:: + + $ pip uninstall -y -r removals.txt + +Next upgrade/add the new requirements:: + + $ pip install --upgrade -r requirements.txt + + +Common steps +^^^^^^^^^^^^ + +Perform these steps after updating the code from either step above. + +Migrate existing database schema with:: + + $ mayan-edms.py performupgrade + +Add new static media:: + + $ mayan-edms.py collectstatic --noinput + +The upgrade procedure is now complete. + + +Backward incompatible changes +----------------------------- + +* None + + +Bugs fixed or issues closed +--------------------------- + +* :gitlab-issue:`563` Recursive Watch Folder + +.. _PyPI: https://pypi.python.org/pypi/mayan-edms/ diff --git a/docs/releases/index.rst b/docs/releases/index.rst index d3b2470bfa..922a5647fa 100644 --- a/docs/releases/index.rst +++ b/docs/releases/index.rst @@ -20,6 +20,7 @@ versions of the documentation contain the release notes for any later releases. .. toctree:: :maxdepth: 1 + 3.1.11 3.1.10 3.1.9 3.1.8 diff --git a/mayan/apps/tags/tests/literals.py b/mayan/apps/tags/tests/literals.py index a1f714ab91..c1206eb2f1 100644 --- a/mayan/apps/tags/tests/literals.py +++ b/mayan/apps/tags/tests/literals.py @@ -5,6 +5,8 @@ TEST_TAG_LABEL_EDITED = 'test-tag-edited' TEST_TAG_COLOR = '#001122' TEST_TAG_COLOR_EDITED = '#221100' +TEST_TAG_LABEL_2 = 'test-tag-2' + TEST_TAG_INDEX_HAS_TAG = 'HAS_TAG' TEST_TAG_INDEX_NO_TAG = 'NO_TAG' TEST_TAG_INDEX_NODE_TEMPLATE = ''' diff --git a/mayan/apps/tags/tests/test_wizard_steps.py b/mayan/apps/tags/tests/test_wizard_steps.py index 273381465c..3539d63c60 100644 --- a/mayan/apps/tags/tests/test_wizard_steps.py +++ b/mayan/apps/tags/tests/test_wizard_steps.py @@ -12,10 +12,12 @@ from sources.tests.literals import ( from ..models import Tag -from .literals import TEST_TAG_COLOR, TEST_TAG_LABEL +from .literals import TEST_TAG_COLOR, TEST_TAG_LABEL, TEST_TAG_LABEL_2 class TaggedDocumentUploadTestCase(GenericDocumentViewTestCase): + auto_upload_document = False + def setUp(self): super(TaggedDocumentUploadTestCase, self).setUp() self.login_user() @@ -24,8 +26,6 @@ class TaggedDocumentUploadTestCase(GenericDocumentViewTestCase): uncompress=TEST_SOURCE_UNCOMPRESS_N ) - self.document.delete() - def _request_upload_interactive_document_create_view(self): with open(TEST_SMALL_DOCUMENT_PATH, mode='rb') as file_object: return self.post( @@ -33,7 +33,7 @@ class TaggedDocumentUploadTestCase(GenericDocumentViewTestCase): data={ 'document_type_id': self.document_type.pk, 'source-file': file_object, - 'tags': self.tag.pk + 'tags': ','.join(map(str, Tag.objects.values_list('pk', flat=True))) } ) @@ -42,11 +42,31 @@ class TaggedDocumentUploadTestCase(GenericDocumentViewTestCase): color=TEST_TAG_COLOR, label=TEST_TAG_LABEL ) + def _create_tag_2(self): + self.tag_2 = Tag.objects.create( + color=TEST_TAG_COLOR, label=TEST_TAG_LABEL_2 + ) + def test_upload_interactive_view_with_access(self): self._create_tag() + self.grant_access( permission=permission_document_create, obj=self.document_type ) response = self._request_upload_interactive_document_create_view() self.assertEqual(response.status_code, 302) + self.assertTrue(self.tag in Document.objects.first().tags.all()) + + def test_upload_interactive_multiple_tags_view_with_access(self): + self._create_tag() + self._create_tag_2() + + self.grant_access( + permission=permission_document_create, obj=self.document_type + ) + response = self._request_upload_interactive_document_create_view() + self.assertEqual(response.status_code, 302) + + self.assertTrue(self.tag in Document.objects.first().tags.all()) + self.assertTrue(self.tag_2 in Document.objects.first().tags.all()) diff --git a/mayan/apps/tags/wizard_steps.py b/mayan/apps/tags/wizard_steps.py index 5ad9a3e8c2..a9bf47da30 100644 --- a/mayan/apps/tags/wizard_steps.py +++ b/mayan/apps/tags/wizard_steps.py @@ -45,7 +45,7 @@ class WizardStepTags(WizardStep): furl_instance = furl(querystring) Tag = apps.get_model(app_label='tags', model_name='Tag') - for tag in Tag.objects.filter(pk__in=furl_instance.args.getlist('tags')): + for tag in Tag.objects.filter(pk__in=furl_instance.args['tags'].split(',')): tag.documents.add(document) From 7ed26f4d4cca9ab796e9146cd2e88d230abd1095 Mon Sep 17 00:00:00 2001 From: Roberto Rosario Date: Sat, 6 Apr 2019 20:17:32 -0400 Subject: [PATCH 2/8] Add checkout details view tests Signed-off-by: Roberto Rosario --- mayan/apps/checkouts/tests/test_views.py | 47 ++++++++++++++++++++---- 1 file changed, 40 insertions(+), 7 deletions(-) diff --git a/mayan/apps/checkouts/tests/test_views.py b/mayan/apps/checkouts/tests/test_views.py index 8f6b74b843..b7500bf437 100644 --- a/mayan/apps/checkouts/tests/test_views.py +++ b/mayan/apps/checkouts/tests/test_views.py @@ -13,6 +13,7 @@ from user_management.tests.literals import ( TEST_ADMIN_USERNAME, ) +from ..literals import STATE_CHECKED_OUT, STATE_LABELS from ..models import DocumentCheckout from ..permissions import ( permission_document_checkin, permission_document_checkin_override, @@ -21,14 +22,25 @@ from ..permissions import ( class DocumentCheckoutViewTestCase(GenericDocumentViewTestCase): + def setUp(self): + super(DocumentCheckoutViewTestCase, self).setUp() + self.login_user() + + def _checkout_document(self): + expiration_datetime = now() + datetime.timedelta(days=1) + + DocumentCheckout.objects.checkout_document( + document=self.document, expiration_datetime=expiration_datetime, + user=self.user, block_new_version=True + ) + self.assertTrue(self.document.is_checked_out()) + def _request_document_check_in_view(self): return self.post( viewname='checkouts:checkin_document', args=(self.document.pk,), ) def test_checkin_document_view_no_permission(self): - self.login_user() - expiration_datetime = now() + datetime.timedelta(days=1) DocumentCheckout.objects.checkout_document( @@ -43,8 +55,6 @@ class DocumentCheckoutViewTestCase(GenericDocumentViewTestCase): self.assertTrue(self.document.is_checked_out()) def test_checkin_document_view_with_access(self): - self.login_user() - expiration_datetime = now() + datetime.timedelta(days=1) DocumentCheckout.objects.checkout_document( @@ -82,14 +92,11 @@ class DocumentCheckoutViewTestCase(GenericDocumentViewTestCase): ) def test_checkout_document_view_no_permission(self): - self.login_user() - response = self._request_document_checkout_view() self.assertEquals(response.status_code, 403) self.assertFalse(self.document.is_checked_out()) def test_checkout_document_view_with_access(self): - self.login_user() self.grant_access( obj=self.document, permission=permission_document_checkout ) @@ -102,6 +109,32 @@ class DocumentCheckoutViewTestCase(GenericDocumentViewTestCase): self.assertEquals(response.status_code, 302) self.assertTrue(self.document.is_checked_out()) + def _request_checkout_detail_view(self): + return self.get( + viewname='checkouts:checkout_info', args=(self.document.pk,), + ) + + def test_checkout_detail_view_no_permission(self): + self._checkout_document() + + response = self._request_checkout_detail_view() + + self.assertNotContains( + response, text=STATE_LABELS[STATE_CHECKED_OUT], status_code=403 + ) + + def test_checkout_detail_view_with_access(self): + self._checkout_document() + + self.grant_access( + obj=self.document, + permission=permission_document_checkout_detail_view + ) + + response = self._request_checkout_detail_view() + + self.assertContains(response, text=STATE_LABELS[STATE_CHECKED_OUT], status_code=200) + def test_document_new_version_after_checkout(self): """ Gitlab issue #231 From f6a0a421a50a518fd34db82d9286427e231bd347 Mon Sep 17 00:00:00 2001 From: Roberto Rosario Date: Sun, 7 Apr 2019 01:07:01 -0400 Subject: [PATCH 3/8] Update the check out info link permission Update the link permission to match the same required permission as the view. Signed-off-by: Roberto Rosario --- HISTORY.rst | 2 ++ mayan/apps/checkouts/links.py | 7 +++---- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/HISTORY.rst b/HISTORY.rst index 7a43061f5b..0d2f753e32 100644 --- a/HISTORY.rst +++ b/HISTORY.rst @@ -1,6 +1,8 @@ 3.1.11 (2019-04-XX) =================== * Fix multiple tag selection wizard step. +* Change the required permission for the checkout info link from + document check in to document checkout details view. 3.1.10 (2019-04-04) =================== diff --git a/mayan/apps/checkouts/links.py b/mayan/apps/checkouts/links.py index 99a3038f06..2abcc9e464 100644 --- a/mayan/apps/checkouts/links.py +++ b/mayan/apps/checkouts/links.py @@ -7,7 +7,8 @@ from navigation import Link from .icons import icon_checkout_info from .permissions import ( permission_document_checkout, permission_document_checkin, - permission_document_checkin_override + permission_document_checkin_override, + permission_document_checkout_detail_view ) @@ -40,11 +41,9 @@ link_checkin_document = Link( args='object.pk', condition=is_checked_out, permissions=( permission_document_checkin, permission_document_checkin_override ), text=_('Check in document'), view='checkouts:checkin_document', - ) link_checkout_info = Link( args='resolved_object.pk', icon_class=icon_checkout_info, permissions=( - permission_document_checkin, permission_document_checkin_override, - permission_document_checkout + permission_document_checkout_detail_view, ), text=_('Check in/out'), view='checkouts:checkout_info', ) From 3a60155bfa02ba809d9703ec84631c0468f8126f Mon Sep 17 00:00:00 2001 From: Roberto Rosario Date: Sun, 7 Apr 2019 01:08:46 -0400 Subject: [PATCH 4/8] Add checkout tests Add link tests. Add checkout info view tests. Move common code to a test mixin. Signed-off-by: Roberto Rosario --- mayan/apps/checkouts/tests/mixins.py | 18 +++++++++ mayan/apps/checkouts/tests/test_links.py | 50 ++++++++++++++++++++++++ mayan/apps/checkouts/tests/test_views.py | 17 ++++---- 3 files changed, 75 insertions(+), 10 deletions(-) create mode 100644 mayan/apps/checkouts/tests/mixins.py create mode 100644 mayan/apps/checkouts/tests/test_links.py diff --git a/mayan/apps/checkouts/tests/mixins.py b/mayan/apps/checkouts/tests/mixins.py new file mode 100644 index 0000000000..ad931f3a45 --- /dev/null +++ b/mayan/apps/checkouts/tests/mixins.py @@ -0,0 +1,18 @@ +from __future__ import unicode_literals + +import datetime + +from django.utils.timezone import now + +from ..models import DocumentCheckout + + +class DocumentCheckoutTestMixin(object): + def _checkout_document(self): + expiration_datetime = now() + datetime.timedelta(days=1) + + DocumentCheckout.objects.checkout_document( + document=self.document, expiration_datetime=expiration_datetime, + user=self.user, block_new_version=True + ) + self.assertTrue(self.document.is_checked_out()) diff --git a/mayan/apps/checkouts/tests/test_links.py b/mayan/apps/checkouts/tests/test_links.py new file mode 100644 index 0000000000..a060cfc740 --- /dev/null +++ b/mayan/apps/checkouts/tests/test_links.py @@ -0,0 +1,50 @@ +from __future__ import unicode_literals + +from documents.tests import GenericDocumentViewTestCase + +from ..links import link_checkout_document, link_checkout_info +from ..permissions import ( + permission_document_checkout, permission_document_checkout_detail_view +) + +from .mixins import DocumentCheckoutTestMixin + + +class CheckoutLinksTestCase(DocumentCheckoutTestMixin, GenericDocumentViewTestCase): + def setUp(self): + super(CheckoutLinksTestCase, self).setUp() + self.login_user() + + def _resolve_checkout_link(self): + self.add_test_view(test_object=self.document) + context = self.get_test_view() + context['user'] = self.user + return link_checkout_document.resolve(context=context) + + def test_checkout_link_no_access(self): + resolved_link = self._resolve_checkout_link() + self.assertEqual(resolved_link, None) + + def test_checkout_link_with_access(self): + self.grant_access( + obj=self.document, permission=permission_document_checkout + ) + resolved_link = self._resolve_checkout_link() + self.assertNotEqual(resolved_link, None) + + def _resolve_checkout_info_link(self): + self.add_test_view(test_object=self.document) + context = self.get_test_view() + context['user'] = self.user + return link_checkout_info.resolve(context=context) + + def test_checkout_info_link_no_access(self): + resolved_link = self._resolve_checkout_info_link() + self.assertEqual(resolved_link, None) + + def test_checkout_info_link_with_access(self): + self.grant_access( + obj=self.document, permission=permission_document_checkout_detail_view + ) + resolved_link = self._resolve_checkout_info_link() + self.assertNotEqual(resolved_link, None) diff --git a/mayan/apps/checkouts/tests/test_views.py b/mayan/apps/checkouts/tests/test_views.py index b7500bf437..152bf7d009 100644 --- a/mayan/apps/checkouts/tests/test_views.py +++ b/mayan/apps/checkouts/tests/test_views.py @@ -20,21 +20,14 @@ from ..permissions import ( permission_document_checkout, permission_document_checkout_detail_view ) +from .mixins import DocumentCheckoutTestMixin -class DocumentCheckoutViewTestCase(GenericDocumentViewTestCase): + +class DocumentCheckoutViewTestCase(DocumentCheckoutTestMixin, GenericDocumentViewTestCase): def setUp(self): super(DocumentCheckoutViewTestCase, self).setUp() self.login_user() - def _checkout_document(self): - expiration_datetime = now() + datetime.timedelta(days=1) - - DocumentCheckout.objects.checkout_document( - document=self.document, expiration_datetime=expiration_datetime, - user=self.user, block_new_version=True - ) - self.assertTrue(self.document.is_checked_out()) - def _request_document_check_in_view(self): return self.post( viewname='checkouts:checkin_document', args=(self.document.pk,), @@ -116,6 +109,10 @@ class DocumentCheckoutViewTestCase(GenericDocumentViewTestCase): def test_checkout_detail_view_no_permission(self): self._checkout_document() + self.grant_access( + obj=self.document, + permission=permission_document_checkout + ) response = self._request_checkout_detail_view() From 9ec021241c3020f7a2c743dba54d2c0ae484f120 Mon Sep 17 00:00:00 2001 From: Roberto Rosario Date: Sun, 7 Apr 2019 20:41:28 -0400 Subject: [PATCH 5/8] Update release notes Signed-off-by: Roberto Rosario --- docs/releases/3.1.11.rst | 44 ++++++++++++++++++++++++++++++++++------ 1 file changed, 38 insertions(+), 6 deletions(-) diff --git a/docs/releases/3.1.11.rst b/docs/releases/3.1.11.rst index e7d593f49d..a92cf49531 100644 --- a/docs/releases/3.1.11.rst +++ b/docs/releases/3.1.11.rst @@ -11,6 +11,8 @@ Other changes ^^^^^^^^^^^^^ * Fix multiple tag selection wizard step. +* Update the check out info link permission. Update the link permission to + match the same required permission as the view. Removals -------- @@ -34,6 +36,42 @@ Type in the console:: the requirements will also be updated automatically. +Migrate existing database schema with:: + + $ mayan-edms.py performupgrade + +Add new static media:: + + $ mayan-edms.py collectstatic --noinput + +The upgrade procedure is now complete. + + +If installed using a direct deployment +^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ + +Remove deprecated requirements:: + + $ curl https://gitlab.com/mayan-edms/mayan-edms/raw/master/removals.txt | sudo -u mayan /opt/mayan-edms/bin/pip uninstall -r /dev/stdin + +Download and install the new version:: + + $ sudo -u mayan /opt/mayan-edms/bin/pip install --no-cache-dir --no-use-pep517 mayan-edms==3.1.11 + +the requirements will also be updated automatically. + +Run the upgrade command:: + + $ sudo -u mayan MAYAN_DATABASE_ENGINE=django.db.backends.postgresql \ + MAYAN_DATABASE_NAME=mayan MAYAN_DATABASE_PASSWORD=mayanuserpass \ + MAYAN_DATABASE_USER=mayan MAYAN_DATABASE_HOST=127.0.0.1 \ + MAYAN_MEDIA_ROOT=/opt/mayan-edms/media /opt/mayan-edms/bin/mayan-edms.py performupgrade + +Add any new static files:: + + $ sudo -u mayan MAYAN_MEDIA_ROOT=/opt/mayan-edms/media /opt/mayan-edms/bin/mayan-edms.py collectstatic --noinput + +The upgrade procedure is now complete. Using Git ^^^^^^^^^ @@ -54,12 +92,6 @@ Next upgrade/add the new requirements:: $ pip install --upgrade -r requirements.txt - -Common steps -^^^^^^^^^^^^ - -Perform these steps after updating the code from either step above. - Migrate existing database schema with:: $ mayan-edms.py performupgrade From 0065edfae96c1b75628d387e904fcc17d165b8d8 Mon Sep 17 00:00:00 2001 From: Roberto Rosario Date: Sun, 7 Apr 2019 22:39:42 -0400 Subject: [PATCH 6/8] Lower the log severity when links don't resolve Signed-off-by: Roberto Rosario --- HISTORY.rst | 1 + mayan/apps/navigation/classes.py | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/HISTORY.rst b/HISTORY.rst index 0d2f753e32..617874aed7 100644 --- a/HISTORY.rst +++ b/HISTORY.rst @@ -3,6 +3,7 @@ * Fix multiple tag selection wizard step. * Change the required permission for the checkout info link from document check in to document checkout details view. +* Lower the log severity when links don't resolve. 3.1.10 (2019-04-04) =================== diff --git a/mayan/apps/navigation/classes.py b/mayan/apps/navigation/classes.py index d035aee7e7..7d3fef2f33 100644 --- a/mayan/apps/navigation/classes.py +++ b/mayan/apps/navigation/classes.py @@ -419,7 +419,7 @@ class Link(object): try: resolved_link.url = node.render(context) except Exception as exception: - logger.error( + logger.debug( 'Error resolving link "%s" URL; %s', self.text, exception ) elif self.url: From 69bd6c116e209f146cf04342de286feec9eb60ee Mon Sep 17 00:00:00 2001 From: Roberto Rosario Date: Sun, 7 Apr 2019 22:45:06 -0400 Subject: [PATCH 7/8] Improve multiple tag wizard step code Previous code produce an error when there were not tag IDs passed to the wizard. Signed-off-by: Roberto Rosario --- mayan/apps/tags/wizard_steps.py | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/mayan/apps/tags/wizard_steps.py b/mayan/apps/tags/wizard_steps.py index a9bf47da30..d0f8be1072 100644 --- a/mayan/apps/tags/wizard_steps.py +++ b/mayan/apps/tags/wizard_steps.py @@ -45,7 +45,12 @@ class WizardStepTags(WizardStep): furl_instance = furl(querystring) Tag = apps.get_model(app_label='tags', model_name='Tag') - for tag in Tag.objects.filter(pk__in=furl_instance.args['tags'].split(',')): + tag_id_list = furl_instance.args.get('tags', '') + + if tag_id_list: + tag_id_list = tag_id_list.split(',') + + for tag in Tag.objects.filter(pk__in=tag_id_list): tag.documents.add(document) From 7d756de3de49fca8508e49a588732f494ee0b23e Mon Sep 17 00:00:00 2001 From: Roberto Rosario Date: Sun, 7 Apr 2019 22:58:01 -0400 Subject: [PATCH 8/8] Add DOCUMENTS_HASH_BLOCK_SIZE setting This new setting is used to control the size of the file blocks when calculating a document's checksum. The default value of 0 disables the features and preserves the current behavior of reading the entire file into memory. Signed-off-by: Roberto Rosario --- HISTORY.rst | 2 ++ docs/releases/3.1.11.rst | 39 ++++++++++++++++++++++++++++---- mayan/apps/documents/models.py | 28 ++++++++++++++++++----- mayan/apps/documents/settings.py | 8 +++++++ 4 files changed, 67 insertions(+), 10 deletions(-) diff --git a/HISTORY.rst b/HISTORY.rst index 617874aed7..5a8746d9fc 100644 --- a/HISTORY.rst +++ b/HISTORY.rst @@ -4,6 +4,8 @@ * Change the required permission for the checkout info link from document check in to document checkout details view. * Lower the log severity when links don't resolve. +* Add DOCUMENTS_HASH_BLOCK_SIZE to control the size of the file + block when calculating a document's checksum. 3.1.10 (2019-04-04) =================== diff --git a/docs/releases/3.1.11.rst b/docs/releases/3.1.11.rst index a92cf49531..2efe86bb2d 100644 --- a/docs/releases/3.1.11.rst +++ b/docs/releases/3.1.11.rst @@ -7,12 +7,43 @@ Released: April XX, 2019 Changes ------- +Memory usage +^^^^^^^^^^^^ + +The ``DOCUMENTS_HASH_BLOCK_SIZE`` setting was added to limit the number of +bytes that will be read into memory when calculating the checksum of a new +document. For compatibility with the current bevahor this setting defaults to +0 which means that it is disabled. Disabling the setting will cause the +entire document's file to be loaded into memory. If documents are not +processing due to out of memory errors (large documents or devices with +limited memory), set ``DOCUMENTS_HASH_BLOCK_SIZE`` to a value other than 0. +Limited tests suggest 65535 to be a good alternative. + + +Tag wizard step +^^^^^^^^^^^^^^^ + +The tag wizard step was fixed and will now allow attaching multple tags to a +new document. + + +Permissions +^^^^^^^^^^^ + +Previously the document checkout information link required one of the following +permissions: document check in, document check in override, or document +checkout. Meanwhile the document checkout information view would require the +document checkout detail view permission. This difference in permissions +has been eliminated and the link will now required the document checkout +detail view permission, same as the view. Update your user role permissions +accordingly. + + Other changes ^^^^^^^^^^^^^ -* Fix multiple tag selection wizard step. -* Update the check out info link permission. Update the link permission to - match the same required permission as the view. +* Lower the log severity when links don't resolve. + Removals -------- @@ -112,6 +143,6 @@ Backward incompatible changes Bugs fixed or issues closed --------------------------- -* :gitlab-issue:`563` Recursive Watch Folder +* None .. _PyPI: https://pypi.python.org/pypi/mayan-edms/ diff --git a/mayan/apps/documents/models.py b/mayan/apps/documents/models.py index f5b973e01d..441622d941 100644 --- a/mayan/apps/documents/models.py +++ b/mayan/apps/documents/models.py @@ -45,7 +45,8 @@ from .permissions import permission_document_view from .settings import ( setting_disable_base_image_cache, setting_disable_transformed_image_cache, setting_display_width, setting_display_height, setting_fix_orientation, - setting_language, setting_zoom_max_level, setting_zoom_min_level + setting_hash_block_size, setting_language, setting_zoom_max_level, + setting_zoom_min_level ) from .signals import ( post_document_created, post_document_type_change, post_version_upload @@ -56,8 +57,8 @@ logger = logging.getLogger(__name__) # document image cache name hash function -def HASH_FUNCTION(data): - return hashlib.sha256(data).hexdigest() +def hash_function(): + return hashlib.sha256() def UUID_FUNCTION(*args, **kwargs): @@ -697,10 +698,25 @@ class DocumentVersion(models.Model): Open a document version's file and update the checksum field using the user provided checksum function """ + block_size = setting_hash_block_size.value + if block_size == 0: + # If the setting value is 0 that means disable read limit. To disable + # the read limit passing None won't work, we pass -1 instead as per + # the Python documentation. + # https://docs.python.org/2/tutorial/inputoutput.html#methods-of-file-objects + block_size = -1 + if self.exists(): - source = self.open() - self.checksum = force_text(HASH_FUNCTION(source.read())) - source.close() + hash_object = hash_function() + with self.open() as file_object: + while (True): + data = file_object.read(block_size) + if not data: + break + + hash_object.update(data) + + self.checksum = force_text(hash_object.hexdigest()) if save: self.save() diff --git a/mayan/apps/documents/settings.py b/mayan/apps/documents/settings.py index 794c433a5e..25001f96b5 100644 --- a/mayan/apps/documents/settings.py +++ b/mayan/apps/documents/settings.py @@ -62,6 +62,14 @@ setting_fix_orientation = namespace.add_setting( 'feature and it is disabled by default.' ) ) +setting_hash_block_size = namespace.add_setting( + global_name='DOCUMENTS_HASH_BLOCK_SIZE', default=0, + help_text=_( + 'Size of blocks to use when calculating the document file\'s ' + 'checksum. A value of 0 disables the block calculation and the entire ' + 'file will be loaded into memory.' + ) +) setting_language = namespace.add_setting( global_name='DOCUMENTS_LANGUAGE', default=DEFAULT_LANGUAGE, help_text=_('Default documents language (in ISO639-3 format).')