Martin Stühmer

I’m Martin, a software architect and developer from the Stuttgart region who’s been building .NET systems since the Framework 2.0 days. Nearly 20 years later, I’m still here—not because I’m stubborn (well, not only), but because the .NET ecosystem keeps delivering value when you cut through the hype and focus on fundamentals.

My work centers on a simple premise: quality isn’t optional, and buzzwords don’t ship features. As Director Consulting Services at CGI, I work with teams building cloud-native solutions on Azure and modern .NET. I help organizations navigate technical decisions using Risk and Cost Driven Architecture (RCDA)—a methodology that brings systematic risk and cost analysis to architecture choices instead of relying on “best practices” pulled from conference slides.

What I Actually Do

Enterprise Architecture & Development: I design and build systems that need to scale, perform, and stay maintainable after the consultants leave. My focus spans the full stack—from Azure infrastructure and DevOps pipelines to .NET application design, performance optimization, and the unglamorous work of making legacy systems coexist with modern approaches. I’ve worked with teams ranging from startups to global enterprises, always with the same goal: shipping production-ready software that solves real business problems without accumulating crippling technical debt.

The work involves hard choices—choosing boring, reliable technologies over exciting new ones when stability matters more than innovation. Designing for the team you have, not the team you wish you had. Building systems that can evolve incrementally instead of requiring big-bang rewrites. It’s less glamorous than conference keynotes make it sound, but it’s what keeps production systems running.

Training & Knowledge Transfer: As a Microsoft Certified Trainer and IHK-certified instructor, I train developers and architects who want depth, not surface-level tutorials. Whether it’s cloud architecture, modern .NET features, or pragmatic testing strategies, my goal is equipping teams to make informed decisions rather than following trends blindly.

My training approach comes from spending years cleaning up messes created by applying “best practices” without understanding context. I don’t teach dogma—I teach judgment. Students learn to evaluate trade-offs, understand when to break rules, and recognize that most software engineering advice comes with implicit assumptions about scale, team structure, and business constraints that may not match their reality.

Open Source Contributions: I maintain several NuGet packages focused on solving real problems I’ve encountered in production systems. Code quality, testability, and developer experience drive these projects—not feature counts or GitHub stars. Each package exists because I’ve repeatedly solved the same problem across different projects and decided the ecosystem needed a better solution than copying code between repositories.

These contributions aren’t just code dumps—they’re maintained, documented, and tested because I actually use them in production. When you depend on one of my packages, you’re getting something that’s survived contact with real-world requirements, not a weekend experiment that seemed like a good idea at the time.

Writing & Teaching: Through this blog, I share perspectives on software engineering that challenge conventional wisdom when warranted. Topics range from .NET evolution and Azure patterns to technical debt management, quality practices, and why “Clean Code” has become empty lip service in many organizations. If you’re looking for balanced, experience-driven insights rather than cheerleading for the latest framework, you’re in the right place.

I write about topics that matter for teams shipping production software—the messy middle ground between academic computer science and “move fast and break things” startup culture. Expect posts that question whether you actually need that microservices architecture, analyze .NET performance characteristics with benchmarks not hand-waving, and explore how to incrementally improve legacy codebases without grinding development to a halt.

My Technical Philosophy

After nearly two decades, here’s what I’ve learned:

  • Fundamentals over frameworks: Languages, patterns, and principles outlast specific tools
  • Quality over velocity: Analyzers, tests, and code reviews prevent more bugs than heroic debugging sessions
  • Context over dogma: “Best practices” depend on team size, domain complexity, and business constraints
  • Pragmatism over purity: Perfect architecture that ships in six months loses to good-enough architecture that ships in six weeks
  • Evidence over opinion: Measure performance, validate assumptions, benchmark alternatives

I’m skeptical of buzzword-driven development, hostile to cargo-cult practices, and allergic to “because everyone else does it” as technical justification. But I’m also pragmatic—sometimes the boring, proven approach is exactly what your production system needs.

The Journey: From Framework to Modern .NET

I started with .NET Framework 2.0 in an era when SOAP web services were cutting-edge and ORMs were controversial. I’ve lived through the rise and fall of Silverlight, WPF’s promise and reality, WCF’s complexity, and the awkward adolescence of ASP.NET Web Forms. I witnessed the .NET Core revolution—Microsoft’s bet-the-company move to open-source, cross-platform development that paid off spectacularly.

This long view shapes how I evaluate new technologies. When someone pitches the latest JavaScript framework as the future, I remember when that was Angular 1.0. When architectural patterns become trendy, I recall which ones survived the test of production systems and which ones became cautionary tales in architecture horror story sessions.

Modern .NET (.NET 6, 8, 9, and now 10) represents the maturation of Microsoft’s platform strategy—combining the stability and enterprise-readiness of .NET Framework with the performance and innovation of .NET Core. But experience teaches caution: every new feature, pattern, or framework comes with costs that conference talks rarely mention. My job is helping teams understand those costs before they commit.

What Drives My Work

Making Technical Debt Visible: Too many organizations treat technical debt as an invisible problem until it becomes an existential crisis. Through RCDA, quality metrics, and transparent architectural decision-making, I help teams quantify, prioritize, and systematically address debt. Not by stopping all feature work for mythical “cleanup sprints,” but by integrating quality improvements into the regular development flow.

Elevating Quality Standards: I’ve seen too many teams accept buggy, untested, unmaintainable code because “we need to ship fast.” This is a false choice. Static analyzers catch bugs in milliseconds. Well-structured tests prevent regressions automatically. Code reviews transfer knowledge and catch design flaws. These practices don’t slow teams down—they prevent the constant firefighting that actually kills velocity.

Bridging Strategy and Implementation: Many architects design ivory-tower systems that fall apart when real requirements and real developers get involved. Many developers focus solely on code without understanding business context. I work in the gap between these extremes—translating business needs into technical strategy, and technical constraints into terms business stakeholders can evaluate.

Published blogs

Copilot Turns Junior Devs Into Syntax Secretaries

Copilot Turns Junior Devs Into Syntax Secretaries

The hype around GitHub Copilot (or any other AI code assistant) is deafening. AI-assisted coding. Effortless automation. 10x productivity.

But here’s the harsh truth: Copilot isn’t empowering junior developers – it’s deskilling them.

Vibe Coding in .NET: Creative Catalyst or Maintenance Risk?

Vibe Coding in .NET: Creative Catalyst or Maintenance Risk?

In the world of software development, there’s a recurring tension between discipline and improvisation. Somewhere along that spectrum lies a phenomenon increasingly referred to as Vibe Coding. The term evokes a style of development where engineers follow intuition and momentum rather than formal plans, processes, or design patterns.

It’s fast, fluid, and occasionally brilliant. But is it sustainable in a .NET-based enterprise context?

Understanding the C# `StringValues`: A Comprehensive Guide

Understanding the C# `StringValues`: A Comprehensive Guide

In C#, the StringValues struct belongs to the Microsoft.Extensions.Primitives namespace, which is widely used in modern .NET applications. This struct plays a crucial role in efficiently managing string collections, especially when handling efficiently, particularly in contexts where multiple strings are involved. In this blog post, we’ll explore the purpose, usage, and key features of the StringValues struct in C#.

Managing Errors, Warnings, and Configurations in C# and .NET

Managing Errors, Warnings, and Configurations in C# and .NET

When we activated static code analysis for the first time in one of my last projects, the overwhelming number of warnings exceeded expectations and highlighted gaps in the code. Without making any changes, the project already had a significant number of warnings. After activating additional analyzers and updating some configurations, this number temporarily increased dramatically.

The high number of warnings was initially daunting, but we saw it as an opportunity to significantly improve our code quality. At first glance, it seemed easier to suppress or ignore these warnings. But as I often remind my team, “The code you create is a valuable legacy, so it’s important to build it carefully.” Ignoring warnings today creates obstacles for future developers—and that could very well include you six months down the line.

This experience reinforced the importance of managing warnings and errors systematically. Let me share some of the lessons we learned, the strategies we used to tame those 60,000 warnings, and how you can apply these techniques to your own projects.

A Tale of Forgotten Pennies and Lost Dollars

A Tale of Forgotten Pennies and Lost Dollars

In software development, there’s a silent debt that accrues interest over time, often hidden beneath layers of code and decisions made in haste or ignorance. This debt is aptly termed technical debt. Much like the german proverb, “Wer den Pfennig nicht ehrt, ist den Taler nicht wert”, (or the english equivalent, “A penny saved is a penny earned”) technical debt reminds us that small oversights or compromises in the present can snowball into significant challenges down the road. This article critically examines the parallels between financial principles and technical debt, emphasizing the importance of addressing both direct and indirect debt while understanding its distinction from external risks such as hacking or abuse.