In this part we will configure the general settings of the server, the Nginx server for hosting a static site and Radicale. Both the static site and Radicale will automatically have SSL certificates generated through ACME. All the configuration is done in the hosts/HOSTNAME/configuration.nix file unless otherwise stated.
General configuration
First we set up the bootloader, since we are using UEFI we need the following settings.
boot.loader = {
grub.enable = true;
grub.device = "nodev";
grub.efiSupport = true;
grub.useOSProber = true;
efi.canTouchEfiVariables = true;
};
Here we install some basic programs, such as neovim for editing files and git for cloning the repository we put our config files in.
environment.systemPackages = with pkgs; [
git
apacheHttpd # We need this for htpasswd, which is used by radicale
];
system.stateVersion = "23.05";
time.timeZone = "Europe/Amsterdam"; # Change to your timezone
i18n.defaultLocale = "en_US.UTF-8";
programs.neovim.enable = true;
Here we create an admin user and disable root login, but we allow the admin user to use doas to get root permissions. We also only enable public key authentication for ssh logins, so be sure to add your public key to the authorized keys section.
services.openssh = {
enable = true;
settings.PasswordAuthentication = false;
settings.KbdInteractiveAuthentication = false;
settings.PermitRootLogin = "no";
};
users.users.admin = {
isNormalUser = true;
extraGroups = [
"docker"
];
openssh.authorizedKeys.keys = [
"YOUR SSH PUBLIC KEY HERE"
"ANOTHER KEY?"
];
};
security.sudo.enable = false;
security.doas.enable = true;
security.doas.extraRules = [{
users = [ "admin" ];
keepEnv = true;
persist = true;
}];
I prefer using doas but you can also decide to use sudo, then you must at least change the following in the configuration:
users.users.admin.extraGroups = [
"docker"
"wheel" # add the admin user to the wheel group
];
security.sudo = {
enable = true; # enable sudo
groups = [
"wheel" # allow users in the wheel group to use sudo
];
};
Lastly, we set the firewall to allow only the following ports:
- Port 22 (ssh)
- Port 443 (https), we will redirect all http traffic to https.
networking.firewall = {
enable = true;
allowedTCPPorts = [ 22 80 443 ];
};
Radicale
services.radicale = {
enable = true;
settings = {
server = {
hosts = [ "0.0.0.0:5232" "[::]:5232" ];
};
auth = {
type = "htpasswd";
htpasswd_filename = "/etc/radicale/users";
htpasswd_encryption = "bcrypt";
};
};
};
Nginx
security.acme = {
acceptTerms = true;
defaults.email = "YOUR EMAIL HERE";
};
services.nginx = {
enable = true;
recommendedProxySettings = true;
recommendedTlsSettings = true;
virtualHosts = {
"domain.com" = {
forceSSL = true;
enableACME = true;
root = "/home/admin/domain.com";
serverAliases = [ "radicale.domain.com" ];
};
"radicale.domain.com" = {
forceSSL = true;
useACMEHost = "domain.com" # reuse the same certificate for this domain
locations."/" = {
# setup a reverse proxy for radicale
proxyPass = "http://localhost:5232/";
extraConfig = ''
proxy_set_header X-Script-Name /;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_pass_header Authorization;
'';
};
};
};
};
For more info:
DNS
Since we are replacing an old server, we first need to change our DNS records such that they point to our newly configured server. This is important because we are trying to setup SSL certificates for our domain name.
First we need to find our public IP, there are several ways to do it, I like to do it like this:
curl -4 ifconfig.co # IPV4
curl ifconfig.co # IPV6
Then go to your domain registrar and change your A and AAAA records.
We also need to setup port forwarding on our router in order to access it from the internet.
So setup a port forwarding rule for ports 80 and 443 using your local IP address (found by using ip addr
).
Installing in a virtual machine
I am root.
sudo su
Partioning the disk
parted /dev/vda mklabel gpt
parted /dev/vda mkpart primary fat32 2048s 500M
parted /dev/vda set 1 esp on
parted -- /dev/vda mkpart primary ext4 500M -1s
parted /dev/vda quit
mkfs.fat -F 32 /dev/vda1
fatlabel /dev/vda1 BOOT
mkfs.ext4 /dev/vda2 -L ROOT
mount /dev/disk/by-label/ROOT /mnt
mkdir -p /mnt/boot
mount /dev/disk/by-label/BOOT /mnt/boot
Configuration
Generate the hardware-configuration and get the configuration files
nixos-generate-config --root /mnt
nix-shell -p git
git clone https://github.com/wjehee/.dotfiles-nix
cp /mnt/etc/nixos/hardware-configuration.nix .dotfiles-nix/hosts/HOSTNAME/
Perform the install
cd .dotfiles-nix/
git add .
nixos-install --flake .#HOSTNAME
Copy the configuration onto the installed version
cd ..
cp -r .dotfiles-nix /mnt/home/admin
- Change into the installed version by running:
nixos-enter
- Change ownership of .dotfiles-nix:
chown -R admin:users home/admin/.dotfiles-nix
- Set the password for the admin user:
passwd admin
- Create the user file for radicale:
htpasswd -B -c /etc/radicale-users USERNAME
- Optionally create more calendar users, by running
htpasswd -B /etc/radicale-users USERNAME
- Exit out of the install with
exit
and thenreboot
It might take some time before the SSL certificates are set up, if it still doesn't work after a while, just SSH into the server and rebuild.