zkk / Vultr/Epik VPS max73.net setup



Acquisizione dominio e VPS

Vulr

Mi collego al sito Vultr ed acquisto un VPS selezionando la voce Deploy New Server con le seguenti caratteristiche:

Catatteristiche del piano scelto:

Altre caratteristiche (Additional Features):

Infine nella sezione Server Hostname & Label inserisco il nome del server VPS, ovvero max73.net.

Posso confermare tramite Deploy Now ed il costo totale risultante è attualmente di $4.20/month.

UPGRADE

Sono passato quasi subito alla seguente piano::

Per totali $6.00/month.

Epik

Mi collego al sito Epik e registro il dominio =max73.net= ed imposto i seguenti valori sotto SET DNS HOST RECORDS, sezione EXTERNAL HOSTS (A,AAAA):

HostTypePoints toTTL
wwwA (IPv4)66.135.14.17300
*A (IPv4)66.135.14.17300
A (IPv4)66.135.14.17300
wwwAAAA (IPv6)2001:19f0:0:42d9:5400:5ff:fe24:792b300
*AAAA (IPv6)2001:19f0:0:42d9:5400:5ff:fe24:792b300
AAAA (IPv6)2001:19f0:0:42d9:5400:5ff:fe24:792b300

Impostazione connessione SSH

Inizialmente posso collegarmi come root utilizzando la password fornita e reperibile dal pannello di controllo del VPS nella sezione Overview (in basso è scritto Password).

Poi posso collegarmi tramite SSH Key e farmi riconoscere dal VPS senza digitare la password, di seguito i passaggi da eseguire dal client:

ssh-keygen
ssh-copy-id root@max73.net  # chiede la password
ssh root@max73.net  # non chiede la password

Attivazione Webserver

Aggiornamento del sistema

apt update
apt upgrade
shutdown -r now

Apertura porte Firewall

ufw status numbered
ufw allow 80
ufw allow 443

Installazione nginx

apt install nginx

Configurazione Landing Page

Rimuovo la pagina di default di nginx e configuro la nuova pagina starts.

mv /var/www/html /var/www/start
mv /var/www/start/index-nginx-debian.html /var/www/start/index.html
rm /etc/nginx/sites-available/default
rm /etc/nginx/sites-enabled/default
touch /etc/nginx/sites-available/start
ln -s /etc/nginx/sites-available/start /etc/nginx/sites-enabled/

All’interno del file di configurazione di /etc/nginx/sites-available/start inserisco:

server {
   listen 80 ;
   listen [::]:80 ;
   root /var/www/start;
   index index.html;
   server_name max73.net www.max73.net ;
   location / {
     try_files $uri $uri/ =404;
   }
}

Configuro la pagina iniziale index.html facendo l’upload sia del file style.css che della pagina html creata con il tema Hugo chiamato Lynx e reperibile al seguente link:

Il contenuto iniziale della pagina index.html è il seguente (inserisco solo il collegamento alla pagina del Blog):

<!DOCTYPE html>
    <html lang="en">
		<!-- HEAD -->
		<head>
			<meta name="generator" content="Hugo 0.135.0">
			<meta charset="utf-8" />
			<meta name="viewport" content="width=device-width, initial-scale=1.0" />
			<meta http-equiv="X-UA-Compatible" content="ie=edge" />
			<title>MyWebsite</title>
			<meta name="title" content="MyWebsite" />
			<meta name="description" content="" />
			<meta name="robots" content="noindex, nofollow" />
			<link rel="alternate" type="application/rss+xml" href="/index.xml" title="MyWebsite" />
			<link type="text/css" rel="stylesheet" href="/style.css" />
		</head>
	<!-- BODY -->
	<body class="flex flex-col h-screen px-6 m-auto text-lg leading-7 bg-neutral max-w-7xl text-neutral-900 dark:bg-neutral-800 dark:text-white sm:px-14 md:px-24 lg:px-32" >
		<main class="flex-grow">
			<article class="flex flex-col items-center justify-center h-full mt-10 text-center">
				<!-- HEADER -->
				<header class="flex flex-col items-center mb-3">
					<h1 class="text-4xl font-extrabold dark:text-white">
						MyWebsite
					</h1>
				</header>
				<div class="flex flex-col flex-wrap min-w-full mt-4 sm:min-w-0">
					<!-- LINK AL BLOG -->
					<a class="link link-myblog mb-3 min-w-full rounded py-2 text-lg sm:px-24" 
						 href="https://blog.max73.net/" target="_self" rel="me noopener noreferrer" >
						<span class="mr-1"> </span>Blog</a>
					<!-- CHIUDO TUTTI I TAG -->
				</div>
			</article>
		</main>
	</body>
</html>

Connessione sicura SSL

apt install python3-certbot-nginx
certbot --nginx

Mi vengono rivolde domande a cui rispondo:

Infine riavvio il server:

systemctl reload nginx.service

Proteggere cartelle con password

E’ possibile proteggere con username/password l’accesso a determinate cartelle. Nel mio caso preferisco proteggere direttamente l’accesso al sottodominio.

apt install apache2-utils
htpasswd -c /etc/nginx/conf.d/htpasswd max # chiede la password

Per la configurazione di ulteriori utenti non utilizzare l’opzione =-c=.

Blog e sottodomini

mkdir /var/www/blog
touch /etc/nginx/sites-available/blog
ln -s /etc/nginx/sites-available/blog /etc/nginx/sites-enabled/

Configurazione /etc/nginx/sites-available/blog con accesso al sottodominio protetto da username/password:

server {
	listen 80 ;
	listen [::]:80 ;
	root /var/www/blog;
	index index.html;
	server_name blog.max73.net ;
	location / {
		auth_basic  "Restricted Area";
		auth_basic_user_file  /etc/nginx/conf.d/htpasswd;
	}
}

Protezione tramite SSL e riavvio del webserver

certbot --nginx -d blog.max73.net
systemctl reload nginx.service

Mail server - invio email

Apertura porta SMTP

Vultr.com blocca la porta 25 pertanto bisogna aprire un ticket di assistenza per sbloccarla.

Postfix

ufw allow 25
ufw allow 587
apt install mailutils postfix

L’installazione di postfix pone un paio di domande alle quali diamo la risposta di default:

Proseguo configurando un utente:

useradd -m -s /bin/bash max
passwd max

Se non mi permette di inserire una password troppo corta devo modificare il file /etc/pam.d/common-password e togliere l’opzione enforce_for_root dove presente. Questo mi permette (come utente root) di forzare l’inserimento della password corta dopo il primo avviso.

A questo punto posso inviare e ricevere email tra gli utenti del VPS, le emails saranno salvate all’interno del file /var/spool/mail/:

echo "Hi there." | mail -s "Email from root" max@max73.net
cat /var/spool/mail/max

SSL

certbot --nginx certonly -d mail.massimo-fontana.net

Ora modifichiamo coerentemente i puntamenti alle chiavi SSL all’interno del file /etc/postfix/main.cf. Sostituiamo le relative righe con le seguenti:

# TLS parameters
smtpd_tls_cert_file=/etc/letsencrypt/live/mail.max73.net/fullchain.pem
smtpd_tls_key_file=/etc/letsencrypt/live/mail.max73.net/privkey.pem

Ogni 2-3 mesi cedrtbot rinnova i certificati. Per poter legger i nuovi certificati postix deve essere riavviato. Inseriamo un cronjob che lo riavvia una volta al giorno:

crontab -e

Inserisco la seguente riga che ricarica postfix ogni giorno alle ore 3:

0 3 * * * systemctl reload postfix

Configurazione DNS

Torniamo sul sito https://epik.com .

All’interno della sezione SET DNS HOST RECORDS apro la sottosezione EMAIL SERVICES (MX) ed inserisco come segue:

All’interno della sezione SET DNS HOST RECORDS apro la sottosezione SUBDOMAINS (CNAME) ed aggiungo come segue:

rDNS (Reverse DNS)

All’interno della configurazione del VPS (settings) inserisco il Reverse DNS sia per la sottosezione IPv4 che per IPv6. Inserisco quindi il riferimento al dominio max73.net in corrispondenza degli indirizzi IPv4 ed IPv6.

DKIM (Domain Keys Identified Mail)

opendkim serve a generare una coppia di chiavi pubbliche/private per il nostro server.

Configurazione VPS

apt install opendkim opendkim-tools
mkdir -p /etc/postfix/dkim
opendkim-genkey -D /etc/postfix/dkim/ -d max73.net -s mail
chgrp opendkim /etc/postfix/dkim/*
chmod g+r /etc/postfix/dkim/*
echo "mail._domainkey.max73.net max73.net:mail:/etc/postfix/dkim/mail.private" > /etc/postfix/dkim/keytable
echo "*@max73.net mail._domainkey.max73.net" > /etc/postfix/dkim/signingtable
echo -e "127.0.0.1\n10.1.0.0/16\n1.2.3.4/24" > /etc/postfix/dkim/trustedhosts

Aggiungo quanto segue alla fine del file /etc/opendkim.conf avendo cura di commentare la riga già presente che inizia con Socket:

KeyTable file:/etc/postfix/dkim/keytable
SigningTable refile:/etc/postfix/dkim/signingtable
InternalHosts refile:/etc/postfix/dkim/trustedhosts

Canonicalization        relaxed/simple
Socket                  inet:12301@localhost

Eseguo i seguenti comandi che aggiungono istruzioni al file di configurazione di postfix, ovvero /etc/postfix/main.cf (fare attenzione che il file /etc/mailname contenga il dominio max73.net), altrimenti inserirlo:

echo "max73.net" > /etc/mailname
postconf -e "myhostname = $(cat /etc/mailname)"
postconf -e "milter_default_action = accept"
postconf -e "milter_protocol = 6"
postconf -e "smtpd_milters = inet:localhost:12301"
postconf -e "non_smtpd_milters = inet:localhost:12301"
systemctl restart opendkim
systemctl enable opendkim
systemctl reload postfix

Configurazione DNS

Torniamo sul sito https://epik.com .

All’interno della sezione SET DNS HOST RECORDS apro la sottosezione TXT RECORDS (TXT) ed inserisco quanto segue:

PriorityHostTXT ValueTTL
0mail._domainkey“v=DKIM1; k=rsa; p=[…]”300

Sostituisco […] con il codice (diviso in 2 parti) all’interno del file /etc/postfix/dkim/mail.txt.

Per comodità verifico il risultato del seguente comando:

echo -e "

v=DKIM1; k=rsa; $(tr -d "
" </etc/postfix/dkim/mail.txt | sed "s/k=rsa.* \"p=/k=rsa; p=/;s/\"\s*\"//;s/\"\s*).*//" | grep -o "p=.*")

"

TEST configurazione

Al seguente LINK è possibile effettuare un test inviando una email all’indirizzo che viene indicato dopo avere premuto Next Step, ad esempio:

echo "Hi there." | mail -s "prova email" test-c1dde1b4@appmaildev.com

DMARK (Domain-based Message Authentication Protocol)

Questo è un protocollo necesario per impedire un utilizzo non autorizzato del proprio dominio.

Configurazione VPS

useradd -m -G mail dmarc

Configurazione DNS

Torniamo sul sito https://epik.com .

All’interno della sezione SET DNS HOST RECORDS apro la sottosezione TXT RECORDS (TXT) ed aggiungo i valori che vengono generati dai seguenti comandi echo:

echo "_dmarc.$(cat /etc/mailname)"
echo "v=DMARC1; p=reject; rua=mailto:dmarc@$(cat /etc/mailname); fo=1"
PriorityHostTXT ValueTTL
0_dmarc.max73.net“v=DMARC1; p=reject; rua=mailto:dmarc@max73.net; fo=1”300

TEST configurazione

Allo stesso modo che per DKIM, vado al link LINK ed effettuo il testo per la verifica della configurazione, ad esempio:

echo "Hi there." | mail -s "prova email" test-c1dde1b4@appmaildev.com

SPF (Sender Policy Framework)

Allo stesso modo che per DKIM e DMARK, SPF previene gli spammer da spedire messaggi che possano apparire inviati dal mio server.

Configurazione VPS

Non necessaria.

Configurazione DNS

cat /etc/mailname
IP4='66.135.14.17'
IP6='2001:19f0:0000:42d9:5400:05ff:fe24:792b'
echo "v=spf1 mx a:mail.$(cat /etc/mailname) ip4:$IP4 ip6:$IP6 -all"

Torniamo sul sito https://epik.com .

All’interno della sezione SET DNS HOST RECORDS apro la sottosezione TXT RECORDS (TXT) ed aggiungo come TXT Value l’output del comando echo che precede.

Per quanto riguarda il campo Host inserisco il contenuto del file /etc/mailname.

PriorityHostTXT ValueTTL
0max73.net“v=spf1 mx a:mail.max73.net ip4:66.135.14.17 ip6:2001:19f0:0000:42d9:5400:05ff:fe24:792b -all”300

TEST configurazione

Allo stesso modo che per DKIM e DMARC, vado al link LINK ed effettuo il testo per la verifica della configurazione, ad esempio:

echo "Hi there." | mail -s "prova email" test-c1dde1b4@appmaildev.com

A questo punto posso permettermi di mandare email come la seguente:

echo "Hi there." | mail -s "prova email" maxmatty@gmail.com

Mail server - ricezione email

Dovecot e spamassassin

apt install dovecot-imapd dovecot-sieve spamassassin spamc
ufw allow 993

Configurazione dovecot

Faccio il backup della configurazione:

mv /etc/dovecot/dovecot.conf /etc/dovecot/dovecot.conf.bak

E sostituisco con la seguente (file /etc/dovecot/dovecot.conf):

# Note that in the dovecot conf, you can use:
# %u for username
# %n for the name in name@domain.tld
# %d for the domain
# %h the user's home directory

# Connections between the mail client and Dovecot needs to be encrypted
ssl = required
ssl_cert = </etc/letsencrypt/live/mail.max73.net/fullchain.pem
ssl_key = </etc/letsencrypt/live/mail.max73.net/privkey.pem
ssl_min_protocol = TLSv1.2
ssl_cipher_list = EECDH+ECDSA+AESGCM:EECDH+aRSA+AESGCM:EECDH+ECDSA+SHA256:EECDH+aRSA+SHA256:EECDH+ECDSA+SHA384:EECDH+ECDSA+SHA256:EECDH+aRSA+SHA384:EDH+aRSA+AESGCM:EDH+aRSA+SHA256:EDH+aRSA:EECDH:!aNULL:!eNULL:!MEDIUM:!LOW:!3DES:!MD5:!EXP:!PSK:!SRP:!DSS:!RC4:!SEED
ssl_prefer_server_ciphers = yes
ssl_dh = </usr/share/dovecot/dh.pem
auth_mechanisms = plain login
auth_username_format = %n

protocols = $protocols imap

# Search for valid users in /etc/passwd
userdb {
	driver = passwd
}
#Fallback: Use plain old PAM to find user passwords
passdb {
	driver = pam
}

# Our mail for each user will be in ~/Mail, and the inbox will be ~/Mail/Inbox
mail_location = maildir:~/Mail:INBOX=~/Mail/Inbox:LAYOUT=fs
namespace inbox {
	inbox = yes
	mailbox Drafts {
		special_use = \Drafts
		auto = subscribe
	}
	mailbox Junk {
		special_use = \Junk
		auto = subscribe
		autoexpunge = 30d
	}
	mailbox Sent {
		special_use = \Sent
		auto = subscribe
	}
	mailbox Trash {
		special_use = \Trash
	}
	mailbox Archive {
		special_use = \Archive
	}
}

# Here we let Postfix use Dovecot's authetication system.
service auth {
	unix_listener /var/spool/postfix/private/auth {
		mode = 0660
		user = postfix
		group = postfix
	}
}

protocol lda {
	mail_plugins = $mail_plugins sieve
}
protocol lmtp {
	mail_plugins = $mail_plugins sieve
}
plugin {
	sieve = ~/.dovecot.sieve
	sieve_default = /var/lib/dovecot/sieve/default.sieve
	sieve_dir = ~/.sieve
	sieve_global_dir = /var/lib/dovecot/sieve/
}

Successivamente diciamo a dovecot di spostare la email considerata spam nella relativa cartella con i seguenti comandi:

mkdir -p /var/lib/dovecot/sieve/
echo -e "require [\"fileinto\", \"mailbox\"];\nif header :contains \"X-Spam-Flag\" \"YES\"\n        {\n                fileinto \"Junk\";\n        }" > /var/lib/dovecot/sieve/default.sieve

Ora creo l’utente vmail che accederà alle emails:

grep -q '^vmail:' /etc/passwd || useradd vmail
chown -R vmail:vmail /var/lib/dovecot
sievec /var/lib/dovecot/sieve/default.sieve
echo -e "auth    required        pam_unix.so nullok\naccount required        pam_unix.so" >> /etc/pam.d/dovecot

Collegare postfix e dovecot

Dobbiamo dire a postfix di chiedere a dovecot per le autenticazioni degli utenti.

I comandi postconf inseriscono ulteriori configurazioni nel file /etc/postfix/main.cf:

postconf -e 'smtpd_sasl_auth_enable = yes'
postconf -e 'smtpd_sasl_type = dovecot'
postconf -e 'smtpd_sasl_path = private/auth'
postconf -e 'mailbox_command = /usr/lib/dovecot/deliver'

Collegare postfix e spamassassin

Eseguo prima il backup del file di configurazione:

cp /etc/postfix/master.cf /etc/postfix/master.cf.bak

Ed eseguo i seguenti 2 comandi per ultimare la configurazione:

sed -i '/^\s*-o/d;/^\s*submission/d;/^\s*smtp/d' /etc/postfix/master.cf
echo -e "smtp unix - - n - - smtp\nsmtp inet n - y - - smtpd\n  -o content_filter=spamassassin\nsubmission inet n       -       y       -       -       smtpd\n  -o syslog_name=postfix/submission\n  -o smtpd_tls_security_level=encrypt\n  -o smtpd_sasl_auth_enable=yes\n  -o smtpd_tls_auth_only=yes\nsmtps     inet  n       -       y       -       -       smtpd\n  -o syslog_name=postfix/smtps\n  -o smtpd_tls_wrappermode=yes\n  -o smtpd_sasl_auth_enable=yes\nspamassassin unix -     n       n       -       -       pipe\n  user=debian-spamd argv=/usr/bin/spamc -f -e /usr/sbin/sendmail -oi -f \${sender} \${recipient}" >> /etc/postfix/master.cf

Aggiungo quindi l’utente max al gruppo mail:

usermod -a -G mail max

Rafforzare la protezione da spam

I seguenti 3 comandi permettono di rafforzare le “difese” da spam:

postconf -e 'smtpd_recipient_restrictions = permit_sasl_authenticated, permit_mynetworks, reject_unauth_destination, reject_unknown_recipient_domain'
echo -e "/^Received:.*/     IGNORE\n/^X-Originating-IP:/    IGNORE\n/^User-Agent:/        IGNORE\n/^X-Mailer:/        IGNORE" >> /etc/postfix/header_checks
postconf -e "header_checks = regexp:/etc/postfix/header_checks"

Fail2ban

E’ un programma che permette di gestire situazioni “anomale” come qualcuno che prova ripetutamente ad entrare nella nostra posta da un determinato IP. In questo caso (ad esempio) mette in quarantena per qualche ora tale indirizzo IP. Installo il relativo pacchetto e creo il file di configurazione con desinenza .local (che ha precedenza su quello con estensione .conf):

apt-get install fail2ban
cp /etc/fail2ban/jail.conf /etc/fail2ban/jail.local

Nel file /etc/fail2ban/jail.local sostituisco i valori delle seguenti sezioni o le aggiungo ex-novo:

[postfix]
enabled  = true
port     = smtp,ssmtp,submission
filter   = postfix
logpath  = /var/log/mail.log

[sasl]
enabled  = true
port     = smtp,ssmtp,submission,imap2,imap3,imaps,pop3,pop3s
filter   = postfix-sasl
# 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  = /var/log/mail.warn
maxretry = 1
bantime  = 21600

[dovecot]
enabled = true
port    = smtp,ssmtp,submission,imap2,imap3,imaps,pop3,pop3s
filter  = dovecot
logpath = /var/log/mail.log

Infine riavvio il server:

shutdown -r now

Configurazione Email client

Posta in arrivo

Posta in uscita