Hello! ๐Ÿ‘‹

I'm Yash Mahalwal

Senior Software Engineer focused on frontend performance and realtime product systems at scale.

profile.ts
const engineer = {
  name: "Yash Mahalwal",
  role: "Senior Software Engineer",
  focus: "Frontend performance + realtime systems",
  currently: "Building product experiences at scale",
  ethos: "Quality without compromise"
}

About

Senior software engineer with five years building web and mobile products used by over 10 million people. I specialise in performance and real-time systems. My core work is frontend engineering with React, Next.js and TypeScript, with enough backend depth to design and own the systems that support the product.

10M+ Users reached
80% Faster payments
8s โ†’ 1.5s Page load (LCP)
100K+ Live events

I work best where engineering decisions connect to user outcomes and product metrics. I care about simple, reliable systems that are easy to reason about, easy to change, and stable enough to keep working as the product grows.

Experience

GrowthDay

Senior Software Engineer

Event-driven payments, live events at scale, and faster pages. payments pipeline100K+ live interactiveNext.js SSRA/B testing
  • Moved payments to a queued, event-driven pipeline with idempotent endpoints; checkout dropped from 12–17s to under 3s.
  • Scaled live events from 500 to 100K+ participants (up to 10M viewers) by moving from P2P to SFU and HLS.
  • Cut LCP from 8s to under 1.5s with Next.js SSR, React Server Components, streaming, and caching.
  • Ran A/B tests with product and marketing; mentored engineers on experimentation.
GrowthDay

Frontend Developer

A real-time discussion platform, stronger OTT playback, and shared web/mobile code. WebRTCWebSocketsOTT streamingcross-platform
  • Built a real-time discussion platform on WebSockets and WebRTC (peer-to-peer) for video, chat, and live interactions on web and mobile.
  • Improved OTT playback with adaptive streaming, buffering, and a persistent mini player; completion up 35%.
  • Shipped a shared web/mobile module synced by CI; cut duplicated logic about 50%.
  • Refactored web and mobile codebases; cut bundle size, network use, and rendering, reducing infrastructure costs about 50% and server overload under high traffic.
American Express

Product Analyst Intern

ML deployment tooling, rollout pipelines, and distributed training infrastructure. ML deploymentserror handlingmodel rolloutScala & Hadoop
  • Built error handling for ML model deployments; unhandled failures down about 70%.
  • Enabled new models through internal deployment pipelines.
  • Built distributed training on Scala and Hadoop for internal ML platforms.
Appointy

Product Developer Intern

Routing architecture, scheduling rules, onboarding forms, and SSR for SEO. nested routingrecurrence UIform builderSSR & GraphQL
  • Built nested layouts and dynamic routing for a more maintainable frontend.
  • Shipped a recurrence rule UI for scheduling; efficiency up about 3x.
  • Built a drag-and-drop form builder; client onboarding time down about 60%.
  • Added SSR with GraphQL; organic traffic up about 35%.

Projects

GitHub Action

Fark.ai

An agentic GitHub Action for backend pull requests. It catches breaking API changes in the diff, confirms real impact by scanning frontend codebases in parallel, and posts review comments. Per-agent token budgets keep runs bounded, and when a limit is hit the pipeline wraps up cleanly and still posts what it finished. That is what makes it work on larger PRs.

4-agent pipeline parallel frontend scan token budgets graceful degradation PR review
4-agent pipeline
01 BE Analyzer Breaking API changes from the diff, grouped into batches
02 Frontend Finder ×N One scan per frontend × batch. Parallel, capped, bounded context per run
03 Comment Generator Impacts merged by batch and change, inline markdown on diff hunks
04 PR Poster Posts the PR review. Summary and comments that could not anchor inline go in the review body.
  • Runs on backend pull requests with frontend repos checked out on the runner. The BE analyzer reads the diff for breaking API surface changes only: REST, GraphQL, and gRPC. Not incidental refactors or style nits.
  • Those changes are grouped into batches with diff line anchors. Each batch is a bounded unit of work for downstream agents instead of re-scanning the entire PR on every pass.
  • A separate frontend finder runs per frontend and batch pair, up to five in parallel by default. Each searches its checkout for confirmed consumer breakage, not speculative string matches.
  • The comment generator merges impacts by batch and change, then writes inline markdown on the matching diff hunks. The PR poster submits the review. Anything that cannot anchor inline lands in the review body with the summary.
  • Every agent run has its own token budget. At 85% it gets a wrap up nudge while tools still work. At 100% tools are cut off and it must return structured output. Past 125% the run aborts. A large PR still ships a useful review, not a crashed Action.
npm package

React Synced State

One user action can open a confirmation modal, a side drawer, and a success toast in the same tick. One shows at a time; the rest wait. Nav, page, and global UI stay on separate layers so a menu and a checkout dialog never compete.

render-time sync per-layer queues max-heap priority mutex ticketing
Open order
Nav
Menu priority 2 opens now active
Page
Modal priority 2 opens now active
Drawer priority 1 opens 2nd waiting
Alert priority 0 opens 3rd waiting
Global
Toast priority 1 opens now active

Page had three overlays waiting in line. Nav and global each had one and showed right away.

  • Built after hitting a React Native edge case: opening several modals in the same tick can freeze the app on some RN versions. The same collision shows up on web as stacked dialogs and bad focus order. The library serializes which overlay is actually visible instead of letting every boolean flip open at once.
  • One click can open a confirmation modal, a side drawer, and a toast together. With plain state they all show. Each surface gets a ticket on its layer; the layer is a mutex, so only the front reads as open and the rest stay closed until their turn.
  • Nav menus, page dialogs, and global toasts sit on separate layers. Each layer is its own mutex with an independent queue, so a hamburger menu and a checkout modal never share a lock or wait on each other.
  • On the page layer, a critical error dialog outranks a routine settings panel because it has higher priority; ties go to whoever opened first. Tickets sit in FIFO queues per priority and a max-heap picks which priority runs. Deletes are lazy: empty priorities leave the heap until the next lookup cleans them up.
  • The provider keeps the queue in a ref and only re-renders when a layer’s front ticket changes, not on every enqueue. Queued hooks return the last closed value during render, so nothing flashes open for a frame. Non-boolean state works too: you define when a value counts as closed instead of forcing everything to true or false.
Parcel plugin

Parcel Add Source

When a docs page shows a live component beside its source, hand-copied snippets drift. This Parcel transformer embeds the file text in the same module at build time, so the demo and the code panel stay matched. The test suite publishes the plugin locally, runs a full Parcel build on a sample project, and verifies the output in Bash.

docs toolchain bash + yalc tests configurable encode actionable diagnostics
Build-time flow
01 Glob in .parcelrc In .parcelrc, each transformers key is a file glob. Only paths like **/CodeSamples/**/*.{ts,tsx} run add-source; everything else skips this plugin so dev builds stay fast.
02 Read source Runs first, before TypeScript. Grabs asset.getCode(): the text you see in the editor, not compiled output.
03 Inject export Encodes the file (base64 by default), then your addSourceCode hook appends __sourceCode to the module.
04 Docs import One import returns the live component and SourceCode. Preview and source panel always match.
Test harness
01 yalc link pretest publishes the built plugin and adds it to test/project before bats runs.
02 Run build Each case copies a config template into the fixture, then runs parcel build on the sample app.
03 Check result Valid config: grep the bundle for the encoded source. Invalid config: CLI shows the expected diagnostic hint.
04 Clean up Teardown: npm run clean drops build/, cache, and the temp config. Suite end: posttest unlinks yalc.
  • Built for the React Synced State docs site. Each sample under CodeSamples/ is one import: the running demo and the source panel both come from that module, so neither can drift on its own.
  • Parcel decides which transformer runs from the glob keys in .parcelrc. This repo scopes add-source to **/CodeSamples/**/*.{ts,tsx} so only demo modules under CodeSamples/ get an embedded __sourceCode string. Widening the glob (for example **/*) would run the plugin on the whole app and slow every dev build.
  • For files that match, add-source must be first in that glob’s transformer list. Anything after TypeScript would embed compiled JavaScript in __sourceCode, which is useless in a docs sidebar.
  • transformer-add-source.config.js exports addSourceCode and an optional encode. Parcel tracks that file as a config dependency, so edits invalidate cached transforms without a manual cache wipe.
  • Parcel ships no transformer test utilities, so integration tests are Bash. npm test links the plugin with yalc, runs bats against test/project, and each case builds the fixture with a different config template. Assertions grep the bundle or read the CLI diagnostic. Each case ends with teardown: npm run clean in the fixture removes the build output, Parcel cache, and the config file that case copied in. When the suite finishes, posttest unlinks yalc from the sample project and clears yalc from the plugin repo so the next run does not inherit stale installs or artifacts.
  • A typo in the glob key or a missing transformer-add-source.config.js fails with ThrowableDiagnostic and a hint in the terminal or dev-server overlay. A wrong addSourceCode signature shows “Invalid transformation function”, not an opaque plugin crash.

Writing

Performance ~20 min

Optimising React Apps

A profiling walkthrough on a real-time stock UI. Covers memoization, state batching, list virtualization, and throttled state updates applied in sequence to measure the impact of each change.

Data / SSR ~15 min

Relay Modern: SSR and Next.js

How to integrate Relay with Next.js for server-side rendering. Covers per-request environments, prefetching with fetchQuery, and serializing the store so the client hydrates without refetching.

Code Sharing ~12 min

Sharing Code Between Projects

Five approaches to sharing code between a web app and React Native: npm packages, Bit, monorepos, git submodules, and file sync, with trade-offs on versioning, DX, and access control.

Security ~5 min

The Heisenberg Manoeuvre

A walkthrough of how a malicious npm package could capture keystrokes while remaining invisible to DevTools. Written as an exercise in understanding supply-chain attacks.

I'd love to hear from you

Open to full-time roles, contract work, part-time engagements, and collaborations.

I've worked on fast pages, live events at scale, payments, and A/B experiments with product. I look forward to difficult problems and an environment that takes engineering seriously.

Available
  • Full-time
  • Contract
  • Part-time
  • Collaboration