What is LXD
LXD is a next generation system container and virtual machine manager. It offers a unified user experience around full Linux systems running inside containers or virtual machines.
LXD is image based and provides images for a wide number of Linux distributions. It provides flexibility and scalability for various use cases, with support for different storage backends and network types and the option to install on hardware ranging from an individual laptop or cloud instance to a full server rack.
I am not discussing the disadvantages , not worth my time 🙂
The main benefits of using LXD Container are:
– LXD containers are much lighter and faster to start than other virtualization technologies such as KVM or Xen.
– You can run multiple containers on a single host and each container can have its own IP address, making it easy to run microservices architectures.
– LXD containers provide better security isolation than other virtualization technologies since each container has its own set of users and permissions.
– LXD containers can be easily moved between different hosts thanks to their built-in live migration feature.
– You can use LXD containers to easily create development and test environments that are identical to your production environment.
I am assuming you’ve Ubuntu 20.x installed let’s begin :-
Before you do anything, let’s make sure Ubuntu is up2date, let’s run the following commands
sudo apt-get update && apt-get upgrade -y
The recommended storage backend for LXD when you run it on Ubuntu is the ZFS filesystem. To enable ZFS support in LXD install the
sudo apt install -y zfsutils-linux
Finally let’s initialize LXD
sudo lxd init
You will get the following, I am using zfs so here’s my output
Do you want to configure a new storage pool? (yes/no) [default=yes]: yes Name of the new storage pool [default=default]: default Name of the storage backend to use (btrfs, dir, lvm, zfs) [default=zfs]: zfs Create a new ZFS pool? (yes/no) [default=yes]: yes Would you like to use an existing block device? (yes/no) [default=no]: yes Path to the existing block device: /dev/sdb
You can always use default but pay close attention to storage backend and and block size
Now let’s create some profile and give them specific permissions, I am using C2 instance from google & my instance are as follows
8CPU and 32GB memory and 40 GB SSD Drive
lxc profile copy default vhosts
What I did above is I copy the default profile and named it vhosts, You can make as many profile as you like but I am just making one at this time.
Now let’s set some limit based on our server configuration
lxc profile set vhosts limits.memory "16GB" lxc profile set vhosts limits.cpu 4 lxc profile set vhosts boot.autostart "true"
I just gave my profile 16gb ram, 4 CPU and I also set my profile to auto start , in the event , I do decide to restart my server so my container will auto start.
As we now setup our profile and set limits, let’s launch this container
lxc launch ubuntu:20.04 container1 --profile vhosts
What’s happening here is , we are launching container1 and telling lxc to use profile vhosts
Now let’s setup disk space for that container
lxc config device add container1 root disk pool=default path=/ lxc config device set container1 root size 35GB
I am just leaving 5GB for the server, you can play with that however you like but this is how I did it.
if you run the following command it will give you the list of container and IP_ ADDRESS
+-----------+---------+------------------------------------+ | NAME | STATE | IPV4 | +-----------+---------+------------------------------------+ |container1 | RUNNING | 10.10.10.2 (eth0) | +-----------+---------+------------------------------------+
Now let’s go inside that container and install just nginx
lxc shell container1
root@container1# apt-get update && apt-get upgrade -y && apt-get install nginx -y
I am not going into detail how to setup nginx, you can click here and read more about my nginx configuration generator
Let’s assume you’ve successfully installed nginx and setup ssl certificates in your container1 web server, now it’s time to deploy proxy container
We will repeat the same step, but change the name
lxc profile copy default proxy lxc profile set proxy limits.memory "16GB" lxc profile set proxy limits.cpu 4 lxc profile set proxy boot.autostart "true"
Let’s setup proxy container
lxc launch ubuntu:20.04 proxy --profile proxy
Let’s Install HA Proxy
Go inside proxy container
lxc shell proxy
root@proxy# apt-get update && apt-get upgrade -y && apt-get install ha-proxy -y
copy the following configuration file & I will explain what it is
global log /dev/log local0 log /dev/log local1 notice chroot /var/lib/haproxy stats socket /run/haproxy/admin.sock mode 660 level admin expose-fd listeners stats timeout 30s user haproxy group haproxy daemon maxconn 4000 # Default SSL material locations ca-base /etc/ssl/certs crt-base /etc/ssl/private # See: https://ssl-config.mozilla.org/#server=haproxy&server-version=2.0.3&config=intermediate ssl-default-bind-ciphers ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20-P OLY1305:ECDHE-RSA-CHACHA20-POLY1305:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-GCM-SHA384 ssl-default-bind-ciphersuites TLS_AES_128_GCM_SHA256:TLS_AES_256_GCM_SHA384:TLS_CHACHA20_POLY1305_SHA256 ssl-default-bind-options ssl-min-ver TLSv1.2 no-tls-tickets defaults log global mode http option httplog option dontlognull timeout connect 10s timeout client 60s timeout server 60s errorfile 400 /etc/haproxy/errors/400.http errorfile 403 /etc/haproxy/errors/403.http errorfile 408 /etc/haproxy/errors/408.http errorfile 500 /etc/haproxy/errors/500.http errorfile 502 /etc/haproxy/errors/502.http errorfile 503 /etc/haproxy/errors/503.http errorfile 504 /etc/haproxy/errors/504.http frontend www mode http option forwardfor option httplog log-format "%ci:%cp [%t] $H $HM $HP $HQ $HU $HV %ft %b/%s %Tw/%Tc/%Tt %B %ts %ac/%fc/%bc/%sc/%rc %sq/%bq" bind :80 acl acl_sohaib.com hdr(host) -i sohaib.com www.sohaib.com use_backend container1 if acl_sohaib.com backend container1 mode http option httpchk option forwardfor server web1 10.10.10.2:80 check frontend www_secure mode tcp option tcplog log-format "%ci:%cp [%t] $H $HM $HP $HQ $HU $HV %ft %b/%s %Tw/%Tc/%Tt %B %ts %ac/%fc/%bc/%sc/%rc %sq/%bq" bind :443 acl tls req.ssl_hello_type 1 tcp-request inspect-delay 5s tcp-request content accept if tls acl acl_sohaib.com_secure req.ssl_sni -i sohaib.com www.sohaib.com use_backend container1_secure if acl_sohaib.com_secure backend container1_secure mode tcp option ssl-hello-chk server web1 10.10.10.2:443 check
Lastly, We’ve to forward the port in main server so exit out everything by typing
In your server outside of containers type the following
sudo lxc config device add proxy port80 proxy listen=tcp:0.0.0.0:80 connect=tcp:127.0.0.1:80 sudo lxc config device add proxy port443 proxy listen=tcp:0.0.0.0:443 connect=tcp:127.0.0.1:443
Now check your domain , I’ve used sohaib.com as an example you can add many backend and acl in ha proxy , I will later post the full configuration showing how to connect 2 containers and 2 backend, or you can post your comment and let me know and I will be more than happy to share that configuration with you.