Back to all roles

ASP.NET Developer

Interview questions for ASP.NET Developer roles.

10 questions

Question 1

Difficulty: medium

Can you walk me through how you would design a new ASP.NET Core web application from scratch?

Sample answer

I’d start by clarifying the business goals, expected traffic, security needs, and integration points before writing any code. From there, I’d choose an architecture that keeps the application maintainable, usually a layered or clean architecture approach with clear separation between controllers, services, repositories, and domain logic. I’d set up dependency injection early, define DTOs to avoid exposing internal entities, and make sure logging and configuration are handled consistently across environments. For data access, I’d decide whether Entity Framework Core is enough or whether a mix of EF and raw SQL makes sense for performance-critical areas. I also like to establish standards for validation, error handling, and authentication from day one. If the app is public-facing, I’d pay close attention to security headers, input validation, and rate limiting. My goal is always to build something that can evolve without becoming fragile after the first few feature releases.

Question 2

Difficulty: hard

How do you troubleshoot performance issues in an ASP.NET application?

Sample answer

I usually approach performance issues in layers instead of guessing. First, I identify where the slowdown is happening: server CPU, database calls, serialization, network latency, or client-side behavior. In ASP.NET Core, I’d check application logs, application insights or tracing tools, and look for repeated expensive operations. A common issue is too many database round trips, so I review queries, indexes, and whether I’m loading more data than needed. I also look at caching opportunities for read-heavy endpoints and verify that async code is used correctly so threads aren’t blocked unnecessarily. If memory pressure is high, I’d check for large object allocations, inefficient middleware, or poorly scoped services. I like to reproduce the issue in a staging environment with realistic data, because performance problems often only appear under load. Once I isolate the bottleneck, I measure before and after to confirm the fix actually helped.

Question 3

Difficulty: medium

Tell me about a time you had to fix a difficult bug in an ASP.NET project.

Sample answer

In one project, we had an issue where a specific API endpoint would occasionally return stale data even after updates were successfully saved. At first, it looked like a caching problem, but the behavior was inconsistent, which made it harder to trace. I started by reviewing the full request flow, including the repository, service layer, and any caching or mapping logic. Eventually I found that a singleton service was holding onto state that should have been scoped per request, so it was effectively reusing old data in certain scenarios. I changed the service lifetime, added better logging, and wrote a regression test to verify the fix. After that, I also reviewed other registrations to make sure we didn’t have similar lifetime issues elsewhere. What I learned was that bugs that seem random are often tied to state management or dependency lifetimes, especially in web applications. I’m careful now to verify service scopes early during implementation.

Question 4

Difficulty: hard

How do you ensure your ASP.NET APIs are secure?

Sample answer

I treat security as part of the design, not something to add at the end. For APIs, I start with strong authentication and authorization, usually JWT or cookie-based auth depending on the use case, and I make sure access is enforced at the endpoint and service levels where appropriate. I validate all incoming data and never trust the client to send clean values. I also use parameterized queries or ORM-generated SQL to reduce injection risk, and I avoid exposing domain entities directly because that can leak sensitive fields. For production, I make sure secrets are stored safely, error messages don’t reveal internals, and HTTPS is enforced. I also pay attention to rate limiting, logging of suspicious activity, and token expiration/refresh behavior. If the application handles sensitive data, I review encryption requirements and data retention rules as well. I think good security is mostly about consistent habits and removing shortcuts that create avoidable exposure.

Question 5

Difficulty: medium

How do you handle dependency injection and service lifetimes in ASP.NET Core?

Sample answer

I use dependency injection as the default pattern because it keeps code testable and makes dependencies explicit. In ASP.NET Core, I’m very deliberate about service lifetimes, because choosing the wrong one can create bugs that are hard to spot. I generally use transient for lightweight, stateless services, scoped for request-based services like data access or business logic tied to a request, and singleton only for truly shared, thread-safe services. A common mistake is injecting a scoped service into a singleton, which can lead to runtime issues or hidden state problems. I also try not to over-register everything by habit; I think about whether a service really needs to be in the container at all. For larger projects, I organize registrations by feature or layer so the startup code stays readable. When I review code, I look for places where lifetime choices might affect performance, thread safety, or test isolation. Getting this right early prevents a lot of downstream issues.

Question 6

Difficulty: medium

How do you approach writing unit tests for ASP.NET code?

Sample answer

I focus on testing behavior rather than trying to test every line. For ASP.NET code, I usually start with the service layer because that is where much of the business logic lives. I mock external dependencies like repositories, email services, or third-party APIs so the tests stay fast and stable. For controllers, I don’t usually test framework behavior itself, but I do verify that the controller returns the right response based on the service outcome. If there’s important routing, model binding, or integration behavior to validate, I’ll add integration tests using the test host so I can confirm the request pipeline works end to end. I also try to make tests readable enough that another developer can understand the intended behavior without digging through implementation details. A test suite is only useful if the team trusts it, so I keep the tests deterministic and maintainable. When bugs come in, I often write a test first to reproduce the issue before fixing it.

Question 7

Difficulty: medium

Describe a situation where you had to work with a legacy ASP.NET application. How did you improve it?

Sample answer

I’ve worked on older ASP.NET applications where the main challenge was not a single bug, but the overall structure. In one case, the application had tightly coupled controllers, business logic mixed into the UI layer, and very little automated testing. My first step was not to rewrite everything, but to stabilize the most important areas. I identified the highest-risk modules and introduced small refactors around them, such as moving logic into services and adding tests around critical workflows. I also cleaned up repeated database access patterns and standardized error handling so support issues were easier to diagnose. Over time, I introduced a more modern structure without forcing a risky big-bang migration. That approach helped the team keep delivering features while improving maintainability in parallel. With legacy systems, I think patience matters as much as technical skill. The best results usually come from incremental improvement, clear priorities, and protecting the business from unnecessary disruption.

Question 8

Difficulty: medium

How do you decide whether to use Entity Framework Core or raw SQL in an ASP.NET project?

Sample answer

My default is to use Entity Framework Core when it fits the problem, because it speeds up development and keeps data access consistent. It works well for most CRUD scenarios, relationship handling, and when the team wants readable, maintainable code. That said, I’m not dogmatic about it. If a query is very complex, performance-sensitive, or needs fine-tuned control over execution, raw SQL or a stored procedure can be the better choice. I also consider how often the query changes and whether the abstraction helps or gets in the way. For reporting-heavy features, I’ve sometimes used a combination: EF Core for normal operations and direct SQL for read-only, high-volume queries. What matters most to me is clarity and measurable performance, not using one approach everywhere. I’d rather choose the simplest tool that satisfies the requirement and keep the option open to optimize specific hotspots if profiling shows the need.

Question 9

Difficulty: hard

How do you handle API versioning in ASP.NET Core?

Sample answer

I use API versioning when there’s a real need to support multiple clients or prevent breaking changes from affecting consumers. The key is to make versioning intentional rather than accidental. In ASP.NET Core, I usually prefer a clear strategy such as URL segment versioning or header-based versioning depending on the client ecosystem. I keep shared logic in the service layer so only the contract and mapping change between versions. That helps avoid duplicating business rules. I also try to keep older versions stable for as long as the business requires, while making the newer version the preferred path for future development. Good documentation is important too, because versioning can confuse consumers if it’s not communicated well. I would avoid creating a new version for every small change; instead, I look for backward-compatible updates first. In practice, versioning is about managing change responsibly and keeping integrations predictable.

Question 10

Difficulty: hard

If a production ASP.NET API started returning 500 errors after a deployment, what would you do?

Sample answer

First, I’d treat it as an incident and focus on restoring service while gathering useful information. I’d check recent deployment changes, application logs, monitoring alerts, and any health check or crash data to identify whether the issue is tied to a specific endpoint or a broader startup problem. If possible, I’d roll back to the last known good version to reduce impact quickly. Then I’d compare configuration differences between environments, because a lot of production failures come from missing secrets, connection string problems, schema mismatches, or incompatible feature flags. If the issue is isolated to a code path, I’d reproduce it in staging with production-like settings and inspect the stack trace carefully. I also like to confirm whether database migrations were applied correctly, since deployment-related 500s often come from data or schema changes. After the immediate fix, I’d document the root cause and add safeguards, such as better validation, health checks, or deployment checks, so the same issue is less likely to happen again.