Allow '.' and '_' for public names

Fix #2593.
Also standardise error messages.
This commit is contained in:
Nicola Soranzo
2016-09-21 15:23:36 +01:00
parent 9ae56b782a
commit 0e0b773edc
4 changed files with 70 additions and 65 deletions
+21 -16
View File
@@ -9,15 +9,20 @@ import re
log = logging.getLogger( __name__ )
VALID_PUBLICNAME_RE = re.compile( "^[a-z0-9\-]+$" )
VALID_PUBLICNAME_SUB = re.compile( "[^a-z0-9\-]" )
# Email validity parameters
VALID_EMAIL_RE = re.compile( "[^@]+@[^@]+\.[^@]+" )
EMAIL_MAX_LEN = 255
# Public name validity parameters
PUBLICNAME_MIN_LEN = 3
PUBLICNAME_MAX_LEN = 255
# Basic regular expression to check email validity.
VALID_EMAIL_RE = re.compile( "[^@]+@[^@]+\.[^@]+" )
VALID_PUBLICNAME_RE = re.compile( "^[a-z0-9._\-]+$" )
VALID_PUBLICNAME_SUB = re.compile( "[^a-z0-9._\-]" )
FILL_CHAR = '-'
# Password validity parameters
PASSWORD_MIN_LEN = 6
def validate_email( trans, email, user=None, check_dup=True ):
"""
@@ -27,9 +32,9 @@ def validate_email( trans, email, user=None, check_dup=True ):
if user and user.email == email:
return message
if not( VALID_EMAIL_RE.match( email ) ):
message = "Please enter your real email address."
elif len( email ) > 255:
message = "Email address exceeds maximum allowable length."
message = "The format of the email address is not correct."
elif len( email ) > EMAIL_MAX_LEN:
message = "Email address cannot be more than %d characters in length." % EMAIL_MAX_LEN
elif check_dup and trans.sa_session.query( trans.app.model.User ).filter_by( email=email ).first():
message = "User with that email already exists."
# If the blacklist is not empty filter out the disposable domains.
@@ -48,13 +53,13 @@ def validate_publicname( trans, publicname, user=None ):
if user and user.username == publicname:
return ''
if len( publicname ) < PUBLICNAME_MIN_LEN:
return "Public name must be at least %d characters in length" % ( PUBLICNAME_MIN_LEN )
return "Public name must be at least %d characters in length." % ( PUBLICNAME_MIN_LEN )
if len( publicname ) > PUBLICNAME_MAX_LEN:
return "Public name cannot be more than %d characters in length" % ( PUBLICNAME_MAX_LEN )
return "Public name cannot be more than %d characters in length." % ( PUBLICNAME_MAX_LEN )
if not( VALID_PUBLICNAME_RE.match( publicname ) ):
return "Public name must contain only lower-case letters, numbers and '-'"
return "Public name must contain only lower-case letters, numbers, '.', '_' and '-'."
if trans.sa_session.query( trans.app.model.User ).filter_by( username=publicname ).first():
return "Public name is taken; please choose another"
return "Public name is taken; please choose another."
return ''
@@ -67,15 +72,15 @@ def transform_publicname( trans, publicname, user=None ):
elif publicname not in [ 'None', None, '' ]:
publicname = publicname.lower()
publicname = re.sub( VALID_PUBLICNAME_SUB, FILL_CHAR, publicname )
publicname = publicname.ljust( 4, FILL_CHAR )[:255]
publicname = publicname.ljust( PUBLICNAME_MIN_LEN + 1, FILL_CHAR )[:PUBLICNAME_MAX_LEN]
if not trans.sa_session.query( trans.app.model.User ).filter_by( username=publicname ).first():
return publicname
return ''
def validate_password( trans, password, confirm ):
if len( password ) < 6:
return "Use a password of at least 6 characters"
if len( password ) < PASSWORD_MIN_LEN:
return "Use a password of at least %d characters." % PASSWORD_MIN_LEN
elif password != confirm:
return "Passwords do not match"
return "Passwords don't match."
return ''
+4 -4
View File
@@ -9,7 +9,7 @@
function validateString(test_string, type) {
var mail_re = /^(([^<>()[\]\\.,;:\s@\"]+(\.[^<>()[\]\\.,;:\s@\"]+)*)|(\".+\"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/;
var username_re = /^[a-z0-9\-]{3,255}$/;
var username_re = /^[a-z0-9._\-]{3,255}$/;
if (type === 'email') {
return mail_re.test(test_string);
} else if (type === 'username'){
@@ -45,9 +45,9 @@
original_username = $( '#name_input' ).val();
$( '#login_info' ).bind( 'submit', function( e ) {
var error_text_email= 'Please enter your valid email address.';
var error_text_email_long= 'Email cannot be more than 255 characters in length.';
var error_text_username_characters = 'Public name must contain only lowercase letters, numbers and "-". It also has to be shorter than 255 characters but longer than 2.';
var error_text_email = 'The format of the email address is not correct.';
var error_text_email_long = 'Email address cannot be more than 255 characters in length.';
var error_text_username_characters = "Public name must contain only lowercase letters, numbers, '.', '_' and '-'. It also must be between 3 and 255 characters in length.";
var email = $( '#email_input' ).val();
var name = $( '#name_input' ).val();
var validForm = true;
+44 -44
View File
@@ -31,7 +31,7 @@ def inherit(context):
<div style="${ 'margin: 1em;' if context.get( 'use_panels', True ) else '' }">
%if redirect_url:
<script type="text/javascript">
<script type="text/javascript">
top.location.href = '${redirect_url | h}';
</script>
%elif message:
@@ -64,27 +64,27 @@ def inherit(context):
%>
<script type="text/javascript">
$(document).ready(function() {
$(document).ready(function() {
function validateString(test_string, type) {
var mail_re = /^(([^<>()[\]\\.,;:\s@\"]+(\.[^<>()[\]\\.,;:\s@\"]+)*)|(\".+\"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/;
//var mail_re_RFC822 = /^([^\x00-\x20\x22\x28\x29\x2c\x2e\x3a-\x3c\x3e\x40\x5b-\x5d\x7f-\xff]+|\x22([^\x0d\x22\x5c\x80-\xff]|\x5c[\x00-\x7f])*\x22)(\x2e([^\x00-\x20\x22\x28\x29\x2c\x2e\x3a-\x3c\x3e\x40\x5b-\x5d\x7f-\xff]+|\x22([^\x0d\x22\x5c\x80-\xff]|\x5c[\x00-\x7f])*\x22))*\x40([^\x00-\x20\x22\x28\x29\x2c\x2e\x3a-\x3c\x3e\x40\x5b-\x5d\x7f-\xff]+|\x5b([^\x0d\x5b-\x5d\x80-\xff]|\x5c[\x00-\x7f])*\x5d)(\x2e([^\x00-\x20\x22\x28\x29\x2c\x2e\x3a-\x3c\x3e\x40\x5b-\x5d\x7f-\xff]+|\x5b([^\x0d\x5b-\x5d\x80-\xff]|\x5c[\x00-\x7f])*\x5d))*$/;
var username_re = /^[a-z0-9\-]{3,255}$/;
if (type === 'email') {
return mail_re.test(test_string);
} else if (type === 'username'){
return username_re.test(test_string);
}
}
function validateString(test_string, type) {
var mail_re = /^(([^<>()[\]\\.,;:\s@\"]+(\.[^<>()[\]\\.,;:\s@\"]+)*)|(\".+\"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/;
//var mail_re_RFC822 = /^([^\x00-\x20\x22\x28\x29\x2c\x2e\x3a-\x3c\x3e\x40\x5b-\x5d\x7f-\xff]+|\x22([^\x0d\x22\x5c\x80-\xff]|\x5c[\x00-\x7f])*\x22)(\x2e([^\x00-\x20\x22\x28\x29\x2c\x2e\x3a-\x3c\x3e\x40\x5b-\x5d\x7f-\xff]+|\x22([^\x0d\x22\x5c\x80-\xff]|\x5c[\x00-\x7f])*\x22))*\x40([^\x00-\x20\x22\x28\x29\x2c\x2e\x3a-\x3c\x3e\x40\x5b-\x5d\x7f-\xff]+|\x5b([^\x0d\x5b-\x5d\x80-\xff]|\x5c[\x00-\x7f])*\x5d)(\x2e([^\x00-\x20\x22\x28\x29\x2c\x2e\x3a-\x3c\x3e\x40\x5b-\x5d\x7f-\xff]+|\x5b([^\x0d\x5b-\x5d\x80-\xff]|\x5c[\x00-\x7f])*\x5d))*$/;
var username_re = /^[a-z0-9._\-]{3,255}$/;
if (type === 'email') {
return mail_re.test(test_string);
} else if (type === 'username'){
return username_re.test(test_string);
}
}
function renderError(message) {
if (!$(".errormessage").size()) {
function renderError(message) {
if (!$(".errormessage").size()) {
$('<div/>').addClass('errormessage').insertBefore('#registrationForm');
}
console.debug( $( '#registrationForm' ) );
console.debug( '.errormessage:', $( '.errormessage' ) );
$(".errormessage").html(message);
}
$(".errormessage").html(message);
}
$("[name='password']").complexify({'minimumChars':6}, function(valid, complexity){
var progressBar = $('.progress-bar');
@@ -95,35 +95,35 @@ def inherit(context):
});
$('#registration').bind('submit', function(e) {
$('#send').attr('disabled', 'disabled');
$('#send').attr('disabled', 'disabled');
// we need this value to detect submitting at backend
var hidden_input = '<input type="hidden" id="create_user_button" name="create_user_button" value="Submit"/>';
$("#email_input").before(hidden_input);
var hidden_input = '<input type="hidden" id="create_user_button" name="create_user_button" value="Submit"/>';
$("#email_input").before(hidden_input);
var error_text_email= 'Please enter your valid email address';
var error_text_email_long= 'Email cannot be more than 255 characters in length';
var error_text_username_characters = 'Public name must contain only lowercase letters, numbers and "-". It also has to be shorter than 255 characters but longer than 2.';
var error_text_password_short = 'Please use a password of at least 6 characters';
var error_text_password_match = "Passwords don't match";
var error_text_email = 'The format of the email address is not correct.';
var error_text_email_long = 'Email address cannot be more than 255 characters in length.';
var error_text_username_characters = "Public name must contain only lowercase letters, numbers, '.', '_' and '-'. It also has to be between 3 and 255 characters in length.";
var error_text_password_short = 'Use a password of at least 6 characters';
var error_text_password_match = "Passwords don't match";
var validForm = true;
var email = $('#email_input').val();
var name = $('#name_input').val();
if (email.length > 255){ renderError(error_text_email_long); validForm = false;}
else if (!validateString(email,"email")){ renderError(error_text_email); validForm = false;}
else if (!($('#password_input').val() === $('#password_check_input').val())){ renderError(error_text_password_match); validForm = false;}
else if ($('#password_input').val().length < 6 ){ renderError(error_text_password_short); validForm = false;}
else if (name && !(validateString(name,"username"))){ renderError(error_text_username_characters); validForm = false;}
var validForm = true;
if (!validForm) {
e.preventDefault();
// reactivate the button if the form wasn't submitted
$('#send').removeAttr('disabled');
}
});
});
var email = $('#email_input').val();
var name = $('#name_input').val();
if (email.length > 255){ renderError(error_text_email_long); validForm = false;}
else if (!validateString(email,"email")){ renderError(error_text_email); validForm = false;}
else if (!($('#password_input').val() === $('#password_check_input').val())){ renderError(error_text_password_match); validForm = false;}
else if ($('#password_input').val().length < 6 ){ renderError(error_text_password_short); validForm = false;}
else if (name && !(validateString(name,"username"))){ renderError(error_text_username_characters); validForm = false;}
if (!validForm) {
e.preventDefault();
// reactivate the button if the form wasn't submitted
$('#send').removeAttr('disabled');
}
});
});
</script>
<div id="registrationForm" class="toolForm">
@@ -195,10 +195,10 @@ def inherit(context):
%endfor
%if not user_type_fd_id_select_field:
<input type="hidden" name="user_type_fd_id" value="${trans.security.encode_id( user_type_form_definition.id )}"/>
%endif
%endif
%endif
<div id="for_bears">
If you see this, please leave following field blank.
If you see this, please leave following field blank.
<input type="text" name="bear_field" size="1" value=""/>
</div>
<div class="form-row">
@@ -207,7 +207,7 @@ def inherit(context):
</form>
%if registration_warning_message:
<div class="alert alert-danger" style="margin: 30px 12px 12px 12px;">
${registration_warning_message}
${registration_warning_message}
</div>
%endif
</div>
+1 -1
View File
@@ -245,7 +245,7 @@ class UserDeserializerTestCase( BaseTestCase ):
self.deserializer.deserialize, user, { 'username': 'ed' }, trans=self.trans )
self.assertTrue( 'Public name must be at least' in str( exception ) )
self.assertRaises( base_manager.ModelDeserializingError, self.deserializer.deserialize,
user, { 'username': 'f.d.r.' }, trans=self.trans )
user, { 'username': 'f,d,r,' }, trans=self.trans )
self.log( "usernames must be unique" )
self.user_manager.create( **user3_data )