How to set up a simple Wireguard VPN

Install Wireguard

I’m using a Debian virtual machine for the server. In Debian 10, you’ll need to install the following two packages:

apt install wireguard-dkms wireguard-tools

Set up keys

First, navigate to /etc/wireguard (If not created, run mkdir /etc/wireguard as root) and then run the following commands as root:

wg genkey | tee laptop-private.key |  wg pubkey > laptop-public.key
wg genkey | tee server-private.key |  wg pubkey > server-public.key

The first line is for the public and private keys of the client, named laptop because, well, it’ll be used on a laptop. But you can choose any other name.

Configure the Wireguard server

First, enable IP forwarding. Since we’re only using IPv4, edit the /etc/sysctl.conf file as root, locate the net.ipv4.ip_forward line, uncomment it and change the value to 1.

Now, you need to create the /etc/wireguard/wg0.conf. This will be both the name of the connection interface and the configuration file for that interface. I’m using just one for a simple setup.

Address =
ListenPort = 51820
PrivateKey = <copy private key from server-private.key>
PostUp   = iptables -A FORWARD -i %i -j ACCEPT; iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
PostDown = iptables -D FORWARD -i %i -j ACCEPT; iptables -t nat -D POSTROUTING -o eth0 -j MASQUERADE

# laptop
PublicKey = <copy public key from laptop-public.key>
AllowedIPs =

Now you are ready to start the Wireguard daemon, so it can accept connections. Just run:

wg-quick up wg0

Some things to know


Address: the private IPv4 addresses (you can also use IPv6 addresses) for the Wireguard server subnet. In this example, clients connection to the server will be assigned IPs ranging from to

ListenPort: the port where Wireguard will listen. Don’t forget to open it in your firewall.

PrivateKey: the content from server-private.key.

PostUp and PostDown: defines steps to be run after the interface is turned on or off, respectively. In this case, iptables is used to set IP masquerade rules to allow all the clients to share the server’s IPv4 address. The rules will then be cleared once the tunnel is down. Don’t forget to change eth0 to your server’s network device.


PublicKey: the content from laptop-public.key.

AllowedIPs: the subnet IP assigned to that client when it connects to the server

Set up the client

On the client side, you’ll also have to install Wireguard. If you’re using Debian, Ubuntu or any distribution based on the previous two, the command will be the same (I’m assuming Ubuntu uses the same package names. If not, change it to your needs). In Arch, the distribution I’m currently using, you can install packages with:

pacman -Syuv wireguard-dkms wireguard-tools

Configure the Wireguard client

Create the /etc/wireguard/wg0.conf file and populate it with the following content:

Address =
PrivateKey = <copy private key from laptop-private.key>

PublicKey = <copy public key from server-public.key>
AllowedIPs =
Endpoint = 
PersistentKeepalive = 25

Some things to know


Addresss: the client’s IP address in Wiregard’s subnet.

PrivateKey: the content from laptop-private.key.


PublicKey: the content from server-public.key.

AllowedIPs: set it to to forward all IPv4 traffic through Wireguard.

Endpoint: the server IP address, followed by the port to connect to.

PersistentKeepalive: the number of seconds you wish the client sends a keepalive packet to the server. This is useful if the client is behind NAT or a firewall

Test the connection

On the client side, run wg-quick up wg0. You should now have a working Wireguard connection just like any VPN.

If you found a typo or an error, please use the comment box to report it. Also, if you found the post useful, please share it on social media, so it can reach a larger audience.


Must have extensions for Firefox

I’ve been a Firefox user since version 1.0, and the Mozilla Suite before that. Shamefully, I also used the infamous Internet Explorer long before that crap evolved to something close to a browser but not quite and still shitty.

During all my years with this browser, I’ve come to use a handful of extensions that I consider essential. The list has changed over the years and has taken many forms. The current one is as follow:

The list is short but I consider all of them essential. Believe it or not, this is the almost complete list of extensions I have installed. I try not to use many of them due to the impact on the browser performance.

Do you consider other extensions essential? Feel free to share them in the comments.

Image by J. Albert Bowden II – CC-BY-2.0


How-to customize the Bash prompt

In order to adapt a bit more my Debian Stable installation to my workflow, I’ve been tweaking the bash prompt. Simplicity and small line width are key here, because I often have tmux running with several panes in the same window and small panes with large one-liner prompts suck a lot! Everything feels crammed and hard to read. Just take a look at the image below to get an idea.

crammed bash prompt

After running a few commands in each pane with this prompt configuration, everything gets really crowded and confuse. For sanity safeguarding reasons and workflow improvement, the only thing to do is customize the prompt.

The Debian Stable bash prompt, shown on the image above, default value is:

if [ "$color_prompt" = yes ]; then
    PS1='${debian_chroot:+($debian_chroot)}\[\033[01;32m\]\u@\h\[\033[00m\]:\[\033[01;34m\]\w\[\033[00m\]\$ '
    PS1='${debian_chroot:+($debian_chroot)}\u@\h:\w\$ '
unset color_prompt force_color_prompt

To make it more useful, I changed the second line to this:

PS1="[\033[00;32m]\u@\h[\033[00m]:\w[\033[00m]\n└─ [$(tput bold)]\$(__git_ps1 '[%s] ')\$: [$(tput sgr0)]"

All put together:

if [ "$color_prompt" = yes ]; then
		PS1="\[\033[00;32m\]\u@\h\[\033[00m\]:\w\[\033[00m\]\n└─ \[$(tput bold)\]\$(__git_ps1 '[%s] ')\$: \[$(tput sgr0)\]"
    PS1='${debian_chroot:+($debian_chroot)}\u@\h:\w\$ '
unset color_prompt force_color_prompt

And this is the result:

readable bash prompt

Not only I get a more readable prompt (and with “more room to breathe”, if you may), but I get the name of the current branch if I’m in a Git repository folder. This is a convenient feature to have if you work with this version control system.

There are a lot more ways one can configure the prompt. Both How-To Geek and Boolean World websites have nice introductory guides to get you started. The Arch Linux wiki entry about this is also a good read. Oh, and RTFM (Read The … Fine … Manual).


Bash: how-to improve history manipulation

By default, up and down keys allow you to navigate your bash history. Another option is the history built-in command and bash expansions (ex.: !2 runs the second command, oldest to newest, from your bash history).

There are also tools, like bash-it, that allow for better history manipulation, but this also adds a lot of other stuff, so it might make your .bashrc load slower. It will make your bash look good as hell too.

Another option for an awesome way to access your bash history is the following snippet, based on bash-it‘s history plugin:

if [ -t 1 ]
    bind '"\e[A": history-search-backward'
    bind '"\e[B": history-search-forward'

With this, you only need to write part of a command, press the up arrow and it will complete it with the commands in bash history file that match to what you’ve written.

I’ve add it to the end of my .bashrc. Together with bash completion, it improves my workflow by a lot.