How To: Set Up Remote Redis on DigitalOcean And Use it on your Local Application
Tags: redis, node
Published: 2020-11-13 18:00:47

**Note:** This configuration can be applied on any server running Ubuntu.

I was recently redesigning an [app](https://sinema.margaiwangara.me) I developed a while ago with Node.js, React and GraphQL because, apparently, its design was "too stretched" and "didn't look so good" (I low-key agree). So, I dove into dribbble to look for an awesome design I could borrow. **Sidebar: I really appreciate all the awesome open source designs created by the super talented UI/UX designers out there**. After a bit of digging, I found a [design](https://dribbble.com/shots/2759291-Movie-Application-UI) by [Ricardo Salazar](https://dribbble.com/riks). It was simple and easily implementable. With a few color changes, I managed to recreate the design and implement my React front-end using data from my GraphQL API.
During this process, I realized that to get the data I wanted, I needed to make a lot of requests to the external API I was using. Despite the API being free and without rate limits, I felt like I was abusing the resources that were provided. To solve this problem, I thought about using a database to store the data then performing the requests from my own server but I realized this would be highly inefficient due to the dynamic nature of the data from the external API. So, I decided to look at other options, that is when I remembered **Redis**.
I had done some storage with Redis before to perform authentication and session management with Express.js. After a bit of research, I came to the conclusion that redis was the way to go. Another issue was that, since I was using shared hosting with a cpanel, I could not install and use redis on my host. I had to find a way. 
Then comes [Github Student Pack](https://education.github.com/pack). Github provides a bunch of resources to help students use services like DigitalOcean by providing coupons and other options. I highly recommend if for students getting into or already developing awesome stuff. I was able to get a coupon for $50 on DigitalOcean and set up my droplet. I also did the initial set-up which has been provided in detail in [this article](https://www.digitalocean.com/community/tutorials/initial-server-setup-with-ubuntu-20-04). 

## Installing Redis on a DigitalOcean droplet
To install redis, run the following commands
```bash

$ sudo apt update 
$ sudo apt install redis-server

```

This will download and install Redis and its dependencies. We will then make some modifications to the Redis config file to add authentication and secure our Redis database.

Open the config file by writing this command.

```bash
$ sudo nano /etc/redis/redis.conf
```

In the config file, we will locate and modify the following areas:
- supervised
- security 
- bind

### Setting supervised to systemd
Locate the line which contains `supervised` option and change it to `systemd` 

```bash
# If you run Redis from upstart or systemd, Redis can interact with your
# supervision tree. Options:
#   supervised no      - no supervision interaction
#   supervised upstart - signal upstart by putting Redis into SIGSTOP mode
#   supervised systemd - signal systemd by writing READY=1 to $NOTIFY_SOCKET
#   supervised auto    - detect upstart or systemd method based on
#                        UPSTART_JOB or NOTIFY_SOCKET environment variables
# Note: these supervision methods only signal "process is ready."
#       They do not enable continuous liveness pings back to your supervisor.
supervised systemd

```

### Modifying Password
Since we need to set a secure password for the Redis, we will need to use openssl to generate a strong password. To generate a password, open a new tab on the terminal and run the command below.

```bash
$ openssl rand 60 | openssl base64 -A
```
The command above generates a strong password made up of random characters.

```bash
vWHK8OXixGiUU1kimf+Bo4WM+vu8t7Bpdk7VZHvtBc7caNeCDBK1Etazy/1Hho+/Uou4Mr1/gXk0hdNM
```
The security section of the Redis config file provides us with an area to specify the password of our Redis server. To set the password, in the config file, locate the security section and uncomment the `#requirepass foobared` then change the password from `foobared` to the password we generated above.

```bash
#/etc/redis/redis.conf

################################## SECURITY ###################################

# Require clients to issue AUTH <PASSWORD> before processing any other
# commands.  This might be useful in environments in which you do not trust
# others with access to the host running redis-server.
#
# This should stay commented out for backward compatibility and because most
# people do not need auth (e.g. they run their own servers).
#
# Warning: since Redis is pretty fast an outside user can try up to
# 150k passwords per second against a good box. This means that you should
# use a very strong password otherwise it will be very easy to break.
#
 requirepass vWHK8OXixGiUU1kimf+Bo4WM+vu8t7Bpdk7VZHvtBc7caNeCDBK1Etazy/1Hho+/Uou4Mr1/gXk0hdNM

```

### Modifying bind
***To make our redis database accessible, we will have to bind it to an external IP address which is not very secure. In this tutorial, we will bind it to 0.0.0.0 which makes it available everywhere***

In the config file we opened above, locate the line below and make sure it is uncommented(by removing the `#` at the beginning if it exists) and change the IP address to `0.0.0.0`.
```bash
#/etc/redis/redis.conf

bind 127.0.0.1 ::1 # change this line to bind 0.0.0.0
```

After modifying the config file, press `ctrl+x` on `Windows or Linux` or `command+x` on `Mac` then press `y` then `enter` to save the file then restart Redis by running the command below.

```bash
$ sudo systemctl restart redis.service
``` 

We can then test our Redis. To test the password, access the Redis command line by running:

```bash
$ redis-cli
```
We then write a series of commands to check if the Redis password works. At first, we try to set a key and value before authentication:
```
127.0.0.0:6379> set hello "Hello World"
```
This produces an error because we need to set the password:

```bash
#Output
(error) NOAUTH Authentication Required
```

We then specify the password we added above in the config file:

```
127.0.0.1:6379> auth <redis-password>
```
Redis will produce a message, `OK`, to inform you that the password has been accepted. We can then try to store the key and value as we tried above.

```bash
# setting value
127.0.0.1:6379> set hello "Hello World"

#getting value
127.0.0.1:6379> get hello

#output "Hello World"
```

We can then exit the Redis client with the command `quit`.

## Using Remote Redis on your local Express Application
**Note:** If you are using a firewall on your DigitalOcean server, you need to enable access for port `6379` in order to use it on your local application. To enable the port for external access:
```bash
$ ufw allow 6379/tcp

#checking if port has been added to ufw list
$ ufw status
```

We then initialize a simple express app by installing a few packages.

```bash
# Initialize Express app
$ npm init -y

# Installing packages - Express and Redis
$ npm install express redis
```

Create an `index.js` file on the root of your project then write the code below:

```javascript
const express = require('express');
const redis = require('redis');

const app = express();

// These should be environment variables, use a package like dotenv to store these data
const REDIS_PORT = 6379;
const REDIS_HOST = "<DO_IP_ADDRESS>" // This is the IP address of your DigitalOcean droplet
const REDIS_PASSWORD = "vWHK8OXixGiUU1kimf+Bo4WM+vu8t7Bpdk7VZHvtBc7caNeCDBK1Etazy/1Hho+/Uou4Mr1/gXk0hdNM" // This is the password we created above for our Redis database.

const redisClient = redis.createClient({
	host: REDIS_HOST,
	port: REDIS_PORT,
	password: REDIS_PASSWORD
});

// Log errors in case of Redis connection failure
redisClient.on('error', error => {
	console.log('Redis Error', error);
});

// Set Express server PORT
const PORT = process.env.PORT || 5000;
app.listen(PORT, () =>
	console.log(`App running in on port ${PORT}`),
);
```

With this, you can use the remote Redis to store and access your data. 

To get more details on securely configuring Redis on your DigitalOcean server, you can check out the link below:

[How To Install and Secure Redis on Ubuntu](https://www.digitalocean.com/community/tutorials/how-to-install-and-secure-redis-on-ubuntu-20-04)