Added mailbox file and activate the auto subscribe

This commit is contained in:
Spitap
2025-10-31 16:36:08 +01:00
parent 0e64b92199
commit 46d7c6acca
2 changed files with 167 additions and 45 deletions

View File

@@ -23,10 +23,9 @@ class Dovecot(base.Installer):
"dovecot-imapd",
"dovecot-lmtpd",
"dovecot-managesieved",
"dovecot-sieve"
"dovecot-sieve",
],
"rpm": [
"dovecot", "dovecot-pigeonhole"]
"rpm": ["dovecot", "dovecot-pigeonhole"],
}
per_version_config_files = {
"2.3": [
@@ -44,9 +43,10 @@ class Dovecot(base.Installer):
"conf.d/10-master.conf",
"conf.d/10-ssl.conf",
"conf.d/10-ssl-keys.try",
"conf.d/15-mailboxes",
"conf.d/20-lmtp.conf",
"conf.d/auth-oauth2.conf.ext",
]
],
}
with_user = True
@@ -73,7 +73,7 @@ class Dovecot(base.Installer):
else:
files += [
f"dovecot-sql-{self.dbengine}.conf.ext=dovecot-sql.conf.ext",
f"dovecot-sql-master-{self.dbengine}.conf.ext=dovecot-sql-master.conf.ext"
f"dovecot-sql-master-{self.dbengine}.conf.ext=dovecot-sql-master.conf.ext",
]
result = []
for path in files:
@@ -107,7 +107,9 @@ class Dovecot(base.Installer):
packages += super().get_packages()
backports_codename = getattr(self, "backports_codename", None)
if backports_codename:
packages = [f"{package}/{backports_codename}-backports" for package in packages]
packages = [
f"{package}/{backports_codename}-backports" for package in packages
]
return packages
def install_packages(self):
@@ -118,7 +120,8 @@ class Dovecot(base.Installer):
package.backend.enable_backports("bookworm")
self.backports_codename = "bookworm"
package.backend.preconfigure(
"dovecot-core", "create-ssl-cert", "boolean", "false")
"dovecot-core", "create-ssl-cert", "boolean", "false"
)
super().install_packages()
def get_template_context(self):
@@ -127,11 +130,17 @@ class Dovecot(base.Installer):
pw_mailbox = pwd.getpwnam(self.mailboxes_owner)
dovecot_package = {"deb": "dovecot-core", "rpm": "dovecot"}
ssl_protocol_parameter = "ssl_protocols"
if package.backend.get_installed_version(dovecot_package[package.backend.FORMAT]) > "2.3":
if (
package.backend.get_installed_version(
dovecot_package[package.backend.FORMAT]
)
> "2.3"
):
ssl_protocol_parameter = "ssl_min_protocol"
ssl_protocols = "!SSLv2 !SSLv3"
if package.backend.get_installed_version("openssl").startswith("1.1") \
or package.backend.get_installed_version("openssl").startswith("3"):
if package.backend.get_installed_version("openssl").startswith(
"1.1"
) or package.backend.get_installed_version("openssl").startswith("3"):
ssl_protocols = "!SSLv3"
if ssl_protocol_parameter == "ssl_min_protocol":
ssl_protocols = "TLSv1.2"
@@ -145,31 +154,38 @@ class Dovecot(base.Installer):
protocols = ""
oauth2_client_id, oauth2_client_secret = utils.create_oauth2_app(
"Dovecot", "dovecot", self.config)
"Dovecot", "dovecot", self.config
)
hostname = self.config.get("general", "hostname")
oauth2_introspection_url = (
f"https://{oauth2_client_id}:{oauth2_client_secret}"
f"@{hostname}/api/o/introspect/"
)
context.update({
"db_driver": self.db_driver,
"mailboxes_owner_uid": pw_mailbox[2],
"mailboxes_owner_gid": pw_mailbox[3],
"mailbox_owner": self.mailboxes_owner,
"modoboa_user": self.config.get("modoboa", "user"),
"modoboa_dbname": self.config.get("modoboa", "dbname"),
"modoboa_dbuser": self.config.get("modoboa", "dbuser"),
"modoboa_dbpassword": self.config.get("modoboa", "dbpassword"),
"protocols": protocols,
"ssl_protocols": ssl_protocols,
"ssl_protocol_parameter": ssl_protocol_parameter,
"modoboa_2_2_or_greater": "" if self.modoboa_2_2_or_greater else "#",
"not_modoboa_2_2_or_greater": "" if not self.modoboa_2_2_or_greater else "#",
"do_move_spam_to_junk": "" if self.app_config["move_spam_to_junk"] else "#",
"oauth2_introspection_url": oauth2_introspection_url,
"radicale_user": self.config.get("radicale", "user"),
})
context.update(
{
"db_driver": self.db_driver,
"mailboxes_owner_uid": pw_mailbox[2],
"mailboxes_owner_gid": pw_mailbox[3],
"mailbox_owner": self.mailboxes_owner,
"modoboa_user": self.config.get("modoboa", "user"),
"modoboa_dbname": self.config.get("modoboa", "dbname"),
"modoboa_dbuser": self.config.get("modoboa", "dbuser"),
"modoboa_dbpassword": self.config.get("modoboa", "dbpassword"),
"protocols": protocols,
"ssl_protocols": ssl_protocols,
"ssl_protocol_parameter": ssl_protocol_parameter,
"modoboa_2_2_or_greater": "" if self.modoboa_2_2_or_greater else "#",
"not_modoboa_2_2_or_greater": (
"" if not self.modoboa_2_2_or_greater else "#"
),
"do_move_spam_to_junk": (
"" if self.app_config["move_spam_to_junk"] else "#"
),
"oauth2_introspection_url": oauth2_introspection_url,
"radicale_user": self.config.get("radicale", "user"),
}
)
return context
def install_config_files(self):
@@ -177,10 +193,14 @@ class Dovecot(base.Installer):
if self.app_config["move_spam_to_junk"]:
utils.mkdir_safe(
f"{self.config_dir}/conf.d/custom_after_sieve",
stat.S_IRWXU | stat.S_IRGRP | stat.S_IXGRP |
stat.S_IROTH | stat.S_IXOTH,
0, 0
)
stat.S_IRWXU
| stat.S_IRGRP
| stat.S_IXGRP
| stat.S_IROTH
| stat.S_IXOTH,
0,
0,
)
super().install_config_files()
def post_run(self):
@@ -191,12 +211,16 @@ class Dovecot(base.Installer):
dbpassword = self.config.get("modoboa", "dbpassword")
backend = database.get_backend(self.config)
backend.load_sql_file(
dbname, dbuser, dbpassword,
self.get_file_path("install_modoboa_postgres_trigger.sql")
dbname,
dbuser,
dbpassword,
self.get_file_path("install_modoboa_postgres_trigger.sql"),
)
backend.load_sql_file(
dbname, dbuser, dbpassword,
self.get_file_path("fix_modoboa_postgres_schema.sql")
dbname,
dbuser,
dbpassword,
self.get_file_path("fix_modoboa_postgres_schema.sql"),
)
for f in glob.glob(f"{self.get_file_path(f'{self.version}/conf.d')}/*"):
if os.path.isfile(f):
@@ -210,9 +234,11 @@ class Dovecot(base.Installer):
# See https://github.com/modoboa/modoboa/issues/2157.
if self.app_config["move_spam_to_junk"]:
# Compile sieve script
sieve_file = f"{self.config_dir}/conf.d/custom_after_sieve/spam-to-junk.sieve"
sieve_file = (
f"{self.config_dir}/conf.d/custom_after_sieve/spam-to-junk.sieve"
)
utils.exec_cmd(f"/usr/bin/sievec {sieve_file}")
system.add_user_to_group(self.mailboxes_owner, 'dovecot')
system.add_user_to_group(self.mailboxes_owner, "dovecot")
def restart_daemon(self):
"""Restart daemon process.
@@ -226,7 +252,8 @@ class Dovecot(base.Installer):
action = "start" if code else "restart"
utils.exec_cmd(
"service {} {} > /dev/null 2>&1".format(self.appname, action),
capture_output=False)
capture_output=False,
)
system.enable_service(self.get_daemon_name())
def backup(self, path):
@@ -234,8 +261,10 @@ class Dovecot(base.Installer):
home_dir = self.config.get("dovecot", "home_dir")
utils.printcolor("Backing up mails", utils.MAGENTA)
if not os.path.exists(home_dir) or os.path.isfile(home_dir):
utils.error("Error backing up emails, provided path "
f" ({home_dir}) seems not right...")
utils.error(
"Error backing up emails, provided path "
f" ({home_dir}) seems not right..."
)
return
dst = os.path.join(path, "mails/")
@@ -257,10 +286,13 @@ class Dovecot(base.Installer):
for dirpath, dirnames, filenames in os.walk(home_dir):
shutil.chown(dirpath, self.mailboxes_owner, self.mailboxes_owner)
for filename in filenames:
shutil.chown(os.path.join(dirpath, filename),
self.mailboxes_owner, self.mailboxes_owner)
shutil.chown(
os.path.join(dirpath, filename),
self.mailboxes_owner,
self.mailboxes_owner,
)
else:
utils.printcolor(
"It seems that emails were not backed up, skipping restoration.",
utils.MAGENTA
utils.MAGENTA,
)

View File

@@ -0,0 +1,90 @@
##
## Mailbox definitions
##
# Each mailbox is specified in a separate mailbox section. The section name
# specifies the mailbox name. If it has spaces, you can put the name
# "in quotes". These sections can contain the following mailbox settings:
#
# auto:
# Indicates whether the mailbox with this name is automatically created
# implicitly when it is first accessed. The user can also be automatically
# subscribed to the mailbox after creation. The following values are
# defined for this setting:
#
# no - Never created automatically.
# create - Automatically created, but no automatic subscription.
# subscribe - Automatically created and subscribed.
#
# special_use:
# A space-separated list of SPECIAL-USE flags (RFC 6154) to use for the
# mailbox. There are no validity checks, so you could specify anything
# you want in here, but it's not a good idea to use flags other than the
# standard ones specified in the RFC:
#
# \All - This (virtual) mailbox presents all messages in the
# user's message store.
# \Archive - This mailbox is used to archive messages.
# \Drafts - This mailbox is used to hold draft messages.
# \Flagged - This (virtual) mailbox presents all messages in the
# user's message store marked with the IMAP \Flagged flag.
# \Important - This (virtual) mailbox presents all messages in the
# user's message store deemed important to user.
# \Junk - This mailbox is where messages deemed to be junk mail
# are held.
# \Sent - This mailbox is used to hold copies of messages that
# have been sent.
# \Trash - This mailbox is used to hold messages that have been
# deleted.
#
# comment:
# Defines a default comment or note associated with the mailbox. This
# value is accessible through the IMAP METADATA mailbox entries
# "/shared/comment" and "/private/comment". Users with sufficient
# privileges can override the default value for entries with a custom
# value.
# NOTE: Assumes "namespace inbox" has been defined in 10-mail.conf.
namespace inbox {
# These mailboxes are widely used and could perhaps be created automatically:
mailbox Drafts {
auto = subscribe
special_use = \Drafts
}
mailbox Junk {
auto = subscribe
special_use = \Junk
}
mailbox Trash {
auto = subscribe
special_use = \Trash
}
# For \Sent mailboxes there are two widely used names. We'll mark both of
# them as \Sent. User typically deletes one of them if duplicates are created.
mailbox Sent {
auto = subscribe
special_use = \Sent
}
# mailbox "Sent Messages" {
# special_use = \Sent
# }
# If you have a virtual "All messages" mailbox:
#mailbox virtual/All {
# special_use = \All
# comment = All my messages
#}
# If you have a virtual "Flagged" mailbox:
#mailbox virtual/Flagged {
# special_use = \Flagged
# comment = All my flagged messages
#}
# If you have a virtual "Important" mailbox:
#mailbox virtual/Important {
# special_use = \Important
# comment = All my important messages
#}
}