What and why?
We all love OpenVPN, but at the same time we hate how much time it takes to have it deployed nicely and with some higher grade of security.
In this series I will show how to configure OpenVPN with virtual users stored in PostgreSQL, make sure that they use Two-Factor Authentication (using Google-Authenticator app).
At the end of the series, I will also go through process of automation this whole thing, to be deployable in minutes using Ansible.
- Create certificates
- Install OpenVPN
- Install dependencies (postgresql server, google-authenticator and pam-pgsql)
- Generate certificates
- Setup database, user and tables.
- Configure PAM
- Configure Google-authenticator
- Configure Control Panel (this needs to be written first)
- Setup user account
- Configure Client (Mac OS X)
- Automate using Ansible
1. Create Certificates.
Easiest way to create and manage certificates for OpenVPN is using EasyRSA script. There are many ways to do get it, however as this blog will mostly focus on CentOS I will provide you with easy ways to get things done on this distribution. EasyRSA for CentOS is available in Extra Packages for Enterprise Linux (EPEL) repository, installation of which is on CentOS is mostly done via long and not so intuitive way as it can be.
To install EPEL on CentOS 7 all you have to do is execute following command:
root# yum -y install epel-release
That’s it! No lengthy links, no copy-paste or using RPM command directly.
Now we should install easy-rsa, the tool that will help up configure required certificate chain wich is required for proper encryption of OpenVPN.
A quote from their GitHub profile: “easy-rsa is a CLI utility to build and manage a PKI CA. In laymen’s terms, this means to create a root certificate authority, and request and sign certificates, including sub-CAs and certificate revocation lists (CRL).”
Installation is again easier than most people believe:
root# yum -y install easy-rsa
Now that we have our easy-rsa installed, we should get to install other required packages.
2. Install OpenVPN
Thanks to EPEL repository this is another fast and simple step:
root# yum -y install openvpn
3. Install dependencies (postgresql, google-authenticator and pam-pgsql
Here we will use another repository, this one is maintained by PostgreSQL community.
root# yum -y install https://download.postgresql.org/pub/repos/yum/10/redhat/rhel-7-x86_64/pgdg-centos10-10-2.noarch.rpm
This will allow us to install latest PostgreSQL and pam-pgsql which we will use to authenticate our users in the database.
Now that we have repo installed we can install our dependencies:
root# yum -y install pam-pgsql10 postgresql10-server google-authenticator
4. Generate certificates
Let’s create the directory for our easyrsa and copy script over to our desired place:
root# mkdir -p /etc/openvpn/easyrsa/ root# cp -ar /usr/share/easy-rsa/3/* /etc/openvpn/easyrsa/
Create easyrsa variables file file
Use your favourite text editor to create text file named vars, contents should be modified to match your information:
set_var EASYRSA_BATCH "yes" set_var EASYRSA_REQ_CN "Common Name" set_var EASYRSA_REQ_COUNTRY "Country" set_var EASYRSA_REQ_PROVINCE "Province" set_var EASYRSA_REQ_CITY "City" set_var EASYRSA_REQ_ORG "Organization Name" set_var EASYRSA_REQ_EMAIL "Administrators EMail" set_var EASYRSA_REQ_OU "Organisation Unit" set_var EASYRSA_KEY_SIZE 2048 set_var EASYRSA_ALGO rsa set_var EASYRSA_CA_EXPIRE 3650 set_var EASYRSA_CERT_EXPIRE 3650 set_var EASYRSA_CRL_DAYS 180 set_var EASYRSA_DIGEST "sha256"
Save this file as /etc/openvpn/easyrsa/vars
Initialise Public Key Infrastructure
To be able to issue our CA and rest of required certificate chain, we first need to initialise PKI. Thanks to easyrsa, it is easy as everything with Linux these days:
root# cd /etc/openvpn/easyrsa root# ./easyrsa init-pki
Create our Certificate Authority certificate.
root# ./easyrsa build-ca nopass
Generate Diffie-Hellman key
Good explanation what it is and why we need DH and RSA for single VPN: https://security.stackexchange.com/questions/65802/ecdsa-ciphers-and-forward-secrecy-question-about-key-exchange/65808#65808
Let’s generate it now:
root# ./easyrsa gen-dh
Build server certificate
root# ./easyrsa build-server-full main nopass
Build TA certificate
root# openvpn --genkey --secret ./pki/private/ta.key
At this point we should have all the certificates our server will need, we will need extra certificates for our client, but we will generate that while preparing client configuration package.