Building a quick uptime monitor for the home office Internet connection
At home I have a gigabit-grade fiber optic connection. It’s been super stable and solid for months. Until last weekend, Youtube stopped working for the kids in the living room TV. I did a quick test and saw that my network backbone was all green, but something wasn’t working. It was a hardware issue on the ISP, which affected my connectivity for an hour or so.
I hadn’t bothered to build a network connectivity monitoring system for my home and home office Internet connection. So this little incident was a good reminder for me to get to it!
A brief background
I’ve written about different monitoring solutions in the past couple of years infrequently. See here for how to monitor expiring SSL certificates, and see here for how to monitor a website. For both of these solutions, I’ve used Azure Application Insights. It’s a clever and affordable service that can be adjusted for all sorts of things. And as you might guess, I’ll use it again to ping my home connection from Azure.
Overview of the solution
I want to monitor if my Internet connection goes down. Ideally, I’d like to build the monitoring outside of my home, so I won’t have to rely on a local compute capacity (such as a virtual machine or a Docker container) to verify if I’m connected. If the connectivity fails, it is hard for the monitoring system to notify me.
Application Insights is capable of pinging HTTP and HTTPS endpoints, so I only need to expose an endpoint externally. It turns out I already have one – I’m using the Plex Media Server system to manage my movies and TV episodes. And Plex exposes a little API with some level of authorization. Let’s try to use that!
The overall solution is rather simple: configure Application Insights to ping my Plex API endpoint every 5 minutes – if it fails, alert me. If I get a proper response (HTTP 200 OK essentially), then do nothing. That’s it.
The Plex API
Plex runs on a physical server for me at home. It exposes an external TCP port at 32400 for clients to connect to my media library. This is useful when traveling and wanting to watch TV remotely, for example.
The API is accessible through the same port. Documentation for the API can be found here. To authorize through the API, we’ll need a Plex Token, which has to be passed as a query string parameter called X-Plex-Token
.
You need to grab the token somewhat clumsily via the Plex media interface under Library
> Any media item
> Get Info
> View XML
> grab the token from the URL. A typical token looks like this:
It’s a 20-character alphanumeric string that seems to derive from your credentials. You’ll have to reset your Plex account password if you want to void any existing token.
With a working token, all we have to do is to query for something from Plex – such as a list of all libraries. The syntax is http://[IP address]:32400/library/sections/?X-Plex-Token=[PlexToken]
.
We can try this with curl
:
To verify we’re getting a proper HTTP response code, we can use curl -I <API-ENDPOINT>
:
Configuring App Insights
Now that we have a working endpoint, it’s easy to hook up App Insights to ping it.
Once you’ve provisioned a new App Insights instance, open Availability
and add a Standard Test
.
We need the URL endpoint – this is the Plex API endpoint (exposed externally). The token has to be part of the query. We test every 5 minutes from at least 5 locations (as per recommendations to make this worthwhile), and we expect an HTTP response of 200 OK.
If it fails, we use the built-in Azure alerting capability in Azure Monitor to do something – perhaps send an email to ourselves, or trigger something more advanced via Logic Apps or Microsoft Teams.
Once configured, it just works:
Ideas for a more advanced solution
There are a few issues here, though. You’ll need to have Plex running at all times, and if your Plex instance fails, the monitoring fails – even if your Internet connection still works. Ideally, I’d move the endpoint to a self-hosted Docker container or virtual machine that exposes a simple REST API.
In addition, the Plex API is now exposed externally without further limitations. I could further limit this by only allowing traffic from specific App Insights IP addresses. You can find the list here.
Lastly, I wish I could utilize Tailscale for this, but sadly, App Insights can’t tunnel through my Tailscale instance.