1604 lines
40 KiB
Markdown
1604 lines
40 KiB
Markdown
# 👀 Server-Setup Overview
|
||
|
||
This repository helps you build a complete self-hosted environment on your own VPS or home server. Replace your dependence on third-party cloud services such as Gmail, Google Drive, Dropbox, and similar platforms by hosting your own secure alternatives under your control. Host your own file server, Git repositories, video conferencing platform, online office suite, RSS reader, file sharing service, uptime monitoring, forms, synchronization tools, email server, VPN server, and many other applications—all on infrastructure that you own and control.
|
||
|
||
|
||
![Server-Setup Demo Image]()
|
||
|
||
|
||
|
||
*Terminal icerisinde yukari asagi yapmak icin 'Shift+Page_Up' ve 'Shift+Page_Down' tuslarini kullanabilirsin*
|
||
*'sudo dmesg -D' kodu ile terminale yazirilan auid yazilarini o oturum icin kisa sureli durdurur*
|
||
|
||
BASE(Yunohost)
|
||
|
||
Ad Blocker(AdGuard Home)
|
||
Video-Voice Call(Element,Synapse)
|
||
Rss(FreshRSS)
|
||
Github Repo Clone(Gitea)
|
||
Realtime Server Monitoring(Glances)
|
||
Advanced Form Platform(Lime Survey)
|
||
Share files and notes with outserver safely(Lufi)
|
||
Run your 'html,css,js' page(my_webapp)
|
||
Store Files,Notes,Calendar,Forms,Photos and OnlyOffice(Nextcloud,OnlyOffice)
|
||
Local file sharing(PairDrop)
|
||
Realtime website analytics(Umami)
|
||
Realtime apps'web urls' monitoring(Uptime Kuma)
|
||
Webmail Client(Snappy Mail)
|
||
File convertion utility(Vert)
|
||
|
||
VPN Server(Wireguard VPN)*For long-term compatibility, it does not run inside YunoHost*
|
||
|
||
Needed Tools
|
||
Real VNC Viewer(For connecting to server easily)
|
||
File Zilla(For upload your website documents to server)
|
||
|
||
|
||
## 📦 Setup
|
||
|
||
Connect to the server through SSH:
|
||
ssh root@SERVER_IP
|
||
|
||
Update the system:
|
||
apt update
|
||
apt full-upgrade -y
|
||
apt autoremove -y
|
||
reboot
|
||
|
||
Reconnect after the reboot:
|
||
ssh root@SERVER_IP
|
||
|
||
|
||
*Optional: Connect through VNC* {
|
||
vncviewer VNC_IP:VNC_PORT
|
||
enter the vnc password(max 8 character)
|
||
|
||
Enter the VNC password and log in as:
|
||
Username: root
|
||
Password: SERVER_PASSWORD
|
||
|
||
Useful terminal shortcuts:
|
||
Scroll up:
|
||
Shift + Page Up
|
||
|
||
Scroll down:
|
||
Shift + Page Down
|
||
|
||
Temporarily stop kernel messages from appearing in the current terminal session:
|
||
sudo dmesg -D
|
||
|
||
Re-enable them:
|
||
sudo dmesg -E
|
||
}
|
||
|
||
|
||
Install the required tools:
|
||
apt install -y curl wget sudo gnupg2 ca-certificates
|
||
|
||
Verify the system:
|
||
cat /etc/os-release
|
||
hostnamectl
|
||
hostname -I
|
||
ip address
|
||
timedatectl
|
||
ip route
|
||
|
||
>Debian 12
|
||
>Correct IPv4 address
|
||
>Correct global IPv6 address (inet6 2a01:c303:2456:2954::1/64 scope global, ipv6 is 2a01:c303:2456:2954::1)
|
||
>Correct hostname
|
||
>Correct date, time and timezone
|
||
>A valid default network route
|
||
|
||
|
||
|
||
|
||
# CLOUDFLARE DNS RECORDS
|
||
Sign In into cloudflare and chose DNS Records>Connect a Domain
|
||
Configure AI training & search policies:
|
||
Search:Allow
|
||
Agent:Allow
|
||
Training:Block
|
||
Import DNS Records:Manual only
|
||
*All Records should be DNS only*
|
||
A domain IPV4
|
||
AAAA domain IPV6
|
||
CNAME www furk4ngg.me
|
||
A * IPV4
|
||
AAAA * IPV6
|
||
|
||
A ads.domain IPV4
|
||
A chat.domain IPV4
|
||
A cloud.domain IPV4
|
||
A convert.domain IPV4
|
||
A docs.domain IPV4
|
||
A forms.domain IPV4
|
||
A git.domain IPV4
|
||
A lufi.domain IPV4
|
||
A mail.domain IPV4
|
||
A pair.domain IPV4
|
||
A rss.domain IPV4
|
||
A syn.domain IPV4
|
||
A uptime.domain IPV4
|
||
A usage.domain IPV4
|
||
A visitors.domain IPV4
|
||
|
||
AAAA ads.domain IPV6
|
||
AAAA chat.domain IPV6
|
||
AAAA cloud.domain IPV6
|
||
AAAA convert.domain IPV6
|
||
AAAA docs.domain IPV6
|
||
AAAA forms.domain IPV6
|
||
AAAA git.domain IPV6
|
||
AAAA lufi.domain IPV6
|
||
AAAA mail.domain IPV6
|
||
AAAA pair.domain IPV6
|
||
AAAA rss.domain IPV6
|
||
AAAA syn.domain IPV6
|
||
AAAA uptime.domain IPV6
|
||
AAAA usage.domain IPV6
|
||
AAAA visitors.domain IPV6
|
||
|
||
|
||
In your domain provider,update your nameserver based on cloudflare nameserver such as 'sam.ns.cloudflare.com' and 'kack.ns.cloudflare.com'
|
||
|
||
hostnamectl set-hostname domain
|
||
|
||
apt update && apt full-upgrade -y
|
||
|
||
curl https://install.yunohost.org | bash
|
||
|
||
|
||
After completing the local YunoHost configuration, create the following domains from 'YunoHost>Domains' for the DNS records that we created:
|
||
AdGuard Home -> ads.domain
|
||
Element -> chat.domain and Synapse -> syn.domain
|
||
FressRSS -> rss.domain
|
||
Gitea -> git.domain
|
||
Glances -> usage.domain
|
||
Lime Survey -> forms.domain
|
||
Lufi -> lufi.domain
|
||
my_webapp -> domain
|
||
Nextcloud -> cloud.domain
|
||
Only Office -> docs.domain
|
||
Pair Drop -> pair.domain
|
||
Umami -> visitors.domain
|
||
Uptime Kuma -> uptime.domain
|
||
Snappy -> mail.domain
|
||
Vert -> convert.domain
|
||
|
||
|
||
|
||
|
||
# Yunohost App Permissions
|
||
*visitors(Ziyaretçiler)* *all_users(Tum yunohost kullanicilari)*
|
||
|
||
AdGuard Home -> all_users
|
||
Element -> all_users
|
||
Synapse -> all_users
|
||
FreshRSS -> all_users
|
||
Gitea -> visitors,all_users
|
||
Glances -> all_users
|
||
Lime Survey -> visitors,all_users
|
||
Lufi -> all_users
|
||
my_webapp -> visitors,all_users
|
||
Nextcloud -> visitors,all_users,admins
|
||
Only Office -> visitors,all_users
|
||
Pair Drop -> all_users
|
||
Umami(visitors.domain) -> all_users
|
||
Uptime Kuma -> all_users
|
||
Snappy -> all_users
|
||
Vert -> all_users
|
||
|
||
|
||
Display tile in portal -> (Yes)
|
||
|
||
|
||
|
||
|
||
## URL CERTIFICATES
|
||
|
||
✅ DNS A record is correct.
|
||
✅ DNS AAAA record is correct.
|
||
✅ The nameservers have been updated.
|
||
✅ HTTP is reachable from outside.
|
||
✅ Nginx is running.
|
||
✅ The server can connect to the Let's Encrypt API.
|
||
✅ Cloudflare proxy is disabled (DNS only).
|
||
After the nameserver changes have fully propagated,
|
||
|
||
sudo yunohost domain cert install
|
||
|
||
|
||
|
||
|
||
# -Web App Ayarlari (Make index work instead of index.html)-
|
||
sudo nano /etc/nginx/conf.d/domain.d/my_webapp.conf
|
||
index index.php index.html; --> index index.html index.htm;
|
||
|
||
try_files $uri $uri/ /index.php?$args =404; --> try_files $uri $uri/ $uri.html =404;
|
||
|
||
```
|
||
location = /favicon.ico {
|
||
log_not_found off;
|
||
access_log off;
|
||
}
|
||
|
||
location = /robots.txt {
|
||
allow all;
|
||
log_not_found off;
|
||
access_log off;
|
||
}
|
||
|
||
location /maintenance/ {
|
||
deny all;
|
||
}
|
||
|
||
location ~ ^/(.+/|)\.(?!well-known/) {
|
||
deny all;
|
||
}
|
||
```
|
||
|
||
sudo nano /etc/nginx/conf.d/furk4ngg.me.d/my_webapp.d/custom_headers.conf
|
||
```
|
||
add_header Referrer-Policy "no-referrer-when-downgrade" always;
|
||
add_header Cross-Origin-Opener-Policy "same-origin" always;
|
||
add_header Cross-Origin-Resource-Policy "same-origin" always;
|
||
```
|
||
|
||
Test
|
||
sudo nginx -t
|
||
|
||
if its ok
|
||
sudo systemctl reload nginx or sudo systemctl restart nginx
|
||
|
||
|
||
|
||
|
||
|
||
# -AdGuard Home Settings-
|
||
ads.domain -> all_users
|
||
ads.domainre:ads.domain/control -> visitors
|
||
ads.domainre:ads.domain/dns-query -> visitors
|
||
|
||
# -Element Settings-
|
||
Enable fedration features by default -> (Yes)
|
||
chat.domain -> all_users
|
||
chat.domain/bundles -> visitors
|
||
|
||
syn.domain -> all_users
|
||
syn.domain/_synapse -> visitors
|
||
syn.domain/livekit -> visitors
|
||
syn.domain/_matrix -> visitors
|
||
syn.domain/.well-known/matrix -> visitors
|
||
|
||
# -Gitea Settings-
|
||
Enable LFS support on this instance -> (Yes)
|
||
Enable support hover SSH protocol -> (Yes)
|
||
git.domain -> all_users,visitors
|
||
admin -> admins
|
||
git.domain.megit.furk4ngg.me/v2 -> visitors
|
||
|
||
# -Lime Survey-
|
||
forms.domain/admin -> admin page
|
||
https://forms.domain/index.php/dashboard/view
|
||
|
||
# -Lufi Settings-
|
||
Install Lufi with LDAP configuration? -> (Yes)
|
||
|
||
# -NextCloud Settings-
|
||
Add the users' home directory in Nextcloud? -> (No)
|
||
|
||
# -Umami Settings-
|
||
visitors.domain -> all_users
|
||
visitors.domain/api -> visitors
|
||
visitors.domain/recorder -> visitors
|
||
visitors.domain/script -> visitors
|
||
|
||
# -Uptime Kuma-
|
||
Choose SQLite database
|
||
|
||
# 📦 OnlyOffice Setup
|
||
Verify that the server settings were successfully updated
|
||
Check healthcheck and api.js
|
||
```
|
||
sudo yunohost service status | grep -i onlyoffice
|
||
curl https://docs.domain/healthcheck
|
||
curl -I https://docs.domain/web-apps/apps/api/documents/api.js
|
||
```
|
||
Verify that the secret keys match
|
||
```
|
||
sudo grep -n -A5 -B5 "secret" /var/www/onlyoffice/config/local.json
|
||
```
|
||
>"secret": {
|
||
> "browser": {
|
||
> "string": "secret_key"
|
||
Paste that key into 'Nextcloud>Administration Settings>ONLYOFFICE'
|
||
>ONLYOFFICE Docs address: https://docs.domain
|
||
>Secret Key: Paste secret_key here
|
||
|
||
Test>
|
||
```
|
||
sudo yunohost app shell nextcloud
|
||
php occ config:app:get onlyoffice jwt_secret
|
||
```
|
||
>secret key
|
||
|
||
Verify the SSL certificate
|
||
```
|
||
curl -Iv https://docs.domain
|
||
```
|
||
Run the curl tests
|
||
```
|
||
sudo -i
|
||
|
||
php /var/www/nextcloud/occ app:disable richdocuments
|
||
php /var/www/nextcloud/occ app:disable richdocumentscode
|
||
php /var/www/nextcloud/occ app:disable office
|
||
php /var/www/nextcloud/occ app:list | grep -i "onlyoffice\|richdocuments\|richdocumentscode\|office"
|
||
```
|
||
```
|
||
sudo apt update
|
||
sudo apt install php8.2-xml php8.2-mbstring php8.2-zip php8.2-gd php8.2-curl
|
||
sudo systemctl restart php8.2-fpm
|
||
php -m | grep -E "SimpleXML|mbstring|zip|gd|curl"
|
||
```
|
||
Verify occ
|
||
```
|
||
sudo -i
|
||
php /var/www/nextcloud/occ status
|
||
```
|
||
|
||
Verify Server Time
|
||
```
|
||
timedatectl status
|
||
```
|
||
|
||
Final diagnosis
|
||
```
|
||
sudo tail -100 /var/log/onlyoffice/docservice.log
|
||
```
|
||
|
||
|
||
|
||
Create a new document
|
||
If the page loads forever, first open F12 → Console
|
||
If analytics.js fails to load:
|
||
Disable Firefox Enhanced Tracking Protection or turn off uBlock, AdGuard, Brave Shields, or any similar blocker for this site
|
||
CTRL + F5
|
||
|
||
# -Mail Settings-
|
||
(Cloudflare)
|
||
*All Records should be DNS only*
|
||
MX domain mail.domain (Priority 10)
|
||
TXT domain "v=spf1 a mx -all"
|
||
TXT _dmarc "v=DMARC1; p=none"
|
||
TXT mail._domainkey "v=DKIM1; h=sha256; k=rsa; p='long value that you can see in Yunohost>Diagnosis>DNS records screen'"
|
||
CAA domain issue "letsencrypt.org"
|
||
PTR domain mail.domain
|
||
|
||
```
|
||
sudo yunohost diagnosis run
|
||
```
|
||
```
|
||
sudo yunohost service status | grep -E "postfix|dovecot|rspamd|opendkim"
|
||
```
|
||
|
||
|
||
|
||
sudo postconf myhostname
|
||
sudo grep -R "mail.domain" /etc/opendkim /etc/postfix /etc/dovecot 2>/dev/null
|
||
|
||
|
||
Which ports are open? ->
|
||
IMAP
|
||
sudo ss -tln | grep -E ":143|:993"
|
||
>143 → IMAP + STARTTLS
|
||
>993 → IMAPS (SSL/TLS)
|
||
|
||
SMTP
|
||
sudo ss -tln | grep -E ":25|:465|:587"
|
||
>✅ 25
|
||
>❌ 465
|
||
>✅ 587
|
||
|
||
|
||
Is STARTTLS actually working? ->
|
||
SMTP
|
||
openssl s_client -starttls smtp -connect domain:587
|
||
>Verify return code: 0 (ok)
|
||
|
||
IMAP
|
||
openssl s_client -connect domain:993
|
||
openssl s_client -starttls imap -connect domain:143
|
||
|
||
|
||
Is SMTP Authentication working ->
|
||
```
|
||
doveadm auth test furk4ngg@domain
|
||
```
|
||
>auth succeeded
|
||
|
||
|
||
Can LDAP see the email address? ->
|
||
```
|
||
postmap -q "furk4ngg@domain" ldap:/etc/postfix/ldap-accounts.cf
|
||
```
|
||
|
||
|
||
What is the mail server hostname? ->
|
||
```
|
||
sudo postconf myhostname
|
||
```
|
||
>myhostname = domain
|
||
|
||
|
||
Verify the mail domains ->
|
||
```
|
||
sudo yunohost user info furk4ngg
|
||
```
|
||
>mail:furk4ngg@domain
|
||
|
||
|
||
Which domains accept mail? ->
|
||
```
|
||
sudo cat /etc/postfix/virtual-mailbox-domains
|
||
```
|
||
|
||
Show the dedicated sender addresses used by applications (Nextcloud, Synapse, etc.) ->
|
||
sudo postmap -s /etc/postfix/app_senders_login_maps
|
||
|
||
## IMAP SETTINGS
|
||
>Admin page -> https://mail.domain/app/?admin
|
||
>username:admin
|
||
>password:/var/www/snappymail/app/data/_data_/_default_/admin_password.txt
|
||
|
||
|
||
Server: domain
|
||
|
||
Port: 993
|
||
|
||
Security: SSL/TLS
|
||
|
||
Use short login: OFF
|
||
|
||
Lowercase login: ON
|
||
|
||
Require verification: ON
|
||
|
||
Allow self signed: OFF
|
||
|
||
|
||
## SMTP SETTINGS
|
||
Server: domain
|
||
|
||
Port: 587
|
||
|
||
Security: STARTTLS
|
||
|
||
Use short login: OFF
|
||
|
||
Lowercase login: ON
|
||
|
||
Use authentication: ON
|
||
|
||
Use login as sender: OFF
|
||
|
||
Force AUTH PLAIN: OFF
|
||
|
||
Use php mail(): OFF
|
||
|
||
Require verification: ON
|
||
|
||
Allow self signed: OFF
|
||
|
||
|
||
## DKIM 1024-bit warning (Upgrade the key to 2048-bit, as preferred by major email providers)
|
||
|
||
sudo opendkim-testkey -d domain -s mail -vvv
|
||
1048 bit starts with MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQ...
|
||
2048 bit starts with MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8A...
|
||
|
||
openssl pkey -in /etc/dkim/domain.mail.key -text -noout | grep "Private-Key"
|
||
>Private-Key: (1024 bit, 2 primes)
|
||
|
||
- Verify your mail configuration
|
||
Before upgrading your DKIM key, verify the following settings
|
||
|
||
System Hostname
|
||
hostnamectl --static
|
||
>domain
|
||
|
||
Postfix Hostname
|
||
postconf myhostname
|
||
>myhostname = mail.example.com
|
||
|
||
MX record
|
||
dig @1.1.1.1 MX example.com +short
|
||
>10 mail.domain.
|
||
|
||
A record
|
||
dig @1.1.1.1 mail.domain A +short
|
||
>VPS's IPV4 Address
|
||
|
||
AAAA record
|
||
dig @1.1.1.1 mail.domain AAAA +short
|
||
>VPS's IPV6 Address
|
||
|
||
|
||
>hostnamectl --static returns example.com
|
||
>postconf myhostname returns mail.example.com
|
||
>your PTR record points to mail.example.com
|
||
>your MX record points to mail.example.com
|
||
|
||
and YunoHost Diagnosis still reports a hostname/EHLO warning, don't panic.
|
||
|
||
This is a common and valid mail server configuration. Using mail.example.com for SMTP while keeping the system hostname as the root domain (example.com) does not, by itself, cause mail delivery problems.
|
||
|
||
If Mail Tester reports SPF, DKIM, DMARC, and Reverse DNS as valid, you can safely continue with the DKIM 2048-bit upgrade.
|
||
|
||
|
||
Back up the existing key
|
||
```
|
||
sudo cp -a /etc/dkim/domain.mail.key \
|
||
/etc/dkim/domain.mail.key.bak
|
||
```
|
||
|
||
Generate a new 2048-bit key
|
||
```
|
||
sudo opendkim-genkey \
|
||
-b 2048 \
|
||
-r \
|
||
-s mail \
|
||
-d domain
|
||
```
|
||
ls
|
||
>mail.private
|
||
>mail.txt
|
||
|
||
|
||
Replace the private key
|
||
```
|
||
sudo mv mail.private /etc/dkim/domain.mail.key
|
||
sudo chown opendkim:root /etc/dkim/domain.mail.key
|
||
sudo chmod 600 /etc/dkim/domain.mail.key
|
||
```
|
||
|
||
Update the DNS record
|
||
cat mail.txt
|
||
|
||
>mail._domainkey IN TXT (
|
||
>"v=DKIM1; k=rsa; p=MIIBIjANBgkqh..."
|
||
>)
|
||
|
||
>Replace only the value of the existing mail._domainkey TXT record in Cloudflare with the new p= key
|
||
|
||
>The value must be on a single line.
|
||
>Do not include the following:
|
||
>❌ (
|
||
>❌ )
|
||
>❌ ""
|
||
>Multiple quoted strings like this.
|
||
|
||
|
||
Restart OpenDKIM
|
||
```
|
||
sudo systemctl restart opendkim
|
||
```
|
||
|
||
Verify the key
|
||
```
|
||
sudo opendkim-testkey \
|
||
-d domain \
|
||
-s mail \
|
||
-v
|
||
```
|
||
|
||
Test>
|
||
https://www.mail-tester.com/
|
||
>Identity verified
|
||
>DKIM signature verified
|
||
>Key length: 2048-bit
|
||
|
||
|
||
|
||
/baska maillerden yonlendirme hesabi/
|
||
|
||
|
||
# TEST ADRESSES
|
||
DNS Checker -> https://mxtoolbox.com/DNSLookup.aspx
|
||
DNS Checker -> https://dnscheck.tools/
|
||
Validate your DKIM and SPF DNS records. -> https://dmarcdkim.com/tools/check-dkim-record?domain=domain
|
||
Mail Tester -> https://www.mail-tester.com/
|
||
MX Records and Blacklist check -> https://mxtoolbox.com/SuperTool.aspx
|
||
SPF Test -> https://mxtoolbox.com/spf.aspx
|
||
What Is My Ip Adress -> https://ifconfig.me/
|
||
Domain Health Report -> https://mxtoolbox.com/emailhealth/
|
||
SEO TEST -> https://www.seobility.net/en/seocheck/
|
||
Web Page Quality -> https://pagespeed.web.dev/
|
||
|
||
|
||
## If its all good
|
||
Create a new account named dmarc@domain in YunoHost.
|
||
TXT _dmarc "v=DMARC1; p=reject; rua=mailto:dmarc@domain; adkim=s; aspf=s; pct=100"
|
||
Test it -> https://easydmarc.com/tools/dmarc-lookup
|
||
|
||
|
||
In your Server Hosting change (Reverse DNS Management>PTR Records(IPV4 to mail.domain / IPV6 to mail.domain))
|
||
|
||
sudo cp /etc/postfix/main.cf /etc/postfix/main.cf.bak
|
||
export TERM=xterm-256color
|
||
sudo vim /etc/postfix/main.cf > myhostname = mail.domain
|
||
|
||
|
||
sudo postconf myhostname
|
||
>myhostname = mail.domain
|
||
|
||
openssl s_client -starttls smtp -connect mail.domain:587
|
||
Type>EHLO test
|
||
>250-mail.domain
|
||
|
||
PTR Test
|
||
dig -x <IPv4> +short
|
||
>mail.domain
|
||
|
||
If all three point to mail.domain, the mail configuration is fully consistent.
|
||
|
||
|
||
|
||
Emails appear under YunoHost → Users
|
||
You can connect and use your mail with these mail providers:Thunderbird,Gmail,Outlook,Proton Mail or with your Webmail Client(Snappy Mail)
|
||
|
||
|
||
## Add a mail Alias
|
||
If you don't want to share your primary email address, you can create aliases for different services.
|
||
Yunohost>Users>user>edit user's account>'brand@domain' add a mail alias then messages sent to brand@domain address are delivered to: user@domain
|
||
|
||
# 📦 Wireguard VPN Setup
|
||
❌ In my opinion, this is not anonymity, since all tunnel traffic exits through a single VPS IP address
|
||
|
||
✅ On public Wi-Fi, all traffic is encrypted until it reaches your VPS
|
||
|
||
✅ You can securely access services such as Nextcloud, Gitea, and SSH
|
||
|
||
✅ You can restrict SSH and management panels so they are only accessible through the VPN
|
||
|
||
✅ You can also route DNS queries through your own server, preventing the local network from seeing them
|
||
|
||
|
||
sudo apt update
|
||
sudo apt install wireguard qrencode
|
||
Test>wg --version
|
||
>wireguard-tools v1.0.20210914 - https://git.zx2c4.com/wireguard-tools/
|
||
|
||
|
||
export TERM=xterm-256color
|
||
sudo nano /etc/sysctl.conf
|
||
Make sure the following are present:
|
||
>net.ipv4.ip_forward=1
|
||
>net.ipv6.conf.all.forwarding=1
|
||
|
||
sudo sysctl -p
|
||
|
||
|
||
sudo -i
|
||
sudo mkdir -p /etc/wireguard
|
||
cd /etc/wireguard
|
||
|
||
|
||
umask 077
|
||
wg genkey > server_private.key
|
||
wg pubkey < server_private.key > server_public.key
|
||
|
||
chmod 600 server_private.key
|
||
chmod 644 server_public.key
|
||
Server Public Key -> sudo cat /etc/wireguard/server_public.key
|
||
>We will use this key for future clients
|
||
|
||
|
||
Server Private Key -> sudo cat /etc/wireguard/server_private.key
|
||
|
||
ls -lah /etc/wireguard
|
||
It should look similar to this:
|
||
>server_private.key
|
||
>server_public.key
|
||
>wg0.conf
|
||
|
||
This test for next step 'Create wg0.conf'
|
||
ip route | grep default
|
||
if (default via ... dev eth0):
|
||
>PostUp = ... -o eth0 ...
|
||
>PostDown = ... -o eth0 ...
|
||
|
||
elif (default via ... dev ens18):
|
||
>PostUp = ... -o ens18 ...
|
||
>PostDown = ... -o ens18 ...
|
||
|
||
|
||
|
||
## Create wg0.conf
|
||
export TERM=xterm-256color
|
||
nano /etc/wireguard/wg0.conf
|
||
```
|
||
[Interface]
|
||
Address = 10.8.0.1/24
|
||
ListenPort = 51820
|
||
PrivateKey = SERVER_PRIVATE_KEY
|
||
|
||
PostUp = iptables -A FORWARD -i wg0 -j ACCEPT; iptables -A FORWARD -o wg0 -j ACCEPT; iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
|
||
PostDown = iptables -D FORWARD -i wg0 -j ACCEPT; iptables -D FORWARD -o wg0 -j ACCEPT; iptables -t nat -D POSTROUTING -o eth0 -j MASQUERADE
|
||
```
|
||
chmod 600 /etc/wireguard/wg0.conf
|
||
|
||
Test -> ls -l /etc/wireguard
|
||
For wg0.conf and server_private.key, you should see the following:
|
||
>-rw-------
|
||
|
||
|
||
## Enable the service
|
||
systemctl enable wg-quick@wg0
|
||
systemctl start wg-quick@wg0
|
||
|
||
Test>
|
||
systemctl status wg-quick@wg0 --no-pager
|
||
wg
|
||
ip addr show wg0
|
||
|
||
|
||
sudo yunohost firewall list
|
||
sudo yunohost firewall allow UDP 51820
|
||
sudo yunohost firewall reload
|
||
|
||
sudo ss -lun | grep 51820
|
||
>*:51820
|
||
|
||
<details>
|
||
<summary>(Optional) Enable IPv6 support (VPS)</summary>
|
||
Verify that the server has working IPv6 connectivity
|
||
ip -6 addr show
|
||
>A global IPv6 address (inet6 2a01:c303:2456:2954::1/64 scope global, ipv6 is 2a01:c303:2456:2954::1)
|
||
|
||
ip -6 route
|
||
>default via ...
|
||
|
||
ping -6 google.com
|
||
>0% packet loss
|
||
|
||
If IPv6 is working, you can assign a Unique Local IPv6 (ULA) prefix to the WireGuard network
|
||
Generate a ULA prefix:
|
||
1)
|
||
openssl rand -hex 5
|
||
>a1b2c3d4e5
|
||
ULA -> fda1:b2c3:d4e5::/64
|
||
|
||
2)
|
||
uuidgen
|
||
>f81d4fae-7dec-11d0-a765-00a0c91e6bf6
|
||
>First 10 character -> f81d4fae7d
|
||
ULA -> fdf8:1d4f:ae7d::/64
|
||
|
||
|
||
VPS
|
||
[Interface]
|
||
Address = 10.8.0.1/24, fdf8:1d4f:ae7d::1/64
|
||
[Peer]
|
||
AllowedIPs = 10.8.0.3/32, fdf8:1d4f:ae7d::3/128
|
||
|
||
PC (desktop -> wg0.conf)
|
||
[Interface]
|
||
Address = 10.8.0.3/24, fdf8:1d4f:ae7d::3/64
|
||
[Peer]
|
||
AllowedIPs = 0.0.0.0/0, ::/0
|
||
|
||
VPS
|
||
nmcli connection delete wg0
|
||
nmcli connection import type wireguard file /etc/wireguard/wg0.conf
|
||
nmcli connection up wg0
|
||
|
||
PC
|
||
nmcli connection show wg0
|
||
>ipv6.addresses: fdf8:1d4f:ae7d::3/64
|
||
|
||
ip addr show wg0
|
||
>inet6 fdf8:1d4f:ae7d::3/64 scope global noprefixroute
|
||
|
||
nmcli device show wg0
|
||
>IP6.ADDRESS[1 or 2]: fdf8:1d4f:ae7d::3/64
|
||
|
||
Test>
|
||
VPS
|
||
ping -6 fdf8:1d4f:ae7d::3
|
||
>0% packet loss
|
||
|
||
PC
|
||
ping -6 fdf8:1d4f:ae7d::1
|
||
>0% packet loss
|
||
|
||
|
||
NAT66 (VPS)
|
||
sysctl net.ipv6.conf.all.forwarding
|
||
>net.ipv6.conf.all.forwarding = 1
|
||
|
||
```
|
||
ip route | grep default
|
||
ip -6 route | grep default
|
||
```
|
||
>If both IPv4 and IPv6 use eth0 as the outbound interface, use eth0 for NAT66 as well
|
||
|
||
|
||
Add NAT66 Rule (VPS):
|
||
sudo ip6tables -t nat -A POSTROUTING -s fdf8:1d4f:ae7d::/64 -o eth0 -j MASQUERADE
|
||
|
||
Test>
|
||
sudo ip6tables -t nat -L -v
|
||
>Chain POSTROUTING
|
||
>MASQUERADE all fdf8:1d4f:ae7d::/64 anywhere
|
||
|
||
PC
|
||
Open the VPN
|
||
curl -6 ifconfig.me
|
||
>IPV6
|
||
ping -6 google.com
|
||
>0% packet loss
|
||
|
||
Verify IPv6 DNS (✅ The client can send IPv6 (AAAA) DNS queries through the VPN using AdGuard Home)
|
||
dig AAAA google.com
|
||
> status: NOERROR
|
||
> google.com. IN AAAA 2a00:1450:4001:...
|
||
|
||
## Change wg0.conf (VPS)
|
||
export TERM=xterm-256color
|
||
nano /etc/wireguard/wg0.conf
|
||
```
|
||
PostUp = iptables -A FORWARD -i wg0 -j ACCEPT; iptables -A FORWARD -o wg0 -j ACCEPT; iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE; ip6tables -A FORWARD -i wg0 -j ACCEPT; ip6tables -A FORWARD -o wg0 -j ACCEPT; ip6tables -t nat -A POSTROUTING -s fdf8:1d4f:ae7d::/64 -o eth0 -j MASQUERADE
|
||
|
||
PostDown = iptables -D FORWARD -i wg0 -j ACCEPT; iptables -D FORWARD -o wg0 -j ACCEPT; iptables -t nat -D POSTROUTING -o eth0 -j MASQUERADE; ip6tables -D FORWARD -i wg0 -j ACCEPT; ip6tables -D FORWARD -o wg0 -j ACCEPT; ip6tables -t nat -D POSTROUTING -s fdf8:1d4f:ae7d::/64 -o eth0 -j MASQUERADE
|
||
```
|
||
>iptables ... → IPv4 forwarding
|
||
>iptables nat ... → IPv4 NAT
|
||
|
||
>ip6tables ... → IPv6 forwarding
|
||
>ip6tables nat ... → IPv6 NAT66
|
||
|
||
|
||
Remove the manually added NAT66 rule first. Otherwise, WireGuard will create the same rule again when it starts, resulting in duplicate NAT66 rules:
|
||
```
|
||
sudo ip6tables -t nat -D POSTROUTING \
|
||
-s fdf8:1d4f:ae7d::/64 -o eth0 -j MASQUERADE
|
||
```
|
||
sudo systemctl restart wg-quick@wg0
|
||
|
||
Test>
|
||
VPS
|
||
sudo ip6tables -t nat -L POSTROUTING -n -v
|
||
>MASQUERADE all fdf8:1d4f:ae7d::/64 ::/0
|
||
|
||
PC
|
||
```
|
||
ping -6 google.com
|
||
curl -6 ifconfig.me
|
||
dig AAAA google.com
|
||
```
|
||
>ping: 0% packet loss
|
||
>curl: VPS's Global IPV6 address
|
||
>dig: status: NOERROR
|
||
|
||
|
||
</details>
|
||
|
||
<details>
|
||
<summary>Create Client Key</summary>
|
||
|
||
<details>
|
||
<summary>For Mobile Clients</summary>
|
||
|
||
## Create Mobile Client Key
|
||
|
||
cd /etc/wireguard
|
||
umask 077
|
||
wg genkey | tee phone_private.key > /dev/null
|
||
wg pubkey < phone_private.key > phone_public.key
|
||
chmod 600 phone_private.key
|
||
chmod 644 phone_public.key
|
||
|
||
Test -> ls -l phone_*
|
||
>-rw------- phone_private.key
|
||
>-rw-r--r-- phone_public.key
|
||
|
||
|
||
Phone Public Key -> sudo cat phone_public.key
|
||
|
||
export TERM=xterm-256color
|
||
nano /etc/wireguard/wg0.conf
|
||
Add this into end of the page
|
||
```
|
||
[Peer]
|
||
# Phone
|
||
PublicKey = PHONE_PUBLIC_KEY
|
||
AllowedIPs = 10.8.0.2/32
|
||
```
|
||
systemctl restart wg-quick@wg0
|
||
wg
|
||
>peer: XXXXXXXXXXXXXXXXXXXXXXXXXXXXX
|
||
>allowed ips: 10.8.0.2/32
|
||
|
||
## Phone.conf
|
||
Phone Private Key -> sudo cat phone_private.key
|
||
Server Public Key -> sudo cat /etc/wireguard/server_public.key
|
||
export TERM=xterm-256color
|
||
nano /etc/wireguard/phone.conf
|
||
```
|
||
[Interface]
|
||
PrivateKey = PHONE_PRIVATE_KEY
|
||
Address = 10.8.0.2/24
|
||
DNS = 1.1.1.1
|
||
|
||
[Peer]
|
||
PublicKey = SERVER_PUBLIC_KEY
|
||
Endpoint = VPS_IP:51820
|
||
AllowedIPs = 0.0.0.0/0, ::/0
|
||
PersistentKeepalive = 25
|
||
```
|
||
QR Code -> qrencode -t ansiutf8 < /etc/wireguard/phone.conf
|
||
|
||
|
||
|
||
Install the official WireGuard application
|
||
Add Tunel(+)
|
||
Scan the QR code
|
||
🎉 You are ready to use yor VPN
|
||
|
||
## Delete Mobile Client Key
|
||
```
|
||
rm -f \
|
||
/etc/wireguard/phone_private.key \
|
||
/etc/wireguard/phone_public.key \
|
||
/etc/wireguard/phone.conf
|
||
```
|
||
and delete this block in wg0.conf
|
||
```
|
||
[Peer]
|
||
# Phone
|
||
PublicKey = PHONE_PUBLIC_KEY
|
||
AllowedIPs = 10.8.0.2/32
|
||
```
|
||
sudo systemctl restart wg-quick@wg0
|
||
</details>
|
||
|
||
|
||
<details>
|
||
<summary>For Desktop Clients</summary>
|
||
|
||
<details>
|
||
<summary>Arch</summary>
|
||
sudo pacman -S wireguard-tools
|
||
</details>
|
||
|
||
<details>
|
||
<summary>Debian/Ubuntu/Raspberry Pi OS</summary>
|
||
sudo apt install wireguard
|
||
</details>
|
||
|
||
<details>
|
||
<summary>Fedora</summary>
|
||
sudo dnf install wireguard-tools
|
||
</details>
|
||
|
||
## Create Desktop Client Key
|
||
|
||
cd /etc/wireguard
|
||
umask 077
|
||
wg genkey | tee desktop_private.key > /dev/null
|
||
wg pubkey < desktop_private.key > desktop_public.key
|
||
chmod 600 desktop_private.key
|
||
chmod 644 desktop_public.key
|
||
|
||
Test -> ls -l
|
||
>-rw------- desktop_private.key
|
||
>-rw-r--r-- desktop_public.key
|
||
|
||
|
||
Desktop Public Key -> sudo cat desktop_public.key
|
||
|
||
export TERM=xterm-256color
|
||
nano /etc/wireguard/wg0.conf
|
||
Add this into end of the page
|
||
```
|
||
[Peer]
|
||
# Desktop
|
||
PublicKey = DESKTOP_PUBLIC_KEY
|
||
AllowedIPs = 10.8.0.3/32
|
||
```
|
||
|
||
systemctl restart wg-quick@wg0
|
||
wg
|
||
>peer: XXXXXXXXXXXXXXXXXXXXXXXXXXXXX
|
||
>allowed ips: 10.8.0.3/32
|
||
|
||
|
||
## desktop.conf
|
||
Desktop Private Key -> sudo cat desktop_private.key
|
||
Server Public Key -> sudo cat /etc/wireguard/server_public.key
|
||
|
||
In your PC
|
||
export TERM=xterm-256color
|
||
sudo nano /etc/wireguard/wg0.conf
|
||
|
||
```
|
||
[Interface]
|
||
PrivateKey = DESKTOP_PRIVATE_KEY
|
||
Address = 10.8.0.3/24
|
||
PreUp = ip route add VPS_IP/32 via 192.168.1.1 dev enp11s0
|
||
PostDown = ip route del VPS_IP/32 via 192.168.1.1 dev enp11s0
|
||
|
||
[Peer]
|
||
PublicKey = SERVER_PUBLIC_KEY
|
||
Endpoint = VPS_IP:51820
|
||
AllowedIPs = 0.0.0.0/0
|
||
PersistentKeepalive = 25
|
||
```
|
||
|
||
|
||
sudo chmod 600 /etc/wireguard/wg0.conf
|
||
|
||
Open VPN -> sudo wg-quick up wg0
|
||
Close VPN -> sudo wg-quick down wg0
|
||
Status -> sudo wg
|
||
|
||
Otomatic Connect when Pc is opened -> sudo systemctl enable wg-quick@wg0
|
||
Close that option -> sudo systemctl disable wg-quick@wg0
|
||
|
||
If you get connection error delete 'DNS = 1.1.1.1' from your desktop.conf and try again
|
||
sudo wg-quick up wg0
|
||
|
||
🎉 You are ready to use yor VPN
|
||
|
||
## Delete Mobile Client Key
|
||
```
|
||
rm -f \
|
||
/etc/wireguard/desktop_private.key \
|
||
/etc/wireguard/desktop_public.key \
|
||
/etc/wireguard/desktop.conf
|
||
```
|
||
and delete this block in wg0.conf
|
||
```
|
||
[Peer]
|
||
# Desktop
|
||
PublicKey = DESKTOP_PUBLIC_KEY
|
||
AllowedIPs = 10.8.0.3/32
|
||
```
|
||
sudo systemctl restart wg-quick@wg0
|
||
</details>
|
||
</details>
|
||
|
||
|
||
|
||
|
||
wg
|
||
>peer: XXXXXXXXXXXXX
|
||
>latest handshake: 5 seconds ago
|
||
>transfer: 120 KiB received, 90 KiB sent
|
||
|
||
|
||
Test -> https://ifconfig.me
|
||
>You should see the VPS_IP
|
||
|
||
DNS Leak Test -> https://browserleaks.com/dns
|
||
|
||
⚠️ If you want to add a new client device, generate a new key pair, assign a new VPN address (10.8.0.2, 10.8.0.3, 10.8.0.4, ...), and repeat the steps above using a different name instead of phone or desktop.
|
||
|
||
|
||
phone.conf/desktop.conf
|
||
Full Tunnel Mode -> AllowedIPs = 0.0.0.0/0 Bütün internet trafiğin VPN'den geçer.
|
||
|
||
Split Tunnel Mode -> AllowedIPs = 10.8.0.0/24 Sadece sunucuna ait trafik VPN'den geçer.
|
||
|
||
|
||
## Delete Server Key
|
||
```
|
||
rm -f \
|
||
/etc/wireguard/server_private.key \
|
||
/etc/wireguard/server_public.key \
|
||
/etc/wireguard/wg0.conf
|
||
```
|
||
sudo systemctl disable --now wg-quick@wg0
|
||
|
||
# -AdGuard Settings-
|
||
Bind to public IP addresses? (If you have an private IP choose NO) -> (Yes)
|
||
Enable DNS-over-HTTPS/TLS/QUIC? -> (No)
|
||
|
||
(Client / PC)
|
||
Remove the following lines if they exist(wg0.conf)
|
||
>PreUp = ...
|
||
>PostDown = ...
|
||
|
||
(VPS)
|
||
Debian / Ubuntu
|
||
```
|
||
sudo apt update
|
||
sudo apt install apache2-utils
|
||
```
|
||
sudo grep -A4 '^users:' /var/www/adguardhome/AdGuardHome.yaml
|
||
>Should see current user
|
||
|
||
New Password
|
||
```
|
||
htpasswd -B -C 10 -n -b USERNAME 'NEW_PASSWORD'
|
||
```
|
||
>USERNAME:$2y$10$...
|
||
|
||
```
|
||
sudo systemctl stop adguardhome
|
||
```
|
||
|
||
sudo cp /var/www/adguardhome/AdGuardHome.yaml \
|
||
/var/www/adguardhome/AdGuardHome.yaml.bak
|
||
|
||
sudo nano /var/www/adguardhome/AdGuardHome.yaml
|
||
|
||
Replace only the password: value in the following section:
|
||
>users:
|
||
>name: USERNAME
|
||
>password: $2y$10$...
|
||
|
||
(VPS)
|
||
Restart AdGuard Home
|
||
```
|
||
sudo systemctl restart adguardhome
|
||
```
|
||
|
||
Status
|
||
```
|
||
sudo chown adguardhome:adguardhome /var/www/adguardhome/AdGuardHome.yaml
|
||
sudo systemctl start adguardhome
|
||
sudo systemctl status adguardhome --no-pager
|
||
```
|
||
|
||
sudo nft -a list chain inet filter input
|
||
Delete the rules that allow TCP/UDP port 53 for everyone.
|
||
>sudo nft delete rule inet filter input handle 6
|
||
>sudo nft delete rule inet filter input handle 8
|
||
>Delete the existing TCP/UDP port 53 allow rules.
|
||
>Recreate the TCP/UDP allow rules without port 53.
|
||
|
||
```
|
||
sudo nft add rule inet filter input \
|
||
tcp dport { 22, 25, 80, 443, 587, 993, 5349, 5350, 7881, 8448 } \
|
||
counter accept
|
||
```
|
||
|
||
```
|
||
sudo nft add rule inet filter input \
|
||
udp dport { 1900, 5349, 5350, 5353, 51820, 55354 } \
|
||
counter accept
|
||
```
|
||
|
||
Then allow DNS access only for WireGuard clients:
|
||
```
|
||
sudo nft add rule inet filter input \
|
||
iifname "wg0" ip saddr 10.8.0.0/24 udp dport 53 counter accept
|
||
```
|
||
```
|
||
sudo nft add rule inet filter input \
|
||
iifname "wg0" ip saddr 10.8.0.0/24 tcp dport 53 counter accept
|
||
```
|
||
|
||
Finally, block DNS access for everyone else:
|
||
```
|
||
sudo nft add rule inet filter input udp dport 53 counter drop
|
||
```
|
||
```
|
||
sudo nft add rule inet filter input tcp dport 53 counter drop
|
||
```
|
||
|
||
Test>
|
||
```
|
||
sudo nft -a list chain inet filter input
|
||
```
|
||
|
||
## Bind AdGuard to the VPN interface
|
||
sudo nano /var/www/adguardhome/AdGuardHome.yaml
|
||
>bind_hosts:
|
||
> \- SERVER_PUBLIC_IP
|
||
> \- SERVER_IPV6
|
||
> 10.8.0.1 -> Add this
|
||
|
||
sudo systemctl restart adguardhome
|
||
|
||
## Verify that AdGuard is listening (VPS)
|
||
|
||
sudo ss -lunpt | grep ':53'
|
||
>SERVER_PUBLIC_IP:53
|
||
>10.8.0.1:53
|
||
>127.0.0.1:53 (dnsmasq)
|
||
|
||
Test(PC)>
|
||
Open The VPN
|
||
ping 10.8.0.1
|
||
>0% packet loss
|
||
|
||
dig google.com
|
||
>status: NOERROR
|
||
>SERVER: 10.8.0.1#53
|
||
|
||
|
||
## Restrict DNS access to WireGuard clients only
|
||
sudo nft -a list chain inet filter input
|
||
Expected result:
|
||
|
||
✔ Localhost -> ACCEPT
|
||
✔ WireGuard (10.8.0.0/24) -> ACCEPT
|
||
✔ Everyone else -> DROP
|
||
|
||
|
||
Add into wg0.conf (Client / PC)
|
||
DNS = 10.8.0.1
|
||
to the [Interface] section
|
||
|
||
On Linux, automatic DNS configuration depends on the distribution's DNS manager (systemd-resolved, NetworkManager, openresolv, etc.). If DNS is not applied automatically, configure your system's DNS resolver manually or use your distribution's recommended integration.
|
||
|
||
|
||
## Linux DNS integration
|
||
<details>
|
||
<summary>General Linux (wg-quick)</summary>
|
||
The VPN can always be started with:
|
||
|
||
Open VPN -> sudo wg-quick up wg0
|
||
Close VPN -> sudo wg-quick down wg0
|
||
Status -> sudo wg
|
||
|
||
Automatic DNS configuration depends on the Linux distribution and the DNS manager in use.
|
||
|
||
If DNS is not configured automatically, follow your distribution's recommended integration or configure your DNS resolver manually.
|
||
</details>
|
||
<details>
|
||
<summary>Arch Linux / Fedora (NetworkManager)</summary>
|
||
Do not install openresolv when using NetworkManager to manage WireGuard connections.
|
||
NetworkManager will manage DNS automatically.
|
||
|
||
(Client / PC)
|
||
Delete DNS = 10.8.0.1
|
||
If you use NetworkManager, remove the DNS = 10.8.0.1 line from the WireGuard configuration. NetworkManager will manage the DNS settings instead.
|
||
|
||
Delete the existing WireGuard connection if it already exists
|
||
nmcli connection delete wg0
|
||
|
||
Import the WireGuard configuration
|
||
nmcli connection import type wireguard file /etc/wireguard/wg0.conf
|
||
|
||
Let NetworkManager manage the DNS settings
|
||
nmcli connection show
|
||
|
||
```
|
||
nmcli connection modify wg0 ipv4.ignore-auto-dns yes
|
||
nmcli connection modify wg0 ipv4.dns "10.8.0.1"
|
||
```
|
||
|
||
IPV6
|
||
```
|
||
nmcli connection modify wg0 ipv6.ignore-auto-dns yes
|
||
nmcli connection modify wg0 ipv6.dns "::"
|
||
```
|
||
|
||
No IPV6
|
||
```
|
||
nmcli connection modify wg0 ipv6.method disabled
|
||
```
|
||
(Client / PC)
|
||
Stop using wg-quick
|
||
NetworkManager will manage the WireGuard connection
|
||
|
||
Open VPN -> nmcli connection up wg0
|
||
Close VPN -> nmcli connection down wg0
|
||
|
||
Test(PC)>
|
||
Open the VPN
|
||
cat /etc/resolv.conf
|
||
>Should see 10.8.0.1
|
||
|
||
Close the VPN
|
||
cat /etc/resolv.conf
|
||
>Should just see 192.168.1.1
|
||
|
||
nmcli connection show wg0
|
||
>ipv4.dns: 10.8.0.1
|
||
</details>
|
||
|
||
|
||
## Verify the VPN tunnel (Client / PC)
|
||
Open the VPN
|
||
```
|
||
ping 10.8.0.1
|
||
```
|
||
>0% packet loss
|
||
|
||
```
|
||
sudo wg
|
||
```
|
||
>latest handshake:
|
||
|
||
## Verify Internet Routing (Client / PC)
|
||
curl -4 ifconfig.me
|
||
When the VPN is enabled, the output should be the public IPv4 address of the VPS.
|
||
When the VPN is disabled, the output should return to the public IP address of the local internet connection.
|
||
|
||
## Verify AdGuard (VPS)
|
||
```
|
||
dig @10.8.0.1 google.com
|
||
```
|
||
>status: NOERROR
|
||
>SERVER: 10.8.0.1#53
|
||
|
||
## Verify the system DNS
|
||
```
|
||
dig google.com
|
||
```
|
||
>SERVER: 10.8.0.1#53
|
||
|
||
## Verify the AdGuard Home Dashboard
|
||
Open the AdGuard Home dashboard and go to: Query Log
|
||
|
||
Refresh a few websites or run: dig google.com
|
||
|
||
Expected result:
|
||
New DNS queries from the WireGuard client should appear in the Query Log.
|
||
The client address should normally be shown as a WireGuard address such as 10.8.0.3.
|
||
|
||
## Verify WireGuard(VPS)
|
||
sudo wg
|
||
>latest handshake:
|
||
|
||
## Verify that public DNS is blocked (Client / PC outside the VPN)
|
||
dig @SERVER_PUBLIC_IP google.com
|
||
dig @SERVER_PUBLIC_IP google.com +tcp
|
||
>no servers could be reached
|
||
>or
|
||
>connection timed out
|
||
|
||
## Fix local DNS resolution for mail services (VPS)
|
||
dig @10.8.0.1 MX srv1.mail-tester.com
|
||
>status: NOERROR
|
||
|
||
dig @127.0.0.1 MX srv1.mail-tester.com
|
||
>... timed out
|
||
|
||
|
||
Forward all local DNS requests to AdGuard Home:
|
||
sudo nano /etc/dnsmasq.d/99-adguard-upstream.conf
|
||
```
|
||
no-resolv
|
||
server=10.8.0.1
|
||
```
|
||
|
||
sudo dnsmasq --test
|
||
>syntax check OK
|
||
|
||
sudo systemctl restart dnsmasq
|
||
sudo systemctl status dnsmasq --no-pager
|
||
|
||
Test>
|
||
dig @127.0.0.1 MX srv1.mail-tester.com
|
||
dig MX srv1.mail-tester.com
|
||
>status: NOERROR for both of them
|
||
|
||
```
|
||
sudo postqueue -f
|
||
sudo tail -f /var/log/mail.log
|
||
```
|
||
>status=sent
|
||
|
||
mailq
|
||
>Mail queue is empty
|
||
|
||
sudo systemctl status dnsmasq
|
||
>active (running)
|
||
|
||
|
||
## Make nftables rules persistent (VPS)
|
||
|
||
Save the current rules:
|
||
sudo nft list ruleset | sudo tee /etc/nftables.conf >/dev/null
|
||
|
||
sudo cat /etc/nftables.conf
|
||
sudo nft list ruleset
|
||
|
||
Check the service is enabled:
|
||
sudo systemctl enable nftables
|
||
sudo systemctl status nftables
|
||
|
||
Reboot system:
|
||
sudo reboot
|
||
|
||
After system:
|
||
sudo nft list ruleset
|
||
sudo nft -a list chain inet filter input
|
||
>WireGuard DNS ACCEPT
|
||
>localhost ACCEPT
|
||
>public DNS DROP
|
||
|
||
DNS Checker -> https://dnscheck.tools/
|
||
What Is My Ip Adress -> https://ifconfig.me/
|
||
|
||
Disable uBlock Origin, AdGuard Browser Extension, Brave Shields, or any other third-party content blocker if the login page does not load correctly
|
||
|
||
Login Page -> https://ads.domain/login.html
|
||
|
||
# DIAGRAM
|
||
|
||
Client
|
||
│
|
||
WireGuard
|
||
│
|
||
10.8.0.1
|
||
│
|
||
AdGuard Home
|
||
│
|
||
Upstream DNS
|
||
│
|
||
Internet
|
||
|
||
localhost (127.0.0.1)
|
||
│
|
||
dnsmasq
|
||
│
|
||
AdGuard Home
|
||
│
|
||
Postfix
|
||
|
||
|
||
|
||
# AI-Assisted Server Setup
|
||
|
||
Use the prompt below with an AI assistant. Replace the placeholders with your own server, operating system, domain, hardware, network and application requirements.
|
||
|
||
```text
|
||
You are an experienced Linux system administrator, network engineer and self-hosting specialist.
|
||
|
||
I want you to create a current, secure and machine-specific installation guide for my server. Use the README instructions provided below as a reference for my intended architecture, applications and preferences, but do not blindly copy outdated commands or configurations.
|
||
|
||
My system:
|
||
|
||
- Server type: [VPS / home server / mini PC / Raspberry Pi / other]
|
||
- Provider or hardware model: [PROVIDER_OR_MODEL]
|
||
- Operating system and version: [OPERATING_SYSTEM]
|
||
- CPU architecture: [amd64 / arm64 / other]
|
||
- RAM: [RAM]
|
||
- Storage: [STORAGE]
|
||
- Public IPv4: [YES / NO]
|
||
- Public IPv6: [YES / NO]
|
||
- Private IP or local network: [PRIVATE_NETWORK_OR_NONE]
|
||
- Domain: [DOMAIN]
|
||
- DNS provider: [DNS_PROVIDER]
|
||
- Reverse proxy or server platform: [YunoHost / Docker / Podman / native packages / other]
|
||
- Firewall system: [YunoHost firewall / nftables / firewalld / UFW / other]
|
||
- VPN clients: [Linux / Windows / Android / iOS / macOS]
|
||
- Linux network manager: [NetworkManager / systemd-networkd / other]
|
||
- Linux DNS manager: [NetworkManager / systemd-resolved / openresolv / other / unknown]
|
||
|
||
Applications I want to install:
|
||
|
||
[LIST_THE_APPLICATIONS]
|
||
|
||
Examples:
|
||
|
||
- YunoHost
|
||
- WireGuard
|
||
- AdGuard Home
|
||
- Nextcloud
|
||
- ONLYOFFICE
|
||
- Gitea
|
||
- Element and Synapse
|
||
- FreshRSS
|
||
- Glances
|
||
- LimeSurvey
|
||
- Lufi
|
||
- PairDrop
|
||
- Umami
|
||
- Uptime Kuma
|
||
- SnappyMail
|
||
- Vert
|
||
- A mail server
|
||
- A custom web application
|
||
|
||
Requirements:
|
||
|
||
1. Check current official documentation and current package names before providing commands.
|
||
2. Adapt every command to my exact operating system, release, network manager, DNS manager, firewall and CPU architecture.
|
||
3. Do not use deprecated packages, obsolete configuration paths or hard-coded software versions unless they are required by the installed platform.
|
||
4. Clearly label every command with where it must be run:
|
||
- VPS / server
|
||
- Client / PC
|
||
- Phone
|
||
- DNS provider dashboard
|
||
- YunoHost web administration
|
||
5. Present the installation in the correct execution order.
|
||
6. Explain briefly what each major step does and what problem it prevents.
|
||
7. Before changing a configuration file:
|
||
- show how to create a backup;
|
||
- state the exact file path;
|
||
- show only the section that must be added or changed.
|
||
8. Never expose or request private keys, passwords, API tokens, JWT secrets or full credentials in the response.
|
||
9. Use placeholders such as:
|
||
- SERVER_PUBLIC_IP
|
||
- SERVER_IPV6
|
||
- DOMAIN
|
||
- VPN_SERVER_PRIVATE_KEY
|
||
- VPN_SERVER_PUBLIC_KEY
|
||
- CLIENT_PRIVATE_KEY
|
||
- CLIENT_PUBLIC_KEY
|
||
10. Verify the real outbound interface instead of assuming that it is eth0.
|
||
11. Avoid manual PreUp and PostDown endpoint routes unless they are genuinely required. Explain why they are needed before adding them.
|
||
12. Prevent NetworkManager, systemd-resolved and openresolv from simultaneously managing the same resolv.conf file.
|
||
13. For NetworkManager clients, prefer NetworkManager-native WireGuard and DNS management.
|
||
14. For wg-quick clients, explain which DNS manager is required and how DNS is restored when the VPN is disconnected.
|
||
15. Keep the server’s local DNS resolution working for mail services, package management and system applications.
|
||
16. Do not create a DNS loop between dnsmasq and AdGuard Home.
|
||
17. If AdGuard Home must bind to a public IP because the VPS has no private IP:
|
||
- allow DNS only from localhost and the WireGuard network;
|
||
- block public TCP and UDP port 53;
|
||
- verify that the server is not an open resolver.
|
||
18. Preserve YunoHost, Fail2Ban, mail, NAT and WireGuard firewall rules.
|
||
19. Do not delete or replace the entire nftables ruleset without first analysing which service manages each table.
|
||
20. Make firewall changes persistent using the method supported by the installed platform.
|
||
21. For mail:
|
||
- verify Postfix, Dovecot, Rspamd and OpenDKIM;
|
||
- verify local DNS and MX resolution;
|
||
- verify STARTTLS;
|
||
- verify SMTP authentication;
|
||
- verify DKIM, SPF, DMARC, MX and PTR;
|
||
- verify that queued messages reach status=sent.
|
||
22. For Nextcloud and ONLYOFFICE:
|
||
- verify healthcheck;
|
||
- verify api.js;
|
||
- verify SSL;
|
||
- verify matching JWT secrets;
|
||
- use the application-specific YunoHost shell or correct application user for occ commands;
|
||
- use the currently installed PHP version rather than hard-coding PHP 8.2.
|
||
23. Include recovery and rollback commands for risky changes.
|
||
24. Include tests after each section.
|
||
25. For every test, provide:
|
||
- where to run it;
|
||
- whether the VPN must be enabled;
|
||
- the expected output;
|
||
- what the result means;
|
||
- what to check if the result is different.
|
||
26. At the end, include a complete final validation checklist.
|
||
27. Clearly identify any step that may be overwritten by a YunoHost upgrade, application upgrade, firewall reload or reboot.
|
||
28. Do not claim that a configuration is persistent until it has been tested after a reboot.
|
||
29. Do not assume that an application permission should be public. Explain the security impact of visitor and all-user access before recommending it.
|
||
30. Prefer the safest configuration that still satisfies my requirements.
|
||
|
||
Important:
|
||
|
||
- Treat the README below as an architecture reference, not as an unquestionable source.
|
||
- Correct any unsafe, duplicated, outdated or technically incorrect instruction you find.
|
||
- If the README conflicts with current official documentation, use the current official method and explicitly state what changed.
|
||
- Do not skip a required step merely because it is absent from the README.
|
||
- Do not add unrelated software.
|
||
- Do not ask unnecessary questions when the system information above is sufficient.
|
||
- When essential information is missing, list the missing values first and then provide the parts of the guide that can already be completed safely.
|
||
|
||
Output format:
|
||
|
||
1. Architecture summary
|
||
2. Assumptions and detected risks
|
||
3. Preparation
|
||
4. DNS and domain configuration
|
||
5. Base platform installation
|
||
6. Application installation order
|
||
7. WireGuard setup
|
||
8. AdGuard Home setup
|
||
9. Client-specific VPN and DNS configuration
|
||
10. Mail configuration
|
||
11. Nextcloud and ONLYOFFICE integration
|
||
12. Firewall and persistence
|
||
13. Security hardening
|
||
14. Tests and expected results
|
||
15. Reboot validation
|
||
16. Rollback instructions
|
||
17. Final checklist
|
||
|
||
Here is the existing README reference:
|
||
|
||
[PASTE_THE_FULL_README_HERE]
|
||
```
|