From 0cc4ec245e85e66e53d9515161973710eb1aabc4 Mon Sep 17 00:00:00 2001
From: Alberto Berti
Date: Mon, 23 Dec 2013 01:00:19 +0100
Subject: [PATCH 01/32] Update italian translation
---
modoboa/locale/it/LC_MESSAGES/django.po | 314 ++++++++--------------
modoboa/locale/it/LC_MESSAGES/djangojs.po | 12 +-
2 files changed, 118 insertions(+), 208 deletions(-)
diff --git a/modoboa/locale/it/LC_MESSAGES/django.po b/modoboa/locale/it/LC_MESSAGES/django.po
index f34f4bd71..425aa602e 100644
--- a/modoboa/locale/it/LC_MESSAGES/django.po
+++ b/modoboa/locale/it/LC_MESSAGES/django.po
@@ -7,8 +7,8 @@ msgid ""
msgstr ""
"Project-Id-Version: PACKAGE VERSION\n"
"Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2013-12-15 10:20+0100\n"
-"PO-Revision-Date: 2013-09-27 00:07+0200\n"
+"POT-Creation-Date: 2013-12-22 23:15+0100\n"
+"PO-Revision-Date: 2013-12-23 00:56+0100\n"
"Last-Translator: Alberto Berti \n"
"Language-Team: ITALIANO \n"
"Language: it\n"
@@ -49,23 +49,23 @@ msgstr "Schema password predefinito"
#: core/app_settings.py:51
msgid "md5crypt (weak)"
-msgstr ""
+msgstr "md5crypt (debole)"
#: core/app_settings.py:52
msgid "sha256 (weak)"
-msgstr ""
+msgstr "sha256 (debole)"
#: core/app_settings.py:53
msgid "md5 (weak)"
-msgstr ""
+msgstr "md5 (debole)"
#: core/app_settings.py:54
msgid "crypt (weak)"
-msgstr ""
+msgstr "crypt (debole)"
#: core/app_settings.py:55
msgid "plain (weak)"
-msgstr ""
+msgstr "plain (debole)"
#: core/app_settings.py:57
msgid "Scheme used to crypt mailbox passwords"
@@ -74,13 +74,13 @@ msgstr ""
#: core/app_settings.py:61
msgid "Rounds"
-msgstr ""
+msgstr "Cicli"
#: core/app_settings.py:64
msgid ""
"Number of rounds to use (only used by sha256crypt and sha512crypt). Must be "
"between 1000 and 999999999, inclusive."
-msgstr ""
+msgstr "Numero di cicli da utilizzare (valido per sha256crypt e sha512crypt). Dev'essere tra 1000 e 999999999, inclusivo."
#: core/app_settings.py:70
msgid "Secret key"
@@ -159,14 +159,12 @@ msgstr ""
"DN')"
#: core/app_settings.py:121
-#, fuzzy
msgid "Users search base"
-msgstr "Ricerca base"
+msgstr "Base ricerca per gli utenti"
#: core/app_settings.py:123
-#, fuzzy
msgid "The distinguished name of the search base used to find users"
-msgstr "Nome particolare della ricerca base"
+msgstr "L'identificativo (dn:) della base di ricerca utilizzata per cercare gli utenti"
#: core/app_settings.py:128
msgid "Search filter"
@@ -210,25 +208,22 @@ msgid "Tell if the LDAP server is an Active Directory one"
msgstr "Segnala se il server LDAP è una Active Directory"
#: core/app_settings.py:154
-#, fuzzy
msgid "Administrator groups"
-msgstr "Amministratori"
+msgstr "Gruppi degli amministratori"
#: core/app_settings.py:157
msgid ""
"Members of those LDAP Posix groups will be created as domain administrators. "
"Use ';' characters to separate groups."
-msgstr ""
+msgstr "Gli appartenenti a questi gruppi LDAP Posix avranno i privilegi di amministratori di dominio. Utilizza il carattere ';' per separare valori multipli."
#: core/app_settings.py:164
-#, fuzzy
msgid "Groups search base"
-msgstr "Ricerca base"
+msgstr "Base ricerca per i gruppi"
#: core/app_settings.py:167
-#, fuzzy
msgid "The distinguished name of the search base used to find groups"
-msgstr "Nome particolare della ricerca base"
+msgstr "L'identificatore (dn:) della base di ricerca utilizzato per trovare i gruppi"
#: core/app_settings.py:172
#: extensions/admin/templates/admin/editdomainform.html:7
@@ -270,9 +265,8 @@ msgid "Invalid syntax"
msgstr "Sintassi errata"
#: core/app_settings.py:233
-#, fuzzy
msgid "Invalid rounds number"
-msgstr "Richiesta non valida"
+msgstr "Numero di cicli non valido"
#: core/app_settings.py:256
msgid "This field is required"
@@ -322,14 +316,12 @@ msgid "Passwords mismatch"
msgstr "La password non corrisponde"
#: core/models.py:50
-#, fuzzy
msgid "password"
-msgstr "Password"
+msgstr "password"
#: core/models.py:52
-#, fuzzy
msgid "last login"
-msgstr "Ultimo login"
+msgstr "ultimo login"
#: core/models.py:81
msgid "You can't delete your own account"
@@ -513,7 +505,7 @@ msgstr "Aggiorna le informazioni personali"
#: extensions/admin/views/identity.py:197
#: extensions/postfix_autoreply/templates/postfix_autoreply/autoreply.html:9
#: extensions/postfix_relay_domains/views.py:63
-#: extensions/sievefilters/views.py:163 extensions/webmail/views.py:170
+#: extensions/sievefilters/views.py:166 extensions/webmail/views.py:170
#: extensions/webmail/views.py:205
msgid "Update"
msgstr "Aggiorna"
@@ -613,9 +605,8 @@ msgid "Web based console to manage domains, accounts and aliases"
msgstr "Interfaccia web per l'amministrazione di domini, account e alias"
#: extensions/admin/__init__.py:55
-#, fuzzy
msgid "Administration"
-msgstr "Amministratori"
+msgstr "Amministrazione"
#: extensions/admin/__init__.py:79
#: extensions/admin/templates/admin/domains.html:2
@@ -668,15 +659,14 @@ msgid "The UNIX account who owns mailboxes on the filesystem"
msgstr "L'account UNIX a cui appartengono le caselle postali nel filsystem"
#: extensions/admin/app_settings.py:26
-#, fuzzy
msgid "Default domain quota"
-msgstr "Limiti predefiniti"
+msgstr "Quota predefinita per il domini"
#: extensions/admin/app_settings.py:29
msgid ""
"Default quota (in MB) applied to freshly created domains with no value "
"specified. A value of 0 means no quota."
-msgstr ""
+msgstr "Quota predefinita (in MB) applicata ai nuovi domini che non la specificano. Un valore 0 implica nessuna quota."
#: extensions/admin/app_settings.py:36
msgid "Automatic account removal"
@@ -690,19 +680,17 @@ msgstr ""
#: extensions/admin/app_settings.py:69 extensions/admin/forms/account.py:178
#: extensions/admin/forms/domain.py:56
msgid "Must be a positive integer"
-msgstr ""
+msgstr "Dev'essere un intero positivo"
#: extensions/admin/lib.py:28
-#, fuzzy
msgid "A mailbox is required"
-msgstr "È richiesta una quota"
+msgstr "É necessaria una casella"
#: extensions/admin/forms/account.py:21
-#, fuzzy
msgid ""
"The user's name. Must be a valid e-mail address for simple users or "
"administrators with a mailbox."
-msgstr "L'utente '%s' deve avere un indirizzo email valido"
+msgstr "Il nome dell'utente. Dev'essere un indirizzo e-mail per gli utenti semplici o gli amministratori che posseggono una casella"
#: extensions/admin/forms/account.py:26
msgid "Role"
@@ -839,11 +827,10 @@ msgid "No recipient defined"
msgstr "Non è stato definito un destinatario"
#: extensions/admin/forms/domain.py:20
-#, fuzzy
msgid ""
"Default quota in MB applied to mailboxes. Leave empty to use the default "
"value."
-msgstr "Quota in MB predefinita applicata alle caselle di posta"
+msgstr "Quota in MB predefinita applicata alle caselle di posta. Lascialo vuoto se vuoi applicare il valore predefinito."
#: extensions/admin/forms/domain.py:29
msgid ""
@@ -856,23 +843,21 @@ msgstr ""
#: extensions/admin/forms/domain.py:75
#: extensions/postfix_relay_domains/forms.py:50
#: extensions/postfix_relay_domains/forms.py:70
-#, fuzzy
msgid "domain alias"
-msgstr "Alias del dominio"
+msgstr "alias del dominio"
#: extensions/admin/forms/domain.py:82 extensions/admin/forms/domain.py:98
#: extensions/postfix_relay_domains/forms.py:58
#: extensions/postfix_relay_domains/forms.py:78
-#, fuzzy, python-format
+#, python-format
msgid "A %s with this name already exists"
-msgstr "Un alias con questo nome esiste già"
+msgstr "Un %s con questo nome esiste già"
#: extensions/admin/forms/domain.py:92
#: extensions/postfix_relay_domains/forms.py:49
#: extensions/postfix_relay_domains/forms.py:71
-#, fuzzy
msgid "domain"
-msgstr "Domini"
+msgstr "dominio"
#: extensions/admin/forms/domain.py:176
msgid "Create a domain administrator"
@@ -1032,14 +1017,13 @@ msgid "Check to activate this domain"
msgstr "Seleziona per attivare questo dominio"
#: extensions/admin/models/domain.py:61
-#, fuzzy
msgid "Domain"
-msgstr "Domini"
+msgstr "Dominio"
#: extensions/admin/models/domain.py:140
#, python-format
msgid "Invalid quota value for domain '%s'"
-msgstr ""
+msgstr "Valore della quota non valido per il dominio '%s'"
#: extensions/admin/models/domain_alias.py:11
#: extensions/postfix_relay_domains/models.py:160
@@ -1056,9 +1040,9 @@ msgid "The domain this alias points to"
msgstr "Il dominio a cui punta questo alias"
#: extensions/admin/models/domain_alias.py:46
-#, fuzzy, python-format
+#, python-format
msgid "A domain %s already exists"
-msgstr "La casella di posta %s esiste già"
+msgstr "Esiste già un dominio %s"
#: extensions/admin/models/domain_alias.py:51
#, python-format
@@ -1090,9 +1074,8 @@ msgid "MB"
msgstr "MB"
#: extensions/admin/templates/admin/domain_options_form.html:5
-#, fuzzy
msgid "You can't create a new domain administrator"
-msgstr "Crea un amministratore di dominio"
+msgstr "Non ti è possibile creare un amministratore di dominio"
#: extensions/admin/templates/admin/domains_table.html:7
#: extensions/admin/templates/admin/identities_table.html:7
@@ -1102,7 +1085,7 @@ msgstr "Tag"
#: extensions/admin/templates/admin/domains_table.html:8
#: extensions/admin/templates/admin/identities_table.html:8
#: extensions/admin/templates/admin/listing.html:17
-#: extensions/sievefilters/views.py:93
+#: extensions/sievefilters/views.py:95
#: extensions/sievefilters/templates/sievefilters/filter.html:17
#: extensions/sievefilters/templates/sievefilters/guieditor.html:5
#: extensions/webmail/templatetags/webmail_tags.py:101
@@ -1257,7 +1240,7 @@ msgstr "Un alias con questo nome esiste già"
#: extensions/admin/views/domain.py:129 extensions/admin/views/identity.py:131
#: extensions/admin/views/identity.py:158
#: extensions/postfix_relay_domains/views.py:32
-#: extensions/sievefilters/views.py:141 extensions/sievefilters/views.py:230
+#: extensions/sievefilters/views.py:144 extensions/sievefilters/views.py:233
#: extensions/webmail/views.py:151
msgid "Create"
msgstr "Crea"
@@ -1374,7 +1357,7 @@ msgstr[0] "Account cancellato"
msgstr[1] "Account cancellati"
#: extensions/admin/views/import.py:39
-#, fuzzy, python-format
+#, python-format
msgid ""
"Provide a CSV file where lines respect one of the following formats:\n"
"\n"
@@ -1389,10 +1372,9 @@ msgstr ""
"Fornire un file CSV le cui righe rispettino uno dei seguenti formati:\n"
"\n"
" - dominio; nome; quota; abilitato
\n"
-" - aliasdominio; nome; dominio target; abilitato
\n"
+" - aliasdominio; nome; dominio di destinazione; abilitato
\n"
"
\n"
-"Il primo elemento di ogni riga è obbligatorio e deve essere uguale a "
-"quello dei valori precedenti.
\n"
+"Il primo elemento di ogni riga è obbligatorio e deve essere uguale a quello dei valori precedenti.
\n"
"\n"
"Come separatore puoi utilizzare un carattere diverso.
\n"
@@ -1411,7 +1393,6 @@ msgid "%d objects imported successfully"
msgstr "%d oggetti importati correttamente"
#: extensions/admin/views/import.py:153
-#, fuzzy
msgid ""
"Provide a CSV file where lines respect one of the following formats:\n"
"\n"
@@ -1428,15 +1409,12 @@ msgid ""
msgstr ""
"Fornire un file CSV le cui righe rispettino uno dei seguenti formati:\n"
"\n"
-"- account; loginname; password; nome; cognome; abilitato; group; "
-"indirizzo[, dominio, ...]
\n"
+"- account; id utente; password; nome; cognome; abilitato; gruppo; indirizzo; quota; [, dominio, ...]
\n"
"- alias; indirizzo; abilitato; destinatario interno
\n"
"- forward; indirizzo; abilitato; destinatario esterno
\n"
-"- dlist; indirizzo; abilitato; destinatario; destinatario; ..."
-"li>\n"
+"
- dlist; indirizzo; abilitato; destinatario; destinatario; ...
\n"
"
\n"
-"Il primo elemento di ogni riga è obbligatorio e deve essere uguale a "
-"quello dei valori precedenti.
\n"
+"Il primo elemento di ogni riga è obbligatorio e deve essere uguale a quello dei valori precedenti.
\n"
"\n"
"Come separatore puoi utilizzare un carattere diverso.
\n"
@@ -1558,9 +1536,8 @@ msgid "pending requests"
msgstr "richieste in sospeso"
#: extensions/amavis/general_callbacks.py:124
-#, fuzzy
msgid "Pending requests"
-msgstr "richieste in sospeso"
+msgstr "Richieste in sospeso"
#: extensions/amavis/general_callbacks.py:134
msgid "Content filter"
@@ -1576,12 +1553,12 @@ msgid "Virus filter"
msgstr "Filtro virus"
#: extensions/amavis/models.py:94 extensions/amavis/models.py:102
-#: extensions/amavis/models.py:110 extensions/sievefilters/views.py:290
+#: extensions/amavis/models.py:110 extensions/sievefilters/views.py:293
msgid "yes"
msgstr "si"
#: extensions/amavis/models.py:95 extensions/amavis/models.py:103
-#: extensions/amavis/models.py:111 extensions/sievefilters/views.py:294
+#: extensions/amavis/models.py:111 extensions/sievefilters/views.py:297
msgid "no"
msgstr "no"
@@ -1631,7 +1608,7 @@ msgstr ""
#: extensions/amavis/sql_listing.py:31
msgid "Score"
-msgstr ""
+msgstr "Punteggio"
#: extensions/amavis/sql_listing.py:35
#: extensions/amavis/templatetags/amavis_tags.py:75
@@ -1708,9 +1685,8 @@ msgid "Quarantine management"
msgstr "Gestione quarantena"
#: extensions/amavis/templates/amavis/main_action_bar.html:3
-#, fuzzy
msgid "Select"
-msgstr "Seleziona un file"
+msgstr "Seleziona"
#: extensions/amavis/templates/amavis/main_action_bar.html:9
msgid "Spam"
@@ -1721,7 +1697,6 @@ msgid "Virus"
msgstr "Virus"
#: extensions/amavis/templates/amavis/main_action_bar.html:11
-#, fuzzy
msgid "Bad Header"
msgstr "Intestazione errata"
@@ -1730,9 +1705,8 @@ msgid "Bad MIME"
msgstr "MIME errato"
#: extensions/amavis/templates/amavis/main_action_bar.html:13
-#, fuzzy
msgid "Banned"
-msgstr "Filtro banned"
+msgstr "Banditi"
#: extensions/amavis/templates/amavis/main_action_bar.html:18
#: extensions/amavis/templatetags/amavis_tags.py:19
@@ -1754,32 +1728,27 @@ msgstr "Tutti i messaggi"
#: extensions/amavis/templates/amavis/main_action_bar.html:31
msgid "All"
-msgstr ""
+msgstr "Tutti"
#: extensions/amavis/templates/amavis/main_action_bar.html:32
-#, fuzzy
msgid "Spam only"
-msgstr "Spam"
+msgstr "Solo messaggi di spam"
#: extensions/amavis/templates/amavis/main_action_bar.html:33
-#, fuzzy
msgid "Virus only"
-msgstr "Virus"
+msgstr "Solo messaggi con virus"
#: extensions/amavis/templates/amavis/main_action_bar.html:34
-#, fuzzy
msgid "Bad Header only"
-msgstr "Intestazione errata"
+msgstr "Solo messaggi con intestazione errata"
#: extensions/amavis/templates/amavis/main_action_bar.html:35
-#, fuzzy
msgid "Bad MIME only"
-msgstr "MIME errato"
+msgstr "Solo messaggi con struttura MIME errata"
#: extensions/amavis/templates/amavis/main_action_bar.html:36
-#, fuzzy
msgid "Banned only"
-msgstr "Filtro banned"
+msgstr "Solo messaggi banditi"
#: extensions/amavis/templates/amavis/notifications/pending_requests.html:1
#, python-format
@@ -1954,23 +1923,21 @@ msgstr ""
"destinatario"
#: extensions/postfix_autoreply/app_settings.py:20
-#, fuzzy
msgid "Default subject"
-msgstr "Editor predefinito"
+msgstr "Oggetto predefinito"
#: extensions/postfix_autoreply/app_settings.py:21
msgid "I'm off"
-msgstr ""
+msgstr "Sono via"
#: extensions/postfix_autoreply/app_settings.py:23
msgid ""
"Default subject used when an auto-reply message is created automatically"
-msgstr ""
+msgstr "Oggetto predefinito utilizzato nei messaggi di risposta automatica"
#: extensions/postfix_autoreply/app_settings.py:28
-#, fuzzy
msgid "Default content"
-msgstr "Editor predefinito"
+msgstr "Corpo del messaggio predefinito"
#: extensions/postfix_autoreply/app_settings.py:30
#, python-format
@@ -1980,18 +1947,21 @@ msgid ""
"Best regards,\n"
"%(name)s\n"
msgstr ""
+"Al momento non posso rispondere. Risponderò al mio ritorno.\n"
+"\n"
+"Distinti saluti,\n"
+"%(name)s"
#: extensions/postfix_autoreply/app_settings.py:36
#, python-format
msgid ""
"Default content used when an auto-reply message is created automatically. "
"The '%(name)s' macro will be replaced by the user's full name."
-msgstr ""
+msgstr "Corpo del messaggio predefinito per i messaggi di risposta automatica. La macro '%(name)s' verrà sostituita con il nome dell'utente. "
#: extensions/postfix_autoreply/forms.py:13
-#, fuzzy
msgid "Activate your auto reply from this date"
-msgstr "Attiva la tua risposta automatica fino a questa data"
+msgstr "Attiva la risposta automatica da questa data"
#: extensions/postfix_autoreply/forms.py:19
msgid "Until"
@@ -2007,9 +1977,8 @@ msgid "This date is over"
msgstr "Questa data è passata"
#: extensions/postfix_autoreply/forms.py:59
-#, fuzzy
msgid "Must be greater than start date"
-msgstr "è maggiore di"
+msgstr "Dev'essere successiva alla data di inizio"
#: extensions/postfix_autoreply/general_callbacks.py:33
#: extensions/postfix_autoreply/templates/postfix_autoreply/autoreply.html:2
@@ -2018,11 +1987,11 @@ msgstr "Messaggio di risposta automatica"
#: extensions/postfix_autoreply/general_callbacks.py:118
msgid "Enable auto-reply"
-msgstr ""
+msgstr "Abilita la risposta automatica"
#: extensions/postfix_autoreply/general_callbacks.py:120
msgid "Enable or disable Postfix auto-reply"
-msgstr ""
+msgstr "Abilita o disabilita la risposta automatica di Postfix"
#: extensions/postfix_autoreply/models.py:20
msgid "subject"
@@ -2054,65 +2023,54 @@ msgstr "Definisci un messaggio da inviare automaticamente quando sei via"
#: extensions/postfix_relay_domains/__init__.py:72
msgid "Relay domains support for Postfix"
-msgstr ""
+msgstr "Supporto ai \"domini relè\" per Postfix"
#: extensions/postfix_relay_domains/__init__.py:89
#: extensions/postfix_relay_domains/general_callbacks.py:100
#: extensions/postfix_relay_domains/limits_callbacks.py:16
-#, fuzzy
msgid "Relay domains"
-msgstr "Nuovo dominio"
+msgstr "Domini relè"
#: extensions/postfix_relay_domains/app_settings.py:10
msgid "Postfix's master.cf path"
-msgstr ""
+msgstr "Percorso del file master.cf di Postfix"
#: extensions/postfix_relay_domains/app_settings.py:12
-#, fuzzy
msgid "Path to the master.cf configuration file"
-msgstr "Percorso del file di log"
+msgstr "Percorso del file di configurazione master.cf"
#: extensions/postfix_relay_domains/forms.py:15
-#, fuzzy
msgid ""
"Alias(es) of this relay domain. Indicate only one name per input, press "
"ENTER to add a new input."
-msgstr ""
-"Alias per questo dominio. Inserire un solo nome alla volta, premere INVIO "
-"per aggiungere un nuovo elemento"
+msgstr "Alias per questo dominio relè. Inserisci un solo nome per casella, premi INVIO per aggiungere un nuovo elemento."
#: extensions/postfix_relay_domains/forms.py:51
#: extensions/postfix_relay_domains/general_callbacks.py:93
-#, fuzzy
msgid "relay domain alias"
-msgstr "Alias del dominio"
+msgstr "Alias del dominio relè"
#: extensions/postfix_relay_domains/forms.py:69
#: extensions/postfix_relay_domains/general_callbacks.py:92
-#, fuzzy
msgid "relay domain"
-msgstr "Nuovo dominio"
+msgstr "Dominio relè"
#: extensions/postfix_relay_domains/general_callbacks.py:35
-#, fuzzy
msgid "Add relay domain"
-msgstr "Aggiungi dominio"
+msgstr "Aggiungi dominio relè"
#: extensions/postfix_relay_domains/general_callbacks.py:101
-#, fuzzy
msgid "Maximum number of relay domains this user can create"
-msgstr "Numero massimo di domini che questo utente può creare"
+msgstr "Numero massimo di domini relè che questo utente può creare"
#: extensions/postfix_relay_domains/general_callbacks.py:103
#: extensions/postfix_relay_domains/limits_callbacks.py:24
-#, fuzzy
msgid "Relay domain aliases"
-msgstr "Alias del dominio"
+msgstr "Alias del dominio relè"
#: extensions/postfix_relay_domains/general_callbacks.py:104
-#, fuzzy
msgid "Maximum number of relay domain aliases this user can create"
-msgstr "Numero massimo di alias di dominio che questo utente può creare"
+msgstr "Numero massimo di alias di un dominio relè che questo utente può creare"
#: extensions/postfix_relay_domains/general_callbacks.py:111
msgid ""
@@ -2121,80 +2079,70 @@ msgid ""
"em>\n"
"- relaydomainalias; name; target; enabled
\n"
msgstr ""
+"\n"
+"- dominio relè; nome; host di destinazione; servizio; abilitato; verifica caselle
\n"
+"- alias dominio relè; nome; destinazione; abilitato
\n"
#: extensions/postfix_relay_domains/limits_callbacks.py:19
-#, fuzzy
msgid "Maximum number of allowed relay domains for a new administrator"
-msgstr "Numero massimo di domini consentiti per un nuovo amministratore"
+msgstr "Numero massimo di domini relè consentiti per un nuovo amministratore"
#: extensions/postfix_relay_domains/limits_callbacks.py:27
-#, fuzzy
msgid "Maximum number of allowed relay domain aliases for a new administrator"
-msgstr ""
-"Numero massimo di alias di dominio consentiti per un nuovo amministratore"
+msgstr "Numero massimo di alias di dominio relè consentiti per un nuovo amministratore"
#: extensions/postfix_relay_domains/models.py:59
-#, fuzzy
msgid "The service name"
-msgstr "Il nome dell'alias"
+msgstr "Il nome del servizio"
#: extensions/postfix_relay_domains/models.py:80
-#, fuzzy
msgid "target host"
msgstr "destinazione"
#: extensions/postfix_relay_domains/models.py:81
-#, fuzzy
msgid "Remote destination of this domain"
-msgstr "Seleziona per attivare questo dominio"
+msgstr "Destinazione remota per questo dominio"
#: extensions/postfix_relay_domains/models.py:89
-#, fuzzy
msgid "verify recipients"
-msgstr "Destinatari"
+msgstr "Verifica destinatari"
#: extensions/postfix_relay_domains/models.py:90
msgid "Check for valid recipients"
-msgstr ""
+msgstr "Verifica validità destinatari"
#: extensions/postfix_relay_domains/models.py:103
-#, fuzzy
msgid "Relay Domain"
-msgstr "Nuovo dominio"
+msgstr "Dominio relè"
#: extensions/postfix_relay_domains/models.py:164
-#, fuzzy
msgid "The relay domain this alias points to"
-msgstr "Il dominio a cui punta questo alias"
+msgstr "Il dominio relè a cui punta questo alias"
#: extensions/postfix_relay_domains/models.py:195
-#, fuzzy, python-format
+#, python-format
msgid "Relay domain %s does not exist"
-msgstr "Il dominio '%s' non esiste"
+msgstr "Il dominio relè '%s' non esiste"
#: extensions/postfix_relay_domains/views.py:26
-#, fuzzy
msgid "Relay domain created"
-msgstr "Dominio creato"
+msgstr "Dominio relè creato"
#: extensions/postfix_relay_domains/views.py:31
-#, fuzzy
msgid "New relay domain"
-msgstr "Nuovo dominio"
+msgstr "Nuovo dominio relè"
#: extensions/postfix_relay_domains/views.py:54
-#, fuzzy
msgid "Relay domain modified"
-msgstr "Dominio modificato"
+msgstr "Dominio relè modificato"
#: extensions/postfix_relay_domains/views.py:77
-#, fuzzy
msgid "Relay domain deleted"
-msgstr "Dominio cancellato"
+msgstr "Dominio relè cancellato"
#: extensions/postfix_relay_domains/templates/postfix_relay_domains/service_field.html:2
msgid "Scan"
-msgstr ""
+msgstr "Cerca"
#: extensions/sievefilters/__init__.py:12
msgid "Plugin to easily create server-side filters"
@@ -2315,53 +2263,53 @@ msgstr ""
msgid "Not enough space on server"
msgstr "Non c'è spazio sufficiente nel server"
-#: extensions/sievefilters/views.py:78
+#: extensions/sievefilters/views.py:80
msgid "Failed to retrieve filters set"
msgstr "Recupero delle impostazioni di filtro fallito"
-#: extensions/sievefilters/views.py:138
+#: extensions/sievefilters/views.py:141
#: extensions/sievefilters/templatetags/sfilters_tags.py:33
msgid "New filter"
msgstr "Nuovo filtro"
-#: extensions/sievefilters/views.py:146
+#: extensions/sievefilters/views.py:149
msgid "Filter created"
msgstr "Filtro creato"
-#: extensions/sievefilters/views.py:160
+#: extensions/sievefilters/views.py:163
#: extensions/sievefilters/templatetags/sfilters_tags.py:78
msgid "Edit filter"
msgstr "Modifica filtro"
-#: extensions/sievefilters/views.py:169
+#: extensions/sievefilters/views.py:172
msgid "Filter modified"
msgstr "Filtro modificato"
-#: extensions/sievefilters/views.py:192
+#: extensions/sievefilters/views.py:195
msgid "Filter removed"
msgstr "Filtro eliminato"
-#: extensions/sievefilters/views.py:193
+#: extensions/sievefilters/views.py:196
msgid "Failed to remove filter"
msgstr "Rimozione del filtro fallita"
-#: extensions/sievefilters/views.py:208
+#: extensions/sievefilters/views.py:211
msgid "Filters set saved"
msgstr "Gruppo filtri salvato"
-#: extensions/sievefilters/views.py:224
+#: extensions/sievefilters/views.py:227
msgid "Filters set created"
msgstr "Gruppo filtri creato"
-#: extensions/sievefilters/views.py:228
+#: extensions/sievefilters/views.py:231
msgid "Create a new filters set"
msgstr "Crea un nuovo gruppo di filtri"
-#: extensions/sievefilters/views.py:247
+#: extensions/sievefilters/views.py:250
msgid "Filters set deleted"
msgstr "Gruppo filtri eliminato"
-#: extensions/sievefilters/views.py:260
+#: extensions/sievefilters/views.py:263
msgid "Filters set activated"
msgstr "Gruppo filtri attivato"
@@ -2649,13 +2597,12 @@ msgid "Automatic folder refresh rate (in seconds)"
msgstr "Frequenza di aggiornamento automatico delle cartelle (in secondi)"
#: extensions/webmail/app_settings.py:103
-#, fuzzy
msgid "Mailboxes container's width"
-msgstr "Proprietario delle caselle postali"
+msgstr "Larghezza del contenitore delle caselle"
#: extensions/webmail/app_settings.py:104
msgid "The width of the mailbox list container"
-msgstr ""
+msgstr "Larghezza della lista delle caselle"
#: extensions/webmail/app_settings.py:111
msgid "Trash folder"
@@ -2703,7 +2650,7 @@ msgstr "Signature delle e-mail personalizzato dall'utente"
#: extensions/webmail/app_settings.py:160
msgid "Value must be a positive integer (> 0)"
-msgstr ""
+msgstr "Il valore dev'essere un intero positivo"
#: extensions/webmail/exceptions.py:20
msgid "Server response"
@@ -2889,9 +2836,9 @@ msgid "Remove the selected mailbox"
msgstr "Elimina la cartella di posta selezionata"
#: lib/dbutils.py:36
-#, fuzzy, python-format
+#, python-format
msgid "Connection to database %s not configured"
-msgstr "Connessione ad amavis fallita: %s"
+msgstr "La connessione con il database %s non è configurata"
#: lib/exceptions.py:67
#, python-format
@@ -2997,36 +2944,3 @@ msgstr "Ricordami"
#: templates/registration/login.html:36
msgid "Log in"
msgstr "Registrati"
-
-#~ msgid "An alias with this name already exists"
-#~ msgstr "Esiste già un alias con questo nome"
-
-#~ msgid "A domain with this name already exists"
-#~ msgstr "Esiste già un dominio con questo nome"
-
-#~ msgid "Edit domain"
-#~ msgstr "Modifica dominio"
-
-#~ msgid "%d pending requests"
-#~ msgstr "%d richieste in sospeso"
-
-#~ msgid "Content Class"
-#~ msgstr "Classe dei contenuti"
-
-#~ msgid "Nothing"
-#~ msgstr "Nulla"
-
-#~ msgid "Bad request"
-#~ msgstr "Richiesta sbagliata"
-
-#~ msgid "Undefined action"
-#~ msgstr "Azione non definita"
-
-#~ msgid "User preferences"
-#~ msgstr "Preferenze utente"
-
-#~ msgid "Per-user settings"
-#~ msgstr "Impostazioni per-utente"
-
-#~ msgid "You need a mailbox in order to define a forward"
-#~ msgstr "Hai bisogno di una casella di posta per definire un inoltro"
diff --git a/modoboa/locale/it/LC_MESSAGES/djangojs.po b/modoboa/locale/it/LC_MESSAGES/djangojs.po
index e60178242..3d7c25ebd 100644
--- a/modoboa/locale/it/LC_MESSAGES/djangojs.po
+++ b/modoboa/locale/it/LC_MESSAGES/djangojs.po
@@ -7,9 +7,9 @@ msgid ""
msgstr ""
"Project-Id-Version: Modoboa\n"
"Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2013-12-15 10:16+0100\n"
-"PO-Revision-Date: 2013-09-27 00:07+0200\n"
-"Last-Translator: Giancarlo Gaifas \n"
+"POT-Creation-Date: 2013-12-22 23:16+0100\n"
+"PO-Revision-Date: 2013-12-23 00:58+0100\n"
+"Last-Translator: Alberto Berti \n"
"Language-Team: Italiano \n"
"Language: it\n"
"MIME-Version: 1.0\n"
@@ -73,7 +73,7 @@ msgstr "Nascondi le intestazioni"
#: extensions/postfix_relay_domains/static/postfix_relay_domains/js/relay_domains.js:49
msgid "Services updated"
-msgstr ""
+msgstr "Servizi aggiornati"
#: extensions/sievefilters/static/sievefilters/js/lib.js:14
msgid "Remove this filter?"
@@ -135,13 +135,9 @@ msgid "Cancel"
msgstr "Elimina"
#: static/js/global.js:314
-#, fuzzy
msgid "Internal error"
msgstr "Errore interno"
#: static/js/searchbar.js:20
msgid "Search..."
msgstr "Ricerca ..."
-
-#~ msgid "Message deleted"
-#~ msgstr "Messaggio eliminato"
From a47e6cf8ee6ebfc85e3368a8ecee8817c869827a Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Mon, 23 Dec 2013 11:19:22 +0100
Subject: [PATCH 02/32] Wrong translations fixed.
---
modoboa/locale/it/LC_MESSAGES/django.po | 3 ++-
1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/modoboa/locale/it/LC_MESSAGES/django.po b/modoboa/locale/it/LC_MESSAGES/django.po
index 425aa602e..5a0c0f658 100644
--- a/modoboa/locale/it/LC_MESSAGES/django.po
+++ b/modoboa/locale/it/LC_MESSAGES/django.po
@@ -1373,6 +1373,7 @@ msgstr ""
"\n"
" - dominio; nome; quota; abilitato
\n"
" - aliasdominio; nome; dominio di destinazione; abilitato
\n"
+" %s\n"
"
\n"
"Il primo elemento di ogni riga è obbligatorio e deve essere uguale a quello dei valori precedenti.
\n"
"\n"
@@ -1950,7 +1951,7 @@ msgstr ""
"Al momento non posso rispondere. Risponderò al mio ritorno.\n"
"\n"
"Distinti saluti,\n"
-"%(name)s"
+"%(name)s\n"
#: extensions/postfix_autoreply/app_settings.py:36
#, python-format
From 4fdb7605ff9c054628ff775af0a3c5ad6a584023 Mon Sep 17 00:00:00 2001
From: Patrick Ben Koetter
Date: Mon, 23 Dec 2013 14:26:25 +0100
Subject: [PATCH 03/32] German translation for upcoming 1.1.0
Translated four sentences
---
modoboa/locale/de/LC_MESSAGES/django.po | 558 +++++++++++-------------
1 file changed, 252 insertions(+), 306 deletions(-)
diff --git a/modoboa/locale/de/LC_MESSAGES/django.po b/modoboa/locale/de/LC_MESSAGES/django.po
index 3fe643142..bd96b891d 100644
--- a/modoboa/locale/de/LC_MESSAGES/django.po
+++ b/modoboa/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgstr ""
"Project-Id-Version: Modoboa-0.9\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2013-12-15 10:21+0100\n"
-"PO-Revision-Date: 2013-12-08 23:33+0100\n"
+"PO-Revision-Date: 2013-12-23 14:26+0100\n"
"Last-Translator: Patrick Ben Koetter
\n"
"Language-Team: DE
\n"
"Language: de\n"
@@ -20,13 +20,17 @@ msgstr ""
"X-Poedit-Country: GERMANY\n"
"X-Poedit-SourceCharset: utf-8\n"
-#: core/__init__.py:52 core/__init__.py:53
-#: extensions/admin/forms/account.py:326 extensions/admin/forms/domain.py:251
-#: extensions/admin/views/domain.py:95 extensions/admin/views/identity.py:127
+#: core/__init__.py:52
+#: core/__init__.py:53
+#: extensions/admin/forms/account.py:326
+#: extensions/admin/forms/domain.py:251
+#: extensions/admin/views/domain.py:95
+#: extensions/admin/views/identity.py:127
#: extensions/postfix_autoreply/app_settings.py:11
#: extensions/postfix_relay_domains/forms.py:138
#: extensions/sievefilters/app_settings.py:50
-#: extensions/stats/app_settings.py:11 extensions/webmail/app_settings.py:11
+#: extensions/stats/app_settings.py:11
+#: extensions/webmail/app_settings.py:11
msgid "General"
msgstr "Grundsätzlich"
@@ -79,12 +83,8 @@ msgid "Rounds"
msgstr "Runden"
#: core/app_settings.py:64
-msgid ""
-"Number of rounds to use (only used by sha256crypt and sha512crypt). Must be "
-"between 1000 and 999999999, inclusive."
-msgstr ""
-"Anzahl zu verwendender Runden (nur für sha256crypt und sha512crypt). Zahl "
-"muss zwischen 1000 und 999999999 liegen."
+msgid "Number of rounds to use (only used by sha256crypt and sha512crypt). Must be between 1000 and 999999999, inclusive."
+msgstr "Anzahl zu verwendender Runden (nur für sha256crypt und sha512crypt). Zahl muss zwischen 1000 und 999999999 liegen."
#: core/app_settings.py:70
msgid "Secret key"
@@ -98,8 +98,10 @@ msgstr "Verwendeter Schlüssel, um Passworte zu ver-/entschlüsseln"
msgid "LDAP settings"
msgstr "LDAP-Einstellungen"
-#: core/app_settings.py:79 extensions/sievefilters/app_settings.py:22
-#: extensions/webmail/app_settings.py:22 extensions/webmail/app_settings.py:42
+#: core/app_settings.py:79
+#: extensions/sievefilters/app_settings.py:22
+#: extensions/webmail/app_settings.py:22
+#: extensions/webmail/app_settings.py:42
msgid "Server address"
msgstr "Server-Adresse"
@@ -107,8 +109,10 @@ msgstr "Server-Adresse"
msgid "The IP address of the DNS name of the LDAP server"
msgstr "Die IP-Adresse des LDAP-Server Hostnamens"
-#: core/app_settings.py:85 extensions/sievefilters/app_settings.py:28
-#: extensions/webmail/app_settings.py:34 extensions/webmail/app_settings.py:58
+#: core/app_settings.py:85
+#: extensions/sievefilters/app_settings.py:28
+#: extensions/webmail/app_settings.py:34
+#: extensions/webmail/app_settings.py:58
msgid "Server port"
msgstr "Server-Port"
@@ -116,7 +120,8 @@ msgstr "Server-Port"
msgid "The TCP port number used by the LDAP server"
msgstr "Der TCP Port des LDAP-Servers"
-#: core/app_settings.py:91 extensions/webmail/app_settings.py:28
+#: core/app_settings.py:91
+#: extensions/webmail/app_settings.py:28
msgid "Use a secured connection"
msgstr "Gesicherte Verbindung verwenden"
@@ -145,11 +150,8 @@ msgid "Bind DN"
msgstr "Bind DN"
#: core/app_settings.py:108
-msgid ""
-"The distinguished name to use when binding to the LDAP server. Leave empty "
-"for an anonymous bind"
-msgstr ""
-"Der DN für einen Bind an den LDAP-Server. Nichts eingeben für anonymen Bind."
+msgid "The distinguished name to use when binding to the LDAP server. Leave empty for an anonymous bind"
+msgstr "Der DN für einen Bind an den LDAP-Server. Nichts eingeben für anonymen Bind."
#: core/app_settings.py:113
msgid "Bind password"
@@ -172,12 +174,8 @@ msgid "Search filter"
msgstr "Suchfilter"
#: core/app_settings.py:130
-msgid ""
-"An optional filter string (e.g. '(objectClass=person)'). In order to be "
-"valid, it must be enclosed in parentheses."
-msgstr ""
-"Ein optionaler Filter z.B. (objectClass=person). Das Filter muss "
-"entsprechend der LDAP-Konvention in Klammern gesetzt werden."
+msgid "An optional filter string (e.g. '(objectClass=person)'). In order to be valid, it must be enclosed in parentheses."
+msgstr "Ein optionaler Filter z.B. (objectClass=person). Das Filter muss entsprechend der LDAP-Konvention in Klammern gesetzt werden."
#: core/app_settings.py:135
msgid "User DN template"
@@ -185,12 +183,8 @@ msgstr "Vorlage für User DN"
#: core/app_settings.py:137
#, python-format
-msgid ""
-"The template used to construct a user's DN. It should contain one "
-"placeholder (ie. %(user)s)"
-msgstr ""
-"Die Vorlage für einen User DN. Sie sollte einen Platzhalter z.B. %(user)s "
-"enthalten."
+msgid "The template used to construct a user's DN. It should contain one placeholder (ie. %(user)s)"
+msgstr "Die Vorlage für einen User DN. Sie sollte einen Platzhalter z.B. %(user)s enthalten."
#: core/app_settings.py:142
msgid "Password attribute"
@@ -213,12 +207,8 @@ msgid "Administrator groups"
msgstr "Administrator-Gruppen"
#: core/app_settings.py:157
-msgid ""
-"Members of those LDAP Posix groups will be created as domain administrators. "
-"Use ';' characters to separate groups."
-msgstr ""
-"Mitglieder dieser LDAP Posix-Gruppe werden als Domain-Administratoren "
-"angelegt werden. Nutzen sie ';', um Gruppen zu separieren."
+msgid "Members of those LDAP Posix groups will be created as domain administrators. Use ';' characters to separate groups."
+msgstr "Mitglieder dieser LDAP Posix-Gruppe werden als Domain-Administratoren angelegt werden. Nutzen sie ';', um Gruppen zu separieren."
#: core/app_settings.py:164
msgid "Groups search base"
@@ -261,7 +251,8 @@ msgstr "Die Standardumleitung wenn kein Programm angegeben wurde"
msgid "Key must be either 16, 24, or 32 bytes long"
msgstr "Schlüssel muss 16, 24 oder 32 Byte lang sein"
-#: core/app_settings.py:227 extensions/postfix_autoreply/app_settings.py:53
+#: core/app_settings.py:227
+#: extensions/postfix_autoreply/app_settings.py:53
msgid "Invalid syntax"
msgstr "Ungültige Syntax"
@@ -273,7 +264,8 @@ msgstr "Ungültige Zahl für Runden"
msgid "This field is required"
msgstr "Dieses Feld ist erforderlich"
-#: core/app_settings.py:317 extensions/amavis/app_settings.py:87
+#: core/app_settings.py:317
+#: extensions/amavis/app_settings.py:87
#: extensions/amavis/templates/amavis/main_action_bar.html:29
#: extensions/webmail/app_settings.py:73
msgid "Display"
@@ -287,12 +279,14 @@ msgstr "Bevorzugte Sprache"
msgid "Prefered language to display pages"
msgstr "Bevorzugte Sprache für Seitendarstellung"
-#: core/forms.py:10 extensions/admin/forms/account.py:19
+#: core/forms.py:10
+#: extensions/admin/forms/account.py:19
#: extensions/admin/templates/admin/editdomainform.html:13
msgid "Username"
msgstr "Benutzername"
-#: core/forms.py:14 extensions/admin/forms/account.py:31
+#: core/forms.py:14
+#: extensions/admin/forms/account.py:31
msgid "Password"
msgstr "Passwort"
@@ -304,7 +298,8 @@ msgstr "Altes Passwort"
msgid "New password"
msgstr "Neues Passwort"
-#: core/forms.py:33 extensions/admin/forms/account.py:34
+#: core/forms.py:33
+#: extensions/admin/forms/account.py:34
msgid "Confirmation"
msgstr "Bestätigung"
@@ -336,7 +331,8 @@ msgstr "Konnte Kennwort nicht aktualisieren: LDAP-Modul nicht installiert"
msgid "account"
msgstr "Konto"
-#: core/models.py:321 extensions/admin/models/domain.py:135
+#: core/models.py:321
+#: extensions/admin/models/domain.py:135
#: extensions/admin/models/domain_alias.py:39
#: extensions/postfix_relay_domains/models.py:134
#: extensions/postfix_relay_domains/models.py:190
@@ -355,11 +351,10 @@ msgstr "Der normale Benutzer '%s' muss eine gültige E-Mail-Adresse besitzen"
#: core/models.py:335
#, python-format
msgid "username and email fields must not differ for '%s'"
-msgstr ""
-"Die Felder für Benutzername und E-Mail für '%s' dürfen sich nicht "
-"unterscheiden"
+msgstr "Die Felder für Benutzername und E-Mail für '%s' dürfen sich nicht unterscheiden"
-#: core/models.py:404 extensions/admin/models/alias.py:33
+#: core/models.py:404
+#: extensions/admin/models/alias.py:33
#: extensions/admin/models/domain.py:32
#: extensions/admin/models/domain_alias.py:17
#: extensions/postfix_autoreply/models.py:28
@@ -380,7 +375,8 @@ msgstr "hinzugefügt"
msgid "modified"
msgstr "verändert"
-#: core/models.py:480 core/models.py:504
+#: core/models.py:480
+#: core/models.py:504
#, python-format
msgid "%(object)s '%(name)s' %(action)s by user %(user)s"
msgstr "%(object)s '%(name)s' %(action)s der Identität %(user)s"
@@ -389,8 +385,10 @@ msgstr "%(object)s '%(name)s' %(action)s der Identität %(user)s"
msgid "deleted"
msgstr "entfernt"
-#: core/tables.py:8 core/templates/core/information.html:8
-#: extensions/admin/tables.py:9 extensions/admin/forms/domain.py:182
+#: core/tables.py:8
+#: core/templates/core/information.html:8
+#: extensions/admin/tables.py:9
+#: extensions/admin/forms/domain.py:182
#: extensions/admin/templates/admin/domains_table.html:5
#: extensions/admin/templates/admin/editdomainform.html:13
#: extensions/admin/templates/admin/identities_table.html:5
@@ -399,15 +397,18 @@ msgstr "entfernt"
msgid "Name"
msgstr "Name"
-#: core/tables.py:10 extensions/admin/tables.py:11
+#: core/tables.py:10
+#: extensions/admin/tables.py:11
msgid "Version"
msgstr "Version"
-#: core/tables.py:12 extensions/admin/tables.py:13
+#: core/tables.py:12
+#: extensions/admin/tables.py:13
msgid "Description"
msgstr "Beschreibung"
-#: core/templates/core/extensions.html:2 core/templatetags/core_tags.py:48
+#: core/templates/core/extensions.html:2
+#: core/templatetags/core_tags.py:48
msgid "Extensions"
msgstr "Erweiterungen"
@@ -415,12 +416,14 @@ msgstr "Erweiterungen"
msgid "Choose the extension(s) to use"
msgstr "Extension auswählen"
-#: core/templates/core/extensions.html:6 core/templates/core/parameters.html:7
+#: core/templates/core/extensions.html:6
+#: core/templates/core/parameters.html:7
#: core/templates/core/user_preferences.html:8
msgid "Save"
msgstr "Speichern"
-#: core/templates/core/information.html:2 core/templatetags/core_tags.py:53
+#: core/templates/core/information.html:2
+#: core/templatetags/core_tags.py:53
msgid "Information"
msgstr "Information"
@@ -444,7 +447,8 @@ msgstr "Gruppenname"
msgid "Last login"
msgstr "Letzte Anmeldung"
-#: core/templates/core/logs.html:2 core/templatetags/core_tags.py:57
+#: core/templates/core/logs.html:2
+#: core/templatetags/core_tags.py:57
msgid "Logs"
msgstr "Logs"
@@ -452,8 +456,10 @@ msgstr "Logs"
msgid "Previously on Modoboa..."
msgstr "Vorher auf Modoboa…"
-#: core/templates/core/logs.html:6 extensions/amavis/sql_listing.py:46
-#: extensions/webmail/lib.py:48 extensions/webmail/lib.py:425
+#: core/templates/core/logs.html:6
+#: extensions/amavis/sql_listing.py:46
+#: extensions/webmail/lib.py:48
+#: extensions/webmail/lib.py:425
msgid "Date"
msgstr "Datum"
@@ -469,7 +475,8 @@ msgstr "Logger"
msgid "Message"
msgstr "Nachricht"
-#: core/templates/core/parameters.html:2 core/templatetags/core_tags.py:62
+#: core/templates/core/parameters.html:2
+#: core/templatetags/core_tags.py:62
msgid "Parameters"
msgstr "Parameter"
@@ -481,7 +488,8 @@ msgstr "Modoboa konfigurieren"
msgid "Modoboa settings"
msgstr "Modoboa-Einstellungen"
-#: core/templates/core/user_index.html:2 core/templatetags/core_tags.py:81
+#: core/templates/core/user_index.html:2
+#: core/templatetags/core_tags.py:81
msgid "Settings"
msgstr "Einstellungen"
@@ -494,7 +502,8 @@ msgstr "Einstellungen"
msgid "Customize Modoboa"
msgstr "Modoboa anpassen"
-#: core/templates/core/user_profile.html:2 core/templatetags/core_tags.py:104
+#: core/templates/core/user_profile.html:2
+#: core/templatetags/core_tags.py:104
msgid "Profile"
msgstr "Profil"
@@ -504,11 +513,13 @@ msgstr "Aktualisieren sie ihre persönlichen Daten"
#: core/templates/core/user_profile.html:8
#: extensions/admin/templates/admin/forward.html:8
-#: extensions/admin/views/alias.py:107 extensions/admin/views/domain.py:165
+#: extensions/admin/views/alias.py:107
+#: extensions/admin/views/domain.py:165
#: extensions/admin/views/identity.py:197
#: extensions/postfix_autoreply/templates/postfix_autoreply/autoreply.html:9
#: extensions/postfix_relay_domains/views.py:63
-#: extensions/sievefilters/views.py:163 extensions/webmail/views.py:170
+#: extensions/sievefilters/views.py:163
+#: extensions/webmail/views.py:170
#: extensions/webmail/views.py:205
msgid "Update"
msgstr "Aktualisieren"
@@ -536,9 +547,7 @@ msgstr "Identität '%s' hat sich erfolgreich angemeldet"
#: core/views/auth.py:43
msgid "Your username and password didn't match. Please try again."
-msgstr ""
-"Ihr Benutzername und Passwort stimmen nicht überein. Bitte versuchen Sie es "
-"noch einmal."
+msgstr "Ihr Benutzername und Passwort stimmen nicht überein. Bitte versuchen Sie es noch einmal."
#: core/views/auth.py:66
#, python-format
@@ -565,7 +574,8 @@ msgstr "Virus senden"
msgid "Send spam"
msgstr "Spam senden"
-#: demo/views.py:18 demo/views.py:43
+#: demo/views.py:18
+#: demo/views.py:43
msgid "Message sent"
msgstr "Nachricht gesendet"
@@ -574,31 +584,26 @@ msgid ""
"\n"
"
Welcome to the online demo!
\n"
"Warning: the demo's concent is resetted every two hours.
\n"
-"To try the demo, the following users are available (username/password"
-"i>):
\n"
+"To try the demo, the following users are available (username/password):
\n"
"\n"
" - A super administrator : admin/password
\n"
" - A domain administrator : admin@demo.local/admin
\n"
" - A simple user : user@demo.local/user
\n"
"
\n"
"Please report any issue or give any suggestion to \n"
-" the "
-"mailing list.
\n"
+" the mailing list.
\n"
msgstr ""
"\n"
"Willkommen zur Online Demo!
\n"
-"Warnung: die Inhalte dieser Demo werden alle zwei Stunden gelöscht."
-"
\n"
-"Folgende User (Benutzername/Kennwort) stehen zum Testen zur "
-"Verfügung:
\n"
+"Warnung: die Inhalte dieser Demo werden alle zwei Stunden gelöscht.
\n"
+"Folgende User (Benutzername/Kennwort) stehen zum Testen zur Verfügung:
\n"
"\n"
" - Super-Administrator : admin/password
\n"
" - Domänen-Administrator : admin@demo.local/admin
\n"
" - Normaler Benutzer: user@demo.local/user
\n"
"
\n"
"Probleme und Anregungen bitte an die\n"
-" Mailingliste berichten.
\n"
+" Mailingliste berichten.\n"
#: extensions/admin/__init__.py:48
msgid "Administration console"
@@ -614,7 +619,8 @@ msgstr "Administration"
#: extensions/admin/__init__.py:79
#: extensions/admin/templates/admin/domains.html:2
-#: extensions/limits/app_settings.py:19 extensions/limits/models.py:17
+#: extensions/limits/app_settings.py:19
+#: extensions/limits/models.py:17
msgid "Domains"
msgstr "Domänen"
@@ -636,7 +642,8 @@ msgstr "Kann Konto nicht importieren (%s): Die Domain existiert nicht"
#: extensions/admin/app_settings.py:11
#: extensions/admin/templates/admin/editdomainform.html:25
-#: extensions/limits/app_settings.py:31 extensions/limits/models.py:23
+#: extensions/limits/app_settings.py:31
+#: extensions/limits/models.py:23
#: extensions/webmail/app_settings.py:107
#: extensions/webmail/templates/webmail/folders.html:4
msgid "Mailboxes"
@@ -647,12 +654,8 @@ msgid "Handle mailboxes on filesystem"
msgstr "Mailbox im Dateisystem verwalten"
#: extensions/admin/app_settings.py:16
-msgid ""
-"Rename or remove mailboxes on the filesystem when they get renamed or "
-"removed within Modoboa"
-msgstr ""
-"Mailboxen auch in Dateisystem umbenennen oder entfernen wenn sie in Modoboa "
-"umbenannt oder entfernt werden"
+msgid "Rename or remove mailboxes on the filesystem when they get renamed or removed within Modoboa"
+msgstr "Mailboxen auch in Dateisystem umbenennen oder entfernen wenn sie in Modoboa umbenannt oder entfernt werden"
#: extensions/admin/app_settings.py:20
msgid "Mailboxes ower"
@@ -660,21 +663,15 @@ msgstr "Mailbox-Besitzer"
#: extensions/admin/app_settings.py:22
msgid "The UNIX account who owns mailboxes on the filesystem"
-msgstr ""
-"UID des virtuellen Benutzers, der Besitzer der Domains, Mailboxen und "
-"Nachrichten im Dateisystem ist."
+msgstr "UID des virtuellen Benutzers, der Besitzer der Domains, Mailboxen und Nachrichten im Dateisystem ist."
#: extensions/admin/app_settings.py:26
msgid "Default domain quota"
msgstr "Standard Domainquota"
#: extensions/admin/app_settings.py:29
-msgid ""
-"Default quota (in MB) applied to freshly created domains with no value "
-"specified. A value of 0 means no quota."
-msgstr ""
-"Standardquota (in MB) für neu erstelle Domains ohne explizite Wertangabe. "
-"Der Wert 0 bedeutet „Kein Quota“"
+msgid "Default quota (in MB) applied to freshly created domains with no value specified. A value of 0 means no quota."
+msgstr "Standardquota (in MB) für neu erstelle Domains ohne explizite Wertangabe. Der Wert 0 bedeutet „Kein Quota“"
#: extensions/admin/app_settings.py:36
msgid "Automatic account removal"
@@ -684,7 +681,8 @@ msgstr "Automatische Konto-Entfernung"
msgid "When a mailbox is removed, also remove the associated account"
msgstr "Beim Löschen der Mailbox auch das Konto entfernen."
-#: extensions/admin/app_settings.py:69 extensions/admin/forms/account.py:178
+#: extensions/admin/app_settings.py:69
+#: extensions/admin/forms/account.py:178
#: extensions/admin/forms/domain.py:56
msgid "Must be a positive integer"
msgstr "Muss eine positive Integer sein"
@@ -694,18 +692,15 @@ msgid "A mailbox is required"
msgstr "Ein Mailbox ist erforderlich"
#: extensions/admin/forms/account.py:21
-#, fuzzy
-msgid ""
-"The user's name. Must be a valid e-mail address for simple users or "
-"administrators with a mailbox."
-msgstr ""
-"Der Anwendername. Muss eine gültige E-Mail-Adresse für 'simple users' sein."
+msgid "The user's name. Must be a valid e-mail address for simple users or administrators with a mailbox."
+msgstr "Der Anwendername. Muss eine gültige E-Mail-Adresse für 'simple users' oder Administratoren mit einer Mailbox sein."
#: extensions/admin/forms/account.py:26
msgid "Role"
msgstr "Rolle"
-#: extensions/admin/forms/account.py:27 extensions/admin/forms/account.py:55
+#: extensions/admin/forms/account.py:27
+#: extensions/admin/forms/account.py:55
msgid "Choose"
msgstr "Auswählen"
@@ -733,37 +728,28 @@ msgstr "Sie können Ihr eigenes Konto nicht deaktivieren"
msgid "E-mail"
msgstr "E-Mail"
-#: extensions/admin/forms/account.py:113 extensions/admin/forms/domain.py:17
+#: extensions/admin/forms/account.py:113
+#: extensions/admin/forms/domain.py:17
msgid "Quota"
msgstr "Quota"
#: extensions/admin/forms/account.py:115
-msgid ""
-"Quota in MB for this mailbox. Define a custom value or use domain's default "
-"one. Leave empty to define an unlimited value (not allowed for domain "
-"administrators)."
-msgstr ""
-"Quota in MB für diese Mailbox. Geben Sie einen eigenen Wert an oder nutzen "
-"Sie den Standardwert der Domain. Lassen Sie das Feld leer für unbegrenztes "
-"Quota - Domänen-Administratoren ist dies nicht gestattet."
+msgid "Quota in MB for this mailbox. Define a custom value or use domain's default one. Leave empty to define an unlimited value (not allowed for domain administrators)."
+msgstr "Quota in MB für diese Mailbox. Geben Sie einen eigenen Wert an oder nutzen Sie den Standardwert der Domain. Lassen Sie das Feld leer für unbegrenztes Quota - Domänen-Administratoren ist dies nicht gestattet."
-#: extensions/admin/forms/account.py:123 extensions/admin/forms/domain.py:26
+#: extensions/admin/forms/account.py:123
+#: extensions/admin/forms/domain.py:26
#: extensions/admin/templates/admin/domains_table.html:6
#: extensions/postfix_relay_domains/forms.py:12
msgid "Alias(es)"
msgstr "Aliase"
#: extensions/admin/forms/account.py:126
-msgid ""
-"Alias(es) of this mailbox. Indicate only one address per input, press ENTER "
-"to add a new input. Use the '*' character to create a 'catchall' alias (ex: "
-"*@domain.tld)."
-msgstr ""
-"Alias(e) für diese Mailbox. Geben Sie jeweils nur eine Adresse pro Eingabe "
-"an. Bestätigen Sie mit ENTER um die Eingabe zu bestätigen. Geben Sie '*' an, "
-"um einen 'catchall'-Alias (Bsp: *@example.com) zu erstellen."
+msgid "Alias(es) of this mailbox. Indicate only one address per input, press ENTER to add a new input. Use the '*' character to create a 'catchall' alias (ex: *@domain.tld)."
+msgstr "Alias(e) für diese Mailbox. Geben Sie jeweils nur eine Adresse pro Eingabe an. Bestätigen Sie mit ENTER um die Eingabe zu bestätigen. Geben Sie '*' an, um einen 'catchall'-Alias (Bsp: *@example.com) zu erstellen."
-#: extensions/admin/forms/account.py:187 extensions/admin/forms/account.py:217
+#: extensions/admin/forms/account.py:187
+#: extensions/admin/forms/account.py:217
#: extensions/admin/forms/alias.py:65
msgid "Domain does not exist"
msgstr "Domain existiert nicht"
@@ -795,24 +781,16 @@ msgid "Email address"
msgstr "E-Mail Adresse"
#: extensions/admin/forms/alias.py:18
-msgid ""
-"The distribution list address. Use the '*' character to create a 'catchall' "
-"address (ex: *@domain.tld)."
-msgstr ""
-"Adresse einer Verteilerliste. Geben Sie '*' an, um einen 'catchall'-Alias "
-"(Bsp: *@example.com) zu erstellen."
+msgid "The distribution list address. Use the '*' character to create a 'catchall' address (ex: *@domain.tld)."
+msgstr "Adresse einer Verteilerliste. Geben Sie '*' an, um einen 'catchall'-Alias (Bsp: *@example.com) zu erstellen."
#: extensions/admin/forms/alias.py:23
msgid "Recipients"
msgstr "Empfänger"
#: extensions/admin/forms/alias.py:25
-msgid ""
-"Mailbox(es) this alias will point to. Indicate only one address per input, "
-"press ENTER to add a new input."
-msgstr ""
-"Mailboxen auf die der Alias verweist. Geben Sie jeweils nur eine Adresse ein "
-"und bestätigen Sie mit ENTER."
+msgid "Mailbox(es) this alias will point to. Indicate only one address per input, press ENTER to add a new input."
+msgstr "Mailboxen auf die der Alias verweist. Geben Sie jeweils nur eine Adresse ein und bestätigen Sie mit ENTER."
#: extensions/admin/forms/alias.py:68
msgid "You don't have access to this domain"
@@ -822,12 +800,14 @@ msgstr "Der Zugriff auf diese Domain ist ihnen nicht gestattet"
msgid "Invalid mailbox"
msgstr "Ungültige Mailbox"
-#: extensions/admin/forms/alias.py:108 extensions/admin/models/alias.py:182
+#: extensions/admin/forms/alias.py:108
+#: extensions/admin/models/alias.py:182
#, python-format
msgid "Local recipient %s not found"
msgstr "Lokaler Empfänger %s nicht gefunden"
-#: extensions/admin/forms/alias.py:112 extensions/admin/forms/alias.py:120
+#: extensions/admin/forms/alias.py:112
+#: extensions/admin/forms/alias.py:120
#, python-format
msgid "Recipient %s already present"
msgstr "Empfänger %s existiert bereits"
@@ -837,21 +817,12 @@ msgid "No recipient defined"
msgstr "Keine Empfänger angegeben"
#: extensions/admin/forms/domain.py:20
-msgid ""
-"Default quota in MB applied to mailboxes. Leave empty to use the default "
-"value."
-msgstr ""
-"Standardquota in MB für Mailboxen. Bei leerem Feld wird der Domain-Standard "
-"genutzt."
+msgid "Default quota in MB applied to mailboxes. Leave empty to use the default value."
+msgstr "Standardquota in MB für Mailboxen. Bei leerem Feld wird der Domain-Standard genutzt."
#: extensions/admin/forms/domain.py:29
-msgid ""
-"Alias(es) of this domain. Indicate only one name per input, press ENTER to "
-"add a new input."
-msgstr ""
-"Alias(e) für diese Mailbox. Geben Sie jeweils nur eine Adresse pro "
-"Eingabefeld an. Bestätigen Sie mit ENTER, um ein neues Eingabefeld zu "
-"erhalten."
+msgid "Alias(es) of this domain. Indicate only one name per input, press ENTER to add a new input."
+msgstr "Alias(e) für diese Mailbox. Geben Sie jeweils nur eine Adresse pro Eingabefeld an. Bestätigen Sie mit ENTER, um ein neues Eingabefeld zu erhalten."
#: extensions/admin/forms/domain.py:75
#: extensions/postfix_relay_domains/forms.py:50
@@ -859,7 +830,8 @@ msgstr ""
msgid "domain alias"
msgstr "Domain-Alias"
-#: extensions/admin/forms/domain.py:82 extensions/admin/forms/domain.py:98
+#: extensions/admin/forms/domain.py:82
+#: extensions/admin/forms/domain.py:98
#: extensions/postfix_relay_domains/forms.py:58
#: extensions/postfix_relay_domains/forms.py:78
#, python-format
@@ -881,12 +853,8 @@ msgid "Automatically create an administrator for this domain"
msgstr "Automatisch Administrator für diese Domain anlegen"
#: extensions/admin/forms/domain.py:185
-msgid ""
-"The administrator's name. Don't include the domain's name here, it will be "
-"automatically appended."
-msgstr ""
-"Name des Administrators. Geben Sie nicht den Domainnamen mit an. Er wird "
-"automatisch hinzugefügt."
+msgid "The administrator's name. Don't include the domain's name here, it will be automatically appended."
+msgstr "Name des Administrators. Geben Sie nicht den Domainnamen mit an. Er wird automatisch hinzugefügt."
#: extensions/admin/forms/domain.py:193
msgid "Create aliases"
@@ -909,7 +877,8 @@ msgstr "Identität %s existiert bereits"
msgid "File name"
msgstr "Dateiname"
-#: extensions/admin/forms/export.py:10 extensions/admin/forms/import_.py:8
+#: extensions/admin/forms/export.py:10
+#: extensions/admin/forms/import_.py:8
msgid "Separator"
msgstr "Separator"
@@ -930,14 +899,11 @@ msgid "Forward messages and store copies into your local mailbox"
msgstr "Nachricht weiterleiten und Kopie in Mailbox ablegen"
#: extensions/admin/forms/forward.py:38
-msgid ""
-"You can't define a forward to a local destination. Please ask your "
-"administrator to create an alias instead."
-msgstr ""
-"Sie können keine Weiterleitung auf ein lokales Ziel anlegen. Bitten Sie "
-"Ihren Administrator stattdessen einen Alias anzulegen."
+msgid "You can't define a forward to a local destination. Please ask your administrator to create an alias instead."
+msgstr "Sie können keine Weiterleitung auf ein lokales Ziel anlegen. Bitten Sie Ihren Administrator stattdessen einen Alias anzulegen."
-#: extensions/admin/forms/import_.py:6 extensions/webmail/forms.py:26
+#: extensions/admin/forms/import_.py:6
+#: extensions/webmail/forms.py:26
msgid "Select a file"
msgstr "Wählen Sie eine Datei"
@@ -957,17 +923,14 @@ msgstr "Passworte verschlüsseln"
msgid "Check this option if passwords contained in your file are not crypted"
msgstr "Auswählen wenn Kennwörter in Datei nicht verschlüsselt sind"
-#: extensions/admin/models/alias.py:16 extensions/admin/models/mailbox.py:51
+#: extensions/admin/models/alias.py:16
+#: extensions/admin/models/mailbox.py:51
msgid "address"
msgstr "Adresse"
#: extensions/admin/models/alias.py:18
-msgid ""
-"The alias address (without the domain part). For a 'catch-all' address, just "
-"enter an * character."
-msgstr ""
-"Die Alias-Adresse (ohne den Domain-Anteil). Geben sie für eine Adresse an, "
-"die alles annimmt, * an."
+msgid "The alias address (without the domain part). For a 'catch-all' address, just enter an * character."
+msgstr "Die Alias-Adresse (ohne den Domain-Anteil). Geben sie für eine Adresse an, die alles annimmt, * an."
#: extensions/admin/models/alias.py:24
msgid "mailboxes"
@@ -1120,12 +1083,14 @@ msgid "Last modification date"
msgstr "Datum der letzten Änderung"
#: extensions/admin/templates/admin/editdomainform.html:24
-#: extensions/limits/app_settings.py:25 extensions/limits/models.py:20
+#: extensions/limits/app_settings.py:25
+#: extensions/limits/models.py:20
msgid "Domain aliases"
msgstr "Domänen-Aliase"
#: extensions/admin/templates/admin/editdomainform.html:26
-#: extensions/limits/app_settings.py:37 extensions/limits/models.py:25
+#: extensions/limits/app_settings.py:37
+#: extensions/limits/models.py:25
msgid "Mailbox aliases"
msgstr "Mailboxen-Aliase"
@@ -1193,13 +1158,15 @@ msgstr "Domain hinzufügen"
#: extensions/admin/templatetags/admin_tags.py:42
#: extensions/admin/templatetags/admin_tags.py:106
-#: extensions/admin/views/import.py:51 extensions/admin/views/import.py:166
+#: extensions/admin/views/import.py:51
+#: extensions/admin/views/import.py:166
msgid "Import"
msgstr "Importiere"
#: extensions/admin/templatetags/admin_tags.py:48
#: extensions/admin/templatetags/admin_tags.py:112
-#: extensions/admin/views/export.py:38 extensions/admin/views/export.py:64
+#: extensions/admin/views/export.py:38
+#: extensions/admin/views/export.py:64
msgid "Export"
msgstr "Exportiere"
@@ -1247,11 +1214,14 @@ msgstr "Berechtigung entfernen"
msgid "Alias with this name already exists"
msgstr "Ein Alias mit diesem Namen existiert bereits"
-#: extensions/admin/views/alias.py:49 extensions/admin/views/domain.py:100
-#: extensions/admin/views/domain.py:129 extensions/admin/views/identity.py:131
+#: extensions/admin/views/alias.py:49
+#: extensions/admin/views/domain.py:100
+#: extensions/admin/views/domain.py:129
+#: extensions/admin/views/identity.py:131
#: extensions/admin/views/identity.py:158
#: extensions/postfix_relay_domains/views.py:32
-#: extensions/sievefilters/views.py:141 extensions/sievefilters/views.py:230
+#: extensions/sievefilters/views.py:141
+#: extensions/sievefilters/views.py:230
#: extensions/webmail/views.py:151
msgid "Create"
msgstr "Erstellen"
@@ -1292,7 +1262,8 @@ msgstr "Weiterleitung verändert"
msgid "Alias modified"
msgstr "Alias verändert"
-#: extensions/admin/views/domain.py:96 extensions/admin/views/identity.py:128
+#: extensions/admin/views/domain.py:96
+#: extensions/admin/views/identity.py:128
msgid "Next"
msgstr "Nächstes"
@@ -1300,7 +1271,8 @@ msgstr "Nächstes"
msgid "Options"
msgstr "optionen"
-#: extensions/admin/views/domain.py:101 extensions/admin/views/identity.py:132
+#: extensions/admin/views/domain.py:101
+#: extensions/admin/views/identity.py:132
msgid "Previous"
msgstr "Vorheriges"
@@ -1336,16 +1308,26 @@ msgstr "Domains exportieren"
#: extensions/admin/views/identity.py:103
#: extensions/admin/views/identity.py:224
-#: extensions/admin/views/identity.py:229 extensions/amavis/views.py:179
-#: extensions/amavis/views.py:185 extensions/amavis/views.py:220
-#: extensions/amavis/views.py:224 extensions/amavis/views.py:226
-#: extensions/webmail/views.py:47 extensions/webmail/views.py:65
-#: extensions/webmail/views.py:79 extensions/webmail/views.py:97
-#: extensions/webmail/views.py:114 extensions/webmail/views.py:200
-#: extensions/webmail/views.py:223 extensions/webmail/views.py:396
-#: extensions/webmail/views.py:430 extensions/webmail/views.py:443
-#: extensions/webmail/views.py:472 extensions/webmail/views.py:512
-#: lib/formutils.py:44 lib/formutils.py:49
+#: extensions/admin/views/identity.py:229
+#: extensions/amavis/views.py:179
+#: extensions/amavis/views.py:185
+#: extensions/amavis/views.py:220
+#: extensions/amavis/views.py:224
+#: extensions/amavis/views.py:226
+#: extensions/webmail/views.py:47
+#: extensions/webmail/views.py:65
+#: extensions/webmail/views.py:79
+#: extensions/webmail/views.py:97
+#: extensions/webmail/views.py:114
+#: extensions/webmail/views.py:200
+#: extensions/webmail/views.py:223
+#: extensions/webmail/views.py:396
+#: extensions/webmail/views.py:430
+#: extensions/webmail/views.py:443
+#: extensions/webmail/views.py:472
+#: extensions/webmail/views.py:512
+#: lib/formutils.py:44
+#: lib/formutils.py:49
msgid "Invalid request"
msgstr "Ungültige Anfrage"
@@ -1376,8 +1358,7 @@ msgid ""
" domainalias; name; targeted domain; enabled\n"
" %s\n"
"\n"
-"The first element of each line is mandatory and must be equal to one of "
-"the previous values.
\n"
+"The first element of each line is mandatory and must be equal to one of the previous values.
\n"
"You can use a different character as separator.
\n"
msgstr ""
"Verwenden sie eine CSV-Datei mit einem der folgenden Formate:\n"
@@ -1386,8 +1367,7 @@ msgstr ""
" domainalias; name; targeted domain; enabled\n"
" %s\n"
"\n"
-"Das erste Element jeder Zeile ist zwingend und muss gleich zum "
-"vorhergehenden sein.
\n"
+"Das erste Element jeder Zeile ist zwingend und muss gleich zum vorhergehenden sein.
\n"
"Ein anderes Zeichen als Trenner ist gestattet.
\n"
#: extensions/admin/views/import.py:50
@@ -1408,27 +1388,23 @@ msgstr "%d Objekte erfolgreich importiert"
msgid ""
"Provide a CSV file where lines respect one of the following formats:\n"
"\n"
-"- account; loginname; password; first name; last name; enabled; group; "
-"address; quota; [, domain, ...]
\n"
+"- account; loginname; password; first name; last name; enabled; group; address; quota; [, domain, ...]
\n"
"- alias; address; enabled; internal recipient
\n"
"- forward; address; enabled; external recipient
\n"
"- dlist; address; enabled; recipient; recipient; ...
\n"
"
\n"
-"The first element of each line is mandatory and must be equal to one of "
-"the previous values.
\n"
+"The first element of each line is mandatory and must be equal to one of the previous values.
\n"
"\n"
"You can use a different character as separator.
\n"
msgstr ""
"Verwenden sie eine CSV-Datei in einem der folgenden Formate:\n"
"\n"
-"- account; loginname; password; first name; last name; enabled; group; "
-"address; quota; [, domain, ...]
\n"
+"- account; loginname; password; first name; last name; enabled; group; address; quota; [, domain, ...]
\n"
"- alias; address; enabled; internal recipient
\n"
"- forward; address; enabled; external recipient
\n"
"- dlist; address; enabled; recipient; recipient; ...
\n"
"
\n"
-"Das erste Element einer Zeile ist zwingend und muss gleich mit einem der "
-"vorhergehenden sein.
\n"
+"Das erste Element einer Zeile ist zwingend und muss gleich mit einem der vorhergehenden sein.
\n"
"\n"
"Ein anderes Zeichen als Separator ist gestattet.
\n"
@@ -1444,7 +1420,8 @@ msgstr "Weiterleitung aktualisiert"
msgid "Simple amavis management frontend"
msgstr "Einfache amavis Management Oberfläche"
-#: extensions/amavis/__init__.py:52 extensions/amavis/general_callbacks.py:17
+#: extensions/amavis/__init__.py:52
+#: extensions/amavis/general_callbacks.py:17
msgid "Quarantine"
msgstr "Quarantäne"
@@ -1458,9 +1435,7 @@ msgstr "Maximales Alter einer Nachricht"
#: extensions/amavis/app_settings.py:16
msgid "Quarantine messages maximum age (in days) before deletion"
-msgstr ""
-"Maximales Alter (in Tagen) von Nachrichten in der Quarantäne bevor sie "
-"gelöscht werden"
+msgstr "Maximales Alter (in Tagen) von Nachrichten in der Quarantäne bevor sie gelöscht werden"
#: extensions/amavis/app_settings.py:19
msgid "Messages releasing"
@@ -1536,18 +1511,16 @@ msgstr "Absender von Benachrichtigungen"
#: extensions/amavis/app_settings.py:74
msgid "The e-mail address used to send notitications"
-msgstr ""
-"Die Mailadresse, die verwendet wird, um Benachrichtigungen zu versenden"
+msgstr "Die Mailadresse, die verwendet wird, um Benachrichtigungen zu versenden"
-#: extensions/amavis/app_settings.py:91 extensions/webmail/app_settings.py:91
+#: extensions/amavis/app_settings.py:91
+#: extensions/webmail/app_settings.py:91
msgid "Number of displayed emails per page"
msgstr "Anzahl dargestellter Nachrichten pro Seite"
#: extensions/amavis/app_settings.py:92
msgid "Set the maximum number of messages displayed in a page"
-msgstr ""
-"Legt die maximale Anzahl von Nachrichten fest, die in einer Seite "
-"dargestellt werden"
+msgstr "Legt die maximale Anzahl von Nachrichten fest, die in einer Seite dargestellt werden"
#: extensions/amavis/general_callbacks.py:81
msgid "pending requests"
@@ -1570,17 +1543,22 @@ msgstr "Verbindung zu amavis fehlgeschlagen: %s"
msgid "Virus filter"
msgstr "Virusfilter"
-#: extensions/amavis/models.py:94 extensions/amavis/models.py:102
-#: extensions/amavis/models.py:110 extensions/sievefilters/views.py:290
+#: extensions/amavis/models.py:94
+#: extensions/amavis/models.py:102
+#: extensions/amavis/models.py:110
+#: extensions/sievefilters/views.py:290
msgid "yes"
msgstr "Ja"
-#: extensions/amavis/models.py:95 extensions/amavis/models.py:103
-#: extensions/amavis/models.py:111 extensions/sievefilters/views.py:294
+#: extensions/amavis/models.py:95
+#: extensions/amavis/models.py:103
+#: extensions/amavis/models.py:111
+#: extensions/sievefilters/views.py:294
msgid "no"
msgstr "Nein"
-#: extensions/amavis/models.py:96 extensions/amavis/models.py:104
+#: extensions/amavis/models.py:96
+#: extensions/amavis/models.py:104
#: extensions/amavis/models.py:112
#: extensions/amavis/templates/amavis/domain_content_filter.html:11
msgid "default"
@@ -1588,9 +1566,7 @@ msgstr "Standard"
#: extensions/amavis/models.py:98
msgid "Bypass virus checks or not. Choose 'default' to use global settings."
-msgstr ""
-"Virus-Prüfungen umgehen oder nicht. Geben Sie, um den Domain-Standard zu "
-"nutzen, keinen individuellen Wert an."
+msgstr "Virus-Prüfungen umgehen oder nicht. Geben Sie, um den Domain-Standard zu nutzen, keinen individuellen Wert an."
#: extensions/amavis/models.py:101
msgid "Spam filter"
@@ -1598,9 +1574,7 @@ msgstr "SPAM-Filter"
#: extensions/amavis/models.py:106
msgid "Bypass spam checks or not. Choose 'default' to use global settings."
-msgstr ""
-"Spam-Prüfungen umgehen oder nicht. Geben Sie, um den Domain-Standard zu "
-"nutzen, keinen individuellen Wert an."
+msgstr "Spam-Prüfungen umgehen oder nicht. Geben Sie, um den Domain-Standard zu nutzen, keinen individuellen Wert an."
#: extensions/amavis/models.py:109
msgid "Banned filter"
@@ -1608,21 +1582,15 @@ msgstr "Filter für unerwünschte Dateien"
#: extensions/amavis/models.py:114
msgid "Bypass banned checks or not. Choose 'default' to use global settings."
-msgstr ""
-"Unerwünschte Dateien umgehen oder nicht. Geben Sie, um den Domain-Standard "
-"zu nutzen, keinen individuellen Wert an."
+msgstr "Unerwünschte Dateien umgehen oder nicht. Geben Sie, um den Domain-Standard zu nutzen, keinen individuellen Wert an."
#: extensions/amavis/models.py:144
msgid "Spam marker"
msgstr "SPAM-Markierung"
#: extensions/amavis/models.py:146
-msgid ""
-"Modify spam subject using the specified text. Choose 'default' to use global "
-"settings."
-msgstr ""
-"Betreff:-Zeile einer Spam-Nachricht mit dem angegebenen Text ergänzen. "
-"Wählen Sie 'Standard' für den systemweiten Standard."
+msgid "Modify spam subject using the specified text. Choose 'default' to use global settings."
+msgstr "Betreff:-Zeile einer Spam-Nachricht mit dem angegebenen Text ergänzen. Wählen Sie 'Standard' für den systemweiten Standard."
#: extensions/amavis/sql_listing.py:31
msgid "Score"
@@ -1635,13 +1603,17 @@ msgid "To"
msgstr "An"
#: extensions/amavis/sql_listing.py:38
-#: extensions/postfix_autoreply/forms.py:11 extensions/webmail/lib.py:44
+#: extensions/postfix_autoreply/forms.py:11
+#: extensions/webmail/lib.py:44
msgid "From"
msgstr "Von"
-#: extensions/amavis/sql_listing.py:42 extensions/sievefilters/forms.py:77
-#: extensions/webmail/forms.py:11 extensions/webmail/lib.py:40
-#: extensions/webmail/lib.py:423 templates/common/email_searchbar.html:6
+#: extensions/amavis/sql_listing.py:42
+#: extensions/sievefilters/forms.py:77
+#: extensions/webmail/forms.py:11
+#: extensions/webmail/lib.py:40
+#: extensions/webmail/lib.py:423
+#: templates/common/email_searchbar.html:6
msgid "Subject"
msgstr "Betreff"
@@ -1810,18 +1782,15 @@ msgstr "Rektion auf diese Nachricht:"
#: extensions/amavis/templates/amavis/notifications/pending_requests.html:14
#, python-format
msgid "Please visit %(listingurl)s for a full listing."
-msgstr ""
-"Bitte besuchen sie %(listingurl)s um eine vollständige Ausgabe zu erhalten."
+msgstr "Bitte besuchen sie %(listingurl)s um eine vollständige Ausgabe zu erhalten."
#: extensions/amavis/templatetags/amavis_tags.py:28
msgid "View full headers"
msgstr "Alle Mail-Header ansehen"
#: extensions/limits/__init__.py:25
-msgid ""
-"Per administrator resources to limit the number of objects they can create"
-msgstr ""
-"Administrator-Ressourcen, um die Anzahl erstellbarer Objekte einzuschränken"
+msgid "Per administrator resources to limit the number of objects they can create"
+msgstr "Administrator-Ressourcen, um die Anzahl erstellbarer Objekte einzuschränken"
#: extensions/limits/__init__.py:56
msgid "Limits"
@@ -1831,15 +1800,14 @@ msgstr "Grenzwerte"
msgid "Default limits"
msgstr "Standard-Grenzwerte"
-#: extensions/limits/app_settings.py:13 extensions/limits/models.py:14
+#: extensions/limits/app_settings.py:13
+#: extensions/limits/models.py:14
msgid "Domain admins"
msgstr "Domänen-Administratoren"
#: extensions/limits/app_settings.py:15
msgid "Maximum number of allowed domain administrators for a new administrator"
-msgstr ""
-"Maximale Anzahl Domänenadministratoren, die ein neuer Administrator "
-"erstellen darf"
+msgstr "Maximale Anzahl Domänenadministratoren, die ein neuer Administrator erstellen darf"
#: extensions/limits/app_settings.py:21
msgid "Maximum number of allowed domains for a new administrator"
@@ -1847,8 +1815,7 @@ msgstr "Maximale Anzahl Domains, die ein neuer Administrator erstellen darf"
#: extensions/limits/app_settings.py:27
msgid "Maximum number of allowed domain aliases for a new administrator"
-msgstr ""
-"Maximale Anzahl Domain Aliase, die ein neuer Administrator erstellen darf"
+msgstr "Maximale Anzahl Domain Aliase, die ein neuer Administrator erstellen darf"
#: extensions/limits/app_settings.py:33
msgid "Maximum number of allowed mailboxes for a new administrator"
@@ -1858,7 +1825,8 @@ msgstr "Maximale Anzahl Mailboxen, die ein neuer Administrator erstellen darf"
msgid "Maximum number of allowed aliases for a new administrator"
msgstr "Maximale Anzahl Aliase, die ein neuer Administrator erstellen darf"
-#: extensions/limits/forms.py:28 extensions/limits/forms.py:35
+#: extensions/limits/forms.py:28
+#: extensions/limits/forms.py:35
msgid "Invalid limit"
msgstr "Ungültiger Grenzwert"
@@ -1868,8 +1836,7 @@ msgstr "Ihre Ressourcen wurde noch nicht initialisiert"
#: extensions/limits/forms.py:61
msgid "You're not allowed to define unlimited values"
-msgstr ""
-"Sie verfügen nicht über ausreichend Rechte, um unbegrenzte Werte anzugeben"
+msgstr "Sie verfügen nicht über ausreichend Rechte, um unbegrenzte Werte anzugeben"
#: extensions/limits/general_callbacks.py:10
msgid "Reseller"
@@ -1922,8 +1889,7 @@ msgstr "Ressourcen-Verbrauch"
#: extensions/postfix_autoreply/__init__.py:26
msgid "Auto-reply (vacation) functionality using Postfix"
-msgstr ""
-"Automatische Antwort (Abwesenheitsbenachrichtigung) über Postfix-Programm"
+msgstr "Automatische Antwort (Abwesenheitsbenachrichtigung) über Postfix-Programm"
#: extensions/postfix_autoreply/__init__.py:47
msgid "Automatic replies"
@@ -1935,9 +1901,7 @@ msgstr "Zeitüberschreitung für automatische Antworten"
#: extensions/postfix_autoreply/app_settings.py:16
msgid "Timeout in seconds between two auto-replies to the same recipient"
-msgstr ""
-"Zeit in Sekunden zwischen zwei automatisierten Antworten an denselben "
-"Empfänger"
+msgstr "Zeit in Sekunden zwischen zwei automatisierten Antworten an denselben Empfänger"
#: extensions/postfix_autoreply/app_settings.py:20
msgid "Default subject"
@@ -1948,8 +1912,7 @@ msgid "I'm off"
msgstr "Ich bin weg"
#: extensions/postfix_autoreply/app_settings.py:23
-msgid ""
-"Default subject used when an auto-reply message is created automatically"
+msgid "Default subject used when an auto-reply message is created automatically"
msgstr "Standardbetreff wenn eine Antwortnachricht automatisch generiert wird"
#: extensions/postfix_autoreply/app_settings.py:28
@@ -1971,12 +1934,8 @@ msgstr ""
#: extensions/postfix_autoreply/app_settings.py:36
#, python-format
-msgid ""
-"Default content used when an auto-reply message is created automatically. "
-"The '%(name)s' macro will be replaced by the user's full name."
-msgstr ""
-"Standardinhalt wenn eine Antwort automatisch erstellt wird. Das '%(name)s' "
-"Makro wird gegen den vollen Anwendernamen ersetzt."
+msgid "Default content used when an auto-reply message is created automatically. The '%(name)s' macro will be replaced by the user's full name."
+msgstr "Standardinhalt wenn eine Antwort automatisch erstellt wird. Das '%(name)s' Makro wird gegen den vollen Anwendernamen ersetzt."
#: extensions/postfix_autoreply/forms.py:13
msgid "Activate your auto reply from this date"
@@ -2038,9 +1997,7 @@ msgstr "Automatische Antwort erfolgreich aktualisiert."
#: extensions/postfix_autoreply/templates/postfix_autoreply/autoreply.html:2
msgid "Define a message to automatically send when you are off"
-msgstr ""
-"Gegen sie eine Nachricht an, die gesendet werden soll, wenn Sie nicht "
-"erreichbar sind"
+msgstr "Gegen sie eine Nachricht an, die gesendet werden soll, wenn Sie nicht erreichbar sind"
#: extensions/postfix_relay_domains/__init__.py:72
msgid "Relay domains support for Postfix"
@@ -2061,12 +2018,8 @@ msgid "Path to the master.cf configuration file"
msgstr "Pfad zur master.cf Konfigurationsdatei"
#: extensions/postfix_relay_domains/forms.py:15
-msgid ""
-"Alias(es) of this relay domain. Indicate only one name per input, press "
-"ENTER to add a new input."
-msgstr ""
-"Alias(e) für diese Relaydomain. Geben Sie jeweils nur einen pro Eingabefeld "
-"an. Bestätigen Sie mit ENTER, um ein weiteres Eingabefeld zu erhalten."
+msgid "Alias(es) of this relay domain. Indicate only one name per input, press ENTER to add a new input."
+msgstr "Alias(e) für diese Relaydomain. Geben Sie jeweils nur einen pro Eingabefeld an. Bestätigen Sie mit ENTER, um ein weiteres Eingabefeld zu erhalten."
#: extensions/postfix_relay_domains/forms.py:51
#: extensions/postfix_relay_domains/general_callbacks.py:93
@@ -2098,25 +2051,20 @@ msgstr "Maximale Anzahl Relaydomain-Aliase, die dieser Anwender erstellen darf"
#: extensions/postfix_relay_domains/general_callbacks.py:111
msgid ""
"\n"
-"relaydomain; name; target host; service; enabled; verify recipients"
-"em>\n"
+"relaydomain; name; target host; service; enabled; verify recipients\n"
"relaydomainalias; name; target; enabled\n"
msgstr ""
"\n"
-"relaydomain; name; target host; service; enabled; verify recipients"
-"em>\n"
+"relaydomain; name; target host; service; enabled; verify recipients\n"
"relaydomainalias; name; target; enabled\n"
#: extensions/postfix_relay_domains/limits_callbacks.py:19
msgid "Maximum number of allowed relay domains for a new administrator"
-msgstr ""
-"Maximale Anzahl Relaydomains, die ein neuer Administrator erstellen darf"
+msgstr "Maximale Anzahl Relaydomains, die ein neuer Administrator erstellen darf"
#: extensions/postfix_relay_domains/limits_callbacks.py:27
msgid "Maximum number of allowed relay domain aliases for a new administrator"
-msgstr ""
-"Maximale Anzahl Relaydomain-Aliase, die ein neuer Administrator erstellen "
-"darf"
+msgstr "Maximale Anzahl Relaydomain-Aliase, die ein neuer Administrator erstellen darf"
#: extensions/postfix_relay_domains/models.py:59
msgid "The service name"
@@ -2257,7 +2205,8 @@ msgstr "Sender"
msgid "Recipient"
msgstr "Empfänger"
-#: extensions/sievefilters/forms.py:80 extensions/webmail/forms.py:8
+#: extensions/sievefilters/forms.py:80
+#: extensions/webmail/forms.py:8
msgid "Cc"
msgstr "Cc"
@@ -2283,9 +2232,7 @@ msgstr "Leite Nachricht um zu"
#: extensions/sievefilters/lib.py:40
msgid "Connection to MANAGESIEVE server failed, check your configuration"
-msgstr ""
-"Verbindung zu MANAGESIEVE-Server fehlgeschlagen. Überprüfen Sie Ihre "
-"Konfiguration."
+msgstr "Verbindung zu MANAGESIEVE-Server fehlgeschlagen. Überprüfen Sie Ihre Konfiguration."
#: extensions/sievefilters/lib.py:85
msgid "Not enough space on server"
@@ -2362,11 +2309,8 @@ msgid "active"
msgstr "aktiv"
#: extensions/sievefilters/templates/sievefilters/index.html:94
-msgid ""
-"No filters set defined yet. You must create one in order to define filters."
-msgstr ""
-"Nich keine Filter-Sätze definiert. Sie müssen einen erstellen, damit sie "
-"Filter erstellen können."
+msgid "No filters set defined yet. You must create one in order to define filters."
+msgstr "Nich keine Filter-Sätze definiert. Sie müssen einen erstellen, damit sie Filter erstellen können."
#: extensions/sievefilters/templatetags/sfilters_tags.py:15
msgid "New filters set"
@@ -2506,7 +2450,8 @@ msgstr "Jahr"
msgid "Total"
msgstr "Gesamt"
-#: extensions/stats/views.py:28 extensions/stats/templates/stats/graphs.html:4
+#: extensions/stats/views.py:28
+#: extensions/stats/templates/stats/graphs.html:4
msgid "No statistics available"
msgstr "Keine Statistik-Daten verfügbar"
@@ -2612,9 +2557,7 @@ msgstr "Aktiviere/Deaktiviere Darstellung von HTML-Links"
#: extensions/webmail/app_settings.py:92
msgid "Sets the maximum number of messages displayed in a page"
-msgstr ""
-"Legt die maximale Anzahl von Nachrichten fest, die in einer Seite "
-"dargestellt werden"
+msgstr "Legt die maximale Anzahl von Nachrichten fest, die in einer Seite dargestellt werden"
#: extensions/webmail/app_settings.py:97
msgid "Listing refresh rate"
@@ -2625,13 +2568,12 @@ msgid "Automatic folder refresh rate (in seconds)"
msgstr "Aktualisierungsintervall für Ordner (in Sekunden)"
#: extensions/webmail/app_settings.py:103
-#, fuzzy
msgid "Mailboxes container's width"
-msgstr "Mailbox-Besitzer"
+msgstr "Breite des Mailboxcontainers"
#: extensions/webmail/app_settings.py:104
msgid "The width of the mailbox list container"
-msgstr ""
+msgstr "Die Breite der Mailbox-Liste"
#: extensions/webmail/app_settings.py:111
msgid "Trash folder"
@@ -2678,9 +2620,8 @@ msgid "User defined email signature"
msgstr "Benutzerdefinierte E-Mail-Signatur"
#: extensions/webmail/app_settings.py:160
-#, fuzzy
msgid "Value must be a positive integer (> 0)"
-msgstr "Muss eine positive Integer sein"
+msgstr "Wert muss eine positive Integer sein (>0)"
#: extensions/webmail/exceptions.py:20
msgid "Server response"
@@ -2711,7 +2652,8 @@ msgstr "Verbindung zu IMAP-Server fehlgeschlagen: %s"
msgid "wrote:"
msgstr "schrieb:"
-#: extensions/webmail/lib.py:437 extensions/webmail/lib.py:441
+#: extensions/webmail/lib.py:437
+#: extensions/webmail/lib.py:441
msgid "Original message"
msgstr "Gesendete Nachrichten"
@@ -2722,7 +2664,8 @@ msgid_plural "%(count)d messages deleted"
msgstr[0] "%(count)d Nachricht gelöscht"
msgstr[1] "%(count)d Nachrichten gelöscht"
-#: extensions/webmail/views.py:116 lib/email_listing.py:138
+#: extensions/webmail/views.py:116
+#: lib/email_listing.py:138
msgid "Empty mailbox"
msgstr "Mailbox leer"
@@ -2735,7 +2678,8 @@ msgstr "Mailbox erstellt."
msgid "Create a new mailbox"
msgstr "Neue Mailbox erstellen"
-#: extensions/webmail/views.py:167 extensions/webmail/views.py:202
+#: extensions/webmail/views.py:167
+#: extensions/webmail/views.py:202
msgid "Edit mailbox"
msgstr "Mailbox bearbeiten"
@@ -2879,7 +2823,8 @@ msgstr "Erlaubnis verweigert: %s"
msgid "Permission denied"
msgstr "Berechtigung verweigert"
-#: lib/formutils.py:187 lib/formutils.py:195
+#: lib/formutils.py:187
+#: lib/formutils.py:195
msgid "Enter a valid domain name"
msgstr "Geben Sie einen gültigen Domain-Namen an"
@@ -2921,7 +2866,8 @@ msgstr "Keine Einträge darzustellen"
msgid "activate"
msgstr "aktivieren"
-#: templates/404.html:4 templates/500.html:4
+#: templates/404.html:4
+#: templates/500.html:4
msgid "Sorry"
msgstr "Entschuldigung"
From b46fb9c10394272b4b447221094d4e32f1d1d07c Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Tue, 24 Dec 2013 18:04:46 +0100
Subject: [PATCH 04/32] Documentation update.
---
doc/getting_started/plugins.rst | 35 ++++++++++++++++++++-------
doc/getting_started/upgrade.rst | 4 +--
doc/integration/imap_and_smtp.rst | 6 -----
modoboa/core/commands/postfix_maps.py | 29 +++++++++++-----------
4 files changed, 43 insertions(+), 31 deletions(-)
diff --git a/doc/getting_started/plugins.rst b/doc/getting_started/plugins.rst
index 2b47858e7..6f70f0d57 100644
--- a/doc/getting_started/plugins.rst
+++ b/doc/getting_started/plugins.rst
@@ -46,7 +46,7 @@ listing page: *relay domain* and *relay domain alias*.
The extension is compatible with the *amavis* and *limits*
ones. Resellers will be able to create both new objects.
-To tell Postfix this feature exists, you must generate two new map
+Replace by the name of the database you use.To tell Postfix this feature exists, you must generate two new map
files and then update your configuration.
To generate the map files, run the following command::
@@ -55,7 +55,24 @@ To generate the map files, run the following command::
Replace values between ``<>`` by yours.
-Edit the :file:`/etc/postfix/main.cf` file.
+Edit the :file:`/etc/postfix/main.cf` file and copy the following
+lines inside::
+
+ relay_domains = :/etc/postfix/maps/sql-relaydomains.cf
+ transport_maps =
+ :/etc/postfix/maps/sql-relaydomains-transport.cf
+ :/etc/postfix/maps/sql-relaydomain-aliases-transport.cf
+
+Replace ```` by the name of the database you use.
+
+Ensure that ``smtpd_recipient_restrictions`` contains at least the
+following options::
+
+ smtpd_recipient_restrictions =
+ permit_mynetworks
+ reject_unauth_destination
+
+Reload postfix.
.. _amavis_frontend:
@@ -311,12 +328,11 @@ configuration files as follows:
``/etc/postfix/main.cf``::
- transport_maps = mysql:/etc/postfix/maps/sql-transport.cf
- virtual_alias_maps = mysql:/etc/postfix/maps/sql-aliases.cf
- mysql:/etc/postfix/mapfiles/sql-domain-aliases-mailboxes.cf,
- mysql:/etc/postfix/mapfiles/sql-email2email.cf,
- mysql:/etc/postfix/maps/sql-autoreplies.cf,
- mysql:/etc/postfix/mapfiles/sql-catchall-aliases.cf
+ transport_maps = mysql:/etc/postfix/maps/sql-autoreplies-transport.cf
+ virtual_alias_maps = :/etc/postfix/maps/sql-aliases.cf
+ :/etc/postfix/mapfiles/sql-domain-aliases-mailboxes.cf,
+ :/etc/postfix/maps/sql-autoreplies.cf,
+ :/etc/postfix/mapfiles/sql-catchall-aliases.cf
.. note::
@@ -327,7 +343,8 @@ configuration files as follows:
autoreply unix - n n - - pipe
flags= user=vmail: argv=/manage.py autoreply $sender $mailbox
-```` is the path of your Modoboa instance.
+Replace ```` by the name of the database you
+use. ```` is the path of your Modoboa instance.
Then, create the requested map files::
diff --git a/doc/getting_started/upgrade.rst b/doc/getting_started/upgrade.rst
index 013e9fb56..6fec4120c 100644
--- a/doc/getting_started/upgrade.rst
+++ b/doc/getting_started/upgrade.rst
@@ -50,8 +50,8 @@ Finally, follow the common procedure::
.. _1.1.0:
-1.1.0: FIXME
-============
+1.1.0: relay domains and better passwords encryption
+====================================================
Due to code refactoring, some modifications need to be done into
:file:`settings.py`:
diff --git a/doc/integration/imap_and_smtp.rst b/doc/integration/imap_and_smtp.rst
index 5c66009fa..7b9d0aa9f 100644
--- a/doc/integration/imap_and_smtp.rst
+++ b/doc/integration/imap_and_smtp.rst
@@ -443,15 +443,9 @@ Use the following configuration in the :file:`/etc/postfix/main.cf` file
virtual_transport = dovecot
dovecot_destination_recipient_limit = 1
- virtual_minimum_uid =
- virtual_gid_maps = static:
- virtual_uid_maps = static:
- virtual_mailbox_base = /var/vmail
-
relay_domains =
virtual_mailbox_domains = :/etc/postfix/sql-domains.cf
virtual_alias_domains = :/etc/postfix/sql-domain-aliases.cf
- virtual_mailbox_maps = :/etc/postfix/sql-mailboxes.cf
virtual_alias_maps = :/etc/postfix/sql-aliases.cf,
:/etc/postfix/sql-domain-aliases-mailboxes.cf,
:/etc/postfix/sql-catchall-aliases.cf
diff --git a/modoboa/core/commands/postfix_maps.py b/modoboa/core/commands/postfix_maps.py
index d37fb1dbb..d5f4968af 100644
--- a/modoboa/core/commands/postfix_maps.py
+++ b/modoboa/core/commands/postfix_maps.py
@@ -104,13 +104,6 @@ class DomainsAliasesMap(MapFile):
sqlite = "SELECT dom.name FROM admin_domain dom INNER JOIN admin_domainalias domal ON dom.id=domal.target_id WHERE domal.name='%s' AND domal.enabled=1 AND dom.enabled=1"
-class MailboxesMap(MapFile):
- filename = 'sql-mailboxes.cf'
- mysql = "SELECT 1 FROM admin_mailbox mb INNER JOIN admin_domain dom ON mb.domain_id=dom.id INNER JOIN core_user user ON mb.user_id=user.id WHERE dom.enabled=1 AND dom.name='%d' AND user.is_active=1 AND mb.address='%u'"
- postgres = "SELECT 1 FROM admin_mailbox mb INNER JOIN admin_domain dom ON mb.domain_id=dom.id INNER JOIN core_user u ON mb.user_id=u.id WHERE dom.enabled AND dom.name='%d' AND u.is_active AND mb.address='%u'"
- sqlite = "SELECT 1 FROM admin_mailbox mb INNER JOIN admin_domain dom ON mb.domain_id=dom.id INNER JOIN core_user user ON mb.user_id=user.id WHERE dom.enabled=1 AND dom.name='%d' AND user.is_active=1 AND mb.address='%u'"
-
-
class AliasesMap(MapFile):
filename = 'sql-aliases.cf'
mysql = "(SELECT concat(mb.address, '@', dom.name) FROM admin_mailbox mb INNER JOIN admin_domain dom ON mb.domain_id=dom.id WHERE mb.id IN (SELECT al_mb.mailbox_id FROM admin_alias_mboxes al_mb INNER JOIN admin_alias al ON al_mb.alias_id=al.id INNER JOIN admin_domain dom ON al.domain_id=dom.id WHERE dom.name='%d' AND dom.enabled=1 AND al.address='%u' AND al.enabled=1)) UNION (SELECT concat(al.address, '@', dom.name) FROM admin_alias al INNER JOIN admin_domain dom ON al.domain_id=dom.id WHERE al.id IN (SELECT al_al.to_alias_id FROM admin_alias_aliases al_al INNER JOIN admin_alias al ON al_al.from_alias_id=al.id INNER JOIN admin_domain dom ON al.domain_id=dom.id WHERE dom.name='%d' AND dom.enabled=1 AND al.address='%u' AND al.enabled=1)) UNION (SELECT al.extmboxes FROM admin_alias al INNER JOIN admin_domain dom ON al.domain_id=dom.id WHERE dom.name='%d' AND dom.enabled=1 AND al.address='%u' AND al.enabled=1 AND al.extmboxes<>'')"
@@ -141,7 +134,7 @@ class MaintainMap(MapFile):
class TransportMap(MapFile):
category = "autoreply"
- filename = 'sql-transport.cf'
+ filename = 'sql-autoreplies-transport.cf'
mysql = "SELECT method FROM postfix_autoreply_transport WHERE domain='%s'"
postgres = "SELECT method FROM postfix_autoreply_transport WHERE domain='%s'"
sqlite = "SELECT method FROM postfix_autoreply_transport WHERE domain='%s'"
@@ -155,20 +148,28 @@ class AutoRepliesMap(MapFile):
sqlite = "SELECT full_address, autoreply_address FROM postfix_autoreply_alias WHERE full_address='%s'"
+class RelayDomainsMap(MapFile):
+ category = "relaydomains"
+ filename = "sql-relaydomains.cf"
+ mysql = "SELECT name FROM postfix_relay_domains_domain WHERE name='%s' AND enabled=1"
+ postgres = "SELECT name FROM postfix_relay_domains_domain WHERE name='%s' AND enabled"
+ sqlite = "SELECT name FROM postfix_relay_domains_domain WHERE name='%s' AND enabled=1"
+
+
class RelayDomainsTransportMap(MapFile):
category = "relaydomains"
filename = "sql-relaydomains-transport.cf"
- mysql = "SELECT CONCAT(srv.name, ':') FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id WHERE rdom.enabled=1 AND rdom.name='%s'"
- postgres = "SELECT srv.name || ':' FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id WHERE rdom.enabled AND rdom.name='%s'"
- sqlite = "SELECT srv.name || ':' FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id WHERE rdom.enabled=1 AND rdom.name='%s'"
+ mysql = "SELECT CONCAT(srv.name, ':[', rdom.target_host, ']') FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id WHERE rdom.enabled=1 AND rdom.name='%s'"
+ postgres = "SELECT srv.name || ':[' || rdom.target_host || ']' FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id WHERE rdom.enabled AND rdom.name='%s'"
+ sqlite = "SELECT srv.name || ':[' || rdom.target_host || ']' FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id WHERE rdom.enabled=1 AND rdom.name='%s'"
class RelayDomainAliasesTransportMap(MapFile):
category = "relaydomains"
filename = "sql-relaydomain-aliases-transport.cf"
- mysql = "SELECT CONCAT(srv.name, ':') FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id INNER JOIN postfix_relay_domains_relaydomainalias AS rdomalias ON rdom.id=rdomalias.target_id WHERE rdom.enabled=1 AND rdomalias.enabled=1 AND rdomalias.name='%s'"
- postgres = "SELECT srv.name || ':' FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id INNER JOIN postfix_relay_domains_relaydomainalias AS rdomalias ON rdom.id=rdomalias.target_id WHERE rdom.enabled AND rdomalias.enabled AND rdomalias.name='%s'"
- sqlite = "SELECT srv.name || ':' FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id INNER JOIN postfix_relay_domains_relaydomainalias AS rdomalias ON rdom.id=rdomalias.target_id WHERE rdom.enabled=1 AND rdomalias.enabled=1 AND rdomalias.name='%s'"
+ mysql = "SELECT CONCAT(srv.name, ':[', rdom.target_host, ']') FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id INNER JOIN postfix_relay_domains_relaydomainalias AS rdomalias ON rdom.id=rdomalias.target_id WHERE rdom.enabled=1 AND rdomalias.enabled=1 AND rdomalias.name='%s'"
+ postgres = "SELECT srv.name || ':[' || rdom.target_host || ']' FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id INNER JOIN postfix_relay_domains_relaydomainalias AS rdomalias ON rdom.id=rdomalias.target_id WHERE rdom.enabled AND rdomalias.enabled AND rdomalias.name='%s'"
+ sqlite = "SELECT srv.name || ':[' || rdom.target_host || ']' FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id INNER JOIN postfix_relay_domains_relaydomainalias AS rdomalias ON rdom.id=rdomalias.target_id WHERE rdom.enabled=1 AND rdomalias.enabled=1 AND rdomalias.name='%s'"
class PostfixMapsCommand(Command):
From 99990c11cd0e48afe6f28962905e4856ce556753 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Fri, 27 Dec 2013 16:05:00 +0100
Subject: [PATCH 05/32] Documentation added.
see #469
---
doc/getting_started/plugins.rst | 9 ++++-----
modoboa/core/commands/postfix_maps.py | 8 ++++++++
2 files changed, 12 insertions(+), 5 deletions(-)
diff --git a/doc/getting_started/plugins.rst b/doc/getting_started/plugins.rst
index 6f70f0d57..0cfd93378 100644
--- a/doc/getting_started/plugins.rst
+++ b/doc/getting_started/plugins.rst
@@ -63,14 +63,13 @@ lines inside::
:/etc/postfix/maps/sql-relaydomains-transport.cf
:/etc/postfix/maps/sql-relaydomain-aliases-transport.cf
-Replace ```` by the name of the database you use.
-
-Ensure that ``smtpd_recipient_restrictions`` contains at least the
-following options::
-
smtpd_recipient_restrictions =
permit_mynetworks
reject_unauth_destination
+ check_recipient_access
+ :/etc/postfix/maps/sql-relay-recipient-verification.cf
+
+Replace ```` by the name of the database you use.
Reload postfix.
diff --git a/modoboa/core/commands/postfix_maps.py b/modoboa/core/commands/postfix_maps.py
index d5f4968af..e7e39476d 100644
--- a/modoboa/core/commands/postfix_maps.py
+++ b/modoboa/core/commands/postfix_maps.py
@@ -172,6 +172,14 @@ class RelayDomainAliasesTransportMap(MapFile):
sqlite = "SELECT srv.name || ':[' || rdom.target_host || ']' FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id INNER JOIN postfix_relay_domains_relaydomainalias AS rdomalias ON rdom.id=rdomalias.target_id WHERE rdom.enabled=1 AND rdomalias.enabled=1 AND rdomalias.name='%s'"
+class RelayRecipientVerification(Mapfile):
+ category = "relaydomains"
+ filename = "sql-relay-recipient-verification.cf"
+ mysql = "SELECT 'reject_unverified_recipient' FROM postfix_relay_domains_relaydomain WHERE verify_recipients=1 AND name='%d'"
+ postgres = "SELECT 'reject_unverified_recipient' FROM postfix_relay_domains_relaydomain WHERE verify_recipients AND name='%d'"
+ sqlite = "SELECT 'reject_unverified_recipient' FROM postfix_relay_domains_relaydomain WHERE verify_recipients=1 AND name='%d'"
+
+
class PostfixMapsCommand(Command):
help = "Generate ready-to-use postfix map files"
From 7561f601eb6c542829a683c463d91ace9b18b261 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Tue, 31 Dec 2013 17:11:58 +0100
Subject: [PATCH 06/32] Fixing unit tests for postgres.
---
modoboa/core/models.py | 8 +++++-
modoboa/extensions/admin/models/alias.py | 10 ++++++-
modoboa/extensions/admin/models/domain.py | 17 +++++++++++-
.../extensions/admin/models/domain_alias.py | 13 ++++-----
modoboa/extensions/admin/tests/account.py | 5 ----
modoboa/extensions/admin/tests/export.py | 24 ++++++++++++-----
modoboa/extensions/admin/tests/import_.py | 2 +-
modoboa/extensions/admin/views/import.py | 2 +-
modoboa/lib/permissions.py | 27 +++++++++----------
9 files changed, 70 insertions(+), 38 deletions(-)
diff --git a/modoboa/core/models.py b/modoboa/core/models.py
index cfb194e39..db3d05f22 100644
--- a/modoboa/core/models.py
+++ b/modoboa/core/models.py
@@ -17,7 +17,7 @@ from django.contrib.auth.models import (
from django.contrib.auth.hashers import make_password, is_password_usable
from modoboa.lib import events, parameters
from modoboa.lib.exceptions import (
- PermDeniedException, InternalError, BadRequest
+ PermDeniedException, InternalError, BadRequest, Conflict
)
from modoboa.lib.sysutils import exec_cmd
from modoboa.core.extensions import exts_pool
@@ -325,6 +325,12 @@ class User(PermissionsMixin):
_("You can't import an account with a role greater than yours")
)
self.username = row[1].strip()
+ try:
+ User.objects.get(username=self.username)
+ except User.DoesNotExist:
+ pass
+ else:
+ raise Conflict
if role == "SimpleUsers":
if (len(row) < 8 or not row[7].strip()):
raise BadRequest(
diff --git a/modoboa/extensions/admin/models/alias.py b/modoboa/extensions/admin/models/alias.py
index 327e4bf0c..62c0d6f5b 100644
--- a/modoboa/extensions/admin/models/alias.py
+++ b/modoboa/extensions/admin/models/alias.py
@@ -2,7 +2,9 @@ import reversion
from django.db import models
from django.utils.translation import ugettext as _, ugettext_lazy
from modoboa.lib.emailutils import split_mailbox
-from modoboa.lib.exceptions import PermDeniedException, BadRequest
+from modoboa.lib.exceptions import (
+ PermDeniedException, BadRequest, Conflict
+)
from .base import AdminObject
from .domain import Domain
from .mailbox import Mailbox
@@ -155,6 +157,12 @@ class Alias(AdminObject):
raise BadRequest(_("Domain '%s' does not exist" % domname))
if not user.can_access(domain):
raise PermDeniedException
+ try:
+ Alias.objects.get(address=localpart, domain__name=domain)
+ except Alias.DoesNotExist:
+ pass
+ else:
+ raise Conflict
self.address = localpart
self.domain = domain
self.enabled = (row[2].strip() == 'True')
diff --git a/modoboa/extensions/admin/models/domain.py b/modoboa/extensions/admin/models/domain.py
index 7c19710dd..c0a13d459 100644
--- a/modoboa/extensions/admin/models/domain.py
+++ b/modoboa/extensions/admin/models/domain.py
@@ -4,7 +4,7 @@ from django.db.models.manager import Manager
from django.utils.translation import ugettext as _, ugettext_lazy
from django.contrib.contenttypes import generic
from modoboa.lib import events, parameters
-from modoboa.lib.exceptions import BadRequest
+from modoboa.lib.exceptions import BadRequest, Conflict
from modoboa.core.models import User, ObjectAccess
from .base import AdminObject
@@ -131,9 +131,24 @@ class Domain(AdminObject):
return self.name
def from_csv(self, user, row):
+ """Create a new domain from a CSV entry.
+
+ The expected fields order is the following::
+
+ "domain", name, quota, enabled
+
+ :param ``core.User`` user: user creating the domain
+ :param str row: a list containing domain's definition
+ """
if len(row) < 4:
raise BadRequest(_("Invalid line"))
self.name = row[1].strip()
+ try:
+ Domain.objects.get(name=self.name)
+ except Domain.DoesNotExist:
+ pass
+ else:
+ raise Conflict
try:
self.quota = int(row[2].strip())
except ValueError:
diff --git a/modoboa/extensions/admin/models/domain_alias.py b/modoboa/extensions/admin/models/domain_alias.py
index a24549b96..29fe93037 100644
--- a/modoboa/extensions/admin/models/domain_alias.py
+++ b/modoboa/extensions/admin/models/domain_alias.py
@@ -38,12 +38,13 @@ class DomainAlias(AdminObject):
if len(row) < 4:
raise BadRequest(_("Invalid line"))
self.name = row[1].strip()
- try:
- Domain.objects.get(name=self.name)
- except Domain.DoesNotExist:
- pass
- else:
- raise Conflict(_("A domain %s already exists" % self.name))
+ for model in [DomainAlias, Domain]:
+ try:
+ model.objects.get(name=self.name)
+ except model.DoesNotExist:
+ pass
+ else:
+ raise Conflict
domname = row[2].strip()
try:
self.target = Domain.objects.get(name=domname)
diff --git a/modoboa/extensions/admin/tests/account.py b/modoboa/extensions/admin/tests/account.py
index 8a79674bf..5ad4d556f 100644
--- a/modoboa/extensions/admin/tests/account.py
+++ b/modoboa/extensions/admin/tests/account.py
@@ -187,11 +187,6 @@ class PermissionsTestCase(ModoTestCase):
account = User.objects.get(username="superadmin2@test.com")
self.clt.logout()
self.clt.login(username="admin@test.com", password="toto")
- self.ajax_get(
- reverse("modoboa.extensions.admin.views.identity.delaccount",
- args=[account.id]),
- {}, 403
- )
self.ajax_post(
reverse("modoboa.extensions.admin.views.identity.delaccount",
args=[account.id]), {}, 403
diff --git a/modoboa/extensions/admin/tests/export.py b/modoboa/extensions/admin/tests/export.py
index c0e727e04..37b49c005 100644
--- a/modoboa/extensions/admin/tests/export.py
+++ b/modoboa/extensions/admin/tests/export.py
@@ -20,17 +20,27 @@ class ExportTestCase(ModoTestCase):
{"filename": "test.csv"}
)
+ def assertListEqual(self, list1, list2):
+ list2 = list2.split('\r\n')
+ for entry in list1.split('\r\n'):
+ if not entry:
+ continue
+ self.assertIn(entry, list2)
+
def test_export_identities(self):
response = self.__export_identities()
- self.assertEqual(response.content, "account;admin;{CRYPT}dTTsGDkA5ZHKg;;;True;SuperAdmins;;\r\naccount;admin@test.com;{PLAIN}toto;;;True;DomainAdmins;admin@test.com;10;test.com\r\naccount;admin@test2.com;{PLAIN}toto;;;True;DomainAdmins;admin@test2.com;10;test2.com\r\naccount;user@test.com;{PLAIN}toto;;;True;SimpleUsers;user@test.com;10\r\naccount;user@test2.com;{PLAIN}toto;;;True;SimpleUsers;user@test2.com;10\r\nalias;alias@test.com;True;user@test.com\r\nforward;forward@test.com;True;user@external.com\r\ndlist;postmaster@test.com;True;toto@titi.com;test@truc.fr\r\n")
+ self.assertListEqual(
+ "account;admin;{CRYPT}dTTsGDkA5ZHKg;;;True;SuperAdmins;;\r\naccount;admin@test.com;{PLAIN}toto;;;True;DomainAdmins;admin@test.com;10;test.com\r\naccount;admin@test2.com;{PLAIN}toto;;;True;DomainAdmins;admin@test2.com;10;test2.com\r\naccount;user@test.com;{PLAIN}toto;;;True;SimpleUsers;user@test.com;10\r\naccount;user@test2.com;{PLAIN}toto;;;True;SimpleUsers;user@test2.com;10\r\nalias;alias@test.com;True;user@test.com\r\nforward;forward@test.com;True;user@external.com\r\ndlist;postmaster@test.com;True;toto@titi.com;test@truc.fr\r\n",
+ response.content.strip()
+ )
def test_export_simpleusers(self):
response = self.__export_identities(
idtfilter="account", grpfilter="SimpleUsers"
)
- self.assertEqual(
- response.content.strip(),
- "account;user@test.com;{PLAIN}toto;;;True;SimpleUsers;user@test.com;10\r\naccount;user@test2.com;{PLAIN}toto;;;True;SimpleUsers;user@test2.com;10"
+ self.assertListEqual(
+ "account;user@test.com;{PLAIN}toto;;;True;SimpleUsers;user@test.com;10\r\naccount;user@test2.com;{PLAIN}toto;;;True;SimpleUsers;user@test2.com;10",
+ response.content.strip()
)
def test_export_superadmins(self):
@@ -46,9 +56,9 @@ class ExportTestCase(ModoTestCase):
response = self.__export_identities(
idtfilter="account", grpfilter="DomainAdmins"
)
- self.assertEqual(
- response.content.strip(),
- "account;admin@test.com;{PLAIN}toto;;;True;DomainAdmins;admin@test.com;10;test.com\r\naccount;admin@test2.com;{PLAIN}toto;;;True;DomainAdmins;admin@test2.com;10;test2.com"
+ self.assertListEqual(
+ "account;admin@test.com;{PLAIN}toto;;;True;DomainAdmins;admin@test.com;10;test.com\r\naccount;admin@test2.com;{PLAIN}toto;;;True;DomainAdmins;admin@test2.com;10;test2.com",
+ response.content.strip()
)
def test_export_aliases(self):
diff --git a/modoboa/extensions/admin/tests/import_.py b/modoboa/extensions/admin/tests/import_.py
index aeeba148e..8f02fed99 100644
--- a/modoboa/extensions/admin/tests/import_.py
+++ b/modoboa/extensions/admin/tests/import_.py
@@ -49,7 +49,7 @@ domainalias;test.alias;test.com;True
"sourcefile": f
}
)
- self.assertIn('A domain test.alias already exists', resp.content)
+ self.assertIn('Object already exists: domainalias', resp.content)
def test_identities_import(self):
f = ContentFile(b"""
diff --git a/modoboa/extensions/admin/views/import.py b/modoboa/extensions/admin/views/import.py
index 5ea28efa4..be306e048 100644
--- a/modoboa/extensions/admin/views/import.py
+++ b/modoboa/extensions/admin/views/import.py
@@ -122,7 +122,7 @@ def importdata(request, formclass=ImportDataForm):
fct = fct[0]
try:
fct(request.user, row, form.cleaned_data)
- except IntegrityError, e:
+ except Conflict:
if form.cleaned_data["continue_if_exists"]:
continue
raise Conflict(
diff --git a/modoboa/lib/permissions.py b/modoboa/lib/permissions.py
index 5cf677aaf..8834a5cfe 100644
--- a/modoboa/lib/permissions.py
+++ b/modoboa/lib/permissions.py
@@ -56,21 +56,18 @@ def grant_access_to_object(user, obj, is_owner=False):
else:
return
- try:
- ObjectAccess.objects.create(user=user, content_type=ct,
- object_id=obj.id, is_owner=is_owner)
- if is_owner:
- from modoboa.core.models import User
- for su in User.objects.filter(is_superuser=True):
- if su == user:
- continue
- try:
- ObjectAccess.objects.create(user=su, content_type=ct, object_id=obj.id)
- except IntegrityError:
- pass
-
- except IntegrityError, e:
- raise ModoboaException(_("Failed to grant access (%s)" % str(e)))
+ ObjectAccess.objects.create(
+ user=user, content_type=ct, object_id=obj.id, is_owner=is_owner
+ )
+ if not is_owner:
+ return
+ from modoboa.core.models import User
+ for su in User.objects.filter(is_superuser=True):
+ if su == user:
+ continue
+ ObjectAccess.objects.get_or_create(
+ user=su, content_type=ct, object_id=obj.id
+ )
def grant_access_to_objects(user, objects, ct):
From 9ae80d74dabb6e85212f44aea099e0057f6f502f Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Tue, 31 Dec 2013 17:41:30 +0100
Subject: [PATCH 07/32] Fixing typo.
---
modoboa/core/commands/postfix_maps.py | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/modoboa/core/commands/postfix_maps.py b/modoboa/core/commands/postfix_maps.py
index e7e39476d..37336ebf1 100644
--- a/modoboa/core/commands/postfix_maps.py
+++ b/modoboa/core/commands/postfix_maps.py
@@ -172,7 +172,7 @@ class RelayDomainAliasesTransportMap(MapFile):
sqlite = "SELECT srv.name || ':[' || rdom.target_host || ']' FROM postfix_relay_domains_service AS srv INNER JOIN postfix_relay_domains_relaydomain AS rdom ON rdom.service_id=srv.id INNER JOIN postfix_relay_domains_relaydomainalias AS rdomalias ON rdom.id=rdomalias.target_id WHERE rdom.enabled=1 AND rdomalias.enabled=1 AND rdomalias.name='%s'"
-class RelayRecipientVerification(Mapfile):
+class RelayRecipientVerification(MapFile):
category = "relaydomains"
filename = "sql-relay-recipient-verification.cf"
mysql = "SELECT 'reject_unverified_recipient' FROM postfix_relay_domains_relaydomain WHERE verify_recipients=1 AND name='%d'"
From 24b7bcaf5655483a2dd66f1143bb2d7a78ea9019 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Tue, 31 Dec 2013 17:50:18 +0100
Subject: [PATCH 08/32] Fixing validation issues.
see #414
---
modoboa/extensions/postfix_autoreply/__init__.py | 2 ++
modoboa/extensions/postfix_autoreply/forms.py | 12 ++++++++----
2 files changed, 10 insertions(+), 4 deletions(-)
diff --git a/modoboa/extensions/postfix_autoreply/__init__.py b/modoboa/extensions/postfix_autoreply/__init__.py
index c28dd67e0..fce457e71 100644
--- a/modoboa/extensions/postfix_autoreply/__init__.py
+++ b/modoboa/extensions/postfix_autoreply/__init__.py
@@ -27,6 +27,8 @@ class PostfixAutoreply(ModoExtension):
def init(self):
from modoboa.extensions.admin.models import Domain
+ from modoboa.extensions.postfix_autoreply.general_callbacks \
+ import onDomainCreated, onMailboxCreated
for dom in Domain.objects.all():
try:
diff --git a/modoboa/extensions/postfix_autoreply/forms.py b/modoboa/extensions/postfix_autoreply/forms.py
index 211186eb1..cf9cd5ad4 100644
--- a/modoboa/extensions/postfix_autoreply/forms.py
+++ b/modoboa/extensions/postfix_autoreply/forms.py
@@ -30,9 +30,12 @@ class ARmessageForm(forms.ModelForm):
def __init__(self, *args, **kwargs):
super(ARmessageForm, self).__init__(*args, **kwargs)
- self.fields.keyOrder = ['subject', 'content', 'fromdate', 'untildate', 'enabled']
+ self.fields.keyOrder = [
+ 'subject', 'content', 'fromdate', 'untildate', 'enabled'
+ ]
if 'instance' in kwargs and kwargs['instance'] is not None:
- self.fields['fromdate'].initial = kwargs['instance'].fromdate
+ self.fields['fromdate'].initial = \
+ kwargs['instance'].fromdate.replace(second=0, microsecond=0)
self.fields['untildate'].initial = kwargs['instance'].untildate
def clean(self):
@@ -46,7 +49,7 @@ class ARmessageForm(forms.ModelForm):
raise forms.ValidationError(self._errors)
if self.cleaned_data["fromdate"] is not None:
if self.cleaned_data["fromdate"] < timezone.now():
- self._errrors["fromdate"] = self.error_class([_("This date is over")])
+ self._errors["fromdate"] = self.error_class([_("This date is over")])
del self.cleaned_data['fromdate']
else:
self.cleaned_data['fromdate'] = timezone.now()
@@ -54,7 +57,8 @@ class ARmessageForm(forms.ModelForm):
if self.cleaned_data["untildate"] < timezone.now():
self._errors["untildate"] = self.error_class([_("This date is over")])
del self.cleaned_data['untildate']
- elif self.cleaned_data['untildate'] < self.cleaned_data['fromdate']:
+ elif 'fromdate' in self.cleaned_data and \
+ self.cleaned_data['untildate'] < self.cleaned_data['fromdate']:
self._errors["untildate"] = \
self.error_class([_("Must be greater than start date")])
del self.cleaned_data['untildate']
From 1f4e9ea5ee3225bcd22adefb7e1d64582f4aca8d Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Tue, 31 Dec 2013 18:11:32 +0100
Subject: [PATCH 09/32] Updating LDAP documentation.
---
doc/getting_started/configuration.rst | 23 ++++++++++++++++++-----
1 file changed, 18 insertions(+), 5 deletions(-)
diff --git a/doc/getting_started/configuration.rst b/doc/getting_started/configuration.rst
index efcf39658..c56271a05 100644
--- a/doc/getting_started/configuration.rst
+++ b/doc/getting_started/configuration.rst
@@ -242,6 +242,17 @@ Modoboa should connect to your LDAP server. They are described just below:
| |server is an Active | |
| |Directory one | |
+--------------------+---------------------------------+--------------------+
+|Administrator groups|Members of those LDAP Posix | |
+| |groups will be created ad domain | |
+| |administrators. Use ';' | |
+| |characters to separate groups. | |
++--------------------+---------------------------------+--------------------+
+|Groups search base |The distinguished name of the | |
+| |search base used to find groups | |
+| | | |
+| | | |
++--------------------+---------------------------------+--------------------+
+
If you need additional parameters, you will find a detailled
documentation `here `_.
@@ -250,12 +261,14 @@ Once the authentication is properly configured, the users defined in
your LDAP directory will be able to connect to Modoboa, the associated
domain and mailboxes will be automatically created if needed.
-.. note::
+The first time a user connects to Modoboa, a local account is created
+if the LDAP username is a valid email address. By default, this
+account belongs to the *SimpleUsers* group and it has a mailbox.
- Users created automatically from an LDAP directory belongs to the
- *SimpleUsers* group and have a mailbox. To do so, usernames have to
- be valid email addresses. If not, LDAP users won't be able to
- access Modoboa.
+To automatically create domain administrators, you can use the
+**Administrator groups** setting. If a LDAP user belongs to one the
+listed groups, its local account will belong to the *DomainAdmins*
+group. In this case, the username is not necessarily an email address.
Users will also be able to update their LDAP password directly from
Modoboa.
From 6b4cdba69f354222e01f102b5062e34f4454fde8 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 2 Jan 2014 15:23:56 +0100
Subject: [PATCH 10/32] Portguese translation update.
---
modoboa/locale/pt_PT/LC_MESSAGES/django.po | 414 ++++++-------------
modoboa/locale/pt_PT/LC_MESSAGES/djangojs.po | 39 +-
2 files changed, 125 insertions(+), 328 deletions(-)
diff --git a/modoboa/locale/pt_PT/LC_MESSAGES/django.po b/modoboa/locale/pt_PT/LC_MESSAGES/django.po
index 278483fb7..3a55652fe 100644
--- a/modoboa/locale/pt_PT/LC_MESSAGES/django.po
+++ b/modoboa/locale/pt_PT/LC_MESSAGES/django.po
@@ -1,9 +1,10 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
-#
+#
# Translators:
# ddu17 , 2013
+# lusitan , 2013
# mikec , 2012
# mikec , 2013
# Sandra Ribeiro , 2012-2013
@@ -13,14 +14,13 @@ msgstr ""
"Project-Id-Version: Modoboa\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2013-12-15 10:21+0100\n"
-"PO-Revision-Date: 2013-10-04 21:10+0000\n"
-"Last-Translator: ddu17 \n"
-"Language-Team: Portuguese (Portugal) (http://www.transifex.com/projects/p/"
-"modoboa/language/pt_PT/)\n"
-"Language: pt_PT\n"
+"PO-Revision-Date: 2013-12-23 11:25+0000\n"
+"Last-Translator: lusitan \n"
+"Language-Team: Portuguese (Portugal) (http://www.transifex.com/projects/p/modoboa/language/pt_PT/)\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
+"Language: pt_PT\n"
"Plural-Forms: nplurals=2; plural=(n != 1);\n"
#: core/__init__.py:52 core/__init__.py:53
@@ -55,23 +55,23 @@ msgstr "Esquema pré-definido para passwords"
#: core/app_settings.py:51
msgid "md5crypt (weak)"
-msgstr ""
+msgstr "md5crypt (fraco)"
#: core/app_settings.py:52
msgid "sha256 (weak)"
-msgstr ""
+msgstr "sha256 (fraco)"
#: core/app_settings.py:53
msgid "md5 (weak)"
-msgstr ""
+msgstr "md5 (fraco)"
#: core/app_settings.py:54
msgid "crypt (weak)"
-msgstr ""
+msgstr "crypt (fraco)"
#: core/app_settings.py:55
msgid "plain (weak)"
-msgstr ""
+msgstr "plain (fraco)"
#: core/app_settings.py:57
msgid "Scheme used to crypt mailbox passwords"
@@ -149,9 +149,7 @@ msgstr "\"Bind DN\""
msgid ""
"The distinguished name to use when binding to the LDAP server. Leave empty "
"for an anonymous bind"
-msgstr ""
-"O nome único usado para fazer o \"bind\" ao servidor LDAP. Deixar vario "
-"para \"bind\" anónimo"
+msgstr "O nome único usado para fazer o \"bind\" ao servidor LDAP. Deixar vario para \"bind\" anónimo"
#: core/app_settings.py:113
msgid "Bind password"
@@ -159,18 +157,15 @@ msgstr "Password para bind"
#: core/app_settings.py:115
msgid "The password to use when binding to the LDAP server (with 'Bind DN')"
-msgstr ""
-"A password usada para fazer o \"bind\" ao servidor LDAP (com 'Bind DN')"
+msgstr "A password usada para fazer o \"bind\" ao servidor LDAP (com 'Bind DN')"
#: core/app_settings.py:121
-#, fuzzy
msgid "Users search base"
-msgstr "Base de pesquisa"
+msgstr ""
#: core/app_settings.py:123
-#, fuzzy
msgid "The distinguished name of the search base used to find users"
-msgstr "O nome único para a pesquisa base"
+msgstr ""
#: core/app_settings.py:128
msgid "Search filter"
@@ -180,9 +175,7 @@ msgstr "Filtro de pesquisa"
msgid ""
"An optional filter string (e.g. '(objectClass=person)'). In order to be "
"valid, it must be enclosed in parentheses."
-msgstr ""
-"Um filtro opcional (ex: '(objetClass=person)'). Tem de estar entre "
-"parênteses para ser válido"
+msgstr "Um filtro opcional (ex: '(objetClass=person)'). Tem de estar entre parênteses para ser válido"
#: core/app_settings.py:135
msgid "User DN template"
@@ -193,9 +186,7 @@ msgstr "Template DN de utilizador"
msgid ""
"The template used to construct a user's DN. It should contain one "
"placeholder (ie. %(user)s)"
-msgstr ""
-"O template usado para construir o DN (nome único). Deve apenas conter um "
-"'placeholder' (ex: %(user)s) "
+msgstr "O template usado para construir o DN (nome único). Deve apenas conter um 'placeholder' (ex: %(user)s) "
#: core/app_settings.py:142
msgid "Password attribute"
@@ -214,25 +205,22 @@ msgid "Tell if the LDAP server is an Active Directory one"
msgstr "Especificar se o servidor LDAP e um Active Directory"
#: core/app_settings.py:154
-#, fuzzy
msgid "Administrator groups"
-msgstr "Administradores"
+msgstr ""
#: core/app_settings.py:157
msgid ""
-"Members of those LDAP Posix groups will be created as domain administrators. "
-"Use ';' characters to separate groups."
+"Members of those LDAP Posix groups will be created as domain administrators."
+" Use ';' characters to separate groups."
msgstr ""
#: core/app_settings.py:164
-#, fuzzy
msgid "Groups search base"
-msgstr "Base de pesquisa"
+msgstr ""
#: core/app_settings.py:167
-#, fuzzy
msgid "The distinguished name of the search base used to find groups"
-msgstr "O nome único para a pesquisa base"
+msgstr ""
#: core/app_settings.py:172
#: extensions/admin/templates/admin/editdomainform.html:7
@@ -261,9 +249,7 @@ msgstr "Redirecionamento pré-definido"
#: core/app_settings.py:190
msgid "The default redirection used when no application is specified"
-msgstr ""
-"O redirecionamento padrão usado quando nenhuma aplicação se encontra "
-"especificada"
+msgstr "O redirecionamento padrão usado quando nenhuma aplicação se encontra especificada"
#: core/app_settings.py:218
msgid "Key must be either 16, 24, or 32 bytes long"
@@ -274,9 +260,8 @@ msgid "Invalid syntax"
msgstr "Sintax inválida"
#: core/app_settings.py:233
-#, fuzzy
msgid "Invalid rounds number"
-msgstr "Pedido inválido"
+msgstr ""
#: core/app_settings.py:256
msgid "This field is required"
@@ -326,14 +311,12 @@ msgid "Passwords mismatch"
msgstr "Passwords não coincidem"
#: core/models.py:50
-#, fuzzy
msgid "password"
-msgstr "Password"
+msgstr ""
#: core/models.py:52
-#, fuzzy
msgid "last login"
-msgstr "Último login"
+msgstr ""
#: core/models.py:81
msgid "You can't delete your own account"
@@ -366,9 +349,7 @@ msgstr "O simple utilizador '%s' deve ter endereço de e-mail válido"
#: core/models.py:335
#, python-format
msgid "username and email fields must not differ for '%s'"
-msgstr ""
-"Os campos nome de utilizador e endereço de email não deve ser diferente para "
-"'%s'"
+msgstr "Os campos nome de utilizador e endereço de email não deve ser diferente para '%s'"
#: core/models.py:404 extensions/admin/models/alias.py:33
#: extensions/admin/models/domain.py:32
@@ -583,31 +564,15 @@ msgid ""
"\n"
"Welcome to the online demo!
\n"
"Warning: the demo's concent is resetted every two hours.
\n"
-"To try the demo, the following users are available (username/password"
-"i>):
\n"
+"To try the demo, the following users are available (username/password):
\n"
"\n"
" - A super administrator : admin/password
\n"
" - A domain administrator : admin@demo.local/admin
\n"
" - A simple user : user@demo.local/user
\n"
"
\n"
"Please report any issue or give any suggestion to \n"
-" the "
-"mailing list.
\n"
-msgstr ""
-"\n"
-"Bem-vindo à demo online!
\n"
-"Aviso: os conteúdos desta demo são limpos a cada duas horas.
\n"
-"Para experimentar a demo, estão disponíveis os seguintes utilizadores "
-"(username/password):
\n"
-"\n"
-" - Super administrador: admin/password
\n"
-" - Administrador de domínio: admin@demo.local/admin
\n"
-" - Utilizador básico: user@demo.local/user
\n"
-"
\n"
-"Para reportar qualquer problema ou apresentar uma sugestão, utilize o "
-"seguinte link \n"
-" mailing "
-"list.
\n"
+" the mailing list.\n"
+msgstr "\nBem-vindo à demo online!
\nAviso: os conteúdos desta demo são limpos a cada duas horas.
\nPara experimentar a demo, estão disponíveis os seguintes utilizadores (username/password):
\n\n - Super administrador: admin/password
\n - Administrador de domínio: admin@demo.local/admin
\n - Utilizador básico: user@demo.local/user
\n
\nPara reportar qualquer problema ou apresentar uma sugestão, utilize o seguinte link \n mailing list.
\n"
#: extensions/admin/__init__.py:48
msgid "Administration console"
@@ -618,9 +583,8 @@ msgid "Web based console to manage domains, accounts and aliases"
msgstr "Consola baseada na web para gestão de domínios, contas e aliases"
#: extensions/admin/__init__.py:55
-#, fuzzy
msgid "Administration"
-msgstr "Administradores"
+msgstr ""
#: extensions/admin/__init__.py:79
#: extensions/admin/templates/admin/domains.html:2
@@ -660,9 +624,7 @@ msgstr "Lidar com caixas de correio no sistema de ficheiros"
msgid ""
"Rename or remove mailboxes on the filesystem when they get renamed or "
"removed within Modoboa"
-msgstr ""
-"Renomear ou remover as caixas de correio no sistema de ficheiros quando "
-"estas são renomeadas no Modoboa"
+msgstr "Renomear ou remover as caixas de correio no sistema de ficheiros quando estas são renomeadas no Modoboa"
#: extensions/admin/app_settings.py:20
msgid "Mailboxes ower"
@@ -673,9 +635,8 @@ msgid "The UNIX account who owns mailboxes on the filesystem"
msgstr "A conta UNIX que detém as caixas de correio no sistema de ficheiros"
#: extensions/admin/app_settings.py:26
-#, fuzzy
msgid "Default domain quota"
-msgstr "Limites predefinidos"
+msgstr ""
#: extensions/admin/app_settings.py:29
msgid ""
@@ -689,8 +650,7 @@ msgstr "Remoção automática de conta"
#: extensions/admin/app_settings.py:38
msgid "When a mailbox is removed, also remove the associated account"
-msgstr ""
-"Ao remover uma caixa de correio estará também a remover a conta associada"
+msgstr "Ao remover uma caixa de correio estará também a remover a conta associada"
#: extensions/admin/app_settings.py:69 extensions/admin/forms/account.py:178
#: extensions/admin/forms/domain.py:56
@@ -698,16 +658,14 @@ msgid "Must be a positive integer"
msgstr ""
#: extensions/admin/lib.py:28
-#, fuzzy
msgid "A mailbox is required"
-msgstr "É necessário uma quota"
+msgstr ""
#: extensions/admin/forms/account.py:21
-#, fuzzy
msgid ""
"The user's name. Must be a valid e-mail address for simple users or "
"administrators with a mailbox."
-msgstr "O simple utilizador '%s' deve ter endereço de e-mail válido"
+msgstr ""
#: extensions/admin/forms/account.py:26
msgid "Role"
@@ -750,10 +708,7 @@ msgid ""
"Quota in MB for this mailbox. Define a custom value or use domain's default "
"one. Leave empty to define an unlimited value (not allowed for domain "
"administrators)."
-msgstr ""
-"Quota em MB para esta caixa de correio. Definir uma valor personalizado ou "
-"usar o valor predefinido pelo domínio. Deixar em branco para definir uma "
-"valor ilimitado (não permitido para administradores do domínio)."
+msgstr "Quota em MB para esta caixa de correio. Definir uma valor personalizado ou usar o valor predefinido pelo domínio. Deixar em branco para definir uma valor ilimitado (não permitido para administradores do domínio)."
#: extensions/admin/forms/account.py:123 extensions/admin/forms/domain.py:26
#: extensions/admin/templates/admin/domains_table.html:6
@@ -766,10 +721,7 @@ msgid ""
"Alias(es) of this mailbox. Indicate only one address per input, press ENTER "
"to add a new input. Use the '*' character to create a 'catchall' alias (ex: "
"*@domain.tld)."
-msgstr ""
-"Alias(es) desta caixa de correio. Indique apenas um endereço por entrada, "
-"clique ENTER para adicionar uma nova entrada. Use o '*' para criar um alias "
-"'catchall' (ex: *@domain.tld)."
+msgstr "Alias(es) desta caixa de correio. Indique apenas um endereço por entrada, clique ENTER para adicionar uma nova entrada. Use o '*' para criar um alias 'catchall' (ex: *@domain.tld)."
#: extensions/admin/forms/account.py:187 extensions/admin/forms/account.py:217
#: extensions/admin/forms/alias.py:65
@@ -806,9 +758,7 @@ msgstr "Endereço de e-mail"
msgid ""
"The distribution list address. Use the '*' character to create a 'catchall' "
"address (ex: *@domain.tld)."
-msgstr ""
-"Os endereços da lista de distribuição. Use o '*' para criar um endereço "
-"'catchall' (Ex: *@domain.tld)."
+msgstr "Os endereços da lista de distribuição. Use o '*' para criar um endereço 'catchall' (Ex: *@domain.tld)."
#: extensions/admin/forms/alias.py:23
msgid "Recipients"
@@ -818,9 +768,7 @@ msgstr "Destinatários"
msgid ""
"Mailbox(es) this alias will point to. Indicate only one address per input, "
"press ENTER to add a new input."
-msgstr ""
-"Caixa(s) de correio para o qual este 'alias' aponta. Indicar apenas um "
-"endereço por entrada, pressionar ENTER para acrescentar uma nova entrada."
+msgstr "Caixa(s) de correio para o qual este 'alias' aponta. Indicar apenas um endereço por entrada, pressionar ENTER para acrescentar uma nova entrada."
#: extensions/admin/forms/alias.py:68
msgid "You don't have access to this domain"
@@ -845,40 +793,35 @@ msgid "No recipient defined"
msgstr "Sem destinatário definido"
#: extensions/admin/forms/domain.py:20
-#, fuzzy
msgid ""
"Default quota in MB applied to mailboxes. Leave empty to use the default "
"value."
-msgstr "Quota em MB aplicada por defeito às caixas de correio"
+msgstr ""
#: extensions/admin/forms/domain.py:29
msgid ""
"Alias(es) of this domain. Indicate only one name per input, press ENTER to "
"add a new input."
-msgstr ""
-"Alias(es) deste domínio. Indicar apenas um nome por entrada, pressionar "
-"ENTER para acrescentar uma nova entrada."
+msgstr "Alias(es) deste domínio. Indicar apenas um nome por entrada, pressionar ENTER para acrescentar uma nova entrada."
#: extensions/admin/forms/domain.py:75
#: extensions/postfix_relay_domains/forms.py:50
#: extensions/postfix_relay_domains/forms.py:70
-#, fuzzy
msgid "domain alias"
-msgstr "Aliases de domínio"
+msgstr ""
#: extensions/admin/forms/domain.py:82 extensions/admin/forms/domain.py:98
#: extensions/postfix_relay_domains/forms.py:58
#: extensions/postfix_relay_domains/forms.py:78
-#, fuzzy, python-format
+#, python-format
msgid "A %s with this name already exists"
-msgstr "Já existe um 'alias' com este nome"
+msgstr ""
#: extensions/admin/forms/domain.py:92
#: extensions/postfix_relay_domains/forms.py:49
#: extensions/postfix_relay_domains/forms.py:71
-#, fuzzy
msgid "domain"
-msgstr "Domínios"
+msgstr ""
#: extensions/admin/forms/domain.py:176
msgid "Create a domain administrator"
@@ -892,9 +835,7 @@ msgstr "Criar automaticamente um administrador para este domínio"
msgid ""
"The administrator's name. Don't include the domain's name here, it will be "
"automatically appended."
-msgstr ""
-"O nome do administrador. Não inclua o nome do domínio já que este será "
-"automaticamente anexado."
+msgstr "O nome do administrador. Não inclua o nome do domínio já que este será automaticamente anexado."
#: extensions/admin/forms/domain.py:193
msgid "Create aliases"
@@ -935,16 +876,13 @@ msgstr "Conservar cópias locais"
#: extensions/admin/forms/forward.py:20
msgid "Forward messages and store copies into your local mailbox"
-msgstr ""
-"Reencaminhar mensagens e armazenar cópias na sua caixa de correio local"
+msgstr "Reencaminhar mensagens e armazenar cópias na sua caixa de correio local"
#: extensions/admin/forms/forward.py:38
msgid ""
"You can't define a forward to a local destination. Please ask your "
"administrator to create an alias instead."
-msgstr ""
-"Não é possível definir um reencaminhamento para um destino local. Por favor "
-"informe-se junto de um administrador para criar um alias."
+msgstr "Não é possível definir um reencaminhamento para um destino local. Por favor informe-se junto de um administrador para criar um alias."
#: extensions/admin/forms/import_.py:6 extensions/webmail/forms.py:26
msgid "Select a file"
@@ -972,11 +910,9 @@ msgstr "endereços"
#: extensions/admin/models/alias.py:18
msgid ""
-"The alias address (without the domain part). For a 'catch-all' address, just "
-"enter an * character."
-msgstr ""
-"O endereço do alias (sem a parte do domínio). Para um endereço 'cath-all', "
-"digite apenas o caractere *"
+"The alias address (without the domain part). For a 'catch-all' address, just"
+" enter an * character."
+msgstr "O endereço do alias (sem a parte do domínio). Para um endereço 'cath-all', digite apenas o caractere *"
#: extensions/admin/models/alias.py:24
msgid "mailboxes"
@@ -1037,9 +973,8 @@ msgid "Check to activate this domain"
msgstr "Marcar para ativar este domínio"
#: extensions/admin/models/domain.py:61
-#, fuzzy
msgid "Domain"
-msgstr "Domínios"
+msgstr ""
#: extensions/admin/models/domain.py:140
#, python-format
@@ -1061,9 +996,9 @@ msgid "The domain this alias points to"
msgstr "O domínio para o qual este alias irá apontar"
#: extensions/admin/models/domain_alias.py:46
-#, fuzzy, python-format
+#, python-format
msgid "A domain %s already exists"
-msgstr "Caixa de correio %s já existe"
+msgstr ""
#: extensions/admin/models/domain_alias.py:51
#, python-format
@@ -1095,9 +1030,8 @@ msgid "MB"
msgstr "MB"
#: extensions/admin/templates/admin/domain_options_form.html:5
-#, fuzzy
msgid "You can't create a new domain administrator"
-msgstr "Criar um administrador de domínio"
+msgstr ""
#: extensions/admin/templates/admin/domains_table.html:7
#: extensions/admin/templates/admin/identities_table.html:7
@@ -1379,7 +1313,7 @@ msgstr[0] "Conta eliminada"
msgstr[1] "Contas eliminadas"
#: extensions/admin/views/import.py:39
-#, fuzzy, python-format
+#, python-format
msgid ""
"Provide a CSV file where lines respect one of the following formats:\n"
"\n"
@@ -1387,15 +1321,9 @@ msgid ""
" - domainalias; name; targeted domain; enabled
\n"
" %s\n"
"
\n"
-"The first element of each line is mandatory and must be equal to one of "
-"the previous values.
\n"
+"The first element of each line is mandatory and must be equal to one of the previous values.
\n"
"You can use a different character as separator.
\n"
msgstr ""
-"Forneça um ficheiro CSV cujas linhas respeitem um dos seguintes formatos:⏎ "
-"⏎ - domain; name; quota; enabled
⏎ - domainalias; "
-"name; targeted domain; enabled
⏎
⏎ O primeiro elemento de "
-"cada linha é obrigatório e deve ser igual a um dos valores anteriores.
⏎ "
-"Pode utilizar um caractere diferente como separador.
⏎\n"
#: extensions/admin/views/import.py:50
msgid "Import domains"
@@ -1412,33 +1340,18 @@ msgid "%d objects imported successfully"
msgstr "%d objetos importados com sucesso"
#: extensions/admin/views/import.py:153
-#, fuzzy
msgid ""
"Provide a CSV file where lines respect one of the following formats:\n"
"\n"
-"- account; loginname; password; first name; last name; enabled; group; "
-"address; quota; [, domain, ...]
\n"
+"- account; loginname; password; first name; last name; enabled; group; address; quota; [, domain, ...]
\n"
"- alias; address; enabled; internal recipient
\n"
"- forward; address; enabled; external recipient
\n"
"- dlist; address; enabled; recipient; recipient; ...
\n"
"
\n"
-"The first element of each line is mandatory and must be equal to one of "
-"the previous values.
\n"
+"The first element of each line is mandatory and must be equal to one of the previous values.
\n"
"\n"
"You can use a different character as separator.
\n"
msgstr ""
-"Forneça um ficheiro CSV cujas linhas respeitem um dos seguintes formatos:⏎\n"
-"⏎\n"
-"- account; loginname; password; first name; last name; enabled; group; "
-"address[, domain, ...]
⏎\n"
-"- alias; address; enabled; internal recipient
⏎\n"
-"- forward; address; enabled; external recipient
⏎\n"
-"- dlist; address; enabled; recipient; recipient; ...
⏎\n"
-"
⏎\n"
-"O primeiro elemento de cada linha é obrigatório e deve ser igual a um dos "
-"valores anteriores..
⏎\n"
-"⏎\n"
-"Pode utilizar um caractere diferente como separador.
⏎\n"
#: extensions/admin/views/import.py:165
msgid "Import identities"
@@ -1466,9 +1379,7 @@ msgstr "Idade maxima da messagem"
#: extensions/amavis/app_settings.py:16
msgid "Quarantine messages maximum age (in days) before deletion"
-msgstr ""
-"Tempo máximo que as mensagens ficam na quarentena (em dias) até serem "
-"eliminadas"
+msgstr "Tempo máximo que as mensagens ficam na quarentena (em dias) até serem eliminadas"
#: extensions/amavis/app_settings.py:19
msgid "Messages releasing"
@@ -1480,9 +1391,7 @@ msgstr "Remover mensagens libertadas"
#: extensions/amavis/app_settings.py:24
msgid "Remove messages marked as released while cleaning up the database"
-msgstr ""
-"Remova as mensagens, marcadas como enviadas, durante a limpeza da base de "
-"dados"
+msgstr "Remova as mensagens, marcadas como enviadas, durante a limpeza da base de dados"
#: extensions/amavis/app_settings.py:28
msgid "Amavis connection mode"
@@ -1561,9 +1470,8 @@ msgid "pending requests"
msgstr "pedidos pendentes"
#: extensions/amavis/general_callbacks.py:124
-#, fuzzy
msgid "Pending requests"
-msgstr "pedidos pendentes"
+msgstr ""
#: extensions/amavis/general_callbacks.py:134
msgid "Content filter"
@@ -1596,9 +1504,7 @@ msgstr "predifinido"
#: extensions/amavis/models.py:98
msgid "Bypass virus checks or not. Choose 'default' to use global settings."
-msgstr ""
-"Ignorar a verificação de vírus ou não. Escolher 'predefinido' para utilizar "
-"as definições gerais."
+msgstr "Ignorar a verificação de vírus ou não. Escolher 'predefinido' para utilizar as definições gerais."
#: extensions/amavis/models.py:101
msgid "Spam filter"
@@ -1606,9 +1512,7 @@ msgstr "Filtro de spam"
#: extensions/amavis/models.py:106
msgid "Bypass spam checks or not. Choose 'default' to use global settings."
-msgstr ""
-"Ignorar filtros de spam ou não. Escolher 'predefinido' para utilizar as "
-"definições gerais."
+msgstr "Ignorar filtros de spam ou não. Escolher 'predefinido' para utilizar as definições gerais."
#: extensions/amavis/models.py:109
msgid "Banned filter"
@@ -1616,9 +1520,7 @@ msgstr "Ficheiros proibidos"
#: extensions/amavis/models.py:114
msgid "Bypass banned checks or not. Choose 'default' to use global settings."
-msgstr ""
-"Ignorar a verificação de ficheiros proibidos. Escolher 'predefinido' para "
-"utilizar as definições gerais."
+msgstr "Ignorar a verificação de ficheiros proibidos. Escolher 'predefinido' para utilizar as definições gerais."
#: extensions/amavis/models.py:144
msgid "Spam marker"
@@ -1626,11 +1528,9 @@ msgstr "Marcador spam"
#: extensions/amavis/models.py:146
msgid ""
-"Modify spam subject using the specified text. Choose 'default' to use global "
-"settings."
-msgstr ""
-"Modifique o assunto de spam usando o texto especificado. Escolha 'default' "
-"para usar as configurações globais."
+"Modify spam subject using the specified text. Choose 'default' to use global"
+" settings."
+msgstr "Modifique o assunto de spam usando o texto especificado. Escolha 'default' para usar as configurações globais."
#: extensions/amavis/sql_listing.py:31
msgid "Score"
@@ -1711,9 +1611,8 @@ msgid "Quarantine management"
msgstr "Gestão de Quarentena"
#: extensions/amavis/templates/amavis/main_action_bar.html:3
-#, fuzzy
msgid "Select"
-msgstr "Escolha um ficheiro"
+msgstr ""
#: extensions/amavis/templates/amavis/main_action_bar.html:9
msgid "Spam"
@@ -1724,18 +1623,16 @@ msgid "Virus"
msgstr "Vírus"
#: extensions/amavis/templates/amavis/main_action_bar.html:11
-#, fuzzy
msgid "Bad Header"
-msgstr "Cabeçalho inválido"
+msgstr ""
#: extensions/amavis/templates/amavis/main_action_bar.html:12
msgid "Bad MIME"
msgstr "Formato MIME inválido"
#: extensions/amavis/templates/amavis/main_action_bar.html:13
-#, fuzzy
msgid "Banned"
-msgstr "Ficheiros proibidos"
+msgstr ""
#: extensions/amavis/templates/amavis/main_action_bar.html:18
#: extensions/amavis/templatetags/amavis_tags.py:19
@@ -1760,29 +1657,24 @@ msgid "All"
msgstr ""
#: extensions/amavis/templates/amavis/main_action_bar.html:32
-#, fuzzy
msgid "Spam only"
-msgstr "Spam"
+msgstr ""
#: extensions/amavis/templates/amavis/main_action_bar.html:33
-#, fuzzy
msgid "Virus only"
-msgstr "Vírus"
+msgstr ""
#: extensions/amavis/templates/amavis/main_action_bar.html:34
-#, fuzzy
msgid "Bad Header only"
-msgstr "Cabeçalho inválido"
+msgstr ""
#: extensions/amavis/templates/amavis/main_action_bar.html:35
-#, fuzzy
msgid "Bad MIME only"
-msgstr "Formato MIME inválido"
+msgstr ""
#: extensions/amavis/templates/amavis/main_action_bar.html:36
-#, fuzzy
msgid "Banned only"
-msgstr "Ficheiros proibidos"
+msgstr ""
#: extensions/amavis/templates/amavis/notifications/pending_requests.html:1
#, python-format
@@ -1792,12 +1684,8 @@ msgid ""
msgid_plural ""
"\n"
"%(counter)s release requests are pending for action.\n"
-msgstr[0] ""
-"\n"
-"%(counter)s pedido de libertação pendente\n"
-msgstr[1] ""
-"\n"
-"%(counter)s pedidos de libertação pendentes\n"
+msgstr[0] "\n%(counter)s pedido de libertação pendente\n"
+msgstr[1] "\n%(counter)s pedidos de libertação pendentes\n"
#: extensions/amavis/templates/amavis/notifications/pending_requests.html:6
msgid "Sketch:"
@@ -1850,10 +1738,9 @@ msgid "Domain admins"
msgstr "Administradores de domínio"
#: extensions/limits/app_settings.py:15
-msgid "Maximum number of allowed domain administrators for a new administrator"
-msgstr ""
-"Número máximo permitido de administradores de domínio para um novo "
-"administrador"
+msgid ""
+"Maximum number of allowed domain administrators for a new administrator"
+msgstr "Número máximo permitido de administradores de domínio para um novo administrador"
#: extensions/limits/app_settings.py:21
msgid "Maximum number of allowed domains for a new administrator"
@@ -1861,8 +1748,7 @@ msgstr "Número máximo permitido de domínios para novo administrador"
#: extensions/limits/app_settings.py:27
msgid "Maximum number of allowed domain aliases for a new administrator"
-msgstr ""
-"Número máximo permitido de aliases de domínio para um novo administrador"
+msgstr "Número máximo permitido de aliases de domínio para um novo administrador"
#: extensions/limits/app_settings.py:33
msgid "Maximum number of allowed mailboxes for a new administrator"
@@ -1903,8 +1789,7 @@ msgstr "Recursos insuficientes"
#: extensions/limits/models.py:15
msgid "Maximum number of domain administrators this user can create"
-msgstr ""
-"Número máximo de administradores de domínio que este utilizador pode criar"
+msgstr "Número máximo de administradores de domínio que este utilizador pode criar"
#: extensions/limits/models.py:18
msgid "Maximum number of domains this user can create"
@@ -1920,8 +1805,7 @@ msgstr "Número máximo de caixas de correio que este utilizador por criar"
#: extensions/limits/models.py:26
msgid "Maximum number of mailbox aliases this user can create"
-msgstr ""
-"Número máximo de aliases para caixas de correio que este utilizador por criar"
+msgstr "Número máximo de aliases para caixas de correio que este utilizador por criar"
#: extensions/limits/models.py:136
msgid "undefined"
@@ -1949,14 +1833,11 @@ msgstr "Tempo limite de resposta automática"
#: extensions/postfix_autoreply/app_settings.py:16
msgid "Timeout in seconds between two auto-replies to the same recipient"
-msgstr ""
-"Tempo limite em segundos entre duas respostas automáticas para o mesmo "
-"destinatário"
+msgstr "Tempo limite em segundos entre duas respostas automáticas para o mesmo destinatário"
#: extensions/postfix_autoreply/app_settings.py:20
-#, fuzzy
msgid "Default subject"
-msgstr "Editor predefinido"
+msgstr ""
#: extensions/postfix_autoreply/app_settings.py:21
msgid "I'm off"
@@ -1968,9 +1849,8 @@ msgid ""
msgstr ""
#: extensions/postfix_autoreply/app_settings.py:28
-#, fuzzy
msgid "Default content"
-msgstr "Editor predefinido"
+msgstr ""
#: extensions/postfix_autoreply/app_settings.py:30
#, python-format
@@ -1989,9 +1869,8 @@ msgid ""
msgstr ""
#: extensions/postfix_autoreply/forms.py:13
-#, fuzzy
msgid "Activate your auto reply from this date"
-msgstr "Ativar o seu aviso de ausência até esta data"
+msgstr ""
#: extensions/postfix_autoreply/forms.py:19
msgid "Until"
@@ -2007,9 +1886,8 @@ msgid "This date is over"
msgstr "Esta data ultrapassa"
#: extensions/postfix_autoreply/forms.py:59
-#, fuzzy
msgid "Must be greater than start date"
-msgstr "é maior do que"
+msgstr ""
#: extensions/postfix_autoreply/general_callbacks.py:33
#: extensions/postfix_autoreply/templates/postfix_autoreply/autoreply.html:2
@@ -2059,138 +1937,113 @@ msgstr ""
#: extensions/postfix_relay_domains/__init__.py:89
#: extensions/postfix_relay_domains/general_callbacks.py:100
#: extensions/postfix_relay_domains/limits_callbacks.py:16
-#, fuzzy
msgid "Relay domains"
-msgstr "Novo domínio"
+msgstr ""
#: extensions/postfix_relay_domains/app_settings.py:10
msgid "Postfix's master.cf path"
msgstr ""
#: extensions/postfix_relay_domains/app_settings.py:12
-#, fuzzy
msgid "Path to the master.cf configuration file"
-msgstr "Caminho para o ficheiro log"
+msgstr ""
#: extensions/postfix_relay_domains/forms.py:15
-#, fuzzy
msgid ""
"Alias(es) of this relay domain. Indicate only one name per input, press "
"ENTER to add a new input."
msgstr ""
-"Alias(es) deste domínio. Indicar apenas um nome por entrada, pressionar "
-"ENTER para acrescentar uma nova entrada."
#: extensions/postfix_relay_domains/forms.py:51
#: extensions/postfix_relay_domains/general_callbacks.py:93
-#, fuzzy
msgid "relay domain alias"
-msgstr "Aliases de domínio"
+msgstr ""
#: extensions/postfix_relay_domains/forms.py:69
#: extensions/postfix_relay_domains/general_callbacks.py:92
-#, fuzzy
msgid "relay domain"
-msgstr "Novo domínio"
+msgstr ""
#: extensions/postfix_relay_domains/general_callbacks.py:35
-#, fuzzy
msgid "Add relay domain"
-msgstr "Adicionar domínio"
+msgstr ""
#: extensions/postfix_relay_domains/general_callbacks.py:101
-#, fuzzy
msgid "Maximum number of relay domains this user can create"
-msgstr "Número máximo de domínios que este utilizador pode criar"
+msgstr ""
#: extensions/postfix_relay_domains/general_callbacks.py:103
#: extensions/postfix_relay_domains/limits_callbacks.py:24
-#, fuzzy
msgid "Relay domain aliases"
-msgstr "Aliases de domínio"
+msgstr ""
#: extensions/postfix_relay_domains/general_callbacks.py:104
-#, fuzzy
msgid "Maximum number of relay domain aliases this user can create"
-msgstr "Número máximo de aliases de domínio que este utilizador pode criar"
+msgstr ""
#: extensions/postfix_relay_domains/general_callbacks.py:111
msgid ""
"\n"
-"relaydomain; name; target host; service; enabled; verify recipients"
-"em>\n"
+"relaydomain; name; target host; service; enabled; verify recipients\n"
"relaydomainalias; name; target; enabled\n"
msgstr ""
#: extensions/postfix_relay_domains/limits_callbacks.py:19
-#, fuzzy
msgid "Maximum number of allowed relay domains for a new administrator"
-msgstr "Número máximo permitido de domínios para novo administrador"
+msgstr ""
#: extensions/postfix_relay_domains/limits_callbacks.py:27
-#, fuzzy
msgid "Maximum number of allowed relay domain aliases for a new administrator"
msgstr ""
-"Número máximo permitido de aliases de domínio para um novo administrador"
#: extensions/postfix_relay_domains/models.py:59
-#, fuzzy
msgid "The service name"
-msgstr "O nome do 'alias'"
+msgstr ""
#: extensions/postfix_relay_domains/models.py:80
-#, fuzzy
msgid "target host"
-msgstr "alvo"
+msgstr ""
#: extensions/postfix_relay_domains/models.py:81
-#, fuzzy
msgid "Remote destination of this domain"
-msgstr "Marcar para ativar este domínio"
+msgstr ""
#: extensions/postfix_relay_domains/models.py:89
-#, fuzzy
msgid "verify recipients"
-msgstr "Destinatários"
+msgstr ""
#: extensions/postfix_relay_domains/models.py:90
msgid "Check for valid recipients"
msgstr ""
#: extensions/postfix_relay_domains/models.py:103
-#, fuzzy
msgid "Relay Domain"
-msgstr "Novo domínio"
+msgstr ""
#: extensions/postfix_relay_domains/models.py:164
-#, fuzzy
msgid "The relay domain this alias points to"
-msgstr "O domínio para o qual este alias irá apontar"
+msgstr ""
#: extensions/postfix_relay_domains/models.py:195
-#, fuzzy, python-format
+#, python-format
msgid "Relay domain %s does not exist"
-msgstr "O domínio '%s' não existe"
+msgstr ""
#: extensions/postfix_relay_domains/views.py:26
-#, fuzzy
msgid "Relay domain created"
-msgstr "Domínio criado"
+msgstr ""
#: extensions/postfix_relay_domains/views.py:31
-#, fuzzy
msgid "New relay domain"
-msgstr "Novo domínio"
+msgstr ""
#: extensions/postfix_relay_domains/views.py:54
-#, fuzzy
msgid "Relay domain modified"
-msgstr "Domínio alterado"
+msgstr ""
#: extensions/postfix_relay_domains/views.py:77
-#, fuzzy
msgid "Relay domain deleted"
-msgstr "Domínio criado"
+msgstr ""
#: extensions/postfix_relay_domains/templates/postfix_relay_domains/service_field.html:2
msgid "Scan"
@@ -2387,8 +2240,7 @@ msgstr "ativo"
#: extensions/sievefilters/templates/sievefilters/index.html:94
msgid ""
"No filters set defined yet. You must create one in order to define filters."
-msgstr ""
-"Não existem grupos de filtros. Terá de criar um para poder definir filtros."
+msgstr "Não existem grupos de filtros. Terá de criar um para poder definir filtros."
#: extensions/sievefilters/templatetags/sfilters_tags.py:15
msgid "New filters set"
@@ -2645,9 +2497,8 @@ msgid "Automatic folder refresh rate (in seconds)"
msgstr "Taxa de actualização automática de pastas (em segundos)"
#: extensions/webmail/app_settings.py:103
-#, fuzzy
msgid "Mailboxes container's width"
-msgstr "Detentor das Caixas de Correio (Owner)"
+msgstr ""
#: extensions/webmail/app_settings.py:104
msgid "The width of the mailbox list container"
@@ -2885,9 +2736,9 @@ msgid "Remove the selected mailbox"
msgstr "Eliminar caixa de correio selecionada"
#: lib/dbutils.py:36
-#, fuzzy, python-format
+#, python-format
msgid "Connection to database %s not configured"
-msgstr "Não foi possível estabelecer ligação com o amavis: %s"
+msgstr ""
#: lib/exceptions.py:67
#, python-format
@@ -2993,36 +2844,3 @@ msgstr "Lembrar-me"
#: templates/registration/login.html:36
msgid "Log in"
msgstr "Entrar"
-
-#~ msgid "An alias with this name already exists"
-#~ msgstr "Já existe um alias com este nome"
-
-#~ msgid "A domain with this name already exists"
-#~ msgstr "Este nome de domínio já existe"
-
-#~ msgid "Edit domain"
-#~ msgstr "Editar domínio"
-
-#~ msgid "%d pending requests"
-#~ msgstr "%d pedidos pendentes"
-
-#~ msgid "Content Class"
-#~ msgstr "Tipo de Conteúdo"
-
-#~ msgid "Nothing"
-#~ msgstr "Nenhum"
-
-#~ msgid "Bad request"
-#~ msgstr "Pedido inválido"
-
-#~ msgid "Undefined action"
-#~ msgstr "Ação indefinida"
-
-#~ msgid "User preferences"
-#~ msgstr "Preferências do utilizador"
-
-#~ msgid "Per-user settings"
-#~ msgstr "Configurações por usuário"
-
-#~ msgid "You need a mailbox in order to define a forward"
-#~ msgstr "Precisa de uma caixa de correio para definir um reencaminhamento"
diff --git a/modoboa/locale/pt_PT/LC_MESSAGES/djangojs.po b/modoboa/locale/pt_PT/LC_MESSAGES/djangojs.po
index 441d28c53..9e2768f05 100644
--- a/modoboa/locale/pt_PT/LC_MESSAGES/djangojs.po
+++ b/modoboa/locale/pt_PT/LC_MESSAGES/djangojs.po
@@ -1,8 +1,9 @@
# SOME DESCRIPTIVE TITLE.
# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER
# This file is distributed under the same license as the PACKAGE package.
-#
+#
# Translators:
+# lusitan , 2013
# mikec , 2012
# Sandra Ribeiro , 2013
msgid ""
@@ -10,14 +11,13 @@ msgstr ""
"Project-Id-Version: Modoboa\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2013-12-15 10:16+0100\n"
-"PO-Revision-Date: 2013-06-03 17:44+0000\n"
-"Last-Translator: Sandra Ribeiro \n"
-"Language-Team: Portuguese (Portugal) (http://www.transifex.com/projects/p/"
-"modoboa/language/pt_PT/)\n"
-"Language: pt_PT\n"
+"PO-Revision-Date: 2013-12-23 11:22+0000\n"
+"Last-Translator: lusitan \n"
+"Language-Team: Portuguese (Portugal) (http://www.transifex.com/projects/p/modoboa/language/pt_PT/)\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
+"Language: pt_PT\n"
"Plural-Forms: nplurals=2; plural=(n != 1);\n"
#: extensions/admin/static/admin/js/admin.js:32
@@ -36,9 +36,7 @@ msgstr "Esta operação irá remover TODOS os dados associados a este domínio."
msgid ""
"This operation will remove all data associated to this domain, excepting "
"accounts."
-msgstr ""
-"Esta operação irá remover TODOS os dados associados a este domínio, excepto "
-"as contas."
+msgstr "Esta operação irá remover TODOS os dados associados a este domínio, excepto as contas."
#: extensions/admin/static/admin/js/admin.js:222
msgid "No domain administrator defined"
@@ -76,7 +74,7 @@ msgstr "Esconder cabeçalho completo"
#: extensions/postfix_relay_domains/static/postfix_relay_domains/js/relay_domains.js:49
msgid "Services updated"
-msgstr ""
+msgstr "Atualizados os serviços"
#: extensions/sievefilters/static/sievefilters/js/lib.js:14
msgid "Remove this filter?"
@@ -138,28 +136,9 @@ msgid "Cancel"
msgstr "Cancelar"
#: static/js/global.js:314
-#, fuzzy
msgid "Internal error"
-msgstr "Erro Interno"
+msgstr "Erro interno"
#: static/js/searchbar.js:20
msgid "Search..."
msgstr "Pesquisar..."
-
-#~ msgid "Message deleted"
-#~ msgstr "Mensagem apagada"
-
-#~ msgid "Delete this domain?"
-#~ msgstr "Apagar este domínio?"
-
-#~ msgid "Delete this account?"
-#~ msgstr "Apagar esta conta?"
-
-#~ msgid "Delete this list?"
-#~ msgstr "Apagar esta lista?"
-
-#~ msgid "Delete this forward?"
-#~ msgstr "Apagar este reencaminhamento?"
-
-#~ msgid "Delete this alias?"
-#~ msgstr "Apagar este alias?"
From e03b002d1b9488c8ad3e7999376e53f5488ea05a Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 2 Jan 2014 15:49:15 +0100
Subject: [PATCH 11/32] Fixing CSS issue.
---
modoboa/static/css/viewmail.css | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/modoboa/static/css/viewmail.css b/modoboa/static/css/viewmail.css
index 778e8dd77..2e669648a 100644
--- a/modoboa/static/css/viewmail.css
+++ b/modoboa/static/css/viewmail.css
@@ -49,6 +49,6 @@ pre {
margin-left: 10px;
margin-right: 20px;
font-weight: bold;
- width: 6.38%;
- padding: 2px 0;
+ width: 7.5%;
+ padding: 0 0 2px 0;
}
\ No newline at end of file
From ea666cdc49042012bf22c8d8397409b720813b52 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 2 Jan 2014 16:23:30 +0100
Subject: [PATCH 12/32] Upgrade procedure updated.
---
doc/getting_started/upgrade.rst | 5 ++++-
1 file changed, 4 insertions(+), 1 deletion(-)
diff --git a/doc/getting_started/upgrade.rst b/doc/getting_started/upgrade.rst
index 6fec4120c..9aa488ed9 100644
--- a/doc/getting_started/upgrade.rst
+++ b/doc/getting_started/upgrade.rst
@@ -72,7 +72,9 @@ Due to code refactoring, some modifications need to be done into
'modoboa.extensions.sievefilters',
)
-#. Add ``'modoboa.extensions.postfix_relay_domains'`` to ``MODOBOA_APPS``
+#. Add ``'modoboa.extensions.postfix_relay_domains'`` to
+ ``MODOBOA_APPS``, just before
+ ``'modoboa.extensions.limits'``
#. ``AUTH_USER_MODEL`` must be set to ``core.User``
@@ -81,6 +83,7 @@ Due to code refactoring, some modifications need to be done into
Then, run the following commands to migrate your installation::
+ $ python manage.py syncdb
$ python manage.py migrate core 0001 --fake
$ python manage.py migrate
$ python manage.py collectstatic
From c27fe9cfbfe90ae522038fe1fb4b041bf051f9b8 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 2 Jan 2014 16:23:52 +0100
Subject: [PATCH 13/32] Wrong import statement fixed.
---
modoboa/demo/views.py | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/modoboa/demo/views.py b/modoboa/demo/views.py
index 18e2a8427..89a88f9f6 100755
--- a/modoboa/demo/views.py
+++ b/modoboa/demo/views.py
@@ -5,7 +5,7 @@ from django.contrib.auth.decorators import login_required
from django.utils.translation import ugettext as _
from modoboa.lib.webutils import render_to_json_response
from modoboa.lib.emailutils import sendmail_simple, sendmail_fromfile
-from modoboa.lib.decorators import needs_mailbox
+from modoboa.extensions.admin.lib import needs_mailbox
@login_required
From dab754275362d044578f5d934d6b41f4373f2a8b Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 2 Jan 2014 16:24:12 +0100
Subject: [PATCH 14/32] Wrong queries fixed.
see #469
---
modoboa/core/commands/postfix_maps.py | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/modoboa/core/commands/postfix_maps.py b/modoboa/core/commands/postfix_maps.py
index 37336ebf1..5ac75ce8a 100644
--- a/modoboa/core/commands/postfix_maps.py
+++ b/modoboa/core/commands/postfix_maps.py
@@ -151,9 +151,9 @@ class AutoRepliesMap(MapFile):
class RelayDomainsMap(MapFile):
category = "relaydomains"
filename = "sql-relaydomains.cf"
- mysql = "SELECT name FROM postfix_relay_domains_domain WHERE name='%s' AND enabled=1"
- postgres = "SELECT name FROM postfix_relay_domains_domain WHERE name='%s' AND enabled"
- sqlite = "SELECT name FROM postfix_relay_domains_domain WHERE name='%s' AND enabled=1"
+ mysql = "SELECT name FROM postfix_relay_domains_relaydomain WHERE name='%s' AND enabled=1"
+ postgres = "SELECT name FROM postfix_relay_domains_relaydomain WHERE name='%s' AND enabled"
+ sqlite = "SELECT name FROM postfix_relay_domains_relaydomain WHERE name='%s' AND enabled=1"
class RelayDomainsTransportMap(MapFile):
From 90b520f79bb4aad2a78d8eb89429cb467114591f Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 2 Jan 2014 16:44:08 +0100
Subject: [PATCH 15/32] Updating demo fixtures.
---
modoboa/extensions/admin/fixtures/demo.json | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/modoboa/extensions/admin/fixtures/demo.json b/modoboa/extensions/admin/fixtures/demo.json
index 206e3d53c..bfa3c89de 100644
--- a/modoboa/extensions/admin/fixtures/demo.json
+++ b/modoboa/extensions/admin/fixtures/demo.json
@@ -1 +1 @@
-[{"pk": 1, "model": "admin.user", "fields": {"username": "admin", "first_name": "", "last_name": "", "is_active": true, "is_superuser": true, "is_staff": false, "last_login": "2012-05-03 16:58:51", "groups": [], "user_permissions": [], "password": "{CRYPT}dTTsGDkA5ZHKg", "email": "", "date_joined": "2012-01-26 15:19:25"}}, {"pk": 2, "model": "admin.user", "fields": {"username": "admin@demo.local", "first_name": "Demo", "last_name": "Administrator", "is_active": true, "is_superuser": false, "is_staff": false, "last_login": "2012-05-24 05:00:12", "groups": [1], "user_permissions": [], "password": "{CRYPT}SJ2bQWwabfH/6", "email": "admin@demo.local", "date_joined": "2012-05-03 16:50:15"}}, {"pk": 4, "model": "admin.user", "fields": {"username": "user@demo.local", "first_name": "Demo", "last_name": "User", "is_active": true, "is_superuser": false, "is_staff": false, "last_login": "2012-05-03 16:56:50", "groups": [2], "user_permissions": [], "password": "{CRYPT}2iAFXtxUA6.7Y", "email": "user@demo.local", "date_joined": "2012-05-03 16:56:50"}}, {"pk": 2, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "domain"], "object_id": 1}}, {"pk": 3, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "user"], "object_id": 2}}, {"pk": 4, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "mailbox"], "object_id": 1}}, {"pk": 5, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "alias"], "object_id": 1}}, {"pk": 6, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "domain"], "object_id": 1}}, {"pk": 7, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "mailbox"], "object_id": 1}}, {"pk": 8, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "user"], "object_id": 2}}, {"pk": 9, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "alias"], "object_id": 1}}, {"pk": 13, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "user"], "object_id": 4}}, {"pk": 14, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "mailbox"], "object_id": 3}}, {"pk": 15, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "mailbox"], "object_id": 3}}, {"pk": 16, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "user"], "object_id": 4}}, {"pk": 1, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:49:40", "last_modification": "2012-05-03 16:49:40"}}, {"pk": 2, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:50:15", "last_modification": "2012-05-03 16:50:36"}}, {"pk": 3, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:50:15", "last_modification": "2012-05-03 16:50:15"}}, {"pk": 4, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:51:04", "last_modification": "2012-05-03 16:51:04"}}, {"pk": 5, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:56:50", "last_modification": "2012-05-03 16:56:50"}}, {"pk": 1, "model": "admin.domain", "fields": {"dates": 1, "enabled": true, "name": "demo.local", "quota": 10}}, {"pk": 1, "model": "admin.mailbox", "fields": {"dates": 2, "quota": 10, "user": 2, "domain": 1, "address": "admin"}}, {"pk": 3, "model": "admin.mailbox", "fields": {"dates": 5, "quota": 10, "user": 4, "domain": 1, "address": "user"}}, {"pk": 1, "model": "admin.alias", "fields": {"dates": 3, "enabled": true, "domain": 1, "mboxes": [1], "address": "postmaster", "extmboxes": ""}}, {"pk": 1, "model": "admin.extension", "fields": {"enabled": true, "name": "limits"}}, {"pk": 2, "model": "admin.extension", "fields": {"enabled": true, "name": "postfix_autoreply"}}, {"pk": 3, "model": "admin.extension", "fields": {"enabled": true, "name": "stats"}}, {"pk": 4, "model": "admin.extension", "fields": {"enabled": true, "name": "amavis"}}, {"pk": 5, "model": "admin.extension", "fields": {"enabled": true, "name": "webmail"}}, {"pk": 6, "model": "admin.extension", "fields": {"enabled": true, "name": "sievefilters"}}, {"pk": "admin@demo.local", "model": "admin.Quota", "fields": {"mbox": 1, "username": "admin@demo.local", "bytes": 0, "messages": 0}}, {"pk": "user@demo.local", "model": "admin.Quota", "fields": {"mbox": 3, "username": "user@demo.local", "bytes": 0, "messages": 0}}]
+[{"pk": 1, "model": "core.user", "fields": {"username": "admin", "first_name": "", "last_name": "", "is_active": true, "is_superuser": true, "is_staff": false, "last_login": "2012-05-03 16:58:51", "groups": [], "user_permissions": [], "password": "{CRYPT}dTTsGDkA5ZHKg", "email": "", "date_joined": "2012-01-26 15:19:25"}}, {"pk": 2, "model": "core.user", "fields": {"username": "admin@demo.local", "first_name": "Demo", "last_name": "Administrator", "is_active": true, "is_superuser": false, "is_staff": false, "last_login": "2012-05-24 05:00:12", "groups": [1], "user_permissions": [], "password": "{CRYPT}SJ2bQWwabfH/6", "email": "admin@demo.local", "date_joined": "2012-05-03 16:50:15"}}, {"pk": 4, "model": "core.user", "fields": {"username": "user@demo.local", "first_name": "Demo", "last_name": "User", "is_active": true, "is_superuser": false, "is_staff": false, "last_login": "2012-05-03 16:56:50", "groups": [2], "user_permissions": [], "password": "{CRYPT}2iAFXtxUA6.7Y", "email": "user@demo.local", "date_joined": "2012-05-03 16:56:50"}}, {"pk": 2, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "domain"], "object_id": 1}}, {"pk": 3, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "user"], "object_id": 2}}, {"pk": 4, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "mailbox"], "object_id": 1}}, {"pk": 5, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "alias"], "object_id": 1}}, {"pk": 6, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "domain"], "object_id": 1}}, {"pk": 7, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "mailbox"], "object_id": 1}}, {"pk": 8, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "user"], "object_id": 2}}, {"pk": 9, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "alias"], "object_id": 1}}, {"pk": 13, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "user"], "object_id": 4}}, {"pk": 14, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "mailbox"], "object_id": 3}}, {"pk": 15, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "mailbox"], "object_id": 3}}, {"pk": 16, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "user"], "object_id": 4}}, {"pk": 1, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:49:40", "last_modification": "2012-05-03 16:49:40"}}, {"pk": 2, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:50:15", "last_modification": "2012-05-03 16:50:36"}}, {"pk": 3, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:50:15", "last_modification": "2012-05-03 16:50:15"}}, {"pk": 4, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:51:04", "last_modification": "2012-05-03 16:51:04"}}, {"pk": 5, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:56:50", "last_modification": "2012-05-03 16:56:50"}}, {"pk": 1, "model": "admin.domain", "fields": {"dates": 1, "enabled": true, "name": "demo.local", "quota": 10}}, {"pk": 1, "model": "admin.mailbox", "fields": {"dates": 2, "quota": 10, "user": 2, "domain": 1, "address": "admin"}}, {"pk": 3, "model": "admin.mailbox", "fields": {"dates": 5, "quota": 10, "user": 4, "domain": 1, "address": "user"}}, {"pk": 1, "model": "admin.alias", "fields": {"dates": 3, "enabled": true, "domain": 1, "mboxes": [1], "address": "postmaster", "extmboxes": ""}}, {"pk": 1, "model": "admin.extension", "fields": {"enabled": true, "name": "limits"}}, {"pk": 2, "model": "admin.extension", "fields": {"enabled": true, "name": "postfix_autoreply"}}, {"pk": 3, "model": "admin.extension", "fields": {"enabled": true, "name": "stats"}}, {"pk": 4, "model": "admin.extension", "fields": {"enabled": true, "name": "amavis"}}, {"pk": 5, "model": "admin.extension", "fields": {"enabled": true, "name": "webmail"}}, {"pk": 6, "model": "admin.extension", "fields": {"enabled": true, "name": "sievefilters"}}, {"pk": "admin@demo.local", "model": "admin.Quota", "fields": {"mbox": 1, "username": "admin@demo.local", "bytes": 0, "messages": 0}}, {"pk": "user@demo.local", "model": "admin.Quota", "fields": {"mbox": 3, "username": "user@demo.local", "bytes": 0, "messages": 0}}]
From 599bab6132e35f6465538d4553dd2f3483f82425 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 2 Jan 2014 16:49:46 +0100
Subject: [PATCH 16/32] Updating demo fixtures.
---
modoboa/extensions/admin/fixtures/demo.json | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/modoboa/extensions/admin/fixtures/demo.json b/modoboa/extensions/admin/fixtures/demo.json
index bfa3c89de..7be1435a1 100644
--- a/modoboa/extensions/admin/fixtures/demo.json
+++ b/modoboa/extensions/admin/fixtures/demo.json
@@ -1 +1 @@
-[{"pk": 1, "model": "core.user", "fields": {"username": "admin", "first_name": "", "last_name": "", "is_active": true, "is_superuser": true, "is_staff": false, "last_login": "2012-05-03 16:58:51", "groups": [], "user_permissions": [], "password": "{CRYPT}dTTsGDkA5ZHKg", "email": "", "date_joined": "2012-01-26 15:19:25"}}, {"pk": 2, "model": "core.user", "fields": {"username": "admin@demo.local", "first_name": "Demo", "last_name": "Administrator", "is_active": true, "is_superuser": false, "is_staff": false, "last_login": "2012-05-24 05:00:12", "groups": [1], "user_permissions": [], "password": "{CRYPT}SJ2bQWwabfH/6", "email": "admin@demo.local", "date_joined": "2012-05-03 16:50:15"}}, {"pk": 4, "model": "core.user", "fields": {"username": "user@demo.local", "first_name": "Demo", "last_name": "User", "is_active": true, "is_superuser": false, "is_staff": false, "last_login": "2012-05-03 16:56:50", "groups": [2], "user_permissions": [], "password": "{CRYPT}2iAFXtxUA6.7Y", "email": "user@demo.local", "date_joined": "2012-05-03 16:56:50"}}, {"pk": 2, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "domain"], "object_id": 1}}, {"pk": 3, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "user"], "object_id": 2}}, {"pk": 4, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "mailbox"], "object_id": 1}}, {"pk": 5, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "alias"], "object_id": 1}}, {"pk": 6, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "domain"], "object_id": 1}}, {"pk": 7, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "mailbox"], "object_id": 1}}, {"pk": 8, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "user"], "object_id": 2}}, {"pk": 9, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "alias"], "object_id": 1}}, {"pk": 13, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "user"], "object_id": 4}}, {"pk": 14, "model": "admin.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "mailbox"], "object_id": 3}}, {"pk": 15, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "mailbox"], "object_id": 3}}, {"pk": 16, "model": "admin.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "user"], "object_id": 4}}, {"pk": 1, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:49:40", "last_modification": "2012-05-03 16:49:40"}}, {"pk": 2, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:50:15", "last_modification": "2012-05-03 16:50:36"}}, {"pk": 3, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:50:15", "last_modification": "2012-05-03 16:50:15"}}, {"pk": 4, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:51:04", "last_modification": "2012-05-03 16:51:04"}}, {"pk": 5, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:56:50", "last_modification": "2012-05-03 16:56:50"}}, {"pk": 1, "model": "admin.domain", "fields": {"dates": 1, "enabled": true, "name": "demo.local", "quota": 10}}, {"pk": 1, "model": "admin.mailbox", "fields": {"dates": 2, "quota": 10, "user": 2, "domain": 1, "address": "admin"}}, {"pk": 3, "model": "admin.mailbox", "fields": {"dates": 5, "quota": 10, "user": 4, "domain": 1, "address": "user"}}, {"pk": 1, "model": "admin.alias", "fields": {"dates": 3, "enabled": true, "domain": 1, "mboxes": [1], "address": "postmaster", "extmboxes": ""}}, {"pk": 1, "model": "admin.extension", "fields": {"enabled": true, "name": "limits"}}, {"pk": 2, "model": "admin.extension", "fields": {"enabled": true, "name": "postfix_autoreply"}}, {"pk": 3, "model": "admin.extension", "fields": {"enabled": true, "name": "stats"}}, {"pk": 4, "model": "admin.extension", "fields": {"enabled": true, "name": "amavis"}}, {"pk": 5, "model": "admin.extension", "fields": {"enabled": true, "name": "webmail"}}, {"pk": 6, "model": "admin.extension", "fields": {"enabled": true, "name": "sievefilters"}}, {"pk": "admin@demo.local", "model": "admin.Quota", "fields": {"mbox": 1, "username": "admin@demo.local", "bytes": 0, "messages": 0}}, {"pk": "user@demo.local", "model": "admin.Quota", "fields": {"mbox": 3, "username": "user@demo.local", "bytes": 0, "messages": 0}}]
+[{"pk": 1, "model": "core.user", "fields": {"username": "admin", "first_name": "", "last_name": "", "is_active": true, "is_superuser": true, "is_staff": false, "last_login": "2012-05-03 16:58:51", "groups": [], "user_permissions": [], "password": "{CRYPT}dTTsGDkA5ZHKg", "email": "", "date_joined": "2012-01-26 15:19:25"}}, {"pk": 2, "model": "core.user", "fields": {"username": "admin@demo.local", "first_name": "Demo", "last_name": "Administrator", "is_active": true, "is_superuser": false, "is_staff": false, "last_login": "2012-05-24 05:00:12", "groups": [1], "user_permissions": [], "password": "{CRYPT}SJ2bQWwabfH/6", "email": "admin@demo.local", "date_joined": "2012-05-03 16:50:15"}}, {"pk": 4, "model": "core.user", "fields": {"username": "user@demo.local", "first_name": "Demo", "last_name": "User", "is_active": true, "is_superuser": false, "is_staff": false, "last_login": "2012-05-03 16:56:50", "groups": [2], "user_permissions": [], "password": "{CRYPT}2iAFXtxUA6.7Y", "email": "user@demo.local", "date_joined": "2012-05-03 16:56:50"}}, {"pk": 2, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "domain"], "object_id": 1}}, {"pk": 3, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "user"], "object_id": 2}}, {"pk": 4, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "mailbox"], "object_id": 1}}, {"pk": 5, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "alias"], "object_id": 1}}, {"pk": 6, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "domain"], "object_id": 1}}, {"pk": 7, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "mailbox"], "object_id": 1}}, {"pk": 8, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "user"], "object_id": 2}}, {"pk": 9, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "alias"], "object_id": 1}}, {"pk": 13, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "user"], "object_id": 4}}, {"pk": 14, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "mailbox"], "object_id": 3}}, {"pk": 15, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "mailbox"], "object_id": 3}}, {"pk": 16, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "user"], "object_id": 4}}, {"pk": 1, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:49:40", "last_modification": "2012-05-03 16:49:40"}}, {"pk": 2, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:50:15", "last_modification": "2012-05-03 16:50:36"}}, {"pk": 3, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:50:15", "last_modification": "2012-05-03 16:50:15"}}, {"pk": 4, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:51:04", "last_modification": "2012-05-03 16:51:04"}}, {"pk": 5, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:56:50", "last_modification": "2012-05-03 16:56:50"}}, {"pk": 1, "model": "admin.domain", "fields": {"dates": 1, "enabled": true, "name": "demo.local", "quota": 10}}, {"pk": 1, "model": "admin.mailbox", "fields": {"dates": 2, "quota": 10, "user": 2, "domain": 1, "address": "admin"}}, {"pk": 3, "model": "admin.mailbox", "fields": {"dates": 5, "quota": 10, "user": 4, "domain": 1, "address": "user"}}, {"pk": 1, "model": "admin.alias", "fields": {"dates": 3, "enabled": true, "domain": 1, "mboxes": [1], "address": "postmaster", "extmboxes": ""}}, {"pk": 1, "model": "core.extension", "fields": {"enabled": true, "name": "limits"}}, {"pk": 2, "model": "core.extension", "fields": {"enabled": true, "name": "postfix_autoreply"}}, {"pk": 3, "model": "core.extension", "fields": {"enabled": true, "name": "stats"}}, {"pk": 4, "model": "core.extension", "fields": {"enabled": true, "name": "amavis"}}, {"pk": 5, "model": "core.extension", "fields": {"enabled": true, "name": "webmail"}}, {"pk": 6, "model": "core.extension", "fields": {"enabled": true, "name": "sievefilters"}}, {"pk": 7, "model": "core.extension", "fields": {"enabled": true, "name": "postfix_relay_domains"}}, {"pk": "admin@demo.local", "model": "admin.Quota", "fields": {"mbox": 1, "username": "admin@demo.local", "bytes": 0, "messages": 0}}, {"pk": "user@demo.local", "model": "admin.Quota", "fields": {"mbox": 3, "username": "user@demo.local", "bytes": 0, "messages": 0}}]
From e14a144920b794b6965e20f9fa0479d2d7a84f2f Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 2 Jan 2014 17:55:36 +0100
Subject: [PATCH 17/32] Updating demo fixtures.
---
modoboa/extensions/admin/fixtures/demo.json | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/modoboa/extensions/admin/fixtures/demo.json b/modoboa/extensions/admin/fixtures/demo.json
index 7be1435a1..f1971a053 100644
--- a/modoboa/extensions/admin/fixtures/demo.json
+++ b/modoboa/extensions/admin/fixtures/demo.json
@@ -1 +1 @@
-[{"pk": 1, "model": "core.user", "fields": {"username": "admin", "first_name": "", "last_name": "", "is_active": true, "is_superuser": true, "is_staff": false, "last_login": "2012-05-03 16:58:51", "groups": [], "user_permissions": [], "password": "{CRYPT}dTTsGDkA5ZHKg", "email": "", "date_joined": "2012-01-26 15:19:25"}}, {"pk": 2, "model": "core.user", "fields": {"username": "admin@demo.local", "first_name": "Demo", "last_name": "Administrator", "is_active": true, "is_superuser": false, "is_staff": false, "last_login": "2012-05-24 05:00:12", "groups": [1], "user_permissions": [], "password": "{CRYPT}SJ2bQWwabfH/6", "email": "admin@demo.local", "date_joined": "2012-05-03 16:50:15"}}, {"pk": 4, "model": "core.user", "fields": {"username": "user@demo.local", "first_name": "Demo", "last_name": "User", "is_active": true, "is_superuser": false, "is_staff": false, "last_login": "2012-05-03 16:56:50", "groups": [2], "user_permissions": [], "password": "{CRYPT}2iAFXtxUA6.7Y", "email": "user@demo.local", "date_joined": "2012-05-03 16:56:50"}}, {"pk": 2, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "domain"], "object_id": 1}}, {"pk": 3, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "user"], "object_id": 2}}, {"pk": 4, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "mailbox"], "object_id": 1}}, {"pk": 5, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "alias"], "object_id": 1}}, {"pk": 6, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "domain"], "object_id": 1}}, {"pk": 7, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "mailbox"], "object_id": 1}}, {"pk": 8, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "user"], "object_id": 2}}, {"pk": 9, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "alias"], "object_id": 1}}, {"pk": 13, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "user"], "object_id": 4}}, {"pk": 14, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "mailbox"], "object_id": 3}}, {"pk": 15, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "mailbox"], "object_id": 3}}, {"pk": 16, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "user"], "object_id": 4}}, {"pk": 1, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:49:40", "last_modification": "2012-05-03 16:49:40"}}, {"pk": 2, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:50:15", "last_modification": "2012-05-03 16:50:36"}}, {"pk": 3, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:50:15", "last_modification": "2012-05-03 16:50:15"}}, {"pk": 4, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:51:04", "last_modification": "2012-05-03 16:51:04"}}, {"pk": 5, "model": "admin.objectdates", "fields": {"creation": "2012-05-03 16:56:50", "last_modification": "2012-05-03 16:56:50"}}, {"pk": 1, "model": "admin.domain", "fields": {"dates": 1, "enabled": true, "name": "demo.local", "quota": 10}}, {"pk": 1, "model": "admin.mailbox", "fields": {"dates": 2, "quota": 10, "user": 2, "domain": 1, "address": "admin"}}, {"pk": 3, "model": "admin.mailbox", "fields": {"dates": 5, "quota": 10, "user": 4, "domain": 1, "address": "user"}}, {"pk": 1, "model": "admin.alias", "fields": {"dates": 3, "enabled": true, "domain": 1, "mboxes": [1], "address": "postmaster", "extmboxes": ""}}, {"pk": 1, "model": "core.extension", "fields": {"enabled": true, "name": "limits"}}, {"pk": 2, "model": "core.extension", "fields": {"enabled": true, "name": "postfix_autoreply"}}, {"pk": 3, "model": "core.extension", "fields": {"enabled": true, "name": "stats"}}, {"pk": 4, "model": "core.extension", "fields": {"enabled": true, "name": "amavis"}}, {"pk": 5, "model": "core.extension", "fields": {"enabled": true, "name": "webmail"}}, {"pk": 6, "model": "core.extension", "fields": {"enabled": true, "name": "sievefilters"}}, {"pk": 7, "model": "core.extension", "fields": {"enabled": true, "name": "postfix_relay_domains"}}, {"pk": "admin@demo.local", "model": "admin.Quota", "fields": {"mbox": 1, "username": "admin@demo.local", "bytes": 0, "messages": 0}}, {"pk": "user@demo.local", "model": "admin.Quota", "fields": {"mbox": 3, "username": "user@demo.local", "bytes": 0, "messages": 0}}]
+[{"pk": 1, "model": "core.user", "fields": {"username": "admin", "first_name": "", "last_name": "", "is_active": true, "is_superuser": true, "is_staff": false, "last_login": "2012-05-03T16:58:51+01:00", "groups": [], "user_permissions": [], "password": "{CRYPT}dTTsGDkA5ZHKg", "email": "", "date_joined": "2012-01-26T15:19:25+01:00"}}, {"pk": 2, "model": "core.user", "fields": {"username": "admin@demo.local", "first_name": "Demo", "last_name": "Administrator", "is_active": true, "is_superuser": false, "is_staff": false, "last_login": "2012-05-24T05:00:12+01:00", "groups": [1], "user_permissions": [], "password": "{CRYPT}SJ2bQWwabfH/6", "email": "admin@demo.local", "date_joined": "2012-05-03T16:50:15+01:00"}}, {"pk": 4, "model": "core.user", "fields": {"username": "user@demo.local", "first_name": "Demo", "last_name": "User", "is_active": true, "is_superuser": false, "is_staff": false, "last_login": "2012-05-03T16:56:50+01:00", "groups": [2], "user_permissions": [], "password": "{CRYPT}2iAFXtxUA6.7Y", "email": "user@demo.local", "date_joined": "2012-05-03T16:56:50+01:00"}}, {"pk": 2, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "domain"], "object_id": 1}}, {"pk": 3, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["core", "user"], "object_id": 2}}, {"pk": 4, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "mailbox"], "object_id": 1}}, {"pk": 5, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "alias"], "object_id": 1}}, {"pk": 6, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "domain"], "object_id": 1}}, {"pk": 7, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "mailbox"], "object_id": 1}}, {"pk": 8, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["core", "user"], "object_id": 2}}, {"pk": 9, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "alias"], "object_id": 1}}, {"pk": 13, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["core", "user"], "object_id": 4}}, {"pk": 14, "model": "core.objectaccess", "fields": {"is_owner": true, "user": 1, "content_type": ["admin", "mailbox"], "object_id": 3}}, {"pk": 15, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["admin", "mailbox"], "object_id": 3}}, {"pk": 16, "model": "core.objectaccess", "fields": {"is_owner": false, "user": 2, "content_type": ["core", "user"], "object_id": 4}}, {"pk": 1, "model": "admin.objectdates", "fields": {"creation": "2012-05-03T16:49:40+01:00", "last_modification": "2012-05-03T16:49:40+01:00"}}, {"pk": 2, "model": "admin.objectdates", "fields": {"creation": "2012-05-03T16:50:15+01:00", "last_modification": "2012-05-03T16:50:36+01:00"}}, {"pk": 3, "model": "admin.objectdates", "fields": {"creation": "2012-05-03T16:50:15+01:00", "last_modification": "2012-05-03T16:50:15+01:00"}}, {"pk": 4, "model": "admin.objectdates", "fields": {"creation": "2012-05-03T16:51:04+01:00", "last_modification": "2012-05-03T16:51:04+01:00"}}, {"pk": 5, "model": "admin.objectdates", "fields": {"creation": "2012-05-03T16:56:50+01:00", "last_modification": "2012-05-03T16:56:50+01:00"}}, {"pk": 1, "model": "admin.domain", "fields": {"dates": 1, "enabled": true, "name": "demo.local", "quota": 10}}, {"pk": 1, "model": "admin.mailbox", "fields": {"dates": 2, "quota": 10, "user": 2, "domain": 1, "address": "admin"}}, {"pk": 3, "model": "admin.mailbox", "fields": {"dates": 5, "quota": 10, "user": 4, "domain": 1, "address": "user"}}, {"pk": 1, "model": "admin.alias", "fields": {"dates": 3, "enabled": true, "domain": 1, "mboxes": [1], "address": "postmaster", "extmboxes": ""}}, {"pk": 1, "model": "core.extension", "fields": {"enabled": true, "name": "limits"}}, {"pk": 2, "model": "core.extension", "fields": {"enabled": true, "name": "postfix_autoreply"}}, {"pk": 3, "model": "core.extension", "fields": {"enabled": true, "name": "stats"}}, {"pk": 4, "model": "core.extension", "fields": {"enabled": true, "name": "amavis"}}, {"pk": 5, "model": "core.extension", "fields": {"enabled": true, "name": "webmail"}}, {"pk": 6, "model": "core.extension", "fields": {"enabled": true, "name": "sievefilters"}}, {"pk": 7, "model": "core.extension", "fields": {"enabled": true, "name": "postfix_relay_domains"}}, {"pk": "admin@demo.local", "model": "admin.quota", "fields": {"mbox": 1, "username": "admin@demo.local", "bytes": 0, "messages": 0}}, {"pk": "user@demo.local", "model": "admin.quota", "fields": {"mbox": 3, "username": "user@demo.local", "bytes": 0, "messages": 0}}]
From 085da9b7edcf0dc64ae15413074941f28e717fa9 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 2 Jan 2014 18:00:51 +0100
Subject: [PATCH 18/32] Updating demo fixtures.
---
modoboa/extensions/limits/fixtures/demo.json | 2 +-
modoboa/lib/fixtures/demo.json | 12 ++++++------
2 files changed, 7 insertions(+), 7 deletions(-)
diff --git a/modoboa/extensions/limits/fixtures/demo.json b/modoboa/extensions/limits/fixtures/demo.json
index 306fdc48d..34c5bcdfe 100644
--- a/modoboa/extensions/limits/fixtures/demo.json
+++ b/modoboa/extensions/limits/fixtures/demo.json
@@ -1 +1 @@
-[{"pk": 1, "model": "limits.limitspool", "fields": {"user": 2}}, {"pk": 1, "model": "limits.limit", "fields": {"curvalue": 0, "name": "domain_admins_limit", "pool": 1, "maxvalue": -2}}, {"pk": 2, "model": "limits.limit", "fields": {"curvalue": 0, "name": "domains_limit", "pool": 1, "maxvalue": -2}}, {"pk": 3, "model": "limits.limit", "fields": {"curvalue": 0, "name": "domain_aliases_limit", "pool": 1, "maxvalue": -2}}, {"pk": 4, "model": "limits.limit", "fields": {"curvalue": 0, "name": "mailboxes_limit", "pool": 1, "maxvalue": 5}}, {"pk": 5, "model": "limits.limit", "fields": {"curvalue": 0, "name": "mailbox_aliases_limit", "pool": 1, "maxvalue": 5}},{"pk": 3, "model": "auth.group", "fields": {"name": "Resellers", "permissions": [["add_user", "admin", "user"], ["change_user", "admin", "user"], ["delete_user", "admin", "user"], ["view_domains", "admin", "domain"], ["add_mailbox", "admin", "mailbox"], ["change_mailbox", "admin", "mailbox"], ["delete_mailbox", "admin", "mailbox"], ["add_alias", "admin", "alias"], ["change_alias", "admin", "alias"], ["delete_alias", "admin", "alias"], ["view_mailboxes", "admin", "mailbox"], ["view_aliases", "admin", "alias"], ["view_domaliases", "admin", "domainalias"], ["add_domainalias", "admin", "domainalias"], ["change_domainalias", "admin", "domainalias"], ["delete_domainalias", "admin", "domainalias"],["view_permissions", "auth", "permission"], ["view_domains", "admin", "domain"], ["add_domain", "admin", "domain"], ["change_domain", "admin", "domain"], ["delete_domain", "admin", "domain"]]}}]
\ No newline at end of file
+[{"pk": 1, "model": "limits.limitspool", "fields": {"user": 2}}, {"pk": 1, "model": "limits.limit", "fields": {"curvalue": 0, "name": "domain_admins_limit", "pool": 1, "maxvalue": -2}}, {"pk": 2, "model": "limits.limit", "fields": {"curvalue": 0, "name": "domains_limit", "pool": 1, "maxvalue": -2}}, {"pk": 3, "model": "limits.limit", "fields": {"curvalue": 0, "name": "domain_aliases_limit", "pool": 1, "maxvalue": -2}}, {"pk": 4, "model": "limits.limit", "fields": {"curvalue": 0, "name": "mailboxes_limit", "pool": 1, "maxvalue": 5}}, {"pk": 5, "model": "limits.limit", "fields": {"curvalue": 0, "name": "mailbox_aliases_limit", "pool": 1, "maxvalue": 5}},{"pk": 3, "model": "auth.group", "fields": {"name": "Resellers", "permissions": [["add_user", "core", "user"], ["change_user", "core", "user"], ["delete_user", "core", "user"], ["view_domains", "admin", "domain"], ["add_mailbox", "admin", "mailbox"], ["change_mailbox", "admin", "mailbox"], ["delete_mailbox", "admin", "mailbox"], ["add_alias", "admin", "alias"], ["change_alias", "admin", "alias"], ["delete_alias", "admin", "alias"], ["view_mailboxes", "admin", "mailbox"], ["view_aliases", "admin", "alias"], ["view_domaliases", "admin", "domainalias"], ["add_domainalias", "admin", "domainalias"], ["change_domainalias", "admin", "domainalias"], ["delete_domainalias", "admin", "domainalias"],["view_permissions", "auth", "permission"], ["view_domains", "admin", "domain"], ["add_domain", "admin", "domain"], ["change_domain", "admin", "domain"], ["delete_domain", "admin", "domain"]]}}]
\ No newline at end of file
diff --git a/modoboa/lib/fixtures/demo.json b/modoboa/lib/fixtures/demo.json
index 046dd26f0..da963902f 100644
--- a/modoboa/lib/fixtures/demo.json
+++ b/modoboa/lib/fixtures/demo.json
@@ -3,7 +3,7 @@
"pk": 2,
"model": "lib.parameter",
"fields": {
- "name": "admin.PASSWORD_SCHEME",
+ "name": "core.PASSWORD_SCHEME",
"value": "crypt"
}
},
@@ -11,7 +11,7 @@
"pk": 3,
"model": "lib.parameter",
"fields": {
- "name": "admin.ITEMS_PER_PAGE",
+ "name": "core.ITEMS_PER_PAGE",
"value": "30"
}
},
@@ -19,7 +19,7 @@
"pk": 4,
"model": "lib.parameter",
"fields": {
- "name": "general.DEFAULT_TOP_REDIRECTION",
+ "name": "core.DEFAULT_TOP_REDIRECTION",
"value": "user"
}
},
@@ -27,15 +27,15 @@
"pk": 6,
"model": "lib.parameter",
"fields": {
- "name": "general.SECRET_KEY",
- "value": "abcdefghijklmnop"
+ "name": "core.SECRET_KEY",
+ "value": ""
}
},
{
"pk": 8,
"model": "lib.parameter",
"fields": {
- "name": "admin.AUTHENTICATION_TYPE",
+ "name": "core.AUTHENTICATION_TYPE",
"value": "local"
}
},
From f2d7a775041c9a854adf061b933386b458c9ad61 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 2 Jan 2014 18:08:37 +0100
Subject: [PATCH 19/32] Updating demo fixtures (last time!)
---
modoboa/extensions/limits/fixtures/demo.json | 2 +-
modoboa/lib/fixtures/demo.json | 8 --------
2 files changed, 1 insertion(+), 9 deletions(-)
diff --git a/modoboa/extensions/limits/fixtures/demo.json b/modoboa/extensions/limits/fixtures/demo.json
index 34c5bcdfe..52a9bc1a1 100644
--- a/modoboa/extensions/limits/fixtures/demo.json
+++ b/modoboa/extensions/limits/fixtures/demo.json
@@ -1 +1 @@
-[{"pk": 1, "model": "limits.limitspool", "fields": {"user": 2}}, {"pk": 1, "model": "limits.limit", "fields": {"curvalue": 0, "name": "domain_admins_limit", "pool": 1, "maxvalue": -2}}, {"pk": 2, "model": "limits.limit", "fields": {"curvalue": 0, "name": "domains_limit", "pool": 1, "maxvalue": -2}}, {"pk": 3, "model": "limits.limit", "fields": {"curvalue": 0, "name": "domain_aliases_limit", "pool": 1, "maxvalue": -2}}, {"pk": 4, "model": "limits.limit", "fields": {"curvalue": 0, "name": "mailboxes_limit", "pool": 1, "maxvalue": 5}}, {"pk": 5, "model": "limits.limit", "fields": {"curvalue": 0, "name": "mailbox_aliases_limit", "pool": 1, "maxvalue": 5}},{"pk": 3, "model": "auth.group", "fields": {"name": "Resellers", "permissions": [["add_user", "core", "user"], ["change_user", "core", "user"], ["delete_user", "core", "user"], ["view_domains", "admin", "domain"], ["add_mailbox", "admin", "mailbox"], ["change_mailbox", "admin", "mailbox"], ["delete_mailbox", "admin", "mailbox"], ["add_alias", "admin", "alias"], ["change_alias", "admin", "alias"], ["delete_alias", "admin", "alias"], ["view_mailboxes", "admin", "mailbox"], ["view_aliases", "admin", "alias"], ["view_domaliases", "admin", "domainalias"], ["add_domainalias", "admin", "domainalias"], ["change_domainalias", "admin", "domainalias"], ["delete_domainalias", "admin", "domainalias"],["view_permissions", "auth", "permission"], ["view_domains", "admin", "domain"], ["add_domain", "admin", "domain"], ["change_domain", "admin", "domain"], ["delete_domain", "admin", "domain"]]}}]
\ No newline at end of file
+[{"pk": 1, "model": "limits.limitspool", "fields": {"user": 2}}, {"pk": 1, "model": "limits.limit", "fields": {"curvalue": 0, "name": "domain_admins_limit", "pool": 1, "maxvalue": -2}}, {"pk": 2, "model": "limits.limit", "fields": {"curvalue": 0, "name": "domains_limit", "pool": 1, "maxvalue": -2}}, {"pk": 3, "model": "limits.limit", "fields": {"curvalue": 0, "name": "domain_aliases_limit", "pool": 1, "maxvalue": -2}}, {"pk": 4, "model": "limits.limit", "fields": {"curvalue": 0, "name": "mailboxes_limit", "pool": 1, "maxvalue": 5}}, {"pk": 5, "model": "limits.limit", "fields": {"curvalue": 0, "name": "mailbox_aliases_limit", "pool": 1, "maxvalue": 5}},{"pk": 3, "model": "auth.group", "fields": {"name": "Resellers", "permissions": [["add_user", "core", "user"], ["change_user", "core", "user"], ["delete_user", "core", "user"], ["view_domains", "admin", "domain"], ["add_mailbox", "admin", "mailbox"], ["change_mailbox", "admin", "mailbox"], ["delete_mailbox", "admin", "mailbox"], ["add_alias", "admin", "alias"], ["change_alias", "admin", "alias"], ["delete_alias", "admin", "alias"], ["view_mailboxes", "admin", "mailbox"], ["view_aliases", "admin", "alias"], ["view_domaliases", "admin", "domainalias"], ["add_domainalias", "admin", "domainalias"], ["change_domainalias", "admin", "domainalias"], ["delete_domainalias", "admin", "domainalias"], ["view_domains", "admin", "domain"], ["add_domain", "admin", "domain"], ["change_domain", "admin", "domain"], ["delete_domain", "admin", "domain"]]}}]
\ No newline at end of file
diff --git a/modoboa/lib/fixtures/demo.json b/modoboa/lib/fixtures/demo.json
index da963902f..cdd99ecb9 100644
--- a/modoboa/lib/fixtures/demo.json
+++ b/modoboa/lib/fixtures/demo.json
@@ -23,14 +23,6 @@
"value": "user"
}
},
- {
- "pk": 6,
- "model": "lib.parameter",
- "fields": {
- "name": "core.SECRET_KEY",
- "value": ""
- }
- },
{
"pk": 8,
"model": "lib.parameter",
From 5af7822b803f8003e497769d6b03b79f19e1267a Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 2 Jan 2014 18:12:48 +0100
Subject: [PATCH 20/32] Version updated to 1.1.0.
---
doc/conf.py | 6 +++---
modoboa/extensions/webmail/lib.py | 4 ++--
setup.py | 2 +-
3 files changed, 6 insertions(+), 6 deletions(-)
diff --git a/doc/conf.py b/doc/conf.py
index 13b3fddff..39fa7e833 100644
--- a/doc/conf.py
+++ b/doc/conf.py
@@ -41,16 +41,16 @@ master_doc = 'index'
# General information about the project.
project = u'Modoboa'
-copyright = u'2013, Antoine Nguyen'
+copyright = u'2014, Antoine Nguyen'
# The version info for the project you're documenting, acts as replacement for
# |version| and |release|, also used in various other places throughout the
# built documents.
#
# The short X.Y version.
-version = '1.0'
+version = '1.1'
# The full version, including alpha/beta/rc tags.
-release = '1.0.1'
+release = '1.1.0'
# The language for content autogenerated by Sphinx. Refer to documentation
# for a list of supported languages.
diff --git a/modoboa/extensions/webmail/lib.py b/modoboa/extensions/webmail/lib.py
index 3eb63628b..0b099f8ef 100644
--- a/modoboa/extensions/webmail/lib.py
+++ b/modoboa/extensions/webmail/lib.py
@@ -582,8 +582,8 @@ def save_attachment(f):
def clean_attachments(attlist):
"""Remove all attachments from the filesystem
- :param attlist: a list of 2-uple. Each element must contain the following information :
- (random name, real name).
+ :param attlist: a list of 2-uple. Each element must contain the
+ following information : (random name, real name).
"""
for att in attlist:
fullpath = os.path.join(settings.MEDIA_ROOT, "webmail", att["tmpname"])
diff --git a/setup.py b/setup.py
index 18f760183..bb2669e0c 100644
--- a/setup.py
+++ b/setup.py
@@ -54,7 +54,7 @@ def read(fname):
setup(
name="modoboa",
- version='1.0.1',
+ version='1.1.0',
url='http://modoboa.org/',
license='MIT',
description="Mail hosting made simple",
From a9611eb01788187d82f54e37421c52997f7d312c Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Fri, 3 Jan 2014 09:53:38 +0100
Subject: [PATCH 21/32] Documentation update.
---
doc/integration/imap_and_smtp.rst | 7 +++++--
1 file changed, 5 insertions(+), 2 deletions(-)
diff --git a/doc/integration/imap_and_smtp.rst b/doc/integration/imap_and_smtp.rst
index 7b9d0aa9f..2ab61583d 100644
--- a/doc/integration/imap_and_smtp.rst
+++ b/doc/integration/imap_and_smtp.rst
@@ -44,8 +44,11 @@ Then, edit the ``inbox`` namespace and add the following lines::
special_use = \Trash
}
-It ensures all the special mailboxes will be automaticaly created for
-new accounts.
+With dovecot 2.1+, it ensures all the special mailboxes will be
+automaticaly created for new accounts.
+
+For dovecot 2.0 and older, use the `autocreate
+`_ plugin.
.. _fs_operations:
From 5151299841f4782b1f44c3f2c66e7fa990eae898 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Mon, 6 Jan 2014 09:52:05 +0100
Subject: [PATCH 22/32] Wrong condition fixed.
fix #507
---
.../postfix_autoreply/management/commands/autoreply.py | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/modoboa/extensions/postfix_autoreply/management/commands/autoreply.py b/modoboa/extensions/postfix_autoreply/management/commands/autoreply.py
index 450fee4fe..63fb9b655 100644
--- a/modoboa/extensions/postfix_autoreply/management/commands/autoreply.py
+++ b/modoboa/extensions/postfix_autoreply/management/commands/autoreply.py
@@ -12,7 +12,7 @@ from modoboa.extensions.postfix_autoreply.models import ARmessage, ARhistoric
def send_autoreply(sender, mailbox, armessage):
- if armessage.fromdate < timezone.now():
+ if armessage.fromdate > timezone.now():
return
if armessage.untildate is not None \
and armessage.untildate < timezone.now():
From 513d59bce3b882033be641ad3f8ee5771fba2f6f Mon Sep 17 00:00:00 2001
From: Carlos Ramos
Date: Sat, 18 Jan 2014 14:56:57 -0600
Subject: [PATCH 23/32] Fix cleanlogs command.
---
modoboa/core/management/commands/cleanlogs.py | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/modoboa/core/management/commands/cleanlogs.py b/modoboa/core/management/commands/cleanlogs.py
index 3da28798f..0cf1c8aac 100644
--- a/modoboa/core/management/commands/cleanlogs.py
+++ b/modoboa/core/management/commands/cleanlogs.py
@@ -4,7 +4,7 @@ import datetime
from optparse import make_option
from django.core.management.base import BaseCommand
from django.utils import timezone
-from modoboa.core import load_settings
+from modoboa.core import load_core_settings
from modoboa.core.models import Log
from modoboa.lib import parameters
@@ -37,7 +37,7 @@ class Command(BaseCommand):
l.addHandler(logging.StreamHandler())
self.verbose = options["verbose"]
- load_settings()
+ load_core_settings()
log_maximum_age = int(parameters.get_admin("LOG_MAXIMUM_AGE"))
self.__vprint("Deleting logs older than %d days..." % log_maximum_age)
limit = timezone.now() - datetime.timedelta(log_maximum_age)
From e7791091253e9568d0cb9a01c1f27a35cc64958b Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Wed, 22 Jan 2014 17:26:44 +0100
Subject: [PATCH 24/32] Catch the proper exception and force the schem to upper
case.
fix #514
---
modoboa/core/password_hashers/__init__.py | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/modoboa/core/password_hashers/__init__.py b/modoboa/core/password_hashers/__init__.py
index c26f9d3fd..66e4d6a64 100644
--- a/modoboa/core/password_hashers/__init__.py
+++ b/modoboa/core/password_hashers/__init__.py
@@ -20,7 +20,7 @@ def get_password_hasher(scheme):
"""
try:
scheme = scheme.replace('-', '')
- hasher = globals()['%sHasher' % scheme]
- except AttributeError:
+ hasher = globals()['%sHasher' % scheme.upper()]
+ except KeyError:
hasher = PLAINHasher
return hasher
From 9984c3a72362fb1742915343e20a0e43a10c7075 Mon Sep 17 00:00:00 2001
From: Carlos Ramos
Date: Wed, 22 Jan 2014 22:38:33 -0600
Subject: [PATCH 25/32] Look in more places for the dovecot binary
fix #510
---
modoboa/extensions/admin/app_settings.py | 7 +++++++
1 file changed, 7 insertions(+)
diff --git a/modoboa/extensions/admin/app_settings.py b/modoboa/extensions/admin/app_settings.py
index 377ce5ebb..3916d35e5 100644
--- a/modoboa/extensions/admin/app_settings.py
+++ b/modoboa/extensions/admin/app_settings.py
@@ -3,6 +3,7 @@ from django.utils.translation import ugettext_lazy
from modoboa.lib.formutils import YesNoField, SeparatorField
from modoboa.lib.sysutils import exec_cmd
from modoboa.lib import parameters
+import os
class AdminParametersForm(parameters.AdminParametersForm):
@@ -47,8 +48,14 @@ class AdminParametersForm(parameters.AdminParametersForm):
super(AdminParametersForm, self).__init__(*args, **kwargs)
hide_fields = False
code, output = exec_cmd("which dovecot")
+ known_paths = ("/usr/sbin/dovecot", "/usr/local/sbin/dovecot")
if not code:
dpath = output.strip()
+ else:
+ for fpath in known_paths:
+ if os.path.isfile(fpath) and os.access(fpath, os.X_OK):
+ dpath = fpath
+ if dpath:
try:
code, version = exec_cmd("%s --version" % dpath)
except OSError:
From bd1b3201eafe7b19a7a3fb12ca3bbc6d714f7e04 Mon Sep 17 00:00:00 2001
From: Carlos Ramos
Date: Wed, 22 Jan 2014 23:05:50 -0600
Subject: [PATCH 26/32] Initialize dpath to make CI not fail
---
modoboa/extensions/admin/app_settings.py | 1 +
1 file changed, 1 insertion(+)
diff --git a/modoboa/extensions/admin/app_settings.py b/modoboa/extensions/admin/app_settings.py
index 3916d35e5..c35a9fab2 100644
--- a/modoboa/extensions/admin/app_settings.py
+++ b/modoboa/extensions/admin/app_settings.py
@@ -47,6 +47,7 @@ class AdminParametersForm(parameters.AdminParametersForm):
def __init__(self, *args, **kwargs):
super(AdminParametersForm, self).__init__(*args, **kwargs)
hide_fields = False
+ dpath = None
code, output = exec_cmd("which dovecot")
known_paths = ("/usr/sbin/dovecot", "/usr/local/sbin/dovecot")
if not code:
From 9cf0fb81f9ceeb1a8f72c747a98da28db2128384 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 23 Jan 2014 14:36:20 +0100
Subject: [PATCH 27/32] Truncate too long policy names.
see #513
---
modoboa/extensions/amavis/lib.py | 7 +++----
modoboa/extensions/amavis/models.py | 2 +-
2 files changed, 4 insertions(+), 5 deletions(-)
diff --git a/modoboa/extensions/amavis/lib.py b/modoboa/extensions/amavis/lib.py
index e098f7513..9a9ed39bd 100644
--- a/modoboa/extensions/amavis/lib.py
+++ b/modoboa/extensions/amavis/lib.py
@@ -12,7 +12,6 @@ from modoboa.lib.webutils import NavigationParameters
from modoboa.extensions.amavis.models import Users, Policy
-
def selfservice(ssfunc=None):
"""Decorator used to expose views to the 'self-service' feature
@@ -121,7 +120,7 @@ def create_user_and_policy(name):
:param str name: name
"""
- policy = Policy.objects.create(policy_name=name)
+ policy = Policy.objects.create(policy_name=name[:32])
Users.objects.create(
email="@%s" % name, fullname=name,
priority=7, policy=policy
@@ -134,7 +133,7 @@ def create_user_and_use_policy(name, policy_name):
:param str name: user record name
:param str policy_name: policy name
"""
- policy = Policy.objects.get(policy_name=policy_name)
+ policy = Policy.objects.get(policy_name=policy_name[:32])
Users.objects.create(
email="@%s" % name, fullname=name,
priority=7, policy=policy
@@ -152,7 +151,7 @@ def update_user_and_policy(oldname, newname):
u = Users.objects.get(email="@%s" % oldname)
u.email = "@%s" % newname
u.fullname = newname
- u.policy.policy_name = newname
+ u.policy.policy_name = newname[:32]
u.policy.save()
u.save()
diff --git a/modoboa/extensions/amavis/models.py b/modoboa/extensions/amavis/models.py
index b15a63c93..50f29305b 100644
--- a/modoboa/extensions/amavis/models.py
+++ b/modoboa/extensions/amavis/models.py
@@ -83,7 +83,7 @@ class Msgrcpt(models.Model):
class Policy(models.Model):
- policy_name = models.CharField(max_length=96, blank=True)
+ policy_name = models.CharField(max_length=32, blank=True)
virus_lover = models.CharField(max_length=3, blank=True, null=True)
spam_lover = models.CharField(max_length=3, blank=True, null=True)
unchecked_lover = models.CharField(max_length=3, blank=True, null=True)
From 7b5c7000bc183b625ee0eaae3f7992635c8bed6b Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Thu, 23 Jan 2014 22:02:04 +0100
Subject: [PATCH 28/32] Support for high precision timers added.
fixes #516
---
.../stats/management/commands/logparser.py | 224 +++++++++++-------
1 file changed, 140 insertions(+), 84 deletions(-)
diff --git a/modoboa/extensions/stats/management/commands/logparser.py b/modoboa/extensions/stats/management/commands/logparser.py
index 0f75eb3f8..eba21090b 100644
--- a/modoboa/extensions/stats/management/commands/logparser.py
+++ b/modoboa/extensions/stats/management/commands/logparser.py
@@ -39,18 +39,20 @@ variables = ["sent", "recv", "bounced", "reject", "spam", "virus",
class LogParser(object):
+
def __init__(self, options, workdir, year=None):
+ """Constructor
+ """
self.logfile = options["logfile"]
+ self.debug = options["debug"]
+ self.verbose = options["verbose"]
try:
self.f = open(self.logfile)
- except IOError, errno:
- if options["debug"]:
- print "%s" % errno
+ except IOError as errno:
+ self._dprint("%s" % errno)
sys.exit(1)
self.workdir = workdir
self.__year = year
- self.debug = options["debug"]
- self.verbose = options["verbose"]
self.cfs = ['AVERAGE', 'MAX']
curtime = time.localtime()
@@ -59,16 +61,74 @@ class LogParser(object):
self.curmonth = curtime.tm_mon
self.data = {}
- domains = Domain.objects.all()
self.domains = []
- for dom in domains:
+ for dom in Domain.objects.all():
self.domains += [str(dom.name)]
self.data[str(dom.name)] = {}
self.data["global"] = {}
self.workdict = {}
self.lupdates = {}
- self.line_expr = re.compile("(\w+)\s+(\d+)\s+(\d+):(\d+):(\d+)\s+([-\w]+)\s+(\w+)/?\w*[[](\d+)[]]:\s+(.*)")
+ self._s_date_expr = \
+ re.compile(r"(?P\w+)\s+(?P\d+)\s+(?P\d+):(?P\d+):(?P\d+)(?P.*)")
+ self._hp_date_expr = \
+ re.compile(r"(?P\d+)-(?P\d+)-(?P\d+)T(?P\d+):(?P\d+):(?P\d+)\.\d+\+\d+:\d+(?P.*)")
+ self.date_expr = None
+ self.line_expr = \
+ re.compile(r"\s+([-\w]+)\s+(\w+)/?\w*[[](\d+)[]]:\s+(.*)")
+ self._id_expr = re.compile(r"(\w+): (.*)")
+ self._prev_se = -1
+ self._prev_mi = -1
+ self._prev_ho = -1
+ self.cur_t = 0
+
+ def _dprint(self, msg):
+ """Print a debug message if required.
+
+ :param str msg: debug message
+ """
+ if not self.debug:
+ return
+ print msg
+
+ def _parse_date(self, line):
+ """Try to match a date inside :kw:`line` and to convert it to
+ a timestamp.
+
+ We try different date format until we find valid one. We then
+ store it for future use.
+
+ :param str line: a log entry
+ :return: the remaining part of the line or None
+ """
+ match = None
+ if self.date_expr is None:
+ for expr in [self._s_date_expr, self._hp_date_expr]:
+ match = expr.match(line)
+ if match is not None:
+ self.date_expr = expr
+ break
+ else:
+ match = self.date_expr.match(line)
+ if match is None:
+ return None
+ ho = match.group("hour")
+ mi = match.group("min")
+ se = match.group("sec")
+ se = int(int(se) / rrdstep) # rrd step is one-minute => se = 0
+ if self._prev_se != se or self._prev_mi != mi or self._prev_ho != ho:
+ mo = match.group("month")
+ da = match.group("day")
+ try:
+ ye = match.group("year")
+ except IndexError:
+ ye = self.year(mo)
+ self.cur_t = str2Time(ye, mo, da, ho, mi, se)
+ self.cur_t = self.cur_t - self.cur_t % rrdstep
+ self._prev_mi = mi
+ self._prev_ho = ho
+ self._prev_se = se
+ return match.group('eol')
def init_rrd(self, fname, m):
"""init_rrd
@@ -119,8 +179,7 @@ class LogParser(object):
m = t - (t % rrdstep)
if not os.path.exists(fname):
self.lupdates[fname] = self.init_rrd(fname, m)
- if self.debug:
- print "[rrd] create new RRD file %s" % fname
+ self._dprint("[rrd] create new RRD file %s" % fname)
else:
if not fname in self.lupdates:
self.lupdates[fname] = rrdtool.last(str(fname))
@@ -164,21 +223,21 @@ class LogParser(object):
self.lupdates[fname] = m
return True
- def initcounters(self, dom, cur_t):
+ def initcounters(self, dom):
init = {}
for v in variables:
init[v] = 0
- self.data[dom][cur_t] = init
+ self.data[dom][self.cur_t] = init
- def inc_counter(self, dom, cur_t, counter, val=1):
+ def inc_counter(self, dom, counter, val=1):
if dom is not None and dom in self.domains:
- if not cur_t in self.data[dom]:
- self.initcounters(dom, cur_t)
- self.data[dom][cur_t][counter] += val
+ if not self.cur_t in self.data[dom]:
+ self.initcounters(dom)
+ self.data[dom][self.cur_t][counter] += val
- if not cur_t in self.data["global"]:
- self.initcounters("global", cur_t)
- self.data["global"][cur_t][counter] += val
+ if not self.cur_t in self.data["global"]:
+ self.initcounters("global")
+ self.data["global"][self.cur_t][counter] += val
def year(self, month):
"""Return the appropriate year
@@ -203,82 +262,79 @@ class LogParser(object):
return self.__year - 1
return self.__year
- def process(self):
- id_expr = re.compile("([0-9A-F]+): (.*)")
- prev_se = -1
- prev_mi = -1
- prev_ho = -1
- for line in self.f.readlines():
- m = self.line_expr.match(line)
- if not m:
- continue
- (mo, da, ho, mi, se, host, prog, pid, log) = m.groups()
- se = int(int(se) / rrdstep) # rrd step is one-minute => se = 0
+ def _parse_line(self, line):
+ """Parse a single log line.
- if prev_se != se or prev_mi != mi or prev_ho != ho:
- cur_t = str2Time(self.year(mo), mo, da, ho, mi, se)
- cur_t = cur_t - cur_t % rrdstep
- prev_mi = mi
- prev_ho = ho
- prev_se = se
- m = id_expr.match(log)
+ :param str line: log line
+ """
+ line = self._parse_date(line)
+ if line is None:
+ return
+ m = self.line_expr.match(line)
+ if not m:
+ return
+ host, prog, pid, log = m.groups()
+ m = self._id_expr.match(log)
+ if m:
+ (line_id, line_log) = m.groups()
+ m = re.search("message-id=<([^>]*)>", line_log)
if m:
- (line_id, line_log) = m.groups()
+ self.workdict[line_id] = {'from': m.group(1), 'size': 0}
+ return
+ m = re.search("from=<([^>]*)>, size=(\d+)", line_log)
+ if m:
+ self.workdict[line_id] = {'from': m.group(1),
+ 'size': string.atoi(m.group(2))}
+ return
- m = re.search("message-id=<([^>]*)>", line_log)
- if m:
- self.workdict[line_id] = {'from': m.group(1), 'size': 0}
- continue
+ m = re.search("to=<([^>]*)>.*status=(\S+)", line_log)
+ if m:
+ if not line_id in self.workdict:
+ self._dprint("Inconsistent mail (%s: %s), skipping" \
+ % (line_id, m.group(1)))
+ return
+ if not m.group(2) in variables:
+ self._dprint("Unsupported status %s, skipping" % m.group(2))
+ return
- m = re.search("from=<([^>]*)>, size=(\d+)", line_log)
- if m:
- self.workdict[line_id] = {'from': m.group(1),
- 'size': string.atoi(m.group(2))}
- continue
+ addrfrom = re.match("([^@]+)@(.+)", self.workdict[line_id]['from'])
+ if addrfrom is not None and addrfrom.group(2) in self.domains:
+ self.inc_counter(addrfrom.group(2), 'sent')
+ self.inc_counter(addrfrom.group(2), 'size_sent',
+ self.workdict[line_id]['size'])
+ addrto = re.match("([^@]+)@(.+)", m.group(1))
+ domname = addrto.group(2) if addrto is not None else None
+ if m.group(2) == "sent":
+ self.inc_counter(addrto.group(2), 'recv')
+ self.inc_counter(addrto.group(2), 'size_recv',
+ self.workdict[line_id]['size'])
+ else:
+ self.inc_counter(domname, m.group(2))
+ return
+ self._dprint("Unknown line format: %s" % line_log)
+ return
- m = re.search("to=<([^>]*)>.*status=(\S+)", line_log)
- if m:
- if not line_id in self.workdict:
- if self.debug:
- print "Inconsistent mail (%s: %s), skipping" % (line_id, m.group(1))
- continue
- if not m.group(2) in variables:
- if self.debug:
- print "Unsupported status %s, skipping" % m.group(2)
- continue
+ m = re.match("NOQUEUE: reject: .*from=<(.*)> to=<([^>]*)>", log)
+ if m:
+ addrto = re.match("([^@]+)@(.+)", m.group(2))
+ if addrto and addrto.group(2) in self.domains:
+ self.inc_counter(addrto.group(2), 'reject')
+ return
+ self._dprint("Unknown line format: %s" % log)
- addrfrom = re.match("([^@]+)@(.+)", self.workdict[line_id]['from'])
- if addrfrom is not None and addrfrom.group(2) in self.domains:
- self.inc_counter(addrfrom.group(2), cur_t, 'sent')
- self.inc_counter(addrfrom.group(2), cur_t, 'size_sent',
- self.workdict[line_id]['size'])
- addrto = re.match("([^@]+)@(.+)", m.group(1))
- domname = addrto.group(2) if addrto is not None else None
- if m.group(2) == "sent":
- self.inc_counter(addrto.group(2), cur_t, 'recv')
- self.inc_counter(addrto.group(2), cur_t, 'size_recv',
- self.workdict[line_id]['size'])
- else:
- self.inc_counter(domname, cur_t, m.group(2))
- continue
+ def process(self):
+ """Process the log file.
- if self.debug:
- print "Unknown line format: %s" % line_log
- else:
- m = re.match("NOQUEUE: reject: .*from=<(.*)> to=<([^>]*)>", log)
- if m:
- addrto = re.match("([^@]+)@(.+)", m.group(2))
- if addrto and addrto.group(2) in self.domains:
- self.inc_counter(addrto.group(2), cur_t, 'reject')
- continue
- if self.debug:
- print "Unknown line format: %s" % log
+ We parse it and then generate standard graphics (day, week,
+ month).
+ """
+ for line in self.f.readlines():
+ self._parse_line(line)
# Sort everything by time
G = Grapher()
for dom, data in self.data.iteritems():
- if self.debug:
- print "[rrd] dealing with domain %s" % dom
+ self._dprint("[rrd] dealing with domain %s" % dom)
for t in sorted(data.keys()):
self.update_rrd(dom, t)
From cd5e69853c993242a1ab669a36fd64ffcda5fa9a Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Fri, 24 Jan 2014 09:51:07 +0100
Subject: [PATCH 29/32] Special case for rejected messages.
see #516
---
.../stats/management/commands/logparser.py | 84 +++++++++----------
1 file changed, 41 insertions(+), 43 deletions(-)
diff --git a/modoboa/extensions/stats/management/commands/logparser.py b/modoboa/extensions/stats/management/commands/logparser.py
index eba21090b..aba3633f4 100644
--- a/modoboa/extensions/stats/management/commands/logparser.py
+++ b/modoboa/extensions/stats/management/commands/logparser.py
@@ -275,52 +275,51 @@ class LogParser(object):
return
host, prog, pid, log = m.groups()
m = self._id_expr.match(log)
- if m:
- (line_id, line_log) = m.groups()
- m = re.search("message-id=<([^>]*)>", line_log)
- if m:
- self.workdict[line_id] = {'from': m.group(1), 'size': 0}
- return
- m = re.search("from=<([^>]*)>, size=(\d+)", line_log)
- if m:
- self.workdict[line_id] = {'from': m.group(1),
- 'size': string.atoi(m.group(2))}
- return
-
- m = re.search("to=<([^>]*)>.*status=(\S+)", line_log)
- if m:
- if not line_id in self.workdict:
- self._dprint("Inconsistent mail (%s: %s), skipping" \
- % (line_id, m.group(1)))
- return
- if not m.group(2) in variables:
- self._dprint("Unsupported status %s, skipping" % m.group(2))
- return
-
- addrfrom = re.match("([^@]+)@(.+)", self.workdict[line_id]['from'])
- if addrfrom is not None and addrfrom.group(2) in self.domains:
- self.inc_counter(addrfrom.group(2), 'sent')
- self.inc_counter(addrfrom.group(2), 'size_sent',
- self.workdict[line_id]['size'])
- addrto = re.match("([^@]+)@(.+)", m.group(1))
- domname = addrto.group(2) if addrto is not None else None
- if m.group(2) == "sent":
- self.inc_counter(addrto.group(2), 'recv')
- self.inc_counter(addrto.group(2), 'size_recv',
- self.workdict[line_id]['size'])
- else:
- self.inc_counter(domname, m.group(2))
- return
- self._dprint("Unknown line format: %s" % line_log)
+ if m is None:
+ self._dprint("Unknown line format: %s" % log)
return
-
- m = re.match("NOQUEUE: reject: .*from=<(.*)> to=<([^>]*)>", log)
- if m:
- addrto = re.match("([^@]+)@(.+)", m.group(2))
+ (line_id, line_log) = m.groups()
+ if line_id == "NOQUEUE":
+ self._dprint("NOQUEUE found")
+ addrto = re.search("to=<([^@]+)@([>]+)>", line_log)
if addrto and addrto.group(2) in self.domains:
self.inc_counter(addrto.group(2), 'reject')
return
- self._dprint("Unknown line format: %s" % log)
+ m = re.search("message-id=<([^>]*)>", line_log)
+ if m is not None:
+ self.workdict[line_id] = {'from': m.group(1), 'size': 0}
+ return
+ m = re.search("from=<([^>]*)>, size=(\d+)", line_log)
+ if m is not None:
+ self.workdict[line_id] = {
+ 'from': m.group(1), 'size': string.atoi(m.group(2))
+ }
+ return
+
+ m = re.search("to=<([^>]*)>.*status=(\S+)", line_log)
+ if m is not None:
+ if not line_id in self.workdict:
+ self._dprint("Inconsistent mail (%s: %s), skipping" \
+ % (line_id, m.group(1)))
+ return
+ if not m.group(2) in variables:
+ self._dprint("Unsupported status %s, skipping" % m.group(2))
+ return
+ addrfrom = re.match("([^@]+)@(.+)", self.workdict[line_id]['from'])
+ if addrfrom is not None and addrfrom.group(2) in self.domains:
+ self.inc_counter(addrfrom.group(2), 'sent')
+ self.inc_counter(addrfrom.group(2), 'size_sent',
+ self.workdict[line_id]['size'])
+ addrto = re.match("([^@]+)@(.+)", m.group(1))
+ domname = addrto.group(2) if addrto is not None else None
+ if m.group(2) == "sent":
+ self.inc_counter(addrto.group(2), 'recv')
+ self.inc_counter(addrto.group(2), 'size_recv',
+ self.workdict[line_id]['size'])
+ else:
+ self.inc_counter(domname, m.group(2))
+ return
+ self._dprint("Unknown line format: %s" % line_log)
def process(self):
"""Process the log file.
@@ -331,7 +330,6 @@ class LogParser(object):
for line in self.f.readlines():
self._parse_line(line)
- # Sort everything by time
G = Grapher()
for dom, data in self.data.iteritems():
self._dprint("[rrd] dealing with domain %s" % dom)
From 6a0e82355e7ac1c2c41454eef52304c0dd3ad8b0 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Fri, 24 Jan 2014 10:19:43 +0100
Subject: [PATCH 30/32] Wrong regexp fixed.
see #516
---
modoboa/extensions/stats/management/commands/logparser.py | 7 +++----
1 file changed, 3 insertions(+), 4 deletions(-)
diff --git a/modoboa/extensions/stats/management/commands/logparser.py b/modoboa/extensions/stats/management/commands/logparser.py
index aba3633f4..d371cd976 100644
--- a/modoboa/extensions/stats/management/commands/logparser.py
+++ b/modoboa/extensions/stats/management/commands/logparser.py
@@ -280,10 +280,9 @@ class LogParser(object):
return
(line_id, line_log) = m.groups()
if line_id == "NOQUEUE":
- self._dprint("NOQUEUE found")
- addrto = re.search("to=<([^@]+)@([>]+)>", line_log)
- if addrto and addrto.group(2) in self.domains:
- self.inc_counter(addrto.group(2), 'reject')
+ m = re.match("reject: .*from=<.*> to=<[^@]+@([^>]+)>", line_log)
+ if addrto and addrto.group(1) in self.domains:
+ self.inc_counter(addrto.group(1), 'reject')
return
m = re.search("message-id=<([^>]*)>", line_log)
if m is not None:
From 71ddb0837bc8aeffa2cb309d60faa437412fb500 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Fri, 24 Jan 2014 10:21:16 +0100
Subject: [PATCH 31/32] Try to find the dovecot binary in more places.
see #510
---
doc/integration/imap_and_smtp.rst | 9 +++++++++
modoboa/core/commands/templates/settings.py.tpl | 2 ++
modoboa/extensions/admin/app_settings.py | 6 +++++-
3 files changed, 16 insertions(+), 1 deletion(-)
diff --git a/doc/integration/imap_and_smtp.rst b/doc/integration/imap_and_smtp.rst
index 2ab61583d..ded944f66 100644
--- a/doc/integration/imap_and_smtp.rst
+++ b/doc/integration/imap_and_smtp.rst
@@ -55,6 +55,15 @@ For dovecot 2.0 and older, use the `autocreate
Operations on the file system
-----------------------------
+.. warning::
+
+ Modoboa needs to access the ``dovecot`` binary to check its
+ version. To find the binary path, we use the ``which`` command
+ first and then try known locations (:file:`/usr/sbin/dovecot` and
+ :file:`/usr/local/sbin/dovecot`). If you installed dovecot in a
+ custom location, please tell us where the binary is by using the
+ ``DOVECOT_LOOKUP_PATH`` setting (see :file:`settings.py`).
+
Three operation types are considered:
#. Mailbox creation
diff --git a/modoboa/core/commands/templates/settings.py.tpl b/modoboa/core/commands/templates/settings.py.tpl
index b7f36115f..87b8caa88 100644
--- a/modoboa/core/commands/templates/settings.py.tpl
+++ b/modoboa/core/commands/templates/settings.py.tpl
@@ -172,6 +172,8 @@ SOUTH_TESTS_MIGRATE = False
#MODOBOA_CUSTOM_LOGO = os.path.join(MEDIA_URL, "custom_logo.png")
+#DOVECOT_LOOKUP_PATH = ('/path/to/dovecot', )
+
AUTHENTICATION_BACKENDS = (
'modoboa.lib.authbackends.SimpleBackend',
)
diff --git a/modoboa/extensions/admin/app_settings.py b/modoboa/extensions/admin/app_settings.py
index c35a9fab2..8daebb4ef 100644
--- a/modoboa/extensions/admin/app_settings.py
+++ b/modoboa/extensions/admin/app_settings.py
@@ -1,4 +1,5 @@
from django import forms
+from django.conf import settings
from django.utils.translation import ugettext_lazy
from modoboa.lib.formutils import YesNoField, SeparatorField
from modoboa.lib.sysutils import exec_cmd
@@ -49,10 +50,13 @@ class AdminParametersForm(parameters.AdminParametersForm):
hide_fields = False
dpath = None
code, output = exec_cmd("which dovecot")
- known_paths = ("/usr/sbin/dovecot", "/usr/local/sbin/dovecot")
if not code:
dpath = output.strip()
else:
+ known_paths = getattr(
+ settings, "DOVECOT_LOOKUP_PATH",
+ ("/usr/sbin/dovecot", "/usr/local/sbin/dovecot")
+ )
for fpath in known_paths:
if os.path.isfile(fpath) and os.access(fpath, os.X_OK):
dpath = fpath
From 485b2a0dd00ce80f0c8b541bcc66a42d5d7f2723 Mon Sep 17 00:00:00 2001
From: Antoine Nguyen
Date: Fri, 24 Jan 2014 10:55:16 +0100
Subject: [PATCH 32/32] Wrong variable name.
see #516
---
modoboa/extensions/stats/management/commands/logparser.py | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/modoboa/extensions/stats/management/commands/logparser.py b/modoboa/extensions/stats/management/commands/logparser.py
index d371cd976..cbcfcb03e 100644
--- a/modoboa/extensions/stats/management/commands/logparser.py
+++ b/modoboa/extensions/stats/management/commands/logparser.py
@@ -280,7 +280,7 @@ class LogParser(object):
return
(line_id, line_log) = m.groups()
if line_id == "NOQUEUE":
- m = re.match("reject: .*from=<.*> to=<[^@]+@([^>]+)>", line_log)
+ addrto = re.match("reject: .*from=<.*> to=<[^@]+@([^>]+)>", line_log)
if addrto and addrto.group(1) in self.domains:
self.inc_counter(addrto.group(1), 'reject')
return