diff --git a/ckanext/odsh/fanstatic/tpsh_validate_password.js b/ckanext/odsh/fanstatic/tpsh_validate_password.js
new file mode 100644
index 0000000000000000000000000000000000000000..f0f8f71b55e4f6a2cd9e52c6a39b09ab302d2dab
--- /dev/null
+++ b/ckanext/odsh/fanstatic/tpsh_validate_password.js
@@ -0,0 +1,71 @@
+"use strict";
+
+function isPasswordValid(password) {
+    if (password.length == 0) return true;
+    var minimumLength = 8;
+    var isValid = 
+        (password.length >= minimumLength) &&
+        (atLeastOneUpperCaseLetter(password)) &&
+        (atLeastOneLowerCaseLetter(password)) &&
+        (atLeastOneNoneLetter(password));
+    return isValid
+
+    function atLeastOneUpperCaseLetter(password) {
+        return (password !== password.toLowerCase())
+    }
+
+    function atLeastOneLowerCaseLetter(password) {
+        return (password !== password.toUpperCase())
+    }
+
+    function atLeastOneNoneLetter(password) {
+        return /[\W\d_]/.test(password)
+    }
+}
+
+
+function showPasswordStatus(isValid, inputElement) {
+    if (isValid) {
+        messageText = '';
+    } else {
+        messageText = 'Passwörter müssen länger als 8 Zeichen sein und Großbuchstaben, Kleinbuchstaben und andere Zeichen enthalten.'
+    }
+    get_error_element(inputElement).innerHTML = messageText;
+
+    function get_error_element(inputElement) {
+        // assumes that there is an element after input_element's parent that
+        // contains a class "inline-error"
+        var currentNode = inputElement.parentNode
+        do {
+            currentNode = currentNode.nextElementSibling;
+        } while (
+            (currentNode !== null) &&
+            !(currentNode.classList.contains('inline-error'))
+        )
+        return currentNode
+    }
+}
+
+
+function setSubmitButtonState(isPasswordValid) {
+    var submitButton = document.getElementsByName('save')[0];
+    submitButton.disabled = !isPasswordValid;
+}
+
+
+ckan.module('tpsh_validate_password', function ($) {
+    return {
+        initialize: function () {
+            $.proxyAll(this, /_on/);
+            this.el.on('input', this._onChange);
+        },
+        
+        _onChange: function(event) {
+            var inputElement = event.target;
+            var newPassword = inputElement.value;
+            var isValid = isPasswordValid(newPassword);
+            showPasswordStatus(isValid, inputElement);
+            setSubmitButtonState(isValid);
+        }
+    };
+});
\ No newline at end of file
diff --git a/ckanext/odsh/logic/action.py b/ckanext/odsh/logic/action.py
index 8c707bcac4ff8ba8afb814010e7052ea0119bdb3..45880b8fdc03378ef303d3b446a38e5cf0454527 100644
--- a/ckanext/odsh/logic/action.py
+++ b/ckanext/odsh/logic/action.py
@@ -53,9 +53,6 @@ def check_password(password):
             any((c.isalpha()==False) for c in password)) #Number or Special character
         
 
-
-
-
 def odsh_user_create(context, data_dict):
     model = context['model']
     password = data_dict.get('password')
@@ -66,10 +63,8 @@ def odsh_user_create(context, data_dict):
         for group in groups:
             group_member_create(context, {'id': group, 'username': user.get('name'), 'role': 'member'})
         return model_dictize.user_dictize(model.User.get(user.get('name')), context)
-                
     else:
-        raise logic.ValidationError({'security': ['Passwort muss mindestens acht Zeichen, einen gross, einen klein Buchstaben und entweder eine Zahl oder Sondernzeichen enthalten!']})
-
+        raise logic.ValidationError({'security': ['Passwort muss mindestens acht Zeichen, einen gross, einen klein Buchstaben und entweder eine Zahl oder Sondernzeichen enthalten!']})          
   
 def tpsh_user_update(context, data_dict):
       password = data_dict.get('password')
diff --git a/ckanext/odsh/templates/user/edit_user_form.html b/ckanext/odsh/templates/user/edit_user_form.html
index 3395173452b1968ebbab4c5cacf8e7edca0d471e..be3545c6d2565a6bc29b1c4da16b207f56d1415a 100644
--- a/ckanext/odsh/templates/user/edit_user_form.html
+++ b/ckanext/odsh/templates/user/edit_user_form.html
@@ -1,4 +1,6 @@
 {% import 'macros/form.html' as form %}
+{% resource 'odsh/tpsh_validate_password.js' %}
+
 
 <form id="user-edit-form" class="dataset-form form-horizontal" method="post" action="{{ action }}">
   {{ form.errors(error_summary) }}
@@ -34,7 +36,12 @@
                   attrs={'autocomplete': 'off'}
                   ) }}
 
+<<<<<<< HEAD
     {{ form.input('password1', type='password', label=_('Password'), id='field-password', value=data.password1, error=errors.password1, classes=['control-medium'], attrs={'autocomplete': 'off'} ) }}
+=======
+    {{ form.input(
+        'password1', type='password', label=_('Password'), id='field-password', value=data.password1, error=errors.password1, classes=['control-medium'], attrs={'autocomplete': 'off', 'data-module': 'tpsh_validate_password'} ) }}
+>>>>>>> 5da13a4a8eb9f308d06e55026dd49aa00180f779
 
     {{ form.input('password2', type='password', label=_('Confirm Password'), id='field-password-confirm', value=data.password2, error=errors.password2, classes=['control-medium'], attrs={'autocomplete': 'off'}) }}
   </fieldset>
diff --git a/ckanext/odsh/tests_tpsh/test_checksum.py b/ckanext/odsh/tests_tpsh/test_checksum.py
index e3e4afc81f3877f47b6fe7944ee5466293ae41d5..6bff5d4fe469025e396c8b7e291e0d99106aad36 100644
--- a/ckanext/odsh/tests_tpsh/test_checksum.py
+++ b/ckanext/odsh/tests_tpsh/test_checksum.py
@@ -1,6 +1,6 @@
 from mock import patch, mock_open
 import nose.tools as nt
-from ckanext.odsh.lib.uploader import _raise_validation_error_if_hash_values_differ, _calculate_hash
+from ckanext.odsh.lib.uploader import _raise_validation_error_if_hash_values_differ, calculate_hash
 import ckantoolkit as ct
 import ckan.logic as logic
 import hashlib
@@ -51,7 +51,7 @@ class testHashException(object):
           # md5sum test.pdf
           expected_hash_pdf = '66123edf64fabf1c073fc45478bf4a57'
           with open(dir_path + '/resources/test.pdf') as f:
-               hash = _calculate_hash(f)
+               hash = calculate_hash(f)
           nt.assert_equal(hash, expected_hash_pdf)
 
                
diff --git a/ckanext/odsh/tests_tpsh/test_password_validation.py b/ckanext/odsh/tests_tpsh/test_password_validation.py
new file mode 100644
index 0000000000000000000000000000000000000000..c999b3974784df07d2da8c3d40ac1d9e11e8026d
--- /dev/null
+++ b/ckanext/odsh/tests_tpsh/test_password_validation.py
@@ -0,0 +1,35 @@
+# encoding: utf-8
+
+import nose.tools as nt
+from ckanext.odsh.logic.action import check_password
+
+class Test_PasswordValidation(object):
+
+    @staticmethod
+    def assert_password_invalid(password):
+        assert not check_password(password)
+    
+    @staticmethod
+    def assert_password_valid(password):
+        assert check_password(password)
+    
+    def test_valid_password(self):
+        self.assert_password_valid('Passwort1 :) :P :D')
+    
+    def test_umlaute(self):
+        self.assert_password_valid('Pässword')
+    
+    def test_no_uppercase(self):
+        self.assert_password_invalid('passwort1')
+    
+    def test_no_lowercase(self):
+        self.assert_password_invalid('PASSWORT1')
+    
+    def test_no_letters(self):
+        self.assert_password_invalid('37459073245!!?===))/=$§äüöÄÜÖ')
+    
+    def test_only_letters(self):
+        self.assert_password_invalid('ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz')
+    
+    def test_to_short(self):
+        self.assert_password_invalid('Pw123')
\ No newline at end of file