I tried to pay for something and ended up debugging third-party spyware

·Clayton Craft

I recently found a mobile data plan from a company that provides service internationally with an eSIM. Honestly, I've been quite happy with the rates and service and want to continue to be a customer. As you can probably tell by the title, it hasn't been all sunshine and roses, as they say.

A few weeks ago, I had a classic "here take my money" situation, I wanted to purchase more credit for my account. This company, like virtually all companies now, offer a "mobile app" for managing your account. No thanks, hard pass. But I'm super lucky though because this company also offers a web portal, and it's entirely possible to manage your account without an app. In theory. Anyways, I went to log in and saw the login prompt on their account portal flash quickly in my browser and then... nothing. A plain white screen. I have all sorts of ad blocking and privacy doo-dads enabled in my browser and on my home network, so I instinctively started twiddling controls to see if I could figure out why the page wasn't loading. I've done this exercise a million times, usually it's some cookie I have to allow through privacy badger, or an exception in ublock origin, or a domain to allow through my unbound filter. I was really struggling to figure out what the issue was in this particular case, because there were LOTS of domains this webpage reached out to when loading.

After discovering that the page does load if I'm connecting outside of my home network, I used Firefox's developer tools to block domains one at a time until I was able to reproduce the issue. It was at this point that Firefox's console gave me another clue: window.FB is undefined Ya, the page was crashing because it was trying to run window.FB, which doesn't exist if it can't fetch the facebook SDK. The login page offers several ways to log in (I personally use the "email" option like a cave person), and one of the options is login through facebook. The page seemed to have a really hard dependency on the facebook SDK though, so much so that it breaks loading the entire login page if it's unable to load the SDK. I currently block all traffic to facebook/meta ASNs at my router, and there's absolutely no way I'm going make an exception for this. Sigh.

I reported this to the company and was surprised to have responses from real people. Unfortunately it has been several weeks, it's still broken, and I still didn't have a way to throw money at them. I would really like to use this service over the summer so I started thinking about how to work around it. There are >1 devices I'd want to use for accessing my account on their web portal thing, so I needed something that was easy to replicate. That ruled out proxying or other complicated "solutions." Firefox userscripts seemed to me like an obvious option, but apparently Firefox doesn't have native support for that and I don't want to add another addon just for this.

While searching for alternatives, I discovered that uBlock Origin, which I already run on all my machines, supports scriptlet injection for running things at document-start, before any page scripts execute. That seemed like exactly what I needed! I would use this to redirect the SDK request to a no-op, and stub out window.FB so any code expecting it doesn't crash! My first attempt:

||connect.facebook.net^$script,domain=app.example.com,redirect=noop.js
app.example.com##+js(set, FB.init, noopFunc)

uBlock Orign's logger confirmed that both rules fired, but the page still crashed. After spending far too long on this task and ignoring all others, I finally realized that I needed to "initialize" the FB thing first before setting init on it. I clearly know what I'm doing (not!), but here we go:

||connect.facebook.net^$script,domain=app.example.com,redirect=noop.js
app.example.com##+js(set, FB, noopFunc)
app.example.com##+js(set, FB.init, noopFunc)

The login page loads fine now with facebook's garbage properly blocked. 😅