thoughts-by-sid

The Production ML Pipeline Nobody Tells You About

December 2, 2025 9 min read

Your model works in a Jupyter notebook. That’s adorable.

I spent three weeks building a side project—a little web app that would analyze Reddit comments and predict which ones might spark interesting discussions. Got the model to 91% accuracy on my test set. Felt like a genius. Then I tried to actually deploy it as a real service people could use.

That’s when I learned that training a model is maybe 10% of the work. The other 90% is everything nobody warns you about.

The Jupyter Notebook Lie

Here’s what they don’t tell you in machine learning courses: that beautiful notebook where your model trains perfectly is a lie. It’s a useful lie, like thinking you can cook because you made pasta once. The notebook is your kitchen with unlimited prep time, perfect ingredients, and no health inspector.

Production is a food truck in Phoenix during summer, serving hundreds of customers an hour, where the refrigerator breaks every Tuesday.

Your notebook assumes clean data shows up in a pandas DataFrame. My production data arrived as Reddit API responses that sometimes timed out, sometimes returned deleted comments, sometimes had encoding issues with emoji, and occasionally just… stopped working because I hit rate limits I didn’t know existed.

Your notebook assumes you can retrain anytime. Production asks: Do I run this on my laptop overnight? Do I pay for cloud GPU time? When do I retrain—daily, weekly, when I notice it’s performing badly? How do I even notice it’s performing badly when I’m asleep or at my day job?

These aren’t edge cases. This is the entire game.

The Silent Killer: Data Drift

I deployed my model. It worked. For about two weeks, everything was beautiful. Then gradually, mysteriously, it started making weird predictions.

Nobody changed my code. My model file was identical. My server was fine. Yet suddenly it was flagging perfectly normal comments as “discussion-worthy” and ignoring obvious flame wars.

Welcome to data drift—the gap between the world your model trained on and the world it’s living in now.

I trained on Reddit data from January through March. Then summer hit. Completely different subreddits started trending. People were talking about different things. The language patterns shifted. My model had learned “what makes good discussion” based on winter discourse about indoor hobbies and politics. Summer brought travel stories and outdoor advice. It was lost.

The model wasn’t broken. The world had just moved on, and my model was still living in March.

The real trick isn’t building models that work. It’s building systems that tell you when they’ve stopped working, and ideally, why.

The Pipeline Isn’t Code, It’s Infrastructure

As a solo developer, I thought I could just write a Flask app, load my model, and call it a day. That worked for exactly one user (me) making one prediction every few minutes.

Then I tried to make it actually useful:

  • What happens when the Reddit API is down? Do I crash, retry, queue requests?
  • How do I store predictions so I’m not re-processing the same comments?
  • When I retrain the model, how do I deploy the new version without downtime?
  • How do I know if the new version is actually better or if I just overfitted to recent data?
  • What if someone hammers my endpoint with requests? Do I rate-limit? Cache?
  • How much is this costing me in API calls and server time?

Suddenly I’m not doing machine learning anymore. I’m doing systems engineering. I’m setting up Redis for caching, writing retry logic with exponential backoff, building scripts to version my models, creating monitoring dashboards to track prediction distributions.

Most of my code has nothing to do with the ML model. It’s plumbing. Boring, essential plumbing that nobody teaches you in Kaggle competitions.

The Part Where Everything Is Probably Failing Right Now

Here’s something I learned the hard way: ML systems fail silently.

One morning I woke up to find my model had been making predictions for three days based on features that were all zeros. A Reddit API endpoint changed its response format. My feature extraction code didn’t crash—it just silently filled in default values when it couldn’t find the fields it expected.

The app worked. The API returned 200 OK. The predictions were complete nonsense, but the system didn’t care. It was technically functioning.

Traditional code fails loudly. You get exceptions, stack traces, error logs. ML systems just quietly start sucking. Your model returns confidently wrong predictions because it’s making decisions based on garbage data, and there’s no error to catch.

The only solution I found was paranoid logging. I started tracking everything: input data distributions, feature value ranges, prediction confidence scores, API response times. I built a dashboard I’d check every morning with my coffee—not because I’m organized, but because I got tired of discovering problems three days late.

Why This Matters Beyond Just Shipping Features

There’s a deeper pattern here that goes beyond ML: the gap between making something work once and making something work reliably over time.

Every engineering discipline has this chasm. You can write a script that works on your laptop. Making it handle real users, scale reasonably, fail gracefully, and stay maintainable for months? Different universe.

ML just makes this gap wider because you’re dealing with non-deterministic behavior. Your model doesn’t execute the same way every time like a function does. It’s more like a plant—it needs ongoing monitoring, occasional feeding with fresh data, and sometimes it just dies for reasons you don’t fully understand.

This is why ML projects in personal portfolios versus ML products people actually use look so different. The demo works beautifully. The production version is held together with monitoring scripts, retry logic, and a Notion doc titled “Why did accuracy drop last Tuesday.”

What Would I Tell My Past Self?

If I could go back to that moment when I first thought “I’ll just deploy this,” I’d know to ask different questions:

How will I know if it’s working next month? What’s my rollback plan? Where is the data pipeline going to break first? What’s my retraining strategy? How do I handle edge cases the model has never seen?

Not because I’m a pessimist, but because production ML isn’t about building a perfect model. It’s about building a reliable system around an imperfect model, and having the infrastructure to improve it over time.

Your Jupyter notebook is where ideas happen. Production is where reality teaches you what you actually didn’t know.

And honestly? That’s the more interesting problem anyway. The model architecture is solved by a blog post and some hyperparameter tuning. The system design? That’s where you actually learn engineering.

You might also enjoy