Future Forward
Non-profit, 2024–2025

The Mission
Surface students' real interests, not what they think they should like.
Background
Career tests have a known flaw: people answer what they want to like, not what they actually like. Ask someone if they'd enjoy being a doctor and they picture the title, not the work. I wanted a tool that did the opposite: inferring interests from things a person had already done and actually felt something about.
That idea became FF Careers. The first version was a web-only React quiz, and it worked well enough to take the project to Ontario DECA Provincials, where it won Provincial Champion. After Provincials, I rebuilt FF Careers from scratch as part of my internship with the Career Education Council.
Architecture
FF Careers v2 unified what had been two separate codebases, a React web app and a native iOS app, onto React Native (with SwiftUI for the native iOS pieces). One shared codebase across iOS, Android, and Web cut future development time by around 20%, since a feature ships once instead of three times.
The backend is Express + TypeScript. I rewrote 20+ of its APIs with Redis caching and backwards-compatible contracts, which dropped query latency by roughly 30% without breaking existing clients.
The data started in Firestore, but as access patterns got more relational I migrated everything to PostgreSQL, AWS-hosted on EC2 and running in Docker, with sensitive user fields encrypted at rest using pgcrypto. Postgres became the single source of truth. Auth still runs through Firebase on the client and Firebase Admin on the server.
One detail I cared about: typing req.user end-to-end instead of casting to any on every protected route. TypeScript declaration merging extends Express's own Request type, so the decoded Firebase user is correctly typed everywhere downstream.
// declaration merging: req.user is typed end-to-end
declare global {
namespace Express {
interface Request {
user?: DecodedIdToken
}
}
}Instead of a quiz, users log tasks they've actually done (group projects, side hustles, classes) and rate how each one felt. Those ratings build up a signature over time.
The Matching Engine
The naive approach here is a hardcoded mapping from answers to careers, which is exactly the aspirational-bias trap I was trying to escape. Instead, matching is built on embeddings.
Every task (its title, description, and the user's written reflection) gets embedded with all-MiniLM-L6-v2 and stored in Pinecone, keyed to that user. I picked that model deliberately: it's a small, fast sentence-transformer producing 384-dimension embeddings, cheap to run and strong at semantic similarity on short text, which is exactly what a one-paragraph reflection is. A heavier model would have added latency and cost for little real gain at this scale.
A separate namespace holds embedded career descriptions. When a user asks for matches, the backend averages their task embeddings into a single signature vector and runs a top-k nearest-neighbour search against the careers namespace.
// average the user's task embeddings into one "signature" vector
const signature = mean(userTaskEmbeddings)
// nearest-neighbour search against the careers namespace
const matches = await pinecone.query({
vector: signature,
namespace: "careers",
topK: 10,
})Pulling matches from unstructured reflections this way surfaced around 80% more relevant insights than the keyword matching it replaced. The signal comes from how someone describes their work, not whether a keyword happened to appear, so it reflects real experience rather than self-reporting.
Inside the App
You browse careers, log tasks, and rate each one with a score and a written response. That response feeds straight back into your signature, so the more you use it the sharper your matches get.

It's live at ffcareers.app, running off the same codebase as the iOS and Android builds.
I really love the mission behind Future Forward, and beyond building the app I got to contribute to a lot of the org's other initiatives too. Here's a video covering some of that work:
Featured Video
Results
FF Careers generated 481+ career reports, reached users across 8 states, holds a 4.2★ Trustpilot rating, and was featured at an Apple × CEC App Showcase.
Beyond the app, I contributed to a few of Future Forward's other initiatives:
Career Fair: a virtual fair with 6 speakers (a McKinsey analyst, the Basel Medical Group CEO, and others); 53 attendees, 29 personalized reports.
Mentorship: in-class sessions across middle and high schools reaching 400+ students, with a measured +80% lift in self-reported future readiness.
Community: helped seed branches and a 300+ member Discord.
Takeaways
Designing for Real Signal
Embedding real logged work beat any quiz I could have written; the data design was the product.
Shipping Cross-Platform
One Expo codebase to iOS, Android, and Web meant less duplication but careful platform-specific edges.
Building Within an Org
The app mattered more because it plugged into real programs and the students they reached.