Projects · 31 of them, 19 live in production

Things I've built.

Most of them run at a dental practice.

01Live · Jun 2026 to present

Patient Dashboard

One row per patient, with linked records one click away, and a live read only mirror the apps that need it read through.

02Live · Sep 2026 to present

Capacity Planner

Demand, capacity and capability across three offices, in one forward view. It reads and never writes back.

03Live · May 2026 to present

Doc Coach

Grades every implant consult from its Zoom call and sends a colored report to the doctor, the treatment coordinator and the CEO.

04Live · Jun 2026 to present

28,745Recordings the poller read

NPC Coach

Finds the new patient calls among thousands of recordings and grades each one with a transcript quote behind every score.

05Live · May 2026 to present

14.5 hrsFirst commit to v1.0.0

Treatment Estimator

Every saved line keeps the price it was quoted.

06Live · Jun 2026 to present

Centralized Diagnostic Filter

Intake and experience surveys where Gemini writes the doctor's page and reads the panorex under the founder's own rules.

07Live · Sep 2026 to present

Hybridge Forms

Our own forms service, built around one rule: no submission is ever lost.

08Open source · Jun to Oct 2026

JobPilot

My open source job hunt autopilot. It scored each role against my profile and tailored a resume and cover letter per match.

22More, in the belt

The rest of the system.

Each one shaped by what it does. Click to open.

The projects in cards
The whole system Skip to all 31 projects

Scroll to fly·Drag to turn the system·Click a world to go thereTap a world to go there

The projects.

Demos

31 of 31

Patient Dashboard, Hybridge Implants LLC

LiveJun 2026 to present

Patient Dashboard

I built the staff side of our patient platform: one row per patient.

453 of 453Blind test against bookings: every chart the record linker picked was right

Read the write up
Case study

I built the staff side of our patient platform: one row per patient, with linked records one click away, and a live read only mirror of the practice management system that the estimator and capacity planner read through.

  • 453 of 453Blind test against bookings: every chart the record linker picked was right
  • 2.6 minHow far the Denticon mirror trailed once the sync ran on a timer, down from 6.0 days
  • About four in fiveIntakes link to their chart on their own
  • 259 linksPut onto charts by the first backfill with 0 errors, each audited and undoable

Problem

Coordinators had four tabs and four ids for one patient. Each system named a patient its own way: the intake survey by response id, the estimator by its own number, the consult grader by Zoom meeting, the experience survey by email. The Denticon id sat in three of them as a hand typed field nothing checked, so it joined nothing.

Solution

Two Cloud Run services from one image. The dashboard, behind Google sign in limited to the company domain, holds no Denticon credentials; a sync service that serves no pages holds them. Webhooks and three scheduled jobs keep a Firestore mirror of offices, providers, patients and appointments current, and a registry API with one secret per caller serves it to the estimator and the capacity planner. Profiles join linked records on the Denticon id at read time.

Process

The vendor API has no patient search, so the mirror is the only patient index there is. It also ignores unknown query parameters and returns the whole table with a 200, so a parameter is allowed only once it is proven to change totalCount. The record matcher was attacked from three angles before it could write, ran in shadow mode, and refuses when unsure. A person's decision always wins: each link write is a transaction that decides again on fresh documents, and every link is versioned, audited and undoable. A journey step with no linked chart reads as unknown.

Result

Started in June 2026 and rebuilt around the Denticon API in September; the sync read the live practice on 29 September. Once the sync ran on a timer the mirror went from 6.0 days behind to 2.6 minutes behind, the linker picked the right chart 453 times out of 453 in a blind test against bookings, about four in five intakes link to their chart on their own, and the capacity planner reads the registry every minute.

Highlights

  • Two Cloud Run services from one image: the dashboard holds no vendor credentials, and the sync service that holds them serves no pages.
  • A query parameter is allowed only once it is proven to change totalCount, because Denticon ignores unknown ones and still answers 200.
  • 77 vendor API operations transcribed, and 14 filters proven before any of them is used.
  • Record matcher attacked from three angles before it could write (4 critical and 11 high findings), then kept in shadow mode.
  • Registry API with one secret per caller, so revoking one consumer never blinds another.
  • 18 webhook subscriptions across three offices, with an hourly sweep and a nightly poll behind them.
  • Caught an hourly sweep printing swept=0/0 while every call failed, and secrets that carried a hidden Windows carriage return.

Built with

  • Next.js 15
  • TypeScript
  • Firestore
  • Cloud Run
  • Cloud Scheduler
  • Cloud Storage
  • Cloud Build
  • GitHub Actions
Capacity Planner, Hybridge Implants LLC

LiveSep 2026 to present

Capacity Planner

One forward view of demand, capacity and capability across three offices.

Every minuteSync from our Denticon mirror, with no vendor credential in the planner

Read the write up
Case study

I replaced the operations lead's staffing workbook with a planner that shows demand, capacity and capability across three offices, reads our Denticon mirror every minute, and never writes back.

  • Every minuteSync from our Denticon mirror, with no vendor credential in the planner
  • 0 write methodsToward Denticon, held there by a test that fails the build
  • 360 of 360Day cells from the old workbook the engine reproduces on every test run
  • 17 daysFrom the first commit on Sep 11 to production on Sep 28

Problem

Staffing for three offices lived in the operations lead's workbook: twenty pasted copies of the same week. Fixed ranges undercounted silently when a row landed outside them, typing over a formula deleted it, and time off entered later never changed the plan. The real cost was last minute coverage calls, and a doctor slammed at one office while another had a free chair.

Solution

A pnpm monorepo: a pure TypeScript engine package with no I/O, and a Next.js 16 app on Cloud Run with Cloud SQL Postgres, Drizzle and Google sign in. The same engine runs in the minute sync and in the browser for instant what if changes, golden tested against the workbook. Bookings come from Denticon through the patient dashboard's registry, so the planner holds no vendor credential and only reads.

Process

Read only is a type level test: the appointment source may have no member named like write, create, update, delete, cancel or book. A mass cancel guard stops any sync that would cancel an office's bookings in bulk and changes nothing, after a silently dropped office code nearly did exactly that. Sync failures return 200 so the scheduler does not retry storm, and staleness shows on a status pill. Cover suggestions rank five keys (capability, willingness, presence, free day, pairing), and every reason shown comes from the rule that produced it.

Result

v0.1.0 reached production on 28 September 2026, 17 days after the first commit, and the first full read of live Denticon data landed at 5:34 the next morning. The operations lead and the office directors plan from it every day, with a Room Board since 20 October and a 7 AM weekday email of what needs action. It cost $27 to run from October 1 to 28, measured.

Highlights

  • Pure engine package with no I/O: the same math in the minute sync and the browser's instant what if, golden tested against the workbook.
  • Postgres over Firestore for person by weekday by location joins; NextAuth over IAP alone so roles and the audit log know who signed in.
  • Its own cloud project, to isolate patient data and stay clear of a sibling app's database connection ceiling.
  • Minute sync behind a version pointer; failures return 200 and show up as staleness.
  • Excel files parsed in the browser and never stored.
  • The logger describes a failed query by its Postgres code, constraint and table only, and an integration test proves no log line carries a patient style name.
  • Cover suggestions ranked on five explainable keys, with ties broken on person id.

Built with

  • Next.js 16
  • TypeScript
  • Cloud SQL Postgres
  • Drizzle
  • NextAuth
  • Cloud Run
  • Cloud Scheduler
  • Playwright
Doc Coach, Hybridge Implants LLC

LiveMay 2026 to present

Doc Coach, Consultation QA Pipeline

I built the tool that grades every implant consult from its Zoom call.

471Consults scored live from May 19 to Oct 28

Read the write up
Case study

I built the tool that grades every implant consult from its Zoom call and sends a colored report to the doctor, the treatment coordinator and the CEO.

  • 471Consults scored live from May 19 to Oct 28
  • 2.7 minMedian transcript to report, Oct
  • 7 + 25Criteria and sub checks
  • 392Older consults regraded on the same rubric

Problem

Consult reviews were written by hand against the CEO's seven criterion Word document, and nothing graded every consult.

Solution

One Cloud Run service in Python. A Zoom webhook starts it when a transcript is ready; it checks the signature, finds the doctor, and asks Vertex AI Gemini 2.5 Pro for a scorecard as JSON against a versioned rubric prompt and schema. Every rationale must quote the transcript with a real timestamp, and each score is colored against that doctor's own 30 day average before the report and PDF go out.

Process

The doctor is found in three layers: Zoom participants against the doctor directory, then transcript speaker labels, then the names Gemini pulls out while scoring. A response that did not finish cleanly is never accepted, and the token budget doubles on a retry. Instead of Workspace domain wide delegation, the pipeline uses an OAuth grant kept in Secret Manager.

Result

471 consults scored live from May 19 to Oct 28 across three offices; median 2.7 minutes from transcript to sent report in October. 392 older consults from November 2025 to May 2026 were regraded on the same rubric, so the trends start in November.

Highlights

  • 471 consults scored live from May 19 to Oct 28 across three offices; median 2.7 minutes from transcript to sent report in October.
  • Versioned rubric prompt and JSON schema for every Gemini response, with a real timestamp behind every quote.
  • A truncated response is never accepted; no consult needed a second scoring attempt in October.
  • A ledger row per consult, joined to Monday.com case outcomes for analytics.
  • An OAuth grant kept in Secret Manager instead of Workspace domain wide delegation.
  • Report cards for every doctor each Monday at 8 AM and on the first weekday of each month.

Built with

  • FastAPI
  • Vertex AI Gemini 2.5 Pro
  • Cloud Run
  • Firestore
  • BigQuery
  • Gmail API
NPC Coach, Hybridge Implants LLC

LiveJun 2026 to present

NPC Coach

I rebuilt a brittle n8n call grader into a coaching platform.

690Real calls graded from June 17 to October 29

Read the write up
Case study

I rebuilt a brittle n8n call grader into a coaching platform: it finds every new patient call, grades it with a quoted transcript line behind each score, and tracks each coordinator's trend.

  • 690Real calls graded from June 17 to October 29
  • 14 minMedian from call end to grade, October
  • 40 / 40 / 20Weighted score + 3 hard gates
  • 16 daysFirst commit to live calls

Problem

An earlier n8n grader proved the idea. Every hour it scored calls as a flat sum out of 60, wrote each result into a Google Doc and emailed a link. It kept no database, so no coordinator had a trend, and no quote stood behind a score.

Solution

A full rebuild on Google Cloud. Every five minutes from 6 AM to 6 PM a Cloud Run Job takes the new recordings from the phone system's SFTP drop, transcribes them with Vertex AI Gemini, keeps the new patient calls, and grades each on six criteria with a transcript quote behind each score, plus three hard gates. Verdicts land in BigQuery, and each coordinator gets the report by email.

Process

The model returns integers and gate answers; plain Python does the 40/40/20 math, so the same verdict always gives the same score. Hard gates show as a flag beside the score. A run lease stops overlapping runs from grading or emailing a call twice.

Result

690 real calls graded from June 17 to October 29, out of 28,745 recordings the poller read; a median 14 minutes from the end of a call to its grade in October. Live calls were graded 16 days after the first commit. Live on Cloud Run behind Google sign in.

Highlights

  • Full rebuild of an n8n prototype: weighted 40/40/20 score, 3 hard gates, a patient urgency state.
  • A verbatim transcript quote behind each of six scoring criteria.
  • The model returns integers and gate answers; plain Python does the 40/40/20 math, so the same verdict always gives the same score.
  • BigQuery system of record behind a React dashboard with per coordinator trends, each colored against their own 30 day average.
  • A 70 minute run lease after overlapping runs sent every report twice.
  • Booking rate is not graded: the playbook calls a patient who books to get off the phone a failure of advocacy.

Built with

  • Python
  • FastAPI
  • Vertex AI Gemini
  • React
  • TypeScript
  • BigQuery
  • Cloud Storage
  • Cloud Run
  • pytest
Treatment Estimator, Hybridge Implants LLC

LiveMay 2026 to present

Treatment Estimator

I rebuilt the practice's quoting tool so every saved line keeps the price it was quoted.

14.5 hrsFirst commit to v1.0.0

Read the write up
Case study

I rebuilt the practice's quoting tool so every saved line keeps the price it was quoted. v1.0.0 shipped 14.5 hours after the first commit, followed by visit sequences and the day's consult schedule as its front page.

  • 14.5 hrsFirst commit to v1.0.0
  • 4 fieldsFrozen on every saved line: price, tier, label, price book version
  • 5Pricing model kinds
  • $34Measured cloud cost, October 1 to 28

Problem

Coordinators quoted from one shared price list with no office prices or tiers. The six month price promise was a line on the PDF, and nothing held a saved quote to it.

Solution

Next.js 16, Postgres and Drizzle. Five pricing model kinds (flat, tiered, tiered by zone, price range, per surface), and every saved line keeps its captured price, tier, label and price book version, so a later price change never reaches a saved quote. Each office has its own versioned price book, and only an admin publishes a change.

Process

Nine architecture decisions written on May 6, before any code. The pricing engine tests reached full coverage at 2:32 AM on the first night, and v1.0.0 shipped 14.5 hours after the first commit. A list of questions with worked numbers let the practice review pricing without reading code.

Result

Live since May 8, 2026. Since then: a drag and drop workspace with phases and scenarios, an Excel export that matches the coordinator's own file, a landing page that is the day's consult schedule, visit sequences built from the estimate, the Hybridge design in one day on September 29, and reopening a presented estimate as its next revision on October 28. It cost $34 to run from October 1 to 28, measured.

Highlights

  • Nine architecture decisions with tradeoffs, written before any code.
  • Every saved line keeps its captured price, tier, label and price book version, so the six month price promise holds.
  • Full test coverage on the pricing engine, and a never check so a new pricing model cannot go unhandled.
  • Visit sequences generated from the estimate and edited in a three pane builder, from the shared Treatment Sequence packages.
  • The landing page is the day's consultation schedule, read from the patient dashboard's registry API.
  • An estimate's arch now comes from its options, so the up front Upper, Lower or Both question is gone.
  • Reopening a presented estimate moves its rows into the next revision, because payments point at option and line ids.

Built with

  • Next.js 16
  • TypeScript
  • Drizzle
  • PostgreSQL
  • Auth.js
  • Cloud Run
  • @react-pdf/renderer
  • Zod
Centralized Diagnostic Filter, Hybridge Implants LLC

LiveJun 2026 to present

Centralized Diagnostic Filter

The practice's own intake and experience surveys, with Gemini writing the doctor's page and a panorex read under the founder's written ruleset.

6Gemini calls, each through one retry and fallback chain

Read the write up
Case study

I built the intake and experience surveys where Gemini writes the doctor's page and reads the panorex under the founder's own rules, and the clinic email waits for both reports.

  • 6Gemini calls, each through one retry and fallback chain
  • 2 of 2Reports before a clinic list gets an email
  • 4 casesThe founder walked through and narrated, turned into the written ruleset
  • 0.3 sFor an experience survey submit to return; the reports follow in the queue

Problem

The pre consult assessment ran on a third party intake platform. The practice did not own its patients' answers, one person could edit a question or add a recipient, and each report was filed by hand.

Solution

An intake and experience survey owned by the practice on Google Cloud. Each submit becomes one Cloud Task for the renderer, which draws the patient summary and the doctor report, with Gemini writing the psychographic and reading the panorex. The governing rule is AI assists, doctors validate.

Process

Our founder walked me through four cases, narrating every call. I turned the narration into a written ruleset where each rule cites its case and timestamp, and implemented it as a Gemini read with structured output: the model lists the teeth, and plain code recomputes the score. Every Gemini call goes through one chain of retries and newer fallback models inside a time budget.

Result

Patients at all three offices fill in the intake before a consult. The founder's review of the first reads shipped as ruleset v2 on 8 July, and since 23 October the clinic email goes out with both reports or waits.

Highlights

  • Turns a veteran clinician's narrated reads into a written, cited panorex ruleset and a running Gemini read.
  • The founder's review of the first AI reads shipped as ruleset v2.
  • The model observes and the code counts: Gemini lists the teeth, and plain code recomputes the score.
  • Every Gemini call has a way out: three tries on the same model, then newer models, inside a time budget.
  • The clinic email waits for both reports, after a single 429 once sent the summary alone.

Built with

  • TypeScript
  • Next.js
  • Cloud Run
  • Cloud Tasks
  • Vertex AI Gemini
  • Firestore
  • Terraform
  • PDF generation
Hybridge Forms, Hybridge Implants LLC

LiveSep 2026 to present

Hybridge Forms

I built our own forms service for our practice websites, around one rule: no submission is ever lost.

15 secondsAbout how long the browser retries with the same id before it keeps the answers on the device

Read the write up
Case study

I built our own forms service for our practice websites, around one rule: no submission is ever lost.

  • 15 secondsAbout how long the browser retries with the same id before it keeps the answers on the device
  • 0Answers, names, emails or phones in any log line
  • 67 leadsAlready on the Monday board got their missing tracking fields on Oct 26, the day the gap was seen
  • $9Measured Google Cloud cost in October, a partial month

Problem

Lead forms on our websites had to keep every inquiry, protect patient privacy, work on a phone, land on the Monday board, and handle conditional questions and spam.

Solution

One owned platform: a public forms app with an embed script, a delivery worker that puts each inquiry on the Monday Leads board and emails the copies, a dashboard and form builder behind IAP, and nightly checks.

Process

Built around one rule: no submission is ever lost. If Firestore fails, the answers go to a private Cloud Storage bucket and the visitor still sees success. If both fail, the server answers 503 and the browser retries over about 15 seconds with the same id, then keeps the answers on the device. A queue task wakes the worker on every send, and a sweep runs every minute.

Result

Live since 6 October 2026. Elmwood's contact form has run on it since 14 October, and on 26 October all six tracking fields reached the Monday board, and the 67 leads already there got their missing ones.

Highlights

  • Firestore first, a private Cloud Storage bucket as the fallback, and the visitor still gets a success.
  • The browser retries over about 15 seconds with the same id, then keeps the answers locally.
  • The logger drops patient fields by name and by shape, so no answer reaches a log line.
  • Every inquiry lands on the Monday board with email copies, in one Hybridge look.
  • A delivery worker wakes on every send, and a sweep runs every minute.

Built with

  • TypeScript
  • Firestore
  • Cloud Storage
  • Cloud Run
  • Cloud Tasks
  • Cloud IAP
  • Vitest
Hybridge Platform, Hybridge Implants LLC

LiveMar 2026 to present

Hybridge Platform

45 live services on 14 Google Cloud projects, with one service holding the Denticon credentials for the apps that need it.

45 servicesLive on Google Cloud across 14 projects, checked Oct 29, 2026

Read the write up
Case study

I mapped the 45 live services I built for a three office practice and its lab, across 14 Google Cloud projects, and the patterns that keep them running.

  • 45 servicesLive on Google Cloud across 14 projects, checked Oct 29, 2026
  • 1 key holderFor Denticon: the apps that need it read the mirror through the CDF registry
  • 1 minThe tightest loops: the planner reads the book and the forms worker sweeps
  • $132Google Cloud from Oct 1 to 28 for the six projects the billing export measured

Problem

Hybridge runs three offices and its own lab on systems that do not talk to each other: Denticon for charts and bookings, Monday for leads and patient boards, Zoom for consults, a phone system that records calls, the lab's case and scan systems, and a lot of spreadsheets. Every team brought one problem.

Solution

Solve each problem where the data already lives. Three shared services carry the most weight: the Denticon sync keeps a copy of Denticon, the CDF registry serves it to other apps, and the PDF renderer turns surveys into reports.

Process

One service holds the Denticon credentials, and the apps that need it read the mirror. Six apps file feature requests through one relay into one list, and a request filed on October 28 was live 19 minutes later.

Result

45 live services in 14 Google Cloud projects on October 29, 2026. The six projects the billing export measured cost $132 from October 1 to 28.

Highlights

  • 45 live services in 14 Google Cloud projects, listed read only with gcloud on Oct 29, 2026.
  • One Denticon key holder; the estimator and the planner read through the CDF registry.
  • The tightest loops run every minute: the planner's sync and the forms delivery sweep.
  • Six apps file feature requests into one list through one relay.

Built with

  • Cloud Run
  • Firestore
  • Cloud SQL
  • BigQuery
  • Cloud Scheduler
  • Cloud Tasks
  • Vertex AI Gemini
  • Cloud IAP
Treatment Sequence, Hybridge Implants LLC

LiveAug 2026 to present

Treatment Sequence

I replaced hand built Word visit plans with shared packages.

11Practice masters transcribed word for word as data, all validated

Read the write up
Case study

I replaced hand built Word visit plans with shared packages that generate the plan from an estimate, let the coordinator edit it in a three pane builder, and export it to Word and PDF.

  • 11Practice masters transcribed word for word as data, all validated
  • 0 errorsIn 271 generation attempts across every live production estimate, audit of Aug 27
  • 4.5 hoursFrom the first commit to the builder live in the estimator, Aug 27
  • 0 tokensShipped as a committed build snapshot, so no registry credential can expire

Problem

Coordinators wrote each patient's visit plan by hand in Word, copied from master documents in Drive. Every change meant renumbering the visits and redating everything after it by hand, on a case that can run for months.

Solution

Two packages. sequence-core holds the domain model, the practice masters stored as data, generation from an estimate, date and wait arithmetic, and the Word and text renderers, with no React. sequence-ui is a three pane React editor: visit list, flowchart and a live document preview. The estimator stores a living plan plus immutable version snapshots, and one shared text module keeps the preview, Word and PDF from drifting apart.

Process

Generation picks a transcribed master that fits the estimate. A procedure with no matching visit prints as a yellow open item, an unsupported combination asks for a manual build, and a free text wait stops date projection instead of guessing. The packages reach the estimator as a committed build snapshot stamped with its source commit, and a check fails if core and ui come from different commits.

Result

Live inside the estimator since 27 August 2026, with save, versions and PDF in a second release that evening. A production audit on 27 August tried every scenario of every live estimate: 263 of 271 attempts matched a validated master, 8 opened empty for a manual build, and 0 errored.

Highlights

  • Every template is a word for word transcription of one practice master, with its source document recorded.
  • Staging became an explicit mode after a bug sent every full arch case to manual build: no implant teeth had been read as no staging.
  • The both arches master was transcribed instead of glued from two single arch masters, because glued plans put visit 6 and visit 8 in the wrong order.
  • A unique index on plan and version number makes the second of two racing saves fail; at most one accepted plan per estimate.
  • Coordinators download Word or PDF of what is on screen, without saving first.
  • No registry and no package token in the Dockerfile: a committed snapshot, after pnpm's file protocol quietly kept serving an old build.

Built with

  • TypeScript
  • React
  • Tailwind CSS
  • dnd-kit
  • docx
  • PostgreSQL
  • Drizzle
  • pnpm
Cowork Dashboard, Hybridge Implants LLC

LiveMay 2026 to present

Cowork Dashboard

Monday.com boards turned into the leadership dashboard.

23Patients left with no lead after fixing the join, mostly retreatment cases

Read the write up
Case study

I fixed the join behind our leadership dashboard, then rebuilt it on Cloud Run with every metric defined once and cash flow read every morning.

  • 23Patients left with no lead after fixing the join, mostly retreatment cases
  • 5.2 s → ~17 msWeekly tab over a multi year range
  • 31% → 5.8%Ambiguous patient to lead links, after first name checks
  • 19 minFrom the finance lead's request in the Feature requests tab to it live

Problem

The first version, in Apps Script, joined patients to leads by name. In a review on June 3, Buffalo's consults and case acceptances read zero. Every metric also had three implementations (card, drilldown and trend), so two tabs could disagree.

Solution

A rebuild on Cloud Run behind IAP. Cloud Scheduler checks Drive every five minutes; a private ingest service parses the four exports with ExcelJS, joins and hashes them, and rebuilds when all four files have changed. The browser loads one pinned snapshot of about 0.4 MB and computes everything locally with the same core package the ingest uses, and each card number is a function of its drilldown rows by construction. Every morning at six the same check reads the three patient boards from the Monday API for the Cash Flow tab.

Process

Business rules were ported verbatim and diffed against the original Apps Script code. When that parity check missed a one day date shift (both sides used the same Excel reader), a golden test pinned 948 dates read off the old production dashboard. A request sequence guard stops stale results from landing.

Result

Live on Cloud Run since 2 September 2026. The Weekly tab dropped from about 5.2 seconds to about 17 ms, ambiguous links fell from 31% to 5.8%, a Cash Flow tab shipped on 15 September and reads Monday every morning since 8 October, and on 28 October a request from the finance lead was live 19 minutes after it was filed.

Highlights

  • Linkage to 98.9% in Rochester and 99.9% in Buffalo by joining on the boards' connect column, then made correct in September: first name checks cut ambiguous links from 31% to 5.8%.
  • Cash flow reads the three patient boards from the Monday API every morning at 6, with Refresh now, pace against a usual month and Rest of month.
  • One metric registry: every card is computed from its own drilldown rows, so the two cannot disagree.
  • Weekly tab from about 5.2 s to about 17 ms.
  • Fixing the join left 23 patients with no lead, mostly retreatment cases filed without a Lead row.
  • A Feature requests tab wired to Launchpad: an October 28 request was live 19 minutes after it was filed.

Built with

  • TypeScript
  • Node.js
  • ExcelJS
  • Cloud Run
  • Cloud Storage
  • Cloud Scheduler
  • Cloud IAP
  • Chart.js
Reconciliation, Hybridge Implants LLC

LiveJun 2026 to present

Reconciliation

I replaced 70 hours a week of manual cross checking with an engine.

70 hrs/weekManual cross checking returned to a three person team

Read the write up
Case study

I replaced 70 hours a week of manual cross checking with an engine that reads three exports and shows the insurance team only the flagged patients.

  • 70 hrs/weekManual cross checking returned to a three person team
  • 8.75 hoursFrom the first commit, a design spec, to the first live revision
  • 8 of 8Wrongly passed patients on one Rochester day, all flagged from v1.10.0
  • 85False flags on one Monday that a date check now catches

Problem

A three person insurance team spent about 70 hours a week cross checking the schedule, the production ledger, and the clinical notes by hand to confirm every patient seen got documented and billed under the right doctor. It was slow and it failed exactly where mistakes cost the most: care documented but never billed, billed with no note behind it, or billed under the wrong provider.

Solution

A pure, deterministic reconciliation engine inside a thin FastAPI app. Two source adapters (Eaglesoft CSV, Denticon xlsx) turn hostile exports into the same typed models, the matcher keys everything on patient_id, and a stack of checks (money against the note, the billing provider against the doctor named in the note, the codes a note claims against the ledger, perio charting, office policy rules) separates verified patients from the few that need a human.

Process

The engine has no network, no database and no clock, and it takes the timestamp as a parameter, so identical inputs give byte identical output and every count traces to a source row. Columns map by name and a missing one stops the run with an error that names it. The app checks the dates inside every file and warns when an export covers the wrong day, after one Monday's notes export defaulted to the previous Friday and showed 85 patients billed with no note. Reviewers sent back every patient the tool got wrong, and each one was traced, fixed, tested and shipped.

Result

Live on Cloud Run. About 70 hours a week of manual cross checking became an exception review, over 3,600 hours a year.

Highlights

  • Pure deterministic engine split from the app shell: same inputs, byte identical, auditable output.
  • Two practice management systems normalized into one set of typed models through a source adapter registry.
  • Matching keyed on patient_id; doctor names in notes match by nickname, initials or one or two typos, and names under five letters must match exactly.
  • A date check across every file caught a notes export from the wrong day that had shown 85 false flags.
  • From spec to first live revision in 8.75 hours on June 16; on July 24 a reviewer's rule went live two minutes after its commit.
  • A Gemini matcher for tooth, surface and wording is built and stays out of the verdict; every flag comes from a rule a reviewer can read.

Built with

  • Python
  • FastAPI
  • Vertex AI Gemini
  • Firestore
  • Cloud Run
  • Google OAuth
  • pytest
Daily Sales Report, Hybridge Implants LLC

LiveSep 2026 to present

Daily Sales Report

I turned the VP of Finance's morning Excel forecast into an automated pipeline.

4.2% → 1.5%Current month revenue error, early in the month to late

Read the write up
Case study

I turned the VP of Finance's morning Excel forecast into an automated pipeline that projects lab revenue and new arch starts three months out, with honest error bands and commentary that cannot invent a number.

  • 4.2% → 1.5%Current month revenue error, early in the month to late
  • 49 sAverage run from wake to finished report, over 22 sent mornings
  • 16 of 16Weekday mornings sent since the October 7 fix, through October 29
  • 108Model constants ported exactly from the original

Problem

The VP of Finance had built a sound forecast in a 14 tab Excel workbook and handed it over with a spec, but it needed a manual paste, recalculate and send every morning, fed by two daily export emails from the dental lab's case system.

Solution

A pure Python engine package with no I/O, and a pipeline package with parsers, a dedupe ledger and a BigQuery loader, with Terraform for the infrastructure. A Cloud Run job runs the model each weekday morning, and a Cloud Run web app behind IAP shows the dashboard, history and a Projections tab. An Apps Script bridge runs inside the VP's own Google account and copies the report attachments to a landing bucket, so the project never holds a credential that can read that mailbox. Gemini writes the commentary over finished numbers only.

Process

Parity first: every acceptance value and edge case from the spec is pinned in the test suite. Every number in the Gemini commentary must appear in the report payload, a list of banned phrases blocks advice the model has no business giving, and if the guard fails the report falls back to a deterministic template. No auto tuning: the best in sample parameter grid scored 2.59% but was 0.62 points worse out of sample. A better lag model sits behind a switch because its 0.28 point gain did not clear the noise floor.

Result

First scheduled report on 24 September 2026, 16 days after the first commit, built by 6:25 each weekday since, in about 49 seconds a run. Every weekday since the 7 October fix went out, 16 of 16 through 29 October. Current month revenue error falls from 4.2% early in the month to 1.5% late, and the report never depends on the LLM.

Highlights

  • Bands calibrated to cover about 68% of outcomes, for this month and the next two.
  • The mail bridge runs in the VP's own account, so the project never holds a mailbox credential.
  • A number guard on the LLM: any figure not in the payload fails the check and the template takes over.
  • No auto tuning: an in sample win that lost 0.62 points out of sample stayed out.
  • A hand typed figure that lived in container memory now persists in BigQuery as rows that supersede instead of overwrite.

Built with

  • Python
  • BigQuery
  • Cloud Run Jobs
  • Cloud Run
  • Cloud IAP
  • Gemini
  • Apps Script
  • Terraform
Marketing Data Warehouse, Hybridge Implants LLC

LiveAug 2026 to present

Marketing Data Warehouse

I built a BigQuery warehouse that joins ad spend, calls and leads to booked patients.

98.6%Of lead to patient matches made by the link staff already keep in Monday, as of October 29

Read the write up
Case study

I built a BigQuery warehouse that joins ad spend, calls and leads to booked patients and treatment value every day, documented so both people and LLMs can query it.

  • 98.6%Of lead to patient matches made by the link staff already keep in Monday, as of October 29
  • 99.3%Agreement with Monday's weekly export, October 29
  • 21 of 22Weekly Gemini eval, 26 October
  • 3.5 hoursFrom design spec to the first sync job in the cloud

Problem

Our marketing numbers lived in five logins, and nothing joined an ad click to a booked patient.

Solution

Google Ads lands through the BigQuery Data Transfer Service; Microsoft Ads, Meta, CallRail, Monday, GA4, Search Console, Business Profile and TapClicks come in through Python connectors running as Cloud Run jobs on Cloud Scheduler. Data moves from raw to staging to marts, every column carries a description, and a data guide tells an LLM what to read first.

Process

A daily ops job checks freshness and drift, alerting on a z score above 3 against a 28 day baseline, and a weekly eval asks Gemini 22 golden questions. The lead to patient join moved from matching on contact details and the Google click ID to the link staff already keep in Monday, with the match method recorded on every row.

Result

Live since 4 August 2026. Ten sources are pulled at 6 AM, a 6:30 email with one tab per source goes to the marketing team every morning, and a Claude connector has answered questions from it since 23 October. The weekly eval scored 21 of 22 on 26 October.

Highlights

  • Lead to patient join on the link staff already keep in Monday: 98.6% of matches as of October 29, the rest by email, with the method on every row.
  • All 657 staging and marts columns described, and a data guide written for LLMs, so a model reads the map first.
  • A 6:30 AM email with one tab per source, sent every morning since October 22.
  • Drift alerts at a z score above 3 against a 28 day baseline.
  • A CallRail backfill looked like the account had no history; the API silently ignores created_after, and start_date brought calls back to June 2025.
  • A rule of thumb for any model reading it: a funnel conversion near 96 percent means a bad join.

Built with

  • Python
  • BigQuery
  • BigQuery Data Transfer
  • Cloud Run Jobs
  • Cloud Scheduler
  • Gemini
  • Gmail API
  • MCP
Marketing Data Connector, Hybridge Implants LLC

LiveOct 2026 to present

Marketing Data Connector

I built a Claude connector for our marketing warehouse: sign in with Google once, and see only the data an owner ticked.

3 hoursFrom the first connector code to the live service on Oct 23

Read the write up
Case study

I built a Claude connector for our marketing warehouse: sign in with Google once, and see only the data an owner ticked. It went live three hours after its first line of code.

  • 3 hoursFrom the first connector code to the live service on Oct 23
  • 480 callsFrom 3 people in the first seven days, Oct 23 to 29
  • 13 boxesAn owner ticks per person; each set gets its own dataset of views
  • 39 of 40Golden questions passed through Claude on main, all 40 answers correct

Problem

Asking Claude about our marketing data took the Google Cloud SDK, two command line sign ins, a database tool, a hand edited Claude config and a fresh Google Cloud login most days. Every new person would repeat all of it.

Solution

A remote MCP server on Cloud Run. An owner page lists the people and 13 boxes, one per data source plus a few that unlock more detail, and each set of boxes gets its own BigQuery dataset of views. Claude writes SQL against the warehouse's own table names, and a guard points every table at that person's dataset before anything runs.

Process

Each question runs as one SELECT against the asker's own views, and Claude ends every answer with where the numbers came from. An accuracy layer that moves metric math to the server is built on main, with an eval that asks Claude 40 golden questions through the connector.

Result

Live since October 23. From October 23 to 29, three people made 480 tool calls on six days, 370 of them queries.

Highlights

  • Live three hours after the first connector code, at 3:06 PM on October 23.
  • 13 boxes per person, and each set of boxes gets its own dataset of views.
  • A guard points every table at the asker's dataset before anything runs.
  • Claude ends every answer with where the numbers came from.
  • An accuracy layer on main moves metric math to the server; 39 of 40 golden questions passed through Claude.

Built with

  • Python
  • MCP
  • Cloud Run
  • BigQuery
  • Google OAuth
  • Claude
Denticon Sync, Hybridge Implants LLC

LiveSep 2026 to present

Denticon Sync

I built the sync that keeps our copy of Denticon fresh for the apps that need it.

2.6 minBehind Denticon once the sync ran on a timer on Sep 21, down from 6.0 days

Read the write up
Case study

I built the sync that keeps our copy of Denticon fresh for the apps that need it: webhooks first, a nightly poll behind them, and the only Denticon credentials in the company.

  • 2.6 minBehind Denticon once the sync ran on a timer on Sep 21, down from 6.0 days
  • 10 minBetween worker runs that fetch each slice a webhook points to, with a 4 AM poll behind them
  • 1 key holderDenticon credentials live on this service alone
  • 6 daysFrom the first Denticon commit on Sep 15 to the sync service live

Problem

Denticon holds every chart and appointment at our three offices, and four services need what is in it. Its API has no patient search, so a copy of our own is the only patient index we have, and only one service should ever hold its credentials. The copy measured 6.0 days behind Denticon on September 21, because nothing ran the sync on a schedule.

Solution

A sync service: the CDF's own image deployed as a second Cloud Run service, holding the only Denticon credentials. Denticon posts a pointer when records change; the receiver saves it and answers inside Denticon's ten second window. A worker every ten minutes fetches each slice and upserts the rows into Firestore, a sweep at twenty past each hour lists any slice a webhook missed, and a 4 AM poll reads everything.

Process

Denticon ignores a query parameter it does not know and returns the whole table with a 200, so only filters proven to change totalCount are allowed. A freshness report starts from the cursors it expects, so a missing one shows as the worst status.

Result

Four services read the mirror and none holds a Denticon credential: the CDF's patient list, the estimator and the capacity planner through the registry, and the report renderer before it emails a patient.

Highlights

  • Webhooks first, a worker every ten minutes, an hourly sweep and a 4 AM poll behind them.
  • From 6.0 days behind to 2.6 minutes behind once the sync ran on a timer.
  • The first read of the live practice ran on September 29.
  • A webhook body is a pointer; the worker fetches the record itself.

Built with

  • Next.js
  • TypeScript
  • Cloud Run
  • Firestore
  • Cloud Scheduler
  • Secret Manager
CDF Registry, Hybridge Implants LLC

LiveSep 2026 to present

CDF Registry

Five read only routes over the Denticon mirror, with a secret per caller and strict office codes.

1 key holderDenticon credentials sit on one service; each caller holds only its own bearer

Read the write up
Case study

I built a small read only API over our Denticon mirror, so the estimator and the capacity planner get the appointment book without holding Denticon keys.

  • 1 key holderDenticon credentials sit on one service; each caller holds only its own bearer
  • 27 minFrom the planner's routes going live on Sep 29 to the planner reading through them
  • 400The answer to an office code the routes do not know, so a typo cannot empty a calendar
  • Every minuteThe capacity planner reads the book and the provider list

Problem

On September 21 two apps needed Denticon's appointment book: the treatment estimator for a landing page of who is coming in today, and the capacity planner for the whole book every minute. Only the CDF may hold Denticon credentials.

Solution

A registry: five read only routes on the CDF dashboard service, over the Firestore mirror that the Denticon sync keeps fresh. The estimator gets one local day of the book; the planner gets the book by date window or by what changed, plus providers, visit types and chairs.

Process

Each caller has its own bearer secret, compared in constant time, and the registry never calls Denticon. Answers to the planner carry each office's mirror health, so it can show old data as old.

Result

Two apps read it: the estimator's landing page, the first screen every coordinator sees, and the capacity planner every minute.

Highlights

  • One secret per caller, so revoking one never blinds another.
  • An unknown office code gets a 400, so a typo cannot empty a calendar.
  • Answers carry each office's mirror health, so old data shows as old.

Built with

  • Next.js
  • TypeScript
  • Cloud Run
  • Firestore
PDF Renderer, Hybridge Implants LLC

LiveJun 2026 to present

PDF Renderer

A Fastify service on Cloud Run that renders each PDF in a fresh headless Chromium, stores it and delivers it.

7 minFrom the first renderer commit on Jun 19 to the service on Cloud Run

Read the write up
Case study

I built the renderer that turns every patient survey into a summary and a doctor report, emails both, and finishes the job on retry.

  • 7 minFrom the first renderer commit on Jun 19 to the service on Cloud Run
  • About 50 sFor one survey's whole delivery, run inside the request with the CPU kept on
  • 3 callersThe delivery queue, the CDF dashboard and an hourly sweep
  • 2 of 2Reports before a clinic list gets an email

Problem

Every intake survey needs a one page summary for the patient and a doctor report for the office.

Solution

A Fastify service on Cloud Run that renders each PDF in a fresh headless Chromium, stores it and delivers it. A survey submit becomes one named Cloud Task, staff on the CDF dashboard can regenerate a report, and an hourly sweep picks up anything unfinished.

Process

Each step is recorded as it lands, and every retry reads that record first. The clinic email waits until both reports exist.

Result

Every intake and experience survey from the three offices goes through it, and so does the CDF dashboard's Regenerate button.

Highlights

  • A fresh headless Chromium for every PDF.
  • Three callers, each with a Google identity token: the queue, the dashboard and an hourly sweep.
  • Each step is recorded as it lands, and every retry reads that record first.

Built with

  • TypeScript
  • Fastify
  • Headless Chromium
  • Cloud Run
  • Cloud Tasks
  • Cloud Scheduler
  • Firestore
  • Vertex AI Gemini
Launchpad, Hybridge Implants LLC

LiveOct 2026 to present

Launchpad

I built one board where staff open every Hybridge app, leaders see what is being built, and six apps send feature requests into one list.

78 minFrom the first commit to a working live board, Oct 22

Read the write up
Case study

I built one board where staff open every Hybridge app, leaders see what is being built, and six apps send feature requests into one list.

  • 78 minFrom the first commit to a working live board, Oct 22
  • 38 projectsOn one board on Oct 29, 2026, 22 of them live
  • 19 minFrom the VP of finance's request in the Cowork tab to the live fix, Oct 28
  • $0.32The whole Google Cloud project, October 1 to 28, measured

Problem

By late October the list of Hybridge projects had reached 38. Staff needed one place to open any of them, four leaders wanted to see what is being built, and change requests arrived in chats and in passing, with no screenshot, no id and no record of what happened to them.

Solution

One page behind Google sign in. The Apps tab shows every project as a card in panes by status, the four leaders also get Work and History, and a Feature requests tab takes a pasted screenshot and a line. The same request screen lives inside six other apps, which all send to one relay.

Process

One editor changes the cards, and each save writes the project and a history entry with who, when and every field's old and new value. The relay is Launchpad's own image deployed a second time, so the board and the relay always run the same code.

Result

38 projects and 21 logged edits by October 29. The request counter reached FR-0006: four requests about three apps, two of them shipped.

Highlights

  • Live 78 minutes after the first commit.
  • One editor; every save logs who, when and each field's old and new value.
  • Six apps file feature requests through one relay into one list.
  • One image deployed twice, so the board and the relay always run the same code.

Built with

  • Next.js 15
  • React 19
  • TypeScript
  • Firestore
  • Cloud Run
  • Cloud IAP
  • Google Chat
Feature Requests Relay, Hybridge Implants LLC

LiveOct 2026 to present

Feature Requests Relay

I built one request screen that six apps share, and a relay that trusts each app only to say who is asking.

6 appsCall one relay, each with its own Google ID token

Read the write up
Case study

I built one request screen that six apps share, and a relay that trusts each app only to say who is asking.

  • 6 appsCall one relay, each with its own Google ID token
  • 8 minFrom the relay going live on Oct 23 to the first request
  • 19 minFrom a request filed in the Cowork Dashboard to the live fix, Oct 28
  • 0 adminsThrough an app: only Launchpad sets a status

Problem

Change requests for our apps arrived in chats and in passing. Launchpad sits behind IAP, and six apps on their own Google Cloud projects needed to file requests from their servers.

Solution

A relay: Launchpad's own image deployed a second time as its own Cloud Run service, with relay mode on and no IAP. Each app serves the same request screen and forwards every call from its own server with a Google ID token for its own account and the person its own sign in already checked.

Process

In relay mode the service answers only the request API and a health check, and Cloud Run lets in only the six app service accounts. Each app may file only about itself, and only Launchpad sets a status.

Result

Six apps file through it: the treatment estimator, the capacity planner, the CDF Patient Dashboard, Hybridge Forms, the Cowork Dashboard and the Doctor Portal. Requests land in Launchpad's Firestore and ping one Google Chat space.

Highlights

  • Each app checks its own people; the relay checks only the app.
  • Every request gets an FR number that never changes.
  • An October 28 request from the Cowork Dashboard was live 19 minutes after it was filed.

Built with

  • Next.js 15
  • TypeScript
  • Firestore
  • Cloud Run
  • Google Chat
CBCT Scan Validator, Hybridge Implants LLC

In testingMar to May 2026

CBCT Scan Validator

Flags bad dental CT scans before they reach the implant design queue.

$62Google Cloud from October 1 to 28, measured

Read the write up
Case study

I built an in house checker that flags bad dental CT scans before they reach the design team, in 37 days, against a six figure vendor quote.

  • $62Google Cloud from October 1 to 28, measured
  • 2.2 sEncoder pass on a laptop CPU with OpenVINO
  • 0.6309Honest AUROC (leaky 0.80 caught)
  • 26 of 30Bad studies the review app's model flagged in testing

Problem

Some CBCT scans arrive unusable: the patient moved, metal threw streaks, or part of the jaw sat outside the field of view. Nobody knew until a designer opened the case and waited on a rescan. A vendor had quoted a six figure build and a monthly fee to run it.

Solution

An in house quality gate. The lab's case system exports each case to a small locked down SFTP box, which hands it to the validator on Cloud Run. The validator scores it with a frozen DentalSegmentator encoder and a small head, then sends the verdict back over SFTP.

Process

Six candidate models sat behind one interface by April 7. Model H's first 0.80 AUROC leaked: seven of the ten bad holdout studies had been in its training data, so I rebuilt the split and kept the honest 0.6309 on 44 test studies. The threshold is priced in rescans, with a missed bad scan counting 15 times a false flag.

Result

Deployed on Cloud Run since April 22 and on v0.6.1 since May 1, 37 days after the first commit. Our testing team checks studies in a review app: of the 30 they marked bad, the review app's model flagged 26. That model is separate from the validator's. It cost $62 on Google Cloud from October 1 to 28, measured.

Highlights

  • Six candidate models behind one interface by April 7; Model H, a frozen DentalSegmentator encoder with a head of about 500K parameters, is the one that worked.
  • Threshold priced in rescans: a missed bad scan costs 15 times a false flag.
  • A strict 20 scan holdout caught a leaky AUROC of 0.80.
  • OpenVINO ran the 30.79M parameter encoder in 2.20 s per pass on a laptop CPU, against 2.56 s for PyTorch and 3.93 s for ONNX Runtime.
  • SFTP both ways with the lab's case system after its API license lapsed.

Built with

  • PyTorch Lightning
  • MONAI
  • OpenVINO
  • FastAPI
  • Cloud Run
  • Eventarc
  • Cloud Storage
  • GitHub Actions
Enterprise Data Project, Hybridge Implants LLC

ShippedDec 2025 to Mar 2026

Enterprise Data Project

I moved team automations onto one self hosted n8n platform on AWS.

Self hostedn8n on AWS via Docker

Case study

I moved team automations onto one self hosted n8n platform on AWS.

  • Self hostedn8n on AWS via Docker
  • One platformFor team automations and scheduled analytics

Problem

Per seat SaaS automations were adding up, and executive analytics depended on manual weekly exports.

Solution

Self hosted n8n on AWS via Docker: one platform for every team automation, with standard data flows across teams.

Process

Moved existing automations into n8n, and built executive analytics pipelines that publish on a schedule.

Result

Team automations and executive analytics run on one shared, self hosted platform.

Highlights

  • Self hosted n8n on AWS via Docker.
  • Executive analytics pipelines that publish on a schedule.
  • Standard data flows for automations across teams.

Built with

  • AWS
  • Docker
  • n8n
  • Data Pipelines
  • Automation
Case Intake, Hybridge Implants LLC

PrototypeSep 2026

Case Intake

I built a morning list of lab cases that duplicate an earlier scan case.

ParkedTurned down by the lab on 30 Sep 2026; its code feeds the Doctor Portal

Case study

I built a morning list of lab cases that duplicate an earlier scan case, so customer service could merge them. It ran as a demo on sample data, and the Doctor Portal took its place.

  • ParkedTurned down by the lab on 30 Sep 2026; its code feeds the Doctor Portal
  • 1 letterThe most a name can be mistyped and still match

Problem

Doctors write the prescription in the lab vendor's customer portal, which cannot edit an existing case, so every prescription arrives as a second case that duplicates the scan case already in the system, and customer service has to catch each pair to merge it.

Solution

A Next.js app in the Hybridge design on Cloud Run behind IAP that lists the likely duplicates. The data sits behind a case source and store interface: sample data, with the vendor's API and Firestore planned.

Process

The name matcher forgives case, spacing, a middle initial, swapped first and last names, and a single mistyped letter. Anything more is a different person.

Result

Demo deployed on 30 September 2026 on sample data. The lab turned the approach down that day, and the Doctor Portal took its place, live on sample data since 28 October 2026.

Highlights

  • Forgiving but bounded name matching: case, spacing, middle initial, swapped names, one typo.
  • Case source and store interfaces: sample data now, the vendor API and Firestore later.
  • Built in the Hybridge design system.

Built with

  • Next.js
  • TypeScript
  • Cloud Run
  • Cloud IAP
Doctor Portal, Hybridge Implants LLC

PrototypeSep 2026 to present

Doctor Portal

A doctor portal built from the lab lead's own mockup: Submit Rx, Cases, Accounting, Resources and Account.

3.7 hoursFrom the sync that made it top priority to a working live link, Oct 28

Read the write up
Case study

I built the lab's doctor portal, where the Rx joins the case the scanner already made, so a doctor never sees a duplicate case. Live on sample data.

  • 3.7 hoursFrom the sync that made it top priority to a working live link, Oct 28
  • 9 minFrom the revision that failed its first visit to the one that fixed it
  • 4 thingsStill pretend, listed on every release note
  • 4 weeksThe portal sat behind other work before the lab lead made it top priority

Problem

Outside doctors send our lab work. A doctor scans the patient and the scanner opens a case in MagicTouch, the lab's case system. The doctor then writes the Rx in MagicTouch's own portal, which cannot edit a case that already exists, so the Rx opens a second case. In the lab lead's words, the doctors "see us cancel one and then they get freaked out."

Solution

A doctor portal built from the lab lead's own July mockup. The doctor sends the scan from the scanner, then adds the Rx to that same case here. A switch in the bar flips between the doctor's view and the lab's, which stands in for MagicTouch until a real link exists.

Process

It went from the sync that made it top priority to a working live link in 3.7 hours. Every release note ends with what is still pretend: sample data, files by name, payments and emails off, no doctor sign in.

Result

A live link on sample data since 28 October 2026, for the lab lead to review. Only Hybridge Google accounts can sign in. Real data waits on a vendor license and the lab server's details, and file uploads to Cloud Storage are next.

Highlights

  • Built from the lab lead's own July mockup.
  • Top priority to a working live link in 3.7 hours.
  • Every release note lists what is still pretend.
  • A doctor and lab switch stands in for MagicTouch until a real link exists.

Built with

  • Next.js
  • TypeScript
  • Firestore
  • Cloud Run
  • Cloud IAP
Hybridge Websites, Hybridge Implants LLC

In buildOct 2026 to present

Hybridge Websites

Two Astro sites on the Hybridge design system, each its own Cloud Run service, every page prerendered.

20 minFrom the first commit on the patient site to its first preview on Cloud Run

Read the write up
Case study

I rebuilt the patient site and the lab site in the premium lab look, checked at 1440 and 390, and both are previewing on Cloud Run.

  • 20 minFrom the first commit on the patient site to its first preview on Cloud Run
  • 7.0 screensPatient home page length at 1440 after the marketing review, down from 13.7
  • 73 pagesCrawled from the live lab site with 118 images, the source of its facts
  • 12 storiesFrom real patients, self hosted at 720p, playing in place

Problem

Hybridge has two public websites: the patient site, where someone weighing full arch implants first meets the practice, and the lab site for the dentists who send our lab their cases. The ask on October 28 was to recreate the patient site with better modern taste, more colour and better UX, then the lab site.

Solution

Two Astro sites on the Hybridge design system, each its own Cloud Run service. Every page is prerendered at build time. The patient site has a 3D full arch to turn and twelve patient stories that play in place; the lab site opens on an exploded full arch that assembles as you scroll.

Process

Pages were built by parallel page agents and read at 1440 and 390, and a marketing review cut the patient home page from 13.7 screens to 7.0.

Result

In build: both sites are previews on Cloud Run for the team to review, not yet on their public domains. The forms show what they would send, and the lab site already redirects 21 old addresses.

Highlights

  • The patient site went from first commit to a Cloud Run preview in 20 minutes.
  • A marketing review cut the patient home page from 13.7 screens to 7.0 at 1440.
  • The lab site's facts come from 73 pages and 118 images crawled from the live site.

Built with

  • Astro
  • TypeScript
  • Cloud Run
  • Cloud Build
LLM persuasion research

ResearchAug 2024 to Jun 2025

Teaching Llama to Argue Better

I trained Llama 3 8B to write counterarguments.

Read the write up
Details

I trained Llama 3 8B to write counterarguments: SFT first, then a reward model trained on ChangeMyView deltas, then GRPO against that judge.

A research project on persuasion: I trained Llama 3 8B to write counterarguments, with SFT, a reward model trained on ChangeMyView deltas, and GRPO.

Highlights

  • SFT, reward model and GRPO with QLoRA (4 bit, LoRA rank 64) in TRL and Unsloth.
  • Preference pairs from ChangeMyView: a reply that earned a delta against one that did not.
  • Evaluated with BLEU, ROUGE-L and the reward model, against the untrained base as control.

Built with

  • Llama 3
  • GRPO
  • ORPO
  • RLHF
  • TRL
  • Unsloth
  • QLoRA
  • LoRA
  • PyTorch
Loan Radar

AcademicJan to May 2025

Loan Radar

A three person class project that scores loan default risk.

Read the write up
Details

A three person class project that scores loan default risk. I built the data pipeline, the MLflow stack and the stress tests, and made training and serving load one saved transform.

Loan Radar scores loan default risk from the public LendingClub book on Chameleon Cloud: containerized ETL, MLflow on Postgres and MinIO, XGBoost, a FastAPI scorer and Prometheus monitoring.

Highlights

  • Built ETL containers that fit medians, encoders and a scaler on training rows only and save them as one pickle that validation and the API both load.
  • Wrote the compose stack for MLflow 2.20 on Postgres and MinIO, plus a Ray head and two workers.
  • Built stress tests on 22,607 held out loans: top features zeroed or inflated, and noise on every feature.
  • 0.79 ms median to score one loan row with the model in process; ROC AUC 0.71 in 2 fold cross validation over 1.81M loans.

Built with

  • Docker Compose
  • FastAPI
  • Flask
  • MLflow
  • MinIO
  • PostgreSQL
  • XGBoost
  • Ray
  • Prometheus
  • Grafana
  • Terraform
Fake News and Sentiment Analysis

AcademicFeb to May 2024

Fake News and Sentiment Analysis

A 4 bit Llama 3 8B labels election tweets true, false or opinion, and RoBERTa reads their mood across about 1.7M tweets.

76%Llama 3 8B accuracy on LIAR test claims

Read the write up
Case study

Three of us labeled 2020 election tweets with a 4 bit Llama 3 8B fine tuned on LIAR (76% on its test claims) and read their mood with RoBERTa. I built the sentiment pass, the maps and the report.

  • 76%Llama 3 8B accuracy on LIAR test claims
  • 1.7Melection tweets in the dataset
  • 315,020tweets under both hashtags, removed from both
  • 1 GPUwhole fine tune in 4 bit on a V100

Problem

"Detect fake news" hides two jobs: is a claim true, and how does a crowd feel. They need different models and different data.

Solution

Llama 3 8B fine tuned with QLoRA on LIAR for True, False or Personal labels, zero shot Twitter RoBERTa for mood, LDA for topics, and Power BI state maps.

Process

Collapsed LIAR's six labels to two, removed tweets that appeared under both hashtags, and capped each answer at one token.

Result

76% on LIAR test claims, more than 156,000 tweets labeled per hashtag, state and swing state maps, and a nine theme topic table.

Highlights

  • 76% on LIAR test claims with a 4 bit Llama 3 8B and an 84M parameter LoRA adapter on one V100.
  • Removed 315,020 tweets that appeared under both hashtags so neither candidate counted them.
  • Built the sentiment pass, the state and swing state maps in Power BI, and the report.

Built with

  • Llama 3
  • QLoRA
  • Unsloth
  • RoBERTa
  • LDA
  • Power BI
  • Python
ResNet CIFAR-10 class competition

AcademicApr 2024

ResNet Under 5M Parameters

A class contest on CIFAR-10 under a 5M parameter, ResNet only cap.

97.12%on the 10,000 CIFAR-10 test images

Read the write up
Case study

A class contest on CIFAR-10 under a 5M parameter, ResNet only cap. Augmentation took our model from 93.76% to 97.12% without adding a parameter.

  • 97.12%on the 10,000 CIFAR-10 test images
  • 4,978,810parameters, under the 5M cap
  • 0 paramsadded by augmentation

Problem

A class contest: the best CIFAR-10 classifier, with hard rules. Stay a ResNet, and stay under 5 million parameters.

Solution

With a bigger model off the table, we added data instead. AutoAugment, random crops, flips and perspective changes gave the model far more variety without adding a single parameter.

Process

Flip and crop alone topped out at 93.76%. Adding AutoAugment reached 95.34%, and adding perspective reached 97.12%. A cosine learning rate schedule beat a step schedule, 97.12% against 92%.

Result

97.12% on the 10,000 CIFAR-10 test images after 300 epochs, with 4,978,810 parameters, 21,190 under the cap.

Highlights

  • Augmentation took our best run from 93.76% to 97.12% at zero parameter cost.
  • 4,978,810 trainable parameters, 21,190 under the 5 million cap.
  • A cosine schedule over 300 epochs beat a step schedule, 97.12% against 92%.

Built with

  • ResNet
  • PyTorch
  • Data Augmentation
  • CIFAR-10
Customer Segmentation and Recommendation System

AcademicFeb to May 2024

Customer Segmentation and Recommendation System

A three person capstone on 33.8M MovieLens ratings.

33.8MMovieLens ratings

Read the write up
Case study

A three person capstone on 33.8M MovieLens ratings: Spark ALS for recommendations, and my MinHash notebook that found movie twins among 330,975 users after Spark kept losing nodes.

  • 33.8MMovieLens ratings
  • 37 sLSH index and query for 330,975 users
  • 0.73rating correlation of the top 100 twins, 0.03 for random pairs
  • 22.2Mcandidate pairs from LSH

Problem

Find the 100 most similar users among 330,975, judged by which movies they rated. Comparing every pair means about 55 billion comparisons.

Solution

MinHash with 30 permutations and an LSH index with 6 bands in datasketch, after Spark's MinHashLSH join kept losing nodes on Dataproc.

Process

Tried 15 to 500 permutations and 2 to 8 bands, kept the setting with the best top 100 correlation, and checked it against random pairs.

Result

0.7348 average rating correlation for the top 100 twins against 0.0323 for random pairs, in 37 seconds of indexing and querying.

Highlights

  • Moved the twins search from Spark to one Python process after Spark's similarity join kept losing nodes.
  • Validated the twins against random pairs: 0.7348 against 0.0323.
  • Team Spark pipeline: per user time split to Parquet on HDFS, damped popularity baseline, ALS at rank 200.

Built with

  • Spark
  • HDFS
  • ALS
  • MinHash LSH
  • datasketch
  • pandas
  • Python
JobPilot open source job hunt autopilot

Open sourceJun to Oct 2026

JobPilot

My open source job hunt autopilot.

Read the write up
Details

My open source job hunt autopilot. It watched 163 company boards, scored each role against my profile, and tailored a resume and cover letter per match, with a calibrated judge keeping the rewrites honest.

An open source job hunt platform: direct board watching across eleven sources, Gemini scoring locked to a schema, a calibrated resume judge with a rewrite loop that keeps to the truth, outreach drafted into Gmail for me to send, and a Next.js console behind IAP. It ran 1,008 times from June 10 to October 8, and a public demo runs on fictional data.

Highlights

  • 163 company boards watched directly, polled in parallel by June 12.
  • 16 patterns of citizenship, clearance and no sponsorship text drop a job before any model sees it.
  • My first resume checker scored a file 100 where ResumeWorded gave 73, so I rebuilt the judge.
  • Recruiter and company outreach drafted into Gmail for me to send, and replies flagged when they land.
  • Open sourced under MIT with a fork guide written to hand to an AI coding agent.

Built with

  • Python
  • Next.js
  • Vertex AI Gemini
  • LaTeX
  • Google Sheets
  • Cloud Run
  • Cloud IAP
  • GitHub Actions

Let's build something.

Tell me what you're working on.