===== Poczta ===== Poczta oparta na systemie Debian z Postfix, Dovecot, MySQL i Roundcube. Protokoły SMTP, IMAP, POP3 - szyfrowane. Webmail wraz z filtrowaniem wiadomości, regułami oraz autoresponderem. ==== Wstęp ==== Wszędzie gdzie pojawia się fraza domain.ltd należy zastąpić swoją domeną. Instalujemy czystego Debiana 10 (Serwer SSH i Podstawowe narzędzia systemowe). Jeśli system postawiliśmy na maszynie wirtualnej to proszę dodać taki oto wpis do pliku /etc/sysctl.conf: net.ipv4.tcp_window_scaling = 0 Oraz przeładować ustawienia kernela: sysctl -p Uaktualnienie systemu: apt update apt upgrade Instalujemy pakiety opcjonalnie (ułatwią pracę): apt install aptitude mc unzip mailutils net-tools ntp Plik /etc/hosts powinien mieć wpis z naszą domeną: 127.0.0.1 localhost 127.0.0.1 domain 127.0.0.1 domain.ltd # The following lines are desirable for IPv6 capable hosts ::1 localhost ip6-localhost ip6-loopback ff02::1 ip6-allnodes ff02::2 ip6-allrouters ==== Certyfikat SSL ==== Ważnym elementem jest szyfrowanie komunikacji między serwerem, a klientem - do tego jest wymagany certyfikat SSL. Certyfikat możemy uzyskać na trzy sposoby: * wygenerować sobie samemu - wadą takiego rozwiązania jest to, że przeglądarka internetowa oraz klient poczty będzie ostrzegał, że certyfikat nie jest podpisany przez zaufaną instytucję - nie polecam * uzyskanie darmowego certyfikatu Let's Encrypt - wadą takiego rozwiązania jest to, że trzeba go odnawiać raz na trzy miesiące - da radę to zautomatyzować, jeśli nie możecie sobie poradzić z certbotem to tu możecie wygenerować sobie za free: [[https://www.sslforfree.com]] * kupienie certyfikatu My dla tutejszego przykładu wygenerujemy sobie certyfikat SSL - natomiast wam zalecam uzyskanie certyfikatu Let's Encrypt lub kupno. cd /etc/ssl/private/ openssl req -new -x509 -nodes -newkey rsa:4096 -keyout ssl.key -out ssl.crt -days 3600 chmod 400 ssl.key chmod 444 ssl.crt ==== Instalacja niezbędnych pakietów ==== Podczas instalacji zostaniemy zapytani w sprawie konfiguracji Posfixa - wybieramy: brak konfiguracji. apt install postfix postfix-mysql postfix-pcre postgrey dovecot-core dovecot-imapd dovecot-pop3d dovecot-lmtpd dovecot-mysql dovecot-sieve dovecot-managesieved mariadb-server mariadb-client ==== MySQL ==== Ustawiamy hasło dla roota, usuwamy zdalny dostęp dla roota, usuwamy użytkownika anonimowego oraz testową bazę danych: root@mars:/etc/ssl/private# mysql_secure_installation NOTE: RUNNING ALL PARTS OF THIS SCRIPT IS RECOMMENDED FOR ALL MariaDB SERVERS IN PRODUCTION USE! PLEASE READ EACH STEP CAREFULLY! In order to log into MariaDB to secure it, we'll need the current password for the root user. If you've just installed MariaDB, and you haven't set the root password yet, the password will be blank, so you should just press enter here. Enter current password for root (enter for none): OK, successfully used password, moving on... Setting the root password ensures that nobody can log into the MariaDB root user without the proper authorisation. Set root password? [Y/n] New password: Re-enter new password: Password updated successfully! Reloading privilege tables.. ... Success! By default, a MariaDB installation has an anonymous user, allowing anyone to log into MariaDB without having to have a user account created for them. This is intended only for testing, and to make the installation go a bit smoother. You should remove them before moving into a production environment. Remove anonymous users? [Y/n] ... Success! Normally, root should only be allowed to connect from 'localhost'. This ensures that someone cannot guess at the root password from the network. Disallow root login remotely? [Y/n] ... Success! By default, MariaDB comes with a database named 'test' that anyone can access. This is also intended only for testing, and should be removed before moving into a production environment. Remove test database and access to it? [Y/n] - Dropping test database... ... Success! - Removing privileges on test database... ... Success! Reloading the privilege tables will ensure that all changes made so far will take effect immediately. Reload privilege tables now? [Y/n] ... Success! Cleaning up... All done! If you've completed all of the above steps, your MariaDB installation should now be secure. Thanks for using MariaDB! Dodajemy bazę i ustawiamy uprawnienia: root@mars:/etc/ssl/private# mysqladmin create postfix root@mars:/etc/ssl/private# mysql Welcome to the MariaDB monitor. Commands end with ; or \g. Your MariaDB connection id is 59 Server version: 10.3.25-MariaDB-0+deb10u1 Debian 10 Copyright (c) 2000, 2018, Oracle, MariaDB Corporation Ab and others. Type 'help;' or '\h' for help. Type '\c' to clear the current input statement. MariaDB [(none)]> GRANT SELECT ON postfix.* TO 'postfix'@'127.0.0.1' IDENTIFIED BY 'tajnehaslo'; Query OK, 0 rows affected (0.000 sec) MariaDB [(none)]> FLUSH PRIVILEGES; Query OK, 0 rows affected (0.000 sec) MariaDB [(none)]> \q Bye Zapisujemy schemat bazy danych do pliku /root/postfix.sql: CREATE TABLE virtual_aliases ( id int(11) NOT NULL AUTO_INCREMENT, source varchar(128) NOT NULL, destination varchar(128) NOT NULL, PRIMARY KEY (id) ); CREATE TABLE virtual_domains ( id int(11) NOT NULL AUTO_INCREMENT, name varchar(64) NOT NULL, PRIMARY KEY (id) ); CREATE TABLE virtual_users ( id int(11) NOT NULL AUTO_INCREMENT, email varchar(128) NOT NULL, password varchar(128) NOT NULL, quota int(11) NOT NULL DEFAULT '1024' COMMENT 'Quota in megabytes', active tinyint(1) NOT NULL DEFAULT '1', PRIMARY KEY (id) ); CREATE TABLE virtual_black_white_list ( id int(11) NOT NULL AUTO_INCREMENT, source varchar(32) NOT NULL UNIQUE COMMENT 'Domain or IP address', access enum('OK','REJECT') NOT NULL COMMENT 'OK or REJECT', reason varchar(128) NOT NULL DEFAULT '', `type` enum('IP','EMAIL') NOT NULL, PRIMARY KEY (id) ); Tworzymy tabele na bazie danych: mysql postfix < /root/postfix.sql Dodanie obsługiwanej domeny: mysql -e "INSERT INTO virtual_domains (name) VALUES ('domain.ltd');" postfix Dodanie konta email (domyślnie jest aktywne oraz ma pojemność 1GB): mysql -e "INSERT INTO virtual_users (email, password) VALUES ('user@domain.ltd', ENCRYPT('haslo'));" postfix Dodanie aliasu: mysql -e "INSERT INTO virtual_aliases (source, destination) VALUES ('alias@domain.ltd', 'user@domain.ltd');" postfix Blokada wcześniej założonej skrzynki: mysql -e "UPDATE virtual_users SET active = 0 WHERE email = 'user@domain.ltd';" postfix Odblokowanie skrzynki: mysql -e "UPDATE virtual_users SET active = 1 WHERE email = 'user@domain.ltd';" postfix Zmiana pojemności skrzynki na 2GB: mysql -e "UPDATE virtual_users SET quota = 2048 WHERE email = 'user@domain.ltd';" postfix Zmiana hasła dla skrzynki: mysql -e "UPDATE virtual_users SET password = ENCRYPT('nowehaslo' WHERE email = 'user@domain.ltd';" postfix Dodanie do białej listy domeny: INSERT INTO virtual_black_white_list (source, access, type) VALUES ('wp.pl', 'OK', 'EMAIL'); Dodanie do czarnej listy domeny: INSERT INTO virtual_black_white_list (source, access, reason, type) VALUES ('spamers.ltd', 'REJECT', 'Your domain is in black list.', 'EMAIL'); Dodanie adresu IP do białej listy: INSERT INTO virtual_black_white_list (source, access, type) VALUES ('1.2.3.4', 'OK', 'IP'); Dodanie adresu IP do czarnej listy: INSERT INTO virtual_black_white_list (source, access, reason, type) VALUES ('2.3.4.5', 'REJECT', 'Your IP addressis in black list.', 'IP'); Domeny do białej/czarnej listy możemy definiować w następujący sposób: * user@domain - adres email * domain.ltd - cała domena * .domain.tld - wszystkie subdomeny w danej domenie * user@ - użytkownik we wszystkich domenach Adresy IP definiujemy wg schematy CIDR. Dokumentacja: [[http://www.postfix.org/access.5.html]] Możemy zarządzać bazą danych aplikacją napisaną pod w/w strukturę tabel: [[https://gitlab.com/kmroczkowski/mailcp]] ==== Użytkownik skrzynek pocztowych ==== Katalogi skrzynek będą przechowywane z uprawnieniami użytkownika do obsługi skrzynek pocztowych, w naszym przypadku to będzie użytkownik vmail: /sbin/groupadd -g 5000 vmail /sbin/useradd -g vmail -u 5000 vmail -d /var/mail -s /bin/false chown -R vmail:vmail /var/mail chmod 750 /var/mail mkdir /var/mail/vhosts chown vmail:dovecot /var/mail/vhosts chmod g+w /var/mail/vhosts ==== Postfix ==== Jeśli mamy swoją konfigurację już na serwerze to robimy backup plików postfixa: cp /etc/postfix/main.cf /etc/postfix/main.cf.bak cp /etc/postfix/master.cf /etc/postfix/master.cf.bak /etc/init.d/postfix stop Linki symboliczne do logów (opcjonalne): ln -s /var/log /etc/postfix/logs ln -s /var/mail/vhosts /etc/postfix/vhosts W pliku /etc/mailname wpisujemy naszą domenę, którą będzie przedstawiał się Postfix: domain.ltd Konfiguracja w pliku /etc/postfix/main.cf (należy wyszukać frazę domain.ltd i zastąpić swoją domeną): smtpd_banner = $myhostname ESMTP $mail_name (Debian/GNU) biff = no append_dot_mydomain = no readme_directory = no compatibility_level = 2 # TLS parameters smtpd_tls_auth_only = yes smtpd_sasl_security_options = noanonymous smtpd_sasl_tls_security_options = noanonymous smtpd_tls_cert_file=/etc/ssl/private/ssl.crt smtpd_tls_key_file=/etc/ssl/private/ssl.key smtp_tls_CAfile = /etc/ssl/certs/ca-certificates.crt smtpd_use_tls=yes smtpd_tls_session_cache_database = btree:${data_directory}/smtpd_scache smtp_tls_session_cache_database = btree:${data_directory}/smtp_scache smtp_tls_security_level = may smtpd_tls_security_level = may smtpd_tls_mandatory_ciphers = high tls_high_cipherlist=EDH+CAMELLIA:EDH+aRSA:EECDH+aRSA+AESGCM:EECDH+aRSA+SHA384:EECDH+aRSA+SHA256:EECDH:+CAMELLIA256:+AES256:+CAMELLIA128:+AES128:+SSLv3:!aNULL:!eNULL:!LOW:!3DES:!MD5:!EXP:!PSK:!DSS:!RC4:!SEED:!ECDSA:CAMELLIA256-SHA:AES256-SHA:CAMELLIA128-SHA:AES128-SHA smtpd_tls_mandatory_protocols = !SSLv2, !SSLv3 smtpd_tls_loglevel = 1 smtp_tls_loglevel = 1 smtpd_sasl_type = dovecot smtpd_sasl_path = private/auth smtpd_sasl_auth_enable = yes myhostname = domain.ltd alias_maps = hash:/etc/aliases alias_database = hash:/etc/aliases myorigin = $myhostname mydomain = $myhostname mydestination = localhost relayhost = mynetworks = 127.0.0.0/8 [::ffff:127.0.0.0]/104 [::1]/128 mailbox_size_limit = 0 #zalaczniki 100MB message_size_limit = 102400000 recipient_delimiter = + inet_interfaces = all inet_protocols = all smtpd_sender_login_maps = mysql:/etc/postfix/mysql-virtual-sender-login-maps.cf smtpd_recipient_restrictions = check_policy_service inet:127.0.0.1:12340, permit_sasl_authenticated, permit_mynetworks, reject_unauth_destination, check_client_access mysql:/etc/postfix/mysql-virtual-access-ip.cf, check_sender_access mysql:/etc/postfix/mysql-virtual-access-email.cf, reject_non_fqdn_hostname, reject_non_fqdn_sender, reject_non_fqdn_recipient, reject_unauth_pipelining, reject_invalid_hostname, reject_rbl_client sbl.spamhaus.org, reject_rbl_client bl.spamcop.net, reject_rbl_client cbl.abuseat.org, # reject_rbl_client dnsbl.sorbs.net, #ostatnio maile z gmail wpadały do tej spamlisty - tymczasowo wyłączyłem u siebie reject_rbl_client zen.spamhaus.org, check_policy_service inet:127.0.0.1:10023 smtpd_helo_restrictions = permit_mynetworks, permit_sasl_authenticated, reject_invalid_helo_hostname, reject_non_fqdn_helo_hostname smtpd_sender_restrictions = permit_mynetworks, permit_sasl_authenticated, reject_non_fqdn_sender # reject_unknown_sender_domain #dla domen nie istniejących np na serwerach swoich smtpd_relay_restrictions = permit_mynetworks, permit_sasl_authenticated, defer_unauth_destination mime_header_checks = pcre:/etc/postfix/mime_header_checks.pcre # Even more Restrictions and MTA params disable_vrfy_command = yes strict_rfc821_envelopes = yes smtpd_delay_reject = yes smtpd_helo_required = yes smtp_always_send_ehlo = yes #smtpd_hard_error_limit = 1 smtpd_timeout = 30s smtp_helo_timeout = 15s smtp_rcpt_timeout = 15s smtpd_recipient_limit = 40 minimal_backoff_time = 180s maximal_backoff_time = 3h relay_domains = mailbox_command = smtpd_sasl_local_domain = $myhostname smtpd_sasl_auth_enable = yes broken_sasl_auth_clients = yes smtputf8_enable = no # Reply Rejection Codes invalid_hostname_reject_code = 550 non_fqdn_reject_code = 550 unknown_address_reject_code = 550 unknown_client_reject_code = 550 unknown_hostname_reject_code = 550 unverified_recipient_reject_code = 550 unverified_sender_reject_code = 550 # Handing off local delivery to Dovecot's LMTP, and telling it where to store mail virtual_transport = lmtp:unix:private/dovecot-lmtp # Virtual domains, users, and aliases virtual_mailbox_domains = mysql:/etc/postfix/mysql-virtual-mailbox-domains.cf virtual_mailbox_maps = mysql:/etc/postfix/mysql-virtual-mailbox-maps.cf virtual_alias_maps = mysql:/etc/postfix/mysql-virtual-alias-maps.cf, mysql:/etc/postfix/mysql-virtual-email2email.cf maximal_queue_lifetime = 1d bounce_queue_lifetime = 1d Tworzymy plik /etc/postfix/mime_header_checks.pcre i uzupełniamy: /^Content-(Disposition|Type).*name\s*\*?=\s*"?([^;]*(\.|=2E)( app|bat|chm|cmd|com|cpl|diagcab|dll|exe|fxp|gadget|grp| hlp|hpj|hta|htc|inf|ins|img|iso|isp|its|jar|jnlp|js|jse| ksh|lnk|mad|maf|mag|mam|maq|mar|mas|mat|mau|mav|maw|mcf| mda|mdw|mdz|msc|msh|msh1|msh2|mshxml|msh1xml|msh2xml|msi| msp|mst|msu|ops|osd|pcd|pif|plg|prf|prg|printerexport| ps1|ps1xml|ps2|ps2xml|psc1|psc2|psd1|psdm1|py|pyc|pyo| pyw|pyz|pyzw|reg|scf|scr|sct|shb|shs|theme|tmp|url|vb| vbe|vbp|vbs|vhd|vhdx|vsmacros|vsw|webpnp|website|ws|wsc| wsf|wsh|xbap|xll|xnk))(\?=)?"?\s*(;|$)/x REJECT Attachment of type $2 not accepted Tworzymy plik /etc/postfix/mysql-virtual-mailbox-domains.cf i uzupełniamy: user = postfix password = tajnehaslo hosts = 127.0.0.1 dbname = postfix query = SELECT 1 FROM virtual_domains WHERE name='%s' Tworzymy plik /etc/postfix/mysql-virtual-mailbox-maps.cf i uzupełniamy: user = postfix password = tajnehaslo hosts = 127.0.0.1 dbname = postfix query = SELECT 1 FROM virtual_users WHERE email='%s' Tworzymy plik /etc/postfix/mysql-virtual-alias-maps.cf i uzupełniamy: user = postfix password = tajnehaslo hosts = 127.0.0.1 dbname = postfix query = SELECT destination FROM virtual_aliases WHERE source='%s' Tworzymy plik /etc/postfix/mysql-virtual-email2email.cf i uzupełniamy: user = postfix password = tajnehaslo hosts = 127.0.0.1 dbname = postfix query = SELECT email FROM virtual_users WHERE email='%s' Tworzymy plik /etc/postfix/mysql-virtual-access-ip.cf i uzupełniamy: user = postfix password = tajnehaslo hosts = 127.0.0.1 dbname = postfix query = SELECT CONCAT(access, IF(reason != '', CONCAT(' ', reason), '')) AS address FROM virtual_black_white_list WHERE source='%s' AND type = 'IP' Tworzymy plik /etc/postfix/mysql-virtual-access-email.cf i uzupełniamy: user = postfix password = tajnehaslo hosts = 127.0.0.1 dbname = postfix query = SELECT CONCAT(access, IF(reason != '', CONCAT(' ', reason), '')) AS address FROM virtual_black_white_list WHERE source='%s' AND type = 'EMAIL' Tworzymy plik /etc/postfix/mysql-virtual-sender-login-maps.cf i uzupełniamy: user = postfix password = tajnehaslo hosts = 127.0.0.1 dbname = postfix query = SELECT email FROM virtual_users WHERE email = '%s' UNION SELECT destination FROM virtual_aliases WHERE source = '%s' Modyfikujemy plik /etc/postfix/master.cf: smtp inet n - n - - smtpd submission inet n - y - - smtpd -o syslog_name=postfix/submission -o smtpd_tls_security_level=encrypt -o smtpd_sasl_auth_enable=yes -o smtpd_sasl_type=dovecot -o smtpd_sasl_path=private/auth -o smtpd_reject_unlisted_recipient=no -o smtpd_client_restrictions=permit_sasl_authenticated,reject -o milter_macro_daemon_name=ORIGINATING# -o smtpd_reject_unlisted_recipient=no smtps inet n - y - - smtpd -o syslog_name=postfix/smtps -o smtpd_tls_wrappermode=yes -o smtpd_sasl_auth_enable=yes -o smtpd_sasl_type=dovecot -o smtpd_sasl_path=private/auth -o smtpd_client_restrictions=permit_sasl_authenticated,reject -o milter_macro_daemon_name=ORIGINATING pickup unix n - y 60 1 pickup cleanup unix n - y - 0 cleanup qmgr unix n - n 300 1 qmgr tlsmgr unix - - y 1000? 1 tlsmgr rewrite unix - - y - - trivial-rewrite bounce unix - - y - 0 bounce defer unix - - y - 0 bounce trace unix - - y - 0 bounce verify unix - - y - 1 verify flush unix n - y 1000? 0 flush proxymap unix - - n - - proxymap proxywrite unix - - n - 1 proxymap smtp unix - - y - - smtp relay unix - - y - - smtp showq unix n - y - - showq error unix - - y - - error retry unix - - y - - error discard unix - - y - - discard local unix - n n - - local virtual unix - n n - - virtual lmtp unix - - y - - lmtp anvil unix - - y - 1 anvil scache unix - - y - 1 scache maildrop unix - n n - - pipe flags=DRhu user=vmail argv=/usr/bin/maildrop -d ${recipient} uucp unix - n n - - pipe flags=Fqhu user=uucp argv=uux -r -n -z -a$sender - $nexthop!rmail ($recipient) ifmail unix - n n - - pipe flags=F user=ftn argv=/usr/lib/ifmail/ifmail -r $nexthop ($recipient) bsmtp unix - n n - - pipe flags=Fq. user=bsmtp argv=/usr/lib/bsmtp/bsmtp -t$nexthop -f$sender $recipient scalemail-backend unix - n n - 2 pipe flags=R user=scalemail argv=/usr/lib/scalemail/bin/scalemail-store ${nexthop} ${user} ${extension} mailman unix - n n - - pipe flags=FR user=list argv=/usr/lib/mailman/bin/postfix-to-mailman.py ${nexthop} ${user} Uprawnienia: chmod -R o-rwx /etc/postfix chmod 755 /etc/postfix chmod 644 /etc/postfix/dynamicmaps.cf chmod 644 /etc/postfix/main.cf Aliasy. W pliku /etc/aliases edytujemy i ustawiamy wpis: ... root: naszemail@domain.ltd Aktualizujemy bazę aliasów: newaliases Restart Postfixa: systemctl restart postfix ==== Dovecot ==== Jeśli mamy swoją konfigurację już na serwerze to robimy backup plików Dovecot: cd /etc/dovecot for f in ./dovecot* ; do cp $f $f.bak; done cd conf.d for f in ./* ; do cp $f $f.bak; done /etc/init.d/dovecot stop Linki symboliczne do logów (opcjonalne): ln -s /var/log /etc/dovecot/logs ln -s /var/mail/vhosts /etc/dovecot/vhosts Edytujemy plik /etc/dovecot/dovecot.conf: !include_try /usr/share/dovecot/protocols.d/*.protocol protocols = imap pop3 lmtp postmaster_address=postmaster at domain.ltd dict { #quota = mysql:/etc/dovecot/dovecot-dict-sql.conf.ext #expire = sqlite:/etc/dovecot/dovecot-dict-sql.conf.ext } !include conf.d/*.conf !include_try local.conf Edytujemy plik /etc/dovecot/dovecot-sql.conf.ext: driver = mysql connect = host=127.0.0.1 dbname=postfix user=postfix password=tajnehaslo default_pass_scheme = SHA512-CRYPT password_query = SELECT email as user, password FROM virtual_users WHERE email='%u'; user_query = SELECT concat('*:storage=', quota, 'M') AS quota_rule FROM virtual_users WHERE email='%u'; iterate_query = SELECT email FROM virtual_users; Edytujemy plik /etc/dovecot/conf.d/10-auth.conf: disable_plaintext_auth = yes auth_mechanisms = plain login #!include auth-system.conf.ext !include auth-sql.conf.ext Edytujemy plik /etc/dovecot/conf.d/10-mail.conf: mail_location = maildir:/var/mail/vhosts/%d/%n/ mail_home = /var/mail/vhosts/%d/%n/ namespace inbox { inbox = yes } mail_uid = vmail mail_gid = vmail mail_privileged_group = vmail mail_plugins=quota protocol !indexer-worker { } Edytujemy plik /etc/dovecot/conf.d/10-master.conf: service imap-login { inet_listener imap { port = 0 } inet_listener imaps { port = 993 ssl = yes } } service pop3-login { inet_listener pop3 { port = 0 } inet_listener pop3s { port = 995 ssl = yes } } service submission-login { inet_listener submission { #port = 587 } } service lmtp { unix_listener /var/spool/postfix/private/dovecot-lmtp { mode = 0600 user = postfix group = postfix } } service imap { # Most of the memory goes to mmap()ing files. You may need to increase this # limit if you have huge mailboxes. #vsz_limit = $default_vsz_limit # Max. number of IMAP processes (connections) #process_limit = 1024 } service pop3 { # Max. number of POP3 processes (connections) #process_limit = 1024 } service submission { # Max. number of SMTP Submission processes (connections) #process_limit = 1024 } service auth { unix_listener /var/spool/postfix/private/auth { mode = 0660 user = postfix group = postfix } unix_listener auth-userdb { mode = 0600 user = vmail } user = dovecot } service auth-worker { user = vmail } service dict { # If dict proxy is used, mail processes should have access to its socket. # For example: mode=0660, group=vmail and global mail_access_groups=vmail unix_listener dict { #mode = 0600 #user = #group = } } service quota-status { executable = quota-status -p postfix inet_listener { port = 12340 # You can choose any port you want } client_limit = 1 } Edytujemy plik /etc/dovecot/conf.d/10-ssl.conf: ssl = required ssl_cert = Edytujemy plik /etc/dovecot/conf.d/15-lda.conf: postmaster_address = root@domain.ltd hostname = domain.ltd protocol lda { # Space separated list of plugins to load (default is global mail_plugins). mail_plugins = $mail_plugins sieve } Edytujemy plik /etc/dovecot/conf.d/15-mailboxes.conf: namespace inbox { mailbox Drafts { auto = subscribe special_use = \Drafts } mailbox Junk { auto = subscribe special_use = \Junk } mailbox Trash { auto = subscribe special_use = \Trash } mailbox Sent { auto = subscribe special_use = \Sent } } Edytujemy plik /etc/dovecot/conf.d/20-imap.conf: protocol imap { # Space separated list of plugins to load (default is global mail_plugins). mail_plugins = $mail_plugins imap_quota # Maximum number of IMAP connections allowed for a user from each IP address. # NOTE: The username is compared case-sensitively. mail_max_userip_connections = 20 } Edytujemy plik /etc/dovecot/conf.d/20-lmtp.conf: protocol lmtp { # Space separated list of plugins to load (default is global mail_plugins). mail_plugins = sieve } Edytujemy plik /etc/dovecot/conf.d/20-managesieve.conf: protocols = $protocols sieve service managesieve-login { inet_listener sieve { port = 4190 } } service managesieve { #process_limit = 1024 } protocol sieve { managesieve_max_line_length = 65536 #managesieve_implementation_string = Dovecot Pigeonhole managesieve_implementation_string = dovecot #log_path = /var/log/dovecot-sieve-errors.log #info_log_path = /var/log/dovecot-sieve.log } Edytujemy plik /etc/dovecot/conf.d/20-pop3.conf: protocol pop3 { mail_plugins = $mail_plugins mail_max_userip_connections = 20 } Edytujemy plik /etc/dovecot/conf.d/90-quota.conf: plugin { quota = maildir:User quota quota_exceeded_message = User %u has exhausted allowed storage space. quota_status_success=DUNNO quota_status_nouser=DUNNO quota_status_overquota="552 5.2.2 Mailbox is full" } Edytujemy plik /etc/dovecot/conf.d/90-sieve-extprograms.conf: service managesieve-login { inet_listener sieve { port = 4190 } } service managesieve { } protocol sieve { managesieve_max_line_length = 65536 managesieve_implementation_string = dovecot #log_path = /var/log/dovecot-sieve-errors.log #info_log_path = /var/log/dovecot-sieve.log } Edytujemy plik /etc/dovecot/conf.d/90-sieve.conf: plugin { sieve_extensions = +vacation-seconds sieve_vacation_min_period = 5m sieve_vacation_default_period = 10m sieve_vacation_max_period = 15m sieve = /var/mail/vhosts/%d/%n/dovecot.sieve sieve_default = /var/lib/dovecot/sieve/default.sieve sieve_global = /var/lib/dovecot/sieve/global/ sieve_dir = /var/mail/vhosts/%d/%n/sieve } Edytujemy plik /etc/dovecot/conf.d/auth-sql.conf.ext: passdb { driver = sql args = /etc/dovecot/dovecot-sql.conf.ext } userdb { driver = sql args = /etc/dovecot/dovecot-sql.conf.ext } Tworzymy katalog /var/lib/dovecot/sieve: mkdir /var/lib/dovecot/sieve Tworzymy i edytujemy plik /var/lib/dovecot/sieve/default.sieve: require ["fileinto"]; # rule:[SPAM] if header :contains "X-Spam-Flag" "YES" { fileinto "Junk"; } Uprawnienia: chown -R root:dovecot /etc/dovecot chmod -R o-rwx /etc/dovecot Restart Dovecot oraz wydajemy polecenie obliczania quot: systemctl restart dovecot doveadm quota recalc -u vmail ==== DNS ==== Aby domena działała prawidłowo to rekordy domeny powinny być ustawione: * rekord MX główny domeny powinien wskazywać na adres serwera poczty, np: domain.ltd MX 1 domain.ltd * rekord A na który wskazuje rekord MX powinien mieć wpisany adres IP naszego serwera poczty np: domain.ltd A 1.2.3.4 * zaleca się, aby też ustawić rekord SPF, w którym zapisze, z jakich adresów IP będzie można wysyłać pocztę w naszej domenie np: domain.ltd TXT 'v=spf1 ip4:1.2.3.4 -all' ==== Webmail ==== Instalujemy Roundcube: aptitude install roundcube roundcube-mysql roundcube-plugins roundcube-plugins-extra Dodajemy do konfiguracji szyfrowanie: ln -s /etc/apache2/mods-available/socache_shmcb.load /etc/apache2/mods-enabled/socache_shmcb.load ln -s /etc/apache2/mods-available/ssl.load /etc/apache2/mods-enabled/ssl.load ln -s /etc/apache2/mods-available/ssl.conf /etc/apache2/mods-enabled/ssl.conf ln -s /etc/apache2/sites-available/default-ssl.conf /etc/apache2/sites-enabled/000-default-ssl.conf Edytujemy plik /etc/apache2/sites-enabled/000-default-ssl.conf i ustawiamy: SSLCertificateFile /etc/ssl/private/ssl.crt SSLCertificateKeyFile /etc/ssl/private/ssl.key Podczas instalacji zostaniemy zapytani o hasło do bazy Roundcube, która zostanie utworzona - wybieramy Yes. Poprosi nas o wpisanie hasła - pozostawiamy puste - zostanie automatycznie wygenerowane do pliku konfiguracji Roundcube. Edytujemy plik /etc/apache2/conf-enabled/roundcube.conf i na samym początku pliku wpisujemy/odkomentujemy wpis: Alias /roundcube /var/lib/roundcube Resteart Apache2: systemctl restart apache2 Edytujemy plik /var/lib/roundcube/config/config.inc.php - odszukujemy i ustawiamy: ... $config['default_host'] = 'ssl://domain.ltd'; $config['imap_auth_type'] = "LOGIN"; $config['imap_conn_options'] = null; ... $config['smtp_server'] = 'domain.ltd'; $config['smtp_port'] = 25; $config['smtp_user'] = '%u'; $config['smtp_pass'] = '%p'; $config['smtp_auth_type'] = 'LOGIN'; ... $config['plugins'] = array('managesieve'); ... Edytujemy plik /var/lib/roundcube/plugins/managesieve/config.inc.php: Aby otworzyć webmaila otwieramy stronę: https://domain.ltd/roundcube/ ==== Auto konfiguracja klienta poczty ==== MS Outlook dosyć dobrze radzi sobie z rozpoznaniem serwerów i konfiguracji pocztowej więc moje próby związane z auto-konfiguracją Outlooka więcej złego robiły niż dobrego. Thunderbird gorzej sobie radzi, ale możemy jemu podpowiedzieć jak ma to robić wystawiając na serwerze webowym plik konfiguracji. Tworzymy katalog: mkdir -p /var/www/html/.well-known/autoconfig/mail Zapisujemy do pliku /var/www/html/.well-known/autoconfig/mail/config-v1.1.xml zawartość: domain.ltd domain.ltd domain.ltd domain.ltd 993 SSL password-cleartext %EMAILADDRESS% domain.ltd 995 SSL password-cleartext %EMAILADDRESS% domain.ltd 465 SSL password-cleartext %EMAILADDRESS% domain.ltd 587 STARTTLS password-cleartext %EMAILADDRESS% ==== Klient poczty ==== Porty: * SMTP: 465 (SSL/TLS) 587 (STARTTLS) * POP3: 995 (SSL/TLS) * IMAP: 993 (SSL/TLS) ==== Fail2Ban ==== Instalujemy: apt install fail2ban W pliku /etc/fail2ban/jail.conf ustawiamy: ... ignoreip = 127.0.0.1/8 ::1 ... bantime = 60m ... findtime = 60m ... [roundcube-auth] port = http,https logpath = %(roundcube_errors_log)s enabled = true ... [postfix-sasl] enabled = true filter = postfix[mode=auth] port = smtp,465,submission,imap,imaps,pop3,pop3s # You might consider monitoring /var/log/mail.warn instead if you are # running postfix since it would provide the same log lines at the # "warn" level but overall at the smaller filesize. logpath = %(postfix_log)s backend = %(postfix_backend)s ... Restart: /etc/init.d/fail2ban restart Status fail2bana sprawdzamy poleceniem: root@mars:/var/log# fail2ban-client status Status |- Number of jail: 3 `- Jail list: postfix-sasl, roundcube-auth, sshd root@mars:/var/log# fail2ban-client status postfix-sasl Status for the jail: postfix-sasl |- Filter | |- Currently failed: 0 | |- Total failed: 0 | `- File list: /var/log/mail.log `- Actions |- Currently banned: 0 |- Total banned: 0 `- Banned IP list: ==== Munin ==== Monitoring zasobów serwera. Instalacja: apt install munin munin-node munin-plugins-extra Konfigurujemy plik /etc/munin/apache24.conf: ScriptAlias /munin-cgi/munin-cgi-graph /usr/lib/munin/cgi/munin-cgi-graph Alias /munin/static/ /var/cache/munin/www/static/ #Require local Require ip nasz_adres_ip Options FollowSymLinks SymLinksIfOwnerMatch Options None #Require local Require ip nasz_adres_ip Options FollowSymLinks SymLinksIfOwnerMatch SetHandler fcgid-script SetHandler cgi-script Alias /munin /var/cache/munin/www Reload konfiguracji Apache: systemctl apache2 reload Munin będzie dostępny pod: http://domain.ltd/munin ==== Przydatne narzędzia ==== * postqueue # postqueue -p -Queue ID- --Size-- ----Arrival Time---- -Sender/Recipient------- 56008207DE 195074 Mon Mar 22 09:28:19 user@domain.ltd (connect to falsedomain.ltd[1.2.3.4]:25: Connection refused) user44@falsedomain.ltd -- 190 Kbytes in 1 Request. * postsuper # postsuper -d 56008207DE postsuper: 56008207DE: removed postsuper: Deleted: 1 message * postmap # postmap -q 'name="fil.cmd"' regexp:/etc/postfix/mime_header_checks REJECT # postmap -q 'Content-Type: name="test.img"; charset=us-ascii' pcre:/root/mime.pcre REJECT Attachment of type test.img not accepted * rblcheck rblcheck -s dnsbl.sorbs.net adresiplubdomena * przenoszenie skrzynek pocztowych via IMAP: [[https://github.com/imapsync/imapsync]] * sprawdzanie czy nasza domena oraz adres IP jest na czarnych listach: [[https://mxtoolbox.com]] [[https://www.spamhaus.org/lookup/]] [[https://www.dnswatch.info]] * tester naszego serwera: [[https://www.mail-tester.com]] * sprawdzanie DNSów naszej domeny: [[https://intodns.com]] * Dodanie naszej domeny do zaufanych w Google: [[https://postmaster.google.com/]] * Dodanie naszej domeny do zaufanych w Microsoft: [[https://sendersupport.olc.protection.outlook.com/pm/]] * Sprawdzenie domeny oraz maili: [[https://bezpiecznapoczta.cert.pl]]