models: Enforce stricter requirements on the full_name field.

This changes the requirements for UserProfile to disallow some
additional characters, with the overall goal of being able to use
formataddr in send_mail.py.

We don't need to be particularly careful in the database migration,
because user full_names are not required to be unique.
This commit is contained in:
Conner Bondurant
2019-06-28 22:41:13 -04:00
committed by Tim Abbott
parent f54a63e2f9
commit c25dcf048d
3 changed files with 38 additions and 3 deletions

View File

@@ -1,5 +1,7 @@
from typing import Dict, List, Optional, Union, cast from typing import Dict, List, Optional, Union, cast
import unicodedata
from django.db.models.query import QuerySet from django.db.models.query import QuerySet
from django.utils.translation import ugettext as _ from django.utils.translation import ugettext as _
@@ -19,7 +21,9 @@ def check_full_name(full_name_raw: str) -> str:
raise JsonableError(_("Name too long!")) raise JsonableError(_("Name too long!"))
if len(full_name) < UserProfile.MIN_NAME_LENGTH: if len(full_name) < UserProfile.MIN_NAME_LENGTH:
raise JsonableError(_("Name too short!")) raise JsonableError(_("Name too short!"))
if list(set(full_name).intersection(UserProfile.NAME_INVALID_CHARS)): for character in full_name:
if (unicodedata.category(character)[0] == 'C' or
character in UserProfile.NAME_INVALID_CHARS):
raise JsonableError(_("Invalid characters in name!")) raise JsonableError(_("Invalid characters in name!"))
return full_name return full_name

View File

@@ -0,0 +1,31 @@
# -*- coding: utf-8 -*-
# Generated by Django 1.11.20 on 2019-06-28 21:45
from __future__ import unicode_literals
from django.db import migrations
from django.db.backends.postgresql_psycopg2.schema import DatabaseSchemaEditor
from django.db.migrations.state import StateApps
from unicodedata import category
NAME_INVALID_CHARS = ['*', '`', "\\", '>', '"', '@']
def remove_name_illegal_chars(apps: StateApps, schema_editor: DatabaseSchemaEditor) -> None:
UserProfile = apps.get_model("zerver", "UserProfile")
for user in UserProfile.objects.all():
stripped = []
for char in user.full_name:
if (char not in NAME_INVALID_CHARS) and (category(char)[0] != "C"):
stripped.append(char)
user.full_name = "".join(stripped)
user.save(update_fields=["full_name"])
class Migration(migrations.Migration):
dependencies = [
('zerver', '0235_userprofile_desktop_icon_count_display'),
]
operations = [
migrations.RunPython(remove_name_illegal_chars)
]

View File

@@ -737,7 +737,7 @@ class UserProfile(AbstractBaseUser, PermissionsMixin):
MAX_NAME_LENGTH = 100 MAX_NAME_LENGTH = 100
MIN_NAME_LENGTH = 2 MIN_NAME_LENGTH = 2
API_KEY_LENGTH = 32 API_KEY_LENGTH = 32
NAME_INVALID_CHARS = ['*', '`', '>', '"', '@'] NAME_INVALID_CHARS = ['*', '`', "\\", '>', '"', '@']
DEFAULT_BOT = 1 DEFAULT_BOT = 1
""" """