mirror of
https://github.com/jwinterm/modoboa.git
synced 2026-10-18 05:51:26 +02:00
Merge pull request #3856 from modoboa/fix/imap-migration-password-escaping
Make sure passwords are properly generated in config file.
This commit is contained in:
@@ -47,11 +47,11 @@ class Migration(models.Model):
|
||||
return self.username
|
||||
|
||||
@property
|
||||
def password(self):
|
||||
def password(self) -> str:
|
||||
"""Password getter."""
|
||||
return decrypt(self._password)
|
||||
return decrypt(self._password).replace("%", "%%")
|
||||
|
||||
@password.setter
|
||||
def password(self, value):
|
||||
def password(self, value: str) -> None:
|
||||
"""Password setter."""
|
||||
self._password = encrypt(value)
|
||||
|
||||
@@ -11,7 +11,7 @@ type = IMAP
|
||||
ssl = false
|
||||
remotehost = localhost
|
||||
remoteuser = {{ migration.mailbox }}
|
||||
remotepass = {{ migration.password }}
|
||||
remotepass = {% autoescape off %}{{ migration.password }}{% endautoescape %}
|
||||
{% if imap_create_folders == False %}
|
||||
createfolders = False
|
||||
{% endif %}
|
||||
@@ -27,7 +27,7 @@ sslcacertfile = /etc/ssl/certs/ca-certificates.crt
|
||||
ssl = no
|
||||
{% endif %}
|
||||
remoteuser = {{ migration }}
|
||||
remotepass = {{ migration.password }}
|
||||
remotepass = {% autoescape off %}{{ migration.password }}{% endautoescape %}
|
||||
readonly = true
|
||||
{% autoescape off %}
|
||||
{% if imap_folder_filter_exclude|length > 0 %}
|
||||
|
||||
@@ -115,6 +115,27 @@ class ManagementCommandTestCase(DataMixin, ModoTestCase):
|
||||
conf.read(path)
|
||||
self.assertTrue(conf.has_section("Account user@test.com"))
|
||||
|
||||
def test_password_escaping(self):
|
||||
"""Check that passwords are escaped when needed."""
|
||||
self.migration.password = "%Test1234"
|
||||
self.migration.save()
|
||||
path = os.path.join(self.workdir, "offlineimap.conf")
|
||||
call_command("generate_offlineimap_config", "--output", path)
|
||||
self.assertTrue(os.path.exists(path))
|
||||
conf = configparser.ConfigParser()
|
||||
conf.read(path)
|
||||
section = "Repository Local_user@test.com"
|
||||
self.assertEqual(conf.get(section, "remotepass"), "%Test1234")
|
||||
|
||||
self.migration.password = "Test&1234"
|
||||
self.migration.save()
|
||||
call_command("generate_offlineimap_config", "--output", path)
|
||||
self.assertTrue(os.path.exists(path))
|
||||
conf = configparser.ConfigParser()
|
||||
conf.read(path)
|
||||
section = "Repository Local_user@test.com"
|
||||
self.assertEqual(conf.get(section, "remotepass"), self.migration.password)
|
||||
|
||||
|
||||
class ViewSetTestCase(DataMixin, ModoAPITestCase):
|
||||
"""ViewSet related tests."""
|
||||
|
||||
@@ -27,12 +27,12 @@ def _get_fernet():
|
||||
return Fernet(secret_key)
|
||||
|
||||
|
||||
def encrypt(clear_value):
|
||||
def encrypt(clear_value: bytes) -> str:
|
||||
"""Encrypt a value using secret_key."""
|
||||
return smart_str(_get_fernet().encrypt(smart_bytes(clear_value)))
|
||||
|
||||
|
||||
def decrypt(encrypted_value):
|
||||
def decrypt(encrypted_value: bytes) -> str:
|
||||
"""Decrypt a value using secret_key."""
|
||||
return smart_str(_get_fernet().decrypt(smart_bytes(encrypted_value)))
|
||||
|
||||
|
||||
Reference in New Issue
Block a user