Software procurement feels like a market. There are vendors, there are alternatives, there are procurement teams whose entire job is to create competitive pressure. But underneath all of that theater, a quieter dynamic is often already settled before anyone opens a contract. The company that owns one indispensable function in your codebase doesn’t need to win a bake-off. They already won.

This is the economics of critical path dependency, and it explains pricing behavior that would otherwise seem irrational. Why does a logging library vendor charge enterprise rates that dwarf the cost of the engineers using it? Why can a payments processor justify fees that consume a meaningful slice of gross margin, year after year, with minimal competitive response? Because the cost of switching isn’t the cost of a new vendor. It’s the cost of touching every system that assumed the old one would be there forever.

The Lock-In Isn’t in the Contract

The standard story about vendor lock-in centers on contracts, proprietary formats, and intentional friction. That story is real but incomplete. The more durable form of lock-in is architectural. It happens when a vendor’s abstraction becomes load-bearing in ways nobody planned.

Consider what happens when an engineering team adopts a third-party authentication library. Initially it’s a time-saving decision, sensible on its merits. Eighteen months later, that library’s session model has quietly shaped how a dozen other services think about identity. The vendor’s data structures appear in middleware, in logging, in tests. Replacing the library is no longer a library replacement. It’s a distributed systems project that nobody has budget for, and which creates risk disproportionate to any savings a competitor might offer. Deleting a database column is already surprisingly risky in a mature codebase. Removing a foundational dependency is an order of magnitude harder.

The vendor knows this. Enterprise software salespeople aren’t naive about their customers’ codebases. They understand adoption curves, and they understand that the price sensitivity of a new customer and the price sensitivity of a customer who has been running their infrastructure for three years are completely different numbers.

The Moment Pricing Power Crystallizes

There is a specific inflection point in any vendor relationship where pricing power transfers. It’s not when you sign the first contract. It’s when the dependency becomes invisible, when engineers stop thinking of it as a vendor choice and start thinking of it as the way things work.

This inflection typically happens around the same time that the engineers who made the original adoption decision move on. Their institutional memory of alternatives, of the evaluation that chose this vendor over others, leaves with them. What remains is code that assumes the current solution is the natural order of things. New engineers inherit it without context. The dependency compounds.

PDF rendering, geolocation, email deliverability, PDF signing, payment tokenization, mapping. These categories have produced some of the most durable pricing power in software precisely because they’re solved problems that nobody wants to re-solve. The switching cost isn’t ignorance. It’s the rational calculation that the engineering time required to migrate could build several new features instead, and that the migration carries real downside risk with zero upside for customers.

Diagram showing an abstraction layer separating a third-party dependency from internal codebase
The abstraction layer between a vendor dependency and your own code is a business decision as much as a technical one.

Why Competition Doesn’t Fix This

The conventional economic response is: build a better alternative, price it lower, and capture the market. This is harder than it sounds, and not just because of sales cycles.

A new entrant in a critical-path category faces an asymmetric problem. Their potential customer already has a working solution. The customer’s switching cost is high, their risk tolerance around core infrastructure is low, and the new vendor can’t demonstrate the one thing that matters most in these categories: years of incident-free production behavior. The incumbent’s reliability record is itself a form of lock-in, separate from any technical dependency.

The incumbent also gets to observe this competitive dynamic and respond selectively. They can cut prices for accounts that are actively evaluating alternatives while maintaining rates elsewhere. This is not theoretical; it’s standard enterprise sales practice. The result is that competition in critical-path categories often produces better pricing for customers who are visibly shopping, and no pricing pressure at all for customers who are deeply integrated and not.

This dynamic helps explain why the second company into a market usually wins it in most software categories, but often doesn’t in infrastructure. Network effects compound differently when the customer’s own code is the network.

What Engineering Teams Can Actually Do

The practical response isn’t to avoid third-party dependencies. That’s not a real option for any team operating at speed. The response is to be deliberate about which dependencies are allowed to become load-bearing.

The distinction that matters is between a dependency that implements a function and a dependency whose abstractions leak into surrounding code. A payment processor that handles card tokenization but returns a standard result type is less dangerous than one whose proprietary error codes get parsed in twenty places across your codebase. The second form of adoption is what actually transfers pricing power.

This suggests a useful engineering discipline: treat the interface between third-party critical-path dependencies and your own code as a first-class design problem. Write an abstraction layer not because it’s architecturally elegant, but because it preserves your ability to make a different economic choice later. This is the kind of technical decision that looks like overhead until the renewal conversation, at which point it looks like leverage.

The Price Is Already Set

When a vendor raises prices on a deeply integrated customer, they are not guessing. They have a reasonable model of the customer’s migration cost, built from support tickets, API usage patterns, and the questions their sales team has fielded. They know, roughly, what it would take to replace them. Their price increase is bounded by that number.

This is why negotiating with a vendor you’re fully integrated with is fundamentally different from competitive procurement. You’re not shopping. You’re settling a claim. The vendor owns a function in your production environment, and the price of that function is whatever they can charge before it becomes cheaper to replace them than to pay.

The best time to think about this is before adoption, when you still have choices and no switching costs. The second best time is right now, while you can still audit which of your dependencies have become load-bearing and decide whether that’s a risk worth carrying at the price currently being charged.