Software Engineer
Loading posts...

How we designed and implemented HackPSU's new authentication platform using Next.js, Firebase, and session cookies to secure multiple subdomains with seamless UX.

How I designed and implemented the bulk templated email delivery platform using React, SendGrid, MJML and NestJS for HackPSU organizers.

How we designed and built a comprehensive inventory tracking system for HackPSU using Next.js, React Query, and NestJS to manage thousands of items across multiple event locations.
Feel free to contact me at kanishksachdev@gmail.com
I’ve been working on an ESP32‑based check‑in system that replaces slow QR code scans at workshops with instant BLE detection, a simple “Check In” button in the browser and a reliable backend integration. Organizers no longer need volunteers standing at every door, and attendees get in with one tap on their phone rather than fumbling with a camera.
In the past attendees would line up, open their camera app, scan a QR code, wait for a redirect and click through. That process can take 5–10 seconds per person, and when 100 people arrive at once it turns into a bottleneck. I wanted:
BLE on ESP32 fits the bill. The microcontroller can both advertise and scan, and some modern browsers (Looking at you Apple) support the Web Bluetooth API, so no native apps are required.
/api/checkin endpoint with the user’s IDOn the ESP32 I use the Arduino framework with NimBLE for low‑power scanning. Here’s a simplified version of the setup:
#include <NimBLEDevice.h>
#define SERVICE_UUID "12345678-1234-5678-1234-56789abcdef0"
void setup() {
Serial.begin(115200);
NimBLEDevice::init("CheckIn-Gateway");
NimBLEScan* pScan = NimBLEDevice::getScan();
pScan->setAdvertisedDeviceCallbacks(new MyScanCallbacks());
pScan->setActiveScan(true);
pScan->start(0, nullptr);
}
class MyScanCallbacks : public NimBLEAdvertisedDeviceCallbacks {
void onResult(NimBLEAdvertisedDevice* advertisedDevice) override {
if (advertisedDevice->haveServiceUUID() &&
advertisedDevice->isAdvertisingService(
NimBLEUUID(SERVICE_UUID))) {
String deviceAddr = advertisedDevice->getAddress().toString().c_str();
checkInUser(deviceAddr);
}
}
};
void checkInUser(const String& deviceAddr) {
// HTTP POST to our backend
HTTPClient http;
http.begin("https://api.hackpsu.org/api/checkin");
http.addHeader("Content-Type", "application/json");
String body = "{\"device\":\"" + deviceAddr + "\"}";
int code = http.POST(body);
http.end();
}
The ESP32 scans indefinitely for BLE advertisements that include our custom service UUID. When it finds one it extracts the MAC address and calls the backend.
On the browser side I use plain JavaScript to start advertising for a few seconds when the user clicks Check In.
async function advertiseForCheckIn() {
const options = {
services: ['12345678-1234-5678-1234-56789abcdef0'],
optionalServices: []
};
try {
const device = await navigator.bluetooth.requestLEAdvertisement(options);
// The browser advertises for a short period automatically
// We rely on the ESP32 to scan and pick us up
fetch('/api/checkin', {
method: 'POST',
headers: {
'Content-Type': 'application/json'
},
body: JSON.stringify({ device: device.id })
}).then({...});
} catch (err) {
console.error('BLE advertise failed', err);
alert('Please enable Bluetooth to check in');
}
}
document.getElementById('checkin-btn')
.addEventListener('click', () => {
advertiseForCheckIn();
});
Note that not all browsers support Web Bluetooth advertising, Chrome on Android works, desktop Safari does not. I include a fallback QR code option for unsupported browsers.
I built a BLE check‑in using ESP32 and Web Bluetooth that replaces slow QR scans, plugs into our existing Next.js auth and attendance services, gives real‑time counts via WebSockets and leaves room for better device security and broader browser support.