Merge branch 'master' into feature/merge_master

This commit is contained in:
Roberto Rosario
2016-03-03 16:46:11 -04:00
24 changed files with 194 additions and 181 deletions

View File

@@ -1,2 +0,0 @@
*
!docker

View File

@@ -1,40 +0,0 @@
FROM ubuntu:15.04
MAINTAINER Roberto Rosario "roberto.rosario@mayan-edms.com"
# Install base Ubuntu libraries
RUN apt-get update && apt-get install -y netcat-openbsd python-dev python-pip gpgv nginx libpq-dev git-core libjpeg-dev libmagic1 libpng-dev libreoffice libtiff-dev gcc ghostscript gpgv tesseract-ocr unpaper poppler-utils && apt-get clean && rm -rf /var/lib/apt/lists/* && rm -f /var/cache/apt/archives/*.deb
ENV MAYAN_INSTALL_DIR=/usr/local/lib/python2.7/dist-packages/mayan
# Install Mayan EDMS, latest production release
RUN pip install mayan-edms==2.0.0
# Install Python clients for PostgreSQL, REDIS, and uWSGI
RUN pip install psycopg2 redis uwsgi
# Create Mayan EDMS basic settings/local.py file
RUN mayan-edms.py createsettings
# Install Mayan EDMS static media files
RUN mayan-edms.py collectstatic --noinput
ADD docker /docker
# Setup Mayan EDMS settings file overrides
RUN cat /docker/conf/mayan/settings.py >> $MAYAN_INSTALL_DIR/settings/local.py
# Setup NGINX
RUN rm /etc/nginx/sites-enabled/default
RUN ln -s /docker/conf/nginx/mayan-edms /etc/nginx/sites-enabled/mayan-edms
# Setup UWSGI
RUN mkdir /var/log/uwsgi
# Persistent Mayan EDMS files
VOLUME $MAYAN_INSTALL_DIR/media
ENTRYPOINT ["/docker/entrypoint.sh"]
EXPOSE 80
CMD ["/docker/bin/run.sh"]

View File

@@ -1,19 +1,34 @@
2.1 (2016-XX)
=============
- Upgrade to use Django 1.8.8. Issue #246.
- Upgrade requirements.
- Remove remaining references to Django's User model. Issue #225
- Rename 'Content' search box to 'OCR'.
- Remove included login required middleware using django-stronghold instead (http://mikegrouchy.com/django-stronghold/).
2.0.2 (2016-02-09)
==================
- Install testing dependencies when installing development dependencies.
- Fix GitLab issue #250 "Empty optional lookup metadata trigger validation error".
- Fix OCR API test.
- Move metadata form value validation to .clean() method.
- Only extract validation error messages from ValidationError exception instances.
- Don't store empty metadata value if the update checkbox is not checked.
- Add 2 second delay to document version tests to workaround MySQL limitation.
- Strip HTML tags from the browser title.
- Remove Docker and Docker Compose files.
2.0.1 (2016-01-22)
==================
- Fix GitLab issue #243, "System allows a user to skip entering values for a required metadata field while uploading a new document"
- Fix GitLab issue #245, "Add multiple metadata not possible"
- Updated Vagrantfile to provision a production box too.
2.0 (2015-12-04)
================
- New source homepage: https://gitlab.com/mayan-edms/mayan-edms
- Update to Django 1.7
- New Bootstrap Frontend UI
@@ -85,7 +100,6 @@
1.1 (2015-02-10)
================
- Uses Celery for background tasks
- Removal of the splash screen
- Adds a home view with common function buttons
@@ -111,7 +125,6 @@
1.0 (2014-08-27)
================
- New home @ https://github.com/mayan-edms/mayan-edms
- Updated to use Django 1.6
- Translation updates

View File

@@ -1,21 +0,0 @@
postgres:
env_file:
- ./environment
image: postgres
volumes:
- /var/lib/postgresql/data
redis:
image: redis
mayan-edms:
env_file:
- ./environment
image: mayanedms/monolithic
links:
- postgres
- redis
ports:
- "80:80"
volumes:
- /usr/local/lib/python2.7/dist-packages/mayan/media

View File

@@ -1,10 +0,0 @@
#!/bin/bash
# Launch NGINX daemon
nginx
# Launch the workers
mayan-edms.py celery worker --settings=mayan.settings.production -Ofair -l ERROR -B &
# Launch uWSGI in foreground
/usr/local/bin/uwsgi --ini /docker/conf/uwsgi/uwsgi.ini

View File

@@ -1,15 +0,0 @@
import os
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.postgresql_psycopg2',
'NAME': os.environ.get('POSTGRES_DB'),
'USER': os.environ.get('POSTGRES_USER'),
'PASSWORD': os.environ.get('POSTGRES_PASSWORD'),
'HOST': os.environ.get('POSTGRES_PORT_5432_TCP_ADDR'),
'PORT': os.environ.get('POSTGRES_PORT_5432_TCP_PORT'),
}
}
BROKER_URL = 'redis://{}:{}/0'.format(os.environ.get('REDIS_PORT_6379_TCP_ADDR'), os.environ.get('REDIS_PORT_6379_TCP_PORT'))
CELERY_RESULT_BACKEND = 'redis://{}:{}/0'.format(os.environ.get('REDIS_PORT_6379_TCP_ADDR'), os.environ.get('REDIS_PORT_6379_TCP_PORT'))

View File

@@ -1,22 +0,0 @@
server {
listen 80;
server_name localhost;
location / {
include uwsgi_params;
uwsgi_pass unix:/run/mayan.sock;
client_max_body_size 30M; # Increse if your plan to upload bigger documents
proxy_read_timeout 30s; # Increase if your document uploads take more than 30 seconds
}
location /static {
alias /usr/local/lib/python2.7/dist-packages/mayan/media/static;
expires 1h;
}
location /favicon.ico {
alias /usr/local/lib/python2.7/dist-packages/mayan/media/static/appearance/images/favicon.ico;
expires 1h;
}
}

View File

@@ -1,14 +0,0 @@
[uwsgi]
chdir = $(MAYAN_INSTALL_DIR)
chmod-socket = 664
chown-socket = www-data:www-data
env = DJANGO_SETTINGS_MODULE=mayan.settings.production
gid = root
logto = /var/log/uwsgi/%n.log
pythonpath = /usr/local/lib/python2.7/dist-packages
master = True
max-requests = 5000
socket = /run/mayan.sock
uid = root
vacuum = True
wsgi-file = $(MAYAN_INSTALL_DIR)/wsgi.py

View File

@@ -1,17 +0,0 @@
#!/bin/bash
set -e
if [[ -z $POSTGRES_PORT_5432_TCP_ADDR ]]; then
echo "** ERROR: You need to link the Postgres container."
exit 1
fi
until nc -z $POSTGRES_PORT_5432_TCP_ADDR $POSTGRES_PORT_5432_TCP_PORT; do
echo "$(date) - waiting for Postgres..."
sleep 1
done
# Migrate database, create initial admin user
mayan-edms.py initialsetup
exec "$@"

94
docs/releases/2.0.2.rst Normal file
View File

@@ -0,0 +1,94 @@
===============================
Mayan EDMS v2.0.2 release notes
===============================
Released: February 15, 2016
Welcome to Mayan EDMS v2.0.2
What's new
==========
Fine tune "Update" checkbox from the metadata entry form
--------------------------------------------------------
Previously the update checkbox was ignored during the metadata step of the
document upload wizard with the wizard always creating a metadata entry for the
new document even if the entry was left blank. The checkbox now controls whether
or not the wizard will store try to create the metadata entry.
Fix empty optional lookup metadata fields behavior
--------------------------------------------------
An edge case was fixed that caused validation to be executed for empty metadata
fields that had a value lookup list.
Remove Docker files
-------------------
Included Docker and Docker Compose files were removed since the Mayan EDMS Docker
(https://gitlab.com/mayan-edms/mayan-edms-docker) repository is stable.
Other changes
-------------
- Only extract validation error messages from ValidationError exception instances.
- Add 2 second delay to document version tests to workaround MySQL not storing
the millisecond part of the document version's timestamp.
- Install testing dependencies when installing development dependencies.
- Fix OCR API test for document version page OCR content.
- Move metadata form value validation to .clean() method.
- Add HTML tags stripping to the browser title generation template.
Removals
--------
* None
Upgrading from a previous version
---------------------------------
Using PIP
~~~~~~~~~
Type in the console::
$ pip install -U mayan-edms
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.
Next upgrade/add the new requirements::
$ pip install --upgrade -r requirements.txt
Common steps
~~~~~~~~~~~~
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 #250 <https://gitlab.com/mayan-edms/mayan-edms/issues/250>`_ Empty optional lookup metadata trigger validation error.
.. _PyPI: https://pypi.python.org/pypi/mayan-edms/

View File

@@ -23,6 +23,8 @@ versions of the documentation contain the release notes for any later releases.
:maxdepth: 1
2.0
2.0.1
2.0.2
1.0 series
----------

View File

@@ -1,3 +0,0 @@
POSTGRES_DB=mayan
POSTGRES_PASSWORD=mayanpassword
POSTGRES_USER=mayan

View File

@@ -1,8 +1,8 @@
from __future__ import unicode_literals
__title__ = 'Mayan EDMS'
__version__ = '2.0.1'
__build__ = 0x020001
__version__ = '2.0.2'
__build__ = 0x020002
__author__ = 'Roberto Rosario'
__author_email__ = 'roberto.rosario@mayan-edms.com'
__description__ = 'Free Open Source Electronic Document Management System'

View File

@@ -1,7 +1,7 @@
{% load i18n %}
{% if title %}
{{ title }}
{{ title|striptags }}
{% else %}
{% if read_only %}
{% blocktrans %}Details for: {{ object }}{% endblocktrans %}

View File

@@ -2,6 +2,8 @@
{% load i18n %}
{% block title %}{% include 'appearance/calculate_form_title.html' %}{% endblock %}
{% block content %}
<h3>{% include 'appearance/calculate_form_title.html' %}</h3>
<hr>

View File

@@ -2,6 +2,8 @@
from __future__ import unicode_literals
import time
from django.core.files import File
from django.core.urlresolvers import reverse
@@ -37,6 +39,10 @@ class DocumentsLinksTestCase(GenericDocumentViewTestCase):
self.assertEqual(resolved_link, None)
def test_document_version_revert_link_with_permission(self):
# Needed by MySQL as milliseconds value is not store in timestamp
# field
time.sleep(2)
with open(TEST_SMALL_DOCUMENT_PATH) as file_object:
self.document.new_version(file_object=File(file_object))

View File

@@ -85,8 +85,8 @@ class DocumentTestCase(TestCase):
def test_auto_trashing(self):
"""
Test document type trashing policies. Documents are moved to the trash,
x amount of time after being uploaded
Test document type trashing policies. Documents are moved to the
trash, x amount of time after being uploaded
"""
self.document_type.trash_time_period = 1
@@ -94,7 +94,9 @@ class DocumentTestCase(TestCase):
self.document_type.trash_time_unit = 'seconds'
self.document_type.save()
time.sleep(1)
# Needed by MySQL as milliseconds value is not store in timestamp
# field
time.sleep(2)
self.assertEqual(Document.objects.count(), 1)
self.assertEqual(DeletedDocument.objects.count(), 0)
@@ -123,6 +125,8 @@ class DocumentTestCase(TestCase):
self.assertEqual(Document.objects.count(), 0)
self.assertEqual(DeletedDocument.objects.count(), 1)
# Needed by MySQL as milliseconds value is not store in timestamp
# field
time.sleep(2)
DocumentType.objects.check_delete_periods()
@@ -216,8 +220,9 @@ class DocumentVersionTestCase(TestCase):
def test_revert_version(self):
self.assertEqual(self.document.versions.count(), 1)
# Needed by MySQL as milliseconds value is not store in timestamp field
time.sleep(1)
# Needed by MySQL as milliseconds value is not store in timestamp
# field
time.sleep(2)
with open(TEST_DOCUMENT_PATH) as file_object:
self.document.new_version(

View File

@@ -79,11 +79,15 @@ class MetadataForm(forms.Form):
attrs={'readonly': 'readonly'}
)
def clean_value(self):
return self.metadata_type.validate_value(
document_type=self.document_type, value=self.cleaned_data['value']
def clean(self):
if self.cleaned_data.get('update') and hasattr(self, 'metadata_type'):
self.cleaned_data['value'] = self.metadata_type.validate_value(
document_type=self.document_type,
value=self.cleaned_data.get('value')
)
return self.cleaned_data
MetadataFormSet = formset_factory(MetadataForm, extra=0)

View File

@@ -126,7 +126,7 @@ class MetadataType(models.Model):
if self.lookup:
lookup_options = self.get_lookup_values()
if value not in lookup_options:
if value and value not in lookup_options:
raise ValidationError(
_('Value is not one of the provided options.')
)

View File

@@ -63,8 +63,9 @@ class MetadataTestCase(TestCase):
self.document.metadata_value_of.test, TEST_DEFAULT_VALUE
)
def test_lookup(self):
def test_lookup_with_incorrect_value(self):
self.metadata_type.lookup = TEST_LOOKUP_TEMPLATE
self.metadata_type.save()
document_metadata = DocumentMetadata(
document=self.document, metadata_type=self.metadata_type,
@@ -76,8 +77,15 @@ class MetadataTestCase(TestCase):
document_metadata.full_clean()
document_metadata.save()
# Should not return error
document_metadata.value = TEST_CORRECT_LOOKUP_VALUE
def test_lookup_with_correct_value(self):
self.metadata_type.lookup = TEST_LOOKUP_TEMPLATE
self.metadata_type.save()
document_metadata = DocumentMetadata(
document=self.document, metadata_type=self.metadata_type,
value=TEST_CORRECT_LOOKUP_VALUE
)
document_metadata.full_clean()
document_metadata.save()
@@ -85,6 +93,22 @@ class MetadataTestCase(TestCase):
self.document.metadata_value_of.test, TEST_CORRECT_LOOKUP_VALUE
)
def test_empty_optional_lookup(self):
"""
Checks for GitLab issue #250
Empty optional lookup metadata trigger validation error
"""
self.metadata_type.lookup = TEST_LOOKUP_TEMPLATE
self.metadata_type.save()
document_metadata = DocumentMetadata(
document=self.document, metadata_type=self.metadata_type
)
document_metadata.full_clean()
document_metadata.save()
def test_validation(self):
self.metadata_type.validation = TEST_DATE_VALIDATOR

View File

@@ -2,7 +2,7 @@ from __future__ import absolute_import, unicode_literals
from django.conf import settings
from django.contrib import messages
from django.core.exceptions import PermissionDenied
from django.core.exceptions import PermissionDenied, ValidationError
from django.core.urlresolvers import reverse, reverse_lazy
from django.http import HttpResponseRedirect
from django.shortcuts import get_object_or_404, render_to_response
@@ -125,18 +125,22 @@ def metadata_edit(request, document_id=None, document_id_list=None):
except Exception as exception:
errors.append(exception)
if errors:
for error in errors:
if settings.DEBUG:
raise
else:
if isinstance(error, ValidationError):
exception_message = ', '.join(error.messages)
else:
exception_message = unicode(error)
messages.error(
request, _(
'Error editing metadata for document: '
'%(document)s; %(exception)s.'
) % {
'document': document,
'exception': ', '.join(exception.messages)
'exception': exception_message
}
)
else:

View File

@@ -71,11 +71,11 @@ class OCRAPITestCase(APITestCase):
self.assertTrue('Mayan EDMS Documentation' in content)
def test_get_document_version_content(self):
def test_get_document_version_page_content(self):
response = self.client.get(
reverse(
'rest_api:document-page-content-view',
args=(self.document.latest_version.pk,)
args=(self.document.latest_version.pages.first().pk,)
),
)

View File

@@ -104,6 +104,7 @@ class DocumentCreateWizard(ViewPermissionCheckMixin, SessionWizardView):
try:
for identifier, metadata in enumerate(self.get_cleaned_data_for_step(STEP_METADATA)):
if metadata.get('update'):
query_dict['metadata%s_id' % identifier] = metadata['id']
query_dict['metadata%s_value' % identifier] = metadata['value']
except TypeError:

View File

@@ -11,3 +11,5 @@ ipython==4.0.3
transifex-client==0.11
wheel==0.26.0
-r testing-base.txt