All projects

Internship - Summer 2025

Capital One

During the summer of 2025, I worked as a Software Engineering Intern on the Graffiti team within Card Tech+ at Capital One.

GoJavaPython Spring BootDockerAWS
§ 01 - OVERVIEW

What is Graffiti?

Graffiti is Capital One's letters and correspondence platform. It composes and sends millions of pieces of physical and digital correspondence to customers every year, handling everything from customer preference application to letter composition, barcode generation, and delivery to print vendors and imaging systems.

§ 02 - THE WORK

What I Did

My internship split into two phases: migrating an existing barcode generation system to a new enterprise API, and building a proof-of-concept API from scratch using modern Go tooling.

IMB Barcode Generation Migration

Every letter Graffiti sends needs an Intelligent Mail Barcode (IMB), the tracking barcode USPS uses to sort and route mail. Generating that barcode was fragmented across the enterprise: several independent services each maintained their own copy of the generation logic, pulling sequence numbers from a shared legacy Postgres database. The goal was to migrate everything onto a single, centralized IMB Generator API instead.

I worked on this migration across three separate services:

  • Letter Orchestration Layer (Java/Spring Boot) - added feature-flag-gated calls to the new API with a silent-failure fallback to the existing logic, implemented OAuth2 credential handling and token refresh, and tracked down a race condition that was intermittently causing a null pointer exception in a preprocessor service.
  • IFMBank-Batch (Java) - this service fed sequence numbers into a legacy "black box" JAR that expected a specially formatted file. I wrote the code to call the new API and reformat its response to exactly match what the JAR expected, gated behind a feature toggle so we could safely cut over.
  • dbmmstmts (Python) - migrated this service with zero downtime using API batching, grouping mail-piece requests before calling the new API, and code shadowing, running the old and new logic side by side and comparing their output before trusting the new path in production.

With all three services validated and switched over, the custom IMB logic in the shared Postgres database became unnecessary, paving the way to decommission it and save on both hosting costs and ongoing maintenance.

Ogen / OpenTelemetry Proof of Concept

For the second half of the internship, I moved from working in a large existing codebase to building an API from scratch in Go, as a technical proof-of-concept for a future upgrade to Capital One's core correspondence API.

I used Ogen, an OpenAPI code generator for Go, to generate routing, request/response types, and validation directly from an OpenAPI spec. On top of that generated layer, I built:

  • Middleware-based routing that dispatches a request to different API version logic based on its Content-Type header.
  • Distributed request tracing with OpenTelemetry.
  • Custom middleware for input validation and masked logging, so sensitive fields never end up in plaintext logs.
  • Support for both JSON and PDF-byte responses, and per-environment configuration for local, QA, dev, and prod.

The finished proof-of-concept became a reference implementation for the team, demonstrating a modern, observable API pattern that the real upgrade could build on.

§ 03 - REFLECTION

Take Aways

Working across two very different kinds of problems, cleaning up entrenched legacy logic in a large production codebase versus building something new from an empty repo, gave me a much better feel for when each mindset applies. The migration work meant being deliberate and cautious: feature toggles, shadowing, and fallbacks all exist to make sure a change to code that mails real letters to real customers never causes downstream breakage. The Ogen project let me move faster and make more opinionated design choices, since it was explicitly a proof-of-concept rather than production infrastructure.

I also got a lot of practice working across languages and stacks in the same week, Java, Python, and Go, along with Docker and AWS tooling, and learned a lot from my mentors about when to ask for help versus dig in further myself.

§ 04 - SOURCE

Where to view

Capital One's codebase is proprietary and confidential, so I'm not able to link to it here. If you'd like to hear more about the work in detail, feel free to reach out.