Your self hosted Linktree, with analytics - Part 2

Your self hosted Linktree, with analytics - Part 2

Tags
Web Development
Date
This is a follow up to my first part on creating your self hosted Linktree

Introduction

In the first part, we have created our frontend for the Linktree. In this part, I cover analytics and deployment to Vercel
 

Let's get started!

Part 1: Creating the serverless function

So far, you have should have your Linktree running in your browser on localhost:3000
Now, we begin by creating the serverless function

Step 1:

Let’s begin by adding MongoDB to our project. Run npm i mongodb --save in the terminal. We are going to be saving our visitors data to this DB
 

Step 2:

Create a new folder called api in the root directory of your project and create a file called log.js
This is where we write our serverless function. Open this file in VS Code

Step 3:

We first import two modules we need
const url = require("url");
const MongoClient = require("mongodb").MongoClient;
The first module, url is needed to parse the MongoDB URI which we’ll be using later on

Step 4:

We then create two variables we need
let cachedDb = null;
const uri = process.env.VISITORSDB;
cachedDb will hold our database object, while uri will store the MongoDB connection string from an environment variable
Next, we write a function to connect to MongoDB

Step 5:

async function connectToDatabase()
{
    if(cachedDb){
        return cachedDb;
    }

    const client = await MongoClient.connect(uri, {
        useNewUrlParser: true,
        useUnifiedTopology: true,
    });

    const db = await client.db(url.parse(uri).pathname.substr(1));

    cachedDb = db;
    return db;
}
The above function connects to MongoDB and assigns the cachedDb variable the object of the database.

Step 6:

Now we export the serverless function which will actually store the data to the database
module.exports = async (req, res) => {
    try {
        console.log("Inside default log function");
        const referer = req.headers["referer"];
        const ip = req.headers["x-forwarded-for"];
        const ua = req.headers["user-agent"];
        const ul = req.headers["accept-language"];
        const dnt = req.headers["dnt"];
        const reg = req.headers["x-vercel-id"];


        d = new Date().toLocaleString('en-IN', { timeZone: 'Asia/Kolkata' });
        info = {ip, ua, ul, dnt, referer, reg, dt: "" + d};

        const db = await connectToDatabase();
        const collection = await db.collection(process.env.COLLECTION);
        await collection
            .insertOne(info)
            .then(() => {
                res.status(200).send();
            })
            .catch(err => {
                throw err;
            });
        }
        catch(error)
        {
            console.log(error);
            res.status(500).send();
        }
};
When our function is called, we get a request and response object passed to our function. The request object contains the headers, which are sent to our Vercel deployment on every request. You can read more about them here
I’ll explain the function part by part
const referer = req.headers["referer"];
const ip = req.headers["x-forwarded-for"];
const ua = req.headers["user-agent"];
const ul = req.headers["accept-language"];
const dnt = req.headers["dnt"];
const reg = req.headers["x-vercel-id"];
In the first part, we extract data from the headers including the user’s IP address and user agent.
d = new Date().toLocaleString('en-IN', { timeZone: 'Asia/Kolkata' });
Here, we create a new Date object to get the current date and time which will then be saved to the database. The timezone parameter converts the time into our local time.
const db = await connectToDatabase();
const collection = await db.collection(process.env.COLLECTION);
In the above line, we connect to the database.
A collection is like a table in MongoDB. You can read more about it here
info = {ip, ua, ul, dnt, referer, reg, dt: "" + d};
Here, we create a JSON object which contains all the data to be written to the database
Now the fun part - we write the data to MongoDB
await collection
            .insertOne(info)
            .then(() => {
                res.status(200).send();
            })
            .catch(err => {
                throw err;
            });
        }
        catch(error)
        {
            res.status(500).send();
        }
The above code writes the info object to MongoDB. If it succeeds, we get a HTTP 200 response, or if it fails we get a HTTP 500 response.
Our serverless function is now ready to start recording analytics. Now let’s put it all together and deploy it!

Part 2: Deployment to Vercel

Step 1: Putting it all on Git

Create an account on GitHub (if you don’t have one already) and set up Git on your PC using these steps.
Create a new repository and push your code. If you haven’t used Git before, I suggest this tutorial.

Step 2: Create a free MongoDB Atlas account

Set up a MongoDB account and a free cluster by following these steps.
In the Add your IP address section, add 0.0.0.0/0 so the database can be accessed by all IP addresses. This is necessary to ensure you can connect and read data from Atlas
notion image
Finally, create a database user and make sure you note down the username, password and the connection string as you’ll need it in the next step

Step 2: Create an account on Vercel

Head over to Vercel and choose sign in with GitHub. You may have to enter your phone number for an OTP. Once done, click on New Project → Choose your GitHub repository and click import. Leave all options as they are, Vercel will auto configure the build environment
Open the section on Environment Variables, and add a variable called COLLECTION the value of which will be the collection name in MongoDB.
Add another environment variable called VISITORSDB and add the connection string which you got from the earlier step. Make sure to replace <password> with your MongoDB user password!
This is how your environment variables should look like
This is how your environment variables should look like
 

And deploy!

With everything done, you can finally click on deploy. Wait for a minute or so until the deployment is done. Once done, you’ll get an URL which you can use to access your project.

How do you check your analytics?

That’s simple - just download MongoDB Compass and use the same connection string as above to login. Once connected, click on the collection name on the left and you should see your database with access logs.

And it’s a wrap!

If you have followed along till here, you should have your Linktree deployed on Vercel with analytics enabled. I hope you enjoyed working on your own Linktree as much as I enjoyed writing this tutorial. If you have any doubts, you can reach out to me using my socials on the homepage
As always, happy hacking!

Loading Comments...