Nefarious WIFI Password sniffer wrapped in a Weather APP

Juliana Mei
3 min readOct 31, 2017


Since it’s Halloween, I’ve been working on an evil app side project. Since we started Javascript, we’ve explored NPM and Node.js. At first, JS had me pulling hair out, then I found some cool NPM libraries that redeemed it for me. I was like COOL, I can npm install wifi-password. This library returns the current wifi name and password in the terminal. Which means I could store those credentials in a database. But how could I trick users into giving me their username and password? Yes, I need to wrap it in an innocuous app, something that needs to ask you for your password to get your location…. the darksky weather app. Most users are not tech savvy, they will type in their password without question! So I started the weekend on this evil side project. I started to LOVE js.

I built it in node.js using google map geolocation API to get latitude and longitude. Pass the latitude and longitude into the second API, dark sky, to get the weather. It was beautiful, I got it working in an evening. Falling in love with JS. Then I started to build the front end and this is when the nightmare started.

I passed the user input (a zip code) to the back with jquery. I realized very quickly that the browser doesn’t recognize require statements. So I npm installed browserify and watchify to get a bundle.js that recognizes js imports. But that didn’t work either. I reached out to a friend for help and he said ‘Why are you even building it with a backend? A simple api call can easily be done in the front.’ Oh ho ho ho, I love it. Keep it simple, right? I scraped the back and rebuilt the front with ajax calls, never having worked with ajax before. I successfully got the API calls to return the results I wanted. Now, when I jquery pass the zip code, I get a result for the first API. But second API would give me an error:

The stuff of nightmares

Ok, so maybe it doesn’t like that I’m doing things asynchronously. So let’s rearrange my code so that I wait for the first result to return. Didn’t work. Let’s try a different get request.

Let’s try XML HttpRequest. Didn’t work.

Let’s try Promises! Didn’t work. Just like that, my whole day is gone.

No matter what I do, I kept getting this CORS error.

The error says I need to include a customized header in the request from my server. But I don’t have a backend, I said. I should be able to do a couple API calls from the front! Interesting fact, Ajax used to have an option where you can say “crossDomain: true” and that’ll bypass it. But that’s been deprecated.

It’s mid-Sunday now. And I’ve scrapped the whole front-only idea. Now I’m rebuilding the whole thing in ExpressJS. If I’m going to have a backend, I’ll DO IT RIGHT. So here I am today, pouring through ExpressJS documentations trying to get a stupid weather app to work. And that moment when I asked myself why I am even building a weather app and realizing this whole nightmare started with a wifi password sniffer — I deserved it. Karma caught up and put me in a hellhole.

.finally(on Monday) I asked Paul about it. He said it’s a browser limitation, when you use other peoples API’s it will limit you to prevent someone else using your API key to make API calls. And then he said something that confused me, he said I’ll have to call my own server to call the other server blah blah blah. WHY IS IT SO COMPLICATED JUST TO MAKE A COUPLE API CALLS?

If anyone is interested, here is the repo:



Juliana Mei

Software Engineer — Blockchain, Cybersecurity, and Commercial Space