Hire .NET developers
.NET is Microsoft's cross-platform application platform, and the first thing to establish when hiring is whether a codebase is modern .NET or the older Windows-only Framework.
What .NET actually is
.NET is a development platform maintained by Microsoft, with C# as its dominant language. The modern platform is open source, runs on Linux and macOS as well as Windows, and ships a major release each year with a clearly dated support window. It is used heavily in enterprise back ends, financial services, healthcare, government and any organisation that already runs Microsoft infrastructure.
The single most important distinction when hiring is between modern .NET and the older .NET Framework. The Framework is Windows-only, receives no new features, and carries a very large installed base of business-critical applications. Modern .NET is cross-platform and actively developed. They share a language and a great deal of syntax, and they differ in deployment, hosting, libraries and performance characteristics enough that experience in one does not fully transfer.
This matters commercially because a large share of available .NET work is migration work, and because a job specification that just says .NET is ambiguous in a way that wastes everybody's time. Establishing which platform, and whether moving between them is in scope, filters the candidate pool more sharply than any other question you can ask.
The part that separates seniors from mid-levels
The runtime is managed, with a generational garbage collector that has server and workstation modes and behaves very differently between them. On a busy service the collector configuration is a real performance decision rather than a default to be left alone, and developers who have run .NET under load can usually tell you about a time it mattered. Alongside it, the platform has invested heavily in allocation-free patterns using spans and memory types, which is where high-performance .NET now lives.
Asynchronous programming is deeply woven into the platform, and it is where most subtle .NET bugs come from. Blocking on an asynchronous call is the classic mistake, and in some hosting models it deadlocks outright. Async all the way through, cancellation tokens passed and honoured, and an understanding of what a synchronisation context does are the marks of someone who has debugged this rather than read about it.
Entity Framework is the third area. It is productive and it hides the database, and the gap between what a developer thinks they asked for and what SQL the database receives is where performance problems live. Change tracking, lazy loading and query translation each produce their own class of surprise, and a senior candidate will have opinions about when to bypass the ORM entirely.
Where .NET is used
The label “.NET developer” covers several jobs that share a technology and little else. These are the settings the work usually turns up in, and the one you are hiring into should shape the whole process, because the judgement each demands is different.
Enterprise line-of-business systems
Internal applications in organisations already running Microsoft infrastructure, often integrated with Active Directory and SQL Server.
Financial services
Trading, risk and back-office systems where performance and correctness both matter and the platform's maturity is valued.
Healthcare and government
Regulated environments with long support requirements, strong identity integration and slow, deliberate upgrade cycles.
Web APIs and microservices
ASP.NET Core services in containers, which is where most new .NET work sits.
Desktop applications
WPF and WinForms applications that remain business-critical, an area with a thinning hiring pool.
Migration projects
Moving Framework applications onto modern .NET, one of the largest categories of available work.
If a candidate's experience sits in a different row of that list from the work you have, that is not a reason to reject them, but it is the thing to probe. Ask what would be different about their approach in your setting. Someone who can answer that has transferable judgement. Someone who says it would be much the same has probably not thought about it.
Which .NET versions are still supported
.NET ships annually with alternating long-term support releases and clearly published end-of-support dates, so whether a codebase is current is a matter of record rather than of judgement.
The table is generated from public release data rather than written by hand, so it states what is supported today rather than what was true when any given article was published. Of the 8 most recent release lines, 3 are still maintained and 5 have passed their published end-of-life date. That distinction is the practical one when you read a job specification: a requirement written against a line that is now out of support tells you the specification is older than the codebase it describes, and it is worth asking which of the two the new developer will actually work in.
| Release | Released | End of life | Status | Latest patch |
|---|---|---|---|---|
| 10 (LTS) | 2025-11-11 | 2028-11-14 | Maintained, long-term support | 10.0.12 (2026-09-08) |
| 9 | 2024-11-12 | 2026-11-10 | Maintained | 9.0.20 (2026-09-08) |
| 8 (LTS) | 2023-11-14 | 2026-11-10 | Maintained, long-term support | 8.0.31 (2026-09-08) |
| 7 | 2022-11-08 | 2024-05-14 | End of life | 7.0.20 (2024-05-29) |
| 6 (LTS) | 2021-11-08 | 2024-11-12 | End of life, long-term support | 6.0.36 (2024-11-12) |
| 5 | 2020-11-10 | 2022-05-10 | End of life | 5.0.17 (2022-05-10) |
| Core 3.1 (LTS) | 2019-12-03 | 2022-12-13 | End of life, long-term support | 3.1.32 (2022-12-13) |
| Core 3.0 | 2019-09-23 | 2020-03-03 | End of life | 3.0.3 (2020-02-19) |
Source: endoflife.date public release data, read 2026-09-25.
Two questions follow from this table in an interview. The first is which line the candidate has most recently shipped against, because someone whose last production work was on an unsupported line has not had to deal with the changes since. The second is how they have handled an upgrade. Version migrations are where you see whether a developer reads release notes, writes characterisation tests before changing anything, and knows how to stage a rollout, or whether they upgrade in place on a Friday and hope.
The toolchain around it
Nobody hires for .NET alone. The surrounding tools are where most of the day-to-day work happens, and a gap in any of them costs more time than a gap in the core library. This is the set that turns up most often on real job specifications alongside it.
- C#
- The language for the overwhelming majority of .NET work.
- ASP.NET Core
- The web framework for APIs and applications, including minimal APIs for smaller services.
- Entity Framework Core
- Object-relational mapping, and the usual source of query surprises.
- Dapper
- A lightweight alternative where explicit SQL and predictable performance are preferred.
- SQL Server or PostgreSQL
- The data store. SQL Server in established estates, PostgreSQL increasingly in new work.
- xUnit with Testcontainers
- Testing, with real dependencies rather than mocked repositories where it matters.
- Azure or containers
- The usual deployment target, though modern .NET runs anywhere.
- Serilog and OpenTelemetry
- Structured logging and tracing, standard in well-run services.
Related skills that frequently appear on the same specification: Microsoft Azure, SQL, React, DevOps, Kubernetes.
What to test in an interview
These are the topics that separate candidates in practice. Each one is given with why it discriminates, what a strong answer sounds like, and the response that should make you slow down. None of them requires a whiteboard.
Modern .NET versus the Framework
The first filter, and the question that most often reveals a mismatch.
- Strong answer: Can state which their recent work used, and describe concrete differences in hosting and deployment.
- Warning sign: Treats them as the same platform with a different version number.
Async and blocking
The most common source of subtle production faults in .NET.
- Strong answer: Async throughout, never blocks on an async call, passes and honours cancellation tokens, and can explain a deadlock they diagnosed.
- Warning sign: Uses blocking calls on async methods and has not seen the consequence yet.
Entity Framework and generated SQL
Where .NET performance problems overwhelmingly originate.
- Strong answer: Inspects generated SQL, controls tracking deliberately, avoids the N plus one pattern, and drops to Dapper or raw SQL when appropriate.
- Warning sign: Has never looked at the SQL, or believes the ORM optimises queries for them.
Dependency injection and service lifetimes
Built into the platform, and misconfiguring lifetimes causes bugs that look like corruption.
- Strong answer: Can explain the lifetimes and what goes wrong when a scoped service is captured by a singleton.
- Warning sign: Registers everything as one lifetime without being able to say why.
Configuration and secrets
Enterprise .NET applications accumulate configuration, and secrets end up in the wrong places.
- Strong answer: Layered configuration, secrets from a vault or managed identity, and validation at startup.
- Warning sign: Connection strings in source control, or configuration differences nobody has catalogued.
Performance work they have done
Separates people who have optimised from people who have read about allocation.
- Strong answer: Has measured with a profiler or benchmark harness, and can quote a before and after.
- Warning sign: Talks about micro-optimisations with no measurement, or has never profiled.
A migration they have run
Most substantial .NET work available is migration work.
- Strong answer: Describes an incremental migration with both versions running, and what could not be moved.
- Warning sign: Has only worked on applications already on the modern platform.
Warning signs in a .NET codebase
The fastest way to read a candidate is to ask what they have found wrong in code they inherited. These are the patterns that come up most often, what they cost, and what fixing them looks like. A developer who recognises three or four of these from their own experience is worth more than one who can recite the documentation.
Blocking on async
- What you see: Calls to .Result or .Wait() on asynchronous methods.
- What it costs: Thread pool starvation under load, and outright deadlock in some hosting models.
- The fix: Async all the way to the entry point. Where a synchronous boundary genuinely exists, isolate it explicitly.
The N plus one through Entity Framework
- What you see: A loop over entities touching a navigation property each iteration.
- What it costs: Hundreds of queries, latency growing with data, invisible with a small development dataset.
- The fix: Eager load deliberately and log generated SQL in development so the pattern is obvious when written.
Tracking entities that are only read
- What you see: Read-only queries executed with change tracking on.
- What it costs: Memory and CPU spent maintaining state nothing will use, on the hottest paths in the application.
- The fix: Disable tracking for read paths. Make it the default for queries that never write.
Captured dependency lifetimes
- What you see: A scoped or transient service injected into a singleton.
- What it costs: State shared across requests, producing data leaking between users, which is a security problem as much as a bug.
- The fix: Enable scope validation and treat the startup error as a design fault rather than something to work around.
Repository wrappers around the ORM
- What you see: A repository layer that re-exposes what Entity Framework already provides.
- What it costs: Two abstractions to maintain, lost query capability, and no actual testing benefit.
- The fix: Use the context directly and test against a real database. Add abstraction only where a genuine second implementation exists.
Running on an unsupported release
- What you see: A production service on a .NET version past its support date.
- What it costs: No security patches, and a widening gap that makes each deferred upgrade larger.
- The fix: Move to a supported long-term release and upgrade on the published cadence rather than in emergencies.
What each level can own
Job titles are not comparable between companies, so it is more useful to describe levels by what a person can be left to own without supervision. These are the boundaries we use when we assess a .NET developer.
- Junior
- Implements endpoints and data access in an existing service under review. Needs guidance on async correctness and query behaviour.
- Mid-level
- Owns a service or area including tests and deployment. Can read generated SQL and debug a dependency injection failure.
- Senior
- Owns service architecture, data access strategy, performance under load, and can run a Framework migration incrementally without stopping delivery.
- Staff
- Owns the estate's version policy, hosting strategy, cross-service contracts and the business case for which legacy applications should be migrated and which should not.
How the work is usually scoped
Team shape follows the kind of work, not the headcount you happen to have budget for. These are the shapes that come up most often and the constraint that actually governs each one.
New ASP.NET Core API
- Usual team: One to two developers.
- What governs it: Fast when the domain is clear. Integration with existing enterprise systems is usually the real scope.
Framework to modern .NET migration
- Usual team: Two developers, one who knows the existing application.
- What governs it: Scoped by dependencies without modern equivalents and by how much Windows-specific behaviour is embedded.
Performance remediation
- Usual team: One senior developer with production access, time-boxed.
- What governs it: Begins with profiling and query inspection. Most gains are in a handful of queries and allocations.
Desktop application maintenance
- Usual team: One developer with WPF or WinForms experience.
- What governs it: The constraint is a thinning hiring pool rather than technical difficulty. Plan for knowledge transfer explicitly.
Team augmentation
- Usual team: One to three developers joining an existing team.
- What governs it: Limited by domain knowledge transfer and review capacity rather than by headcount.
Migration work you may actually be hiring for
A large share of .NET work is not new development. It is moving an existing system from one state to another while it stays in service. These are the migrations that come up most often, and each one asks for a different kind of experience from the person you hire.
.NET Framework to modern .NET
- Why teams do it: Cross-platform hosting, better performance, active development and a healthier hiring pool.
- What to watch: Inventory dependencies first. Libraries with no modern equivalent are the decision points, and Windows-specific behaviour such as registry access, identity and scheduled tasks needs explicit replacement. Migrate project by project with both able to run.
Controllers to minimal APIs
- Why teams do it: Less ceremony and faster startup for small services.
- What to watch: Worth it for genuinely small services; for large applications the structure controllers impose is usually the better trade. This is not an upgrade that must be done.
SQL Server to PostgreSQL
- Why teams do it: Licensing cost and cross-platform hosting, usually alongside a wider move off Windows.
- What to watch: Entity Framework abstracts much of it, but stored procedures, specific data types and query hints do not translate. The work is proportional to how much logic lives in the database.
Synchronous code to async throughout
- Why teams do it: Thread pool efficiency and throughput under concurrent load.
- What to watch: This has to go all the way to the entry point. A half-converted codebase with blocking calls at the boundary performs worse than either extreme, so scope it by call chain rather than by file.
Migration work rewards a different temperament from greenfield work. The useful question in an interview is not whether someone has done the specific migration you face, but whether they have ever run one incrementally: behind a flag, with both paths live, and with a way back. Developers who have only done big-bang cutovers tend to propose them again.
What a good brief for this role contains
Most of the time lost in hiring a .NET developer is lost before anyone is interviewed, in the gap between what the brief says and what the team actually needs. These are the points that, for this technology specifically, change who the right candidate is. A brief that answers them can be matched in days. One that does not produces a shortlist that looks reasonable and converts badly.
- Whether the codebase is modern .NET or .NET Framework. This is the single most important line in the brief.
- What the hosting target is: Windows, Linux containers, Azure services, or a mix.
- Which data access approach is used, and how much logic lives in stored procedures.
- Whether a migration is in scope, and if so whether the application is still actively developed.
- What identity and authentication the application uses, since enterprise integration is often the hardest part.
- Whether desktop technologies are involved, because that is a separate and thinning pool.
If you cannot answer some of these yet, that is normal and it is still worth writing down which ones are open. An unknown that is named can be worked around. An unknown that is papered over in a job specification turns into a rejected shortlist and a restart four weeks later.
What the US market pays for this work
.NET work is counted by the US Bureau of Labor Statistics under Software Developers. That classification is broader than the technology itself, so treat the figures as the shape of the market a .NET developer is hired into rather than as a rate card for the skill. Across the United States the Bureau counts 1,687,890 people in this occupation, with a median annual wage of $135,980.
The spread matters more than the midpoint. The 90th percentile is about 2.6 times the 10th, which is a wide band for a single occupation and tells you that the title on its own carries very little pricing information. Two people described as a .NET developer can sit at $82,460 and $214,670 in the same national dataset. When a budget is set from a median without asking which end of that range the work actually needs, the hire that follows is usually the wrong one in one direction or the other.
Related classifications are worth reading alongside it, because teams hiring for .NET frequently end up recruiting against these titles too:
| Occupation | Employed | 25th percentile | Median | 75th percentile | 90th percentile |
|---|---|---|---|---|---|
| Software Developers | 1,687,890 | $105,210 | $135,980 | $171,980 | $214,670 |
| Computer Programmers | 92,230 | $75,850 | $100,390 | $130,680 | $160,460 |
| Computer Systems Analysts | 519,530 | $82,860 | $105,850 | $134,110 | $167,710 |
Source: BLS Occupational Employment and Wage Statistics, May 2025. Figures cover all US employers and are not FuturByte rates.
These are employer-side wage figures for people on a US payroll. They exclude employer taxes, benefits, recruitment cost and the months a seat sits empty, all of which are real and none of which appear in a salary line. The useful way to read the table is as the cost of the alternative you are comparing against, not as a number to match.
How US metro markets compare for this role
The same job is priced very differently across the country. Ranked by median annual wage for Software Developers, the gap between the highest and lowest of the 28 metro areas covered here is a factor of about 1.7. San Jose sits at the top with a median of $213,110; Pittsburgh sits at the bottom with $124,500. A budget built from a national median will be wrong in both of those markets, in opposite directions.
| Metro area | Employed | Median wage | vs US median | Location quotient |
|---|---|---|---|---|
| San Jose, CA | 87,350 | $213,110 | +57% | 7.09 |
| San Francisco, CA | 69,030 | $186,640 | +37% | 2.68 |
| Seattle, WA | 92,770 | $167,280 | +23% | 4.10 |
| New York, NY | 121,000 | $166,830 | +23% | 1.17 |
| Boston, MA | 42,310 | $166,090 | +22% | 1.44 |
| San Diego, CA | 20,610 | $163,270 | +20% | 1.23 |
| Los Angeles, CA | 55,540 | $160,920 | +18% | 0.82 |
| Portland, OR | 18,260 | $156,000 | +15% | 1.39 |
| Washington, D.C. | 69,060 | $154,930 | +14% | 2.03 |
| Baltimore, MD | 16,850 | $138,900 | +2% | 1.14 |
| Denver, CO | 27,010 | $137,610 | +1% | 1.55 |
| Charlotte, NC | 20,820 | $135,920 | 0% | 1.41 |
| Chicago, IL | 40,370 | $134,380 | -1% | 0.82 |
| Austin, TX | 31,960 | $134,120 | -1% | 2.28 |
| Dallas-Fort Worth, TX | 67,030 | $133,290 | -2% | 1.52 |
| Philadelphia, PA | 28,480 | $133,040 | -2% | 0.91 |
| Atlanta, GA | 36,300 | $132,960 | -2% | 1.16 |
| Raleigh, NC | 12,580 | $132,770 | -2% | 1.56 |
| Miami, FL | 18,900 | $132,650 | -2% | 0.62 |
| Phoenix, AZ | 29,380 | $131,750 | -3% | 1.14 |
| Minneapolis-St. Paul, MN | 27,410 | $130,920 | -4% | 1.29 |
| Detroit, MI | 24,870 | $130,760 | -4% | 1.20 |
| Tampa, FL | 14,230 | $130,450 | -4% | 0.91 |
| Orlando, FL | 13,440 | $129,620 | -5% | 0.88 |
| Salt Lake City, UT | 19,040 | $129,600 | -5% | 2.12 |
| Houston, TX | 22,940 | $129,440 | -5% | 0.64 |
| Kansas City, MO | 12,160 | $124,990 | -8% | 1.02 |
| Pittsburgh, PA | 10,320 | $124,500 | -8% | 0.85 |
Location quotient compares how concentrated this occupation is in the metro against the national average. A value above 1 means the metro has more of this work than its size would predict.
The location quotient column is the more useful one for hiring. A high median tells you what a role costs; a high quotient tells you whether the people exist. San Jose, San Francisco, Seattle, Washington, D.C., Denver, Austin each have a quotient of 1.5 or above, meaning the work is concentrated there well beyond what the size of the local economy would predict. Those are the markets where a search is likely to be quick and competitive at the same time, and where a counter-offer is most likely to take a candidate off the table late in the process.
The opposite case is worth planning for too. In a metro with a low quotient, the total pool is small even when wages look reasonable, so the realistic options are to widen the search radius, accept a longer time to hire, or bring the capability in from outside the local market entirely. That last option is what most teams are weighing when they come to us.
Hiring risks worth naming
Every one of these has produced a bad hire somewhere. They are written down so that the process tests for them deliberately rather than discovering them in month three.
Framework-only experience for modern work. Ask which platform their recent production work used. Hosting and deployment differ enough to matter from week one.
ORM dependence without SQL ability. Ask them to explain what a query produces. In enterprise .NET, SQL competence is not optional.
No async discipline. Ask about a deadlock or thread pool exhaustion they have seen. This fault is common and expensive.
Windows-only assumptions in cross-platform work. Ask what changes when the service runs in a Linux container. File paths, identity and scheduled tasks are the usual surprises.
Hiring .NET developers by metro area
Wages for this occupation vary more between US metro areas than most budget models assume. Each page below sets out the published employment and wage figures for that market, how it compares with the national picture, and what the local industry mix means for the kind of .NET developer who will be available.
- New York, NY $166,830 median
- Seattle, WA $167,280 median
- San Jose, CA $213,110 median
- Washington, D.C. $154,930 median
- San Francisco, CA $186,640 median
- Dallas-Fort Worth, TX $133,290 median
- Los Angeles, CA $160,920 median
- Boston, MA $166,090 median
- Chicago, IL $134,380 median
- Atlanta, GA $132,960 median
- Austin, TX $134,120 median
- Phoenix, AZ $131,750 median
- Philadelphia, PA $133,040 median
- Minneapolis-St. Paul, MN $130,920 median
- Denver, CO $137,610 median
- Detroit, MI $130,760 median
- Houston, TX $129,440 median
- Charlotte, NC $135,920 median
- San Diego, CA $163,270 median
- Salt Lake City, UT $129,600 median
- Miami, FL $132,650 median
- Portland, OR $156,000 median
- Baltimore, MD $138,900 median
- Tampa, FL $130,450 median
- Orlando, FL $129,620 median
- Raleigh, NC $132,770 median
- Kansas City, MO $124,990 median
- Pittsburgh, PA $124,500 median
Frequently asked questions
What is the difference between .NET and .NET Framework?
The Framework is the older Windows-only platform, still supported but receiving no new features. Modern .NET is cross-platform, open source, and released annually with dated support windows. They share C# and much syntax, and differ in hosting, deployment, available libraries and performance. When a job specification says only .NET, the first clarifying question is which one.
Should we migrate our .NET Framework application?
It depends on whether the application is still changing. If it is actively developed, migration pays for itself in performance, deployment flexibility and hiring. If it is stable and rarely touched, the honest answer is often to leave it and budget for its eventual replacement. Migrating a frozen application for its own sake is a common and expensive mistake.
Do we need Windows servers for .NET?
Not for modern .NET, which runs well in Linux containers and is frequently deployed that way. You do for .NET Framework applications. If moving off Windows hosting is a goal, it is really a migration project rather than an infrastructure one.
Is C# experience the same as .NET experience?
Largely, since C# is the language for most .NET work. The gap is platform knowledge: hosting models, configuration, dependency injection, deployment and the ecosystem. Someone who has written C# in one context will still need time to be effective in a different .NET hosting model.
Why is our .NET application slow?
In most cases we look at, it is database access rather than the runtime: N plus one queries, change tracking left on for read paths, or missing indexes. After that, blocking on async calls under load is the next most common. Both are diagnosable quickly by someone who knows to look, and neither is a reason to doubt the platform.
Should we use Entity Framework or Dapper?
Entity Framework for most application code, where productivity matters and the queries are ordinary. Dapper for hot paths where you want the SQL to be exactly what you wrote. Many healthy codebases use both, and a developer with strong opinions about using only one is usually telling you something about their experience rather than about the tools.
Is the .NET hiring pool shrinking?
Not for modern .NET, which is healthy and cross-platform. It is thinning for older desktop technologies such as WPF and WinForms, where the applications remain business-critical and the available developers are steadily moving on. If you depend on those, treat knowledge transfer as an active risk rather than something to handle later.
Which .NET version should we target?
A long-term support release still within its window, which the table on this page reflects from public data. The annual cadence and dated support windows make planning unusually easy here, and there is little excuse for drifting past end of life.