cswork / libraryOpen practice workspace

Interview guides · Amerisure

Amerisure Software Engineer Interview Guide

Amerisure Software Engineer interview guide: five reported rounds, behavioral STAR prep, and C#, .NET, REST, SQL Server and Azure topics.

The 60-second brief

Amerisure is a property and casualty insurance company. Candidates describe the Software Engineer role as building and maintaining the systems behind its insurance operations, used by policyholders, agency partners and internal claims teams. The reported work runs on the Microsoft technology stack and mixes updating older systems with new feature work, turning insurance business rules into code along the way.

This guide is for candidates interviewing for a Software Engineer role at Amerisure, including the Software Engineer II level that candidates describe as asking for roughly 2 to 5 years of professional experience. It covers the five reported rounds, the background, motivation and teamwork questions candidates report, and the discussion-based technical topics: C# and .NET, asynchronous code, REST API design, secure and fast code, SQL Server database work, and the Azure, deployment and networking basics that appear in reported loops.

Candidates report five rounds over roughly 4-6 weeks: Introductory Screen, Team Discussions, Behavioral Evaluation, Technical Discussion and Final Team Discussions. They describe the tone as conversational rather than a coding gauntlet.

Focus areas

  • Microsoft technology stack
  • Cloud computing (general)
  • Networking (general)

Overview

The role as candidates describe it is enterprise application work on the Microsoft stack. The reported requirements are C# and the .NET Framework or .NET Core, object-oriented design, RESTful APIs and SQL Server, with Azure, Angular or React, and insurance or financial-services experience listed as extras. Day to day, that means new API endpoints, tuning existing database queries, troubleshooting production issues, and working with product owners, QA engineers and DevOps teammates in an Agile/Scrum setup. Prepare to talk about your own work in exactly those terms.

The loop is reported as discussion-based, and most of the reported questions are about you: your background, why this position, what you want from a next team, a project you are proud of, and how you behave with colleagues. Technical questions are reported as high-level conversations about experience, so the winning preparation is a small set of projects you can explain end to end, with the design decisions and trade-offs you made, rather than algorithm drills.

Spend your time in three blocks. First, a story bank of real episodes (a disagreement, a scope change, a code review, helping a colleague, a database tuning job) each told with a clear result. Second, a project walk-through for a .NET or SQL Server system you built: layers, data access, error handling and logging, hosting and deployment. Third, short, correct explanations of synchronous versus asynchronous C#, REST API design for an internal service, secure and performant code, efficient SQL, and the Azure hosting and networking path of an app you know. The plan below sequences these across seven days.

The Amerisure interview process

The five stages below are what candidates report, in that order, over roughly 4-6 weeks. The number of team members you meet is reported to vary with the team and the seniority of the role.

Introductory Screen

Candidates report this first stage as a conversation in which the recruiting side explains Amerisure and the open engineering positions. Treat it as your first impression: arrive with a concise career narrative, a reason for this specific role, and a few questions of your own about the team and its stack.

What to demonstrate

  • How clearly you summarise your background and the direction of your career
  • Whether your interest in this role and in insurance software is specific rather than generic
  • Basic fit between your experience and the Microsoft-stack position described to you

How to prepare

  • Write a three-part career story (where you started, what you built most recently, why this role next) and say it aloud until it is short and natural.
  • Read up on what property and casualty insurance is, and who the policyholders, agency partners and claims teams are, so your answer to what you know about Amerisure is concrete.
  • Prepare two or three questions about the team, its .NET and SQL Server work and how projects are run.

Team Discussions

Candidates report meeting several members of the engineering group, with conversation centred on your background and your motivations for applying. Questions reported for this loop include why this position, what you want from your next team and a project you are proud of, so prepare answers to those that carry real detail.

What to demonstrate

  • How clearly you explain your background and your motivations for applying
  • How well you explain your past work and your own contribution to it
  • Conversational and collaborative style across several different people

How to prepare

  • Pick one project you are proud of and write its architecture on one page: users, components, data store, deployment, and the hardest decision you made.
  • Write a two-sentence answer to why this role and why insurance that mentions something specific from the role's reported work, such as modernizing older systems or API and query work.
  • Practice separating what you personally did from what the team did: speak in the first person for your own decisions and credit the team for shared outcomes.

Behavioral Evaluation

Candidates describe this stage as conversations about team fit, collaboration and communication style. The reported themes are conflict over design or priorities, working with product managers, QA and business stakeholders, supporting peers and adapting when requirements change. Answer with structured stories that have a concrete result.

What to demonstrate

  • Collaboration with cross-functional colleagues such as product owners, QA and business stakeholders
  • How you handle disagreement, shifting scope and feedback on your code
  • Communication style, including explaining technical issues to non-technical people

How to prepare

  • Build a bank of five or six STAR stories and tag each with the themes it can serve: disagreement, scope change, mentoring, cross-team work, a compromise made to hit a deadline.
  • Rehearse the disagreement with a senior engineer or manager and the significant scope-change stories until each ends with a measurable or observable outcome.
  • Prepare a plain-language explanation of one technical problem you solved, as if told to a claims or business colleague.

Technical Discussion

Candidates report high-level discussion of your familiarity with the Microsoft stack and your past projects, rather than live algorithm coding. The stack topics candidates list are .NET Framework and .NET Core, C# fundamentals such as asynchronous programming, SQL Server and Entity Framework, migration of legacy applications, and, as an advanced area, Azure services and CI/CD pipelines. Reported loops also weight cloud computing, cloud infrastructure fundamentals and networking, so prepare those alongside the .NET material.

What to demonstrate

  • Practical working knowledge of C#, .NET and SQL Server shown through your past projects
  • Engineering judgement: the trade-offs behind architectural and data-access choices
  • Ability to explain technical ideas such as async versus sync code accurately and plainly

How to prepare

  • Be ready to explain synchronous versus asynchronous C#: async and await, Task, why blocking on .Result or .Wait() can deadlock, and I/O-bound versus CPU-bound work.
  • Outline a REST API for a new internal service (resources, verbs, status codes, validation, authentication, versioning, error responses), and prepare a SQL Server query or schema you improved, with how you found the problem and what changed.
  • Prepare cloud and networking basics for a .NET app: App Service versus Functions versus VMs, Azure SQL, Key Vault, Application Insights; HTTP and TLS, DNS, load balancers, VNets and private endpoints; and how you would troubleshoot an app that cannot reach its SQL database.
  • Be ready to walk through how your code moved from commit to production: build, automated tests, pipeline stages and approvals, deployment, and how you rolled back a bad release.

Final Team Discussions

Candidates report concluding conversations with team members to confirm alignment on culture and technical fit. Reuse your strongest stories and keep your details consistent from one conversation to the next, and have a couple of fresh examples ready in case a topic comes up again.

What to demonstrate

  • Alignment on culture with the team members you meet
  • Technical fit with the work of the team you would join

How to prepare

  • Review the stories and project walk-through you have already told, keep the facts and numbers identical, and pick one new detail or example you could add.
  • Prepare questions about how the team handles code review, production support and deployment pipelines.
  • Have a clear answer to what role you naturally take in a team, with two examples.

Where candidates lose points

Giving a motivation answer that could be about any employer

Learn what property and casualty insurance is and who uses the systems (policyholders, agency partners, claims teams), then tie one part of your experience, such as legacy modernization or API work, to that. Write it down and test whether another company's name could replace Amerisure unchanged.

Treating a conversational round as casual and telling rambling stories with no result

Structure each story as situation, task, action, result, and finish on an outcome. Practice aloud with a timer you set yourself so the story stays tight, and prepare a story for each reported theme: disagreement, scope change, feedback, helping a teammate.

Describing every result as a team result, so your own contribution is unclear

State what you decided, built or changed in the first person singular, and credit the team for shared results. Rehearse each story once, replacing every plural pronoun with a named action of your own.

Listing C#, .NET and SQL Server on your resume but being unable to walk through a real system

Prepare one .NET project you can draw: layers, data access with Entity Framework or SQL, error handling and logging, hosting and deployment, plus one trade-off you made. Know a migration or modernization episode in case it comes up.

Answering sync versus async C# with definitions only

Explain what happens to the thread during an awaited I/O call, when async helps (I/O-bound work) and when it does not (CPU-bound), and why blocking on .Result can deadlock. Add a short example from your own code.

Questions & practice

Can you explain the difference between synchronous and asynchronous programming in C#?

Medium · High-Level Technical & Architecture

Approach

  1. A synchronous call holds the calling thread until the work finishes. With async/await, an awaited Task that has not completed returns the thread to its caller or to the thread pool, and the rest of the method runs as a continuation later. For I/O-bound work, no thread is held during the wait. Async is not the same as parallelism.
  2. The compiler rewrites an async method into a state machine. After an await, the continuation resumes on the captured SynchronizationContext if there is one (the UI thread in WPF or WinForms). ASP.NET Core has none, and library code often uses ConfigureAwait(false) to avoid capturing it.
  3. Main pitfall: blocking on async code with .Result or .Wait(). That can deadlock where a SynchronizationContext exists (UI apps, classic ASP.NET) and can starve the thread pool in ASP.NET Core. Use async all the way down, and keep async void for event handlers, because its exceptions cannot be awaited or caught by the caller.
  4. Run independent I/O calls together with Task.WhenAll. Awaiting it rethrows the first exception, while the task's Exception property holds all of them. Don't run two queries at once on the same EF Core DbContext, because it is not thread-safe.
  5. For CPU-bound work, Task.Run moves the work off a UI thread, but in a web API it only swaps one pool thread for another. Pass a CancellationToken down to I/O calls. Consider ValueTask only on hot paths that often complete synchronously.

Follow-up

  • What happens if you call .Result on a Task inside a WPF app or classic ASP.NET?
  • When, if ever, would you use Task.Run inside an ASP.NET Core controller?
  • How would you cancel a long-running database query when the HTTP client disconnects?

Track a rolling failure rate per destination for circuit decisions

Easy · sliding window · ring buffer · circuit breaker

The egress service delivers about 1,500 webhooks per second across roughly 40,000 destinations, each call bounded by a 10 second timeout. Maintain, per destination, the failure rate over the trailing 60 seconds so a caller can ask before dispatch whether the circuit should open. Attempts arrive as (destination_id, finished_at_ms, outcome). Requirement: amortised O(1) per attempt, with total memory bounded by the destination count rather than by traffic. Give the structure, its exact memory, and the rule that stops a destination with three attempts from opening a circuit.

Approach

  1. Name the exact-deque version and then reject it as the default. Holding timestamps and advancing a tail pointer past anything older than now minus 60 seconds is a correct two-pointer window at amortised O(1) per attempt, but its memory tracks in-window traffic, so one destination in a retry storm holds hundreds of thousands of entries while thousands of quiet destinations hold none.
  2. Use a ring of 60 one-second buckets per destination, each bucket a pair of counters for attempts and failures. On an attempt, advance the ring by the elapsed whole seconds, zeroing at most min(elapsed, 60) buckets, then increment the head. That is amortised O(1) with a fixed footprint per destination.
  3. State the footprint: 60 buckets times two 4-byte counters is 480 bytes of payload per destination, so 40,000 destinations is roughly 20 to 25 MB with per-entry overhead, bounded by the catalogue rather than by the rate. The cost is granularity, since the oldest bucket ages out in whole seconds, which is far tighter than the decision needs.
  4. Require a minimum sample before the circuit may open. A destination with three attempts and three failures reads as 100 percent and is not evidence; a floor of roughly 20 attempts in the window makes the ratio meaningful, and below that floor use a run of consecutive failures as the trigger instead.

Follow-up

  • The fleet is 30 instances and each sees roughly a thirtieth of a destination's traffic. Where does the rate actually live, and what does a per-instance answer get wrong?
  • A destination answers in 9.5 seconds and succeeds. It is not failing but it is consuming your per-destination concurrency. What signal should open the circuit here?

Find overlapping job attempts and peak concurrency from lease records

Medium · sweep line · intervals · leases

A day of job_run history yields about 50,000,000 attempt records: (job_run_id, job_type, attempt, started_at, finished_at which is NULL when the worker died, lease_expires_at). Leases expire on a clock, so a job that outran its lease ran twice. Produce (a) every job_run_id whose attempts overlapped in wall-clock time and (b) the peak number of simultaneously running attempts per job_type with the minute it occurred. Target O(n log n). State how you treat a NULL finished_at and what clock skew does to your answer.

Approach

  1. Define the interval before sorting anything: an attempt occupies [started_at, COALESCE(finished_at, lease_expires_at)). finished_at is observed and lease_expires_at is only a promise, so every attempt without a finish contributes an estimate and the whole result is a lower bound on overlap rather than an exact count.
  2. For peak concurrency, sweep: emit 2n endpoints, sort by (timestamp, kind) with ends ordered before starts at equal timestamps, then walk the sequence maintaining a counter per job_type and record each type's maximum with its timestamp. O(n log n) dominated by the sort, O(n) space, or O(1) extra if the sort is external and the walk streams.
  3. For overlap detection, do not compare attempts pairwise. A single global sort by (job_run_id, started_at) gives both the grouping and the order; within a group, keep the maximum end seen so far and report an overlap exactly when the next start is less than that running maximum, which is one linear pass after the sort.
  4. Half-open intervals matter and are easy to get wrong: with closed intervals an attempt ending at the same millisecond another begins reads as concurrency two, and across 50,000,000 records that artefact swamps the real signal.

Follow-up

  • A handler is not idempotent and you have found 400 overlapping jobs. Which of them actually caused damage, and what would you query to find out?
  • Peak concurrency for one job_type is 4 against a configured cap of 4. Is the cap working, or is the data hiding attempts that never started?

Explain why the owner filter ignores the listing index

Medium · composite index · query plans · sort elimination

The only index on resource is (tenant_id, status, updated_at DESC, resource_id DESC). A new endpoint returns one user's resources across all statuses, newest created first: WHERE tenant_id = $1 AND owner_user_id = $2 ORDER BY created_at DESC LIMIT 20. On a tenant with 2M rows it takes 900 ms and EXPLAIN shows a sort above a large scan. Explain precisely why the existing index cannot serve it, give the index that can, and state which of these the new index still will not help: owner_user_id alone across tenants; the same query ordered by updated_at. PostgreSQL 16.

Approach

  1. Separate the two jobs an index does. For filtering, a composite btree is seekable only on a left prefix, so with no predicate on status the scan can at best range over tenant_id and test owner_user_id per row; PostgreSQL 16 has no btree skip scan to jump the unconstrained column.
  2. For ordering, the index is sorted by (status, updated_at) within a tenant and not by created_at, so the LIMIT cannot stop early: every matching row is read and then sorted. That is the 'Sort Method: top-N heapsort' line, and it is why the plan reads 2M rows to answer with 20.
  3. Derive the replacement from the access path — equality, equality, then the ordering column: CREATE INDEX CONCURRENTLY ON resource (tenant_id, owner_user_id, created_at DESC). The scan seeks to the (tenant, owner) range and walks 20 entries in order, so the Sort node disappears along with the row-read.
  4. Treat INCLUDE (title, status) as conditional, not free. An index-only scan still visits the heap for any row whose page is not marked all-visible, so on a table taking 1.2k writes/second the win depends on autovacuum keeping the visibility map current, and the wider index costs more on every insert.

Follow-up

  • 90% of rows are status='active'. Would a partial index WHERE status = 'active' change your answer, and for which of the three queries?
  • A dashboard runs this for 40 owners in one page load. What changes about the design?

Stop tag and share joins from fanning out a page

Medium · join fan-out · semi-joins · many-to-many

resource_tag is (resource_id, tag_id) with PK (resource_id, tag_id); resource_share is (resource_id, shared_with_user_id, permission). The tagged-and-shared listing inner-joins resource to both, filters tenant_id, tag_id = ANY($2) and shared_with_user_id = $3, orders by updated_at DESC and takes 50. Pages come back with fewer than 50 distinct resources and the total in the header is far too high. Explain the row multiplication, rewrite both the page query and the count query so each is correct, and name the index each one needs. PostgreSQL 16.

Approach

  1. Do the arithmetic against the predicates that are actually there. An inner join emits one row per matching child row, and both joins are filtered: tag_id = ANY($2) admits only the requested tags, shared_with_user_id = $3 admits one user's share rows. So a resource holding three of the requested tags and shared with $3 once yields three rows, not one — the multiplier is its count of matching tags times its share rows for that single user, and that second factor is 1 unless the table admits duplicate (resource_id, shared_with_user_id) pairs. LIMIT 50 then limits rows rather than resources, and COUNT(*) counts pairs — the header is the product, not the population.
  2. Reject DISTINCT as the fix. It deduplicates after the product has been built, so the planner must materialise and sort the fanned-out set before the LIMIT can apply, and it leaves any SUM or AVG in the same select list wrong.
  3. Rewrite both filters as semi-joins, keeping resource as the only row source: AND EXISTS (SELECT 1 FROM resource_tag rt WHERE rt.resource_id = r.resource_id AND rt.tag_id = ANY($2)) and the same shape against resource_share. A semi-join stops at the first match per resource and preserves the driving index order, so ORDER BY updated_at DESC, resource_id DESC LIMIT 50 still stops after 50 rows.
  4. Count with the same predicates and no join at all: SELECT count(*) FROM resource r WHERE r.tenant_id = $1 AND r.status = 'active' AND EXISTS (...) AND EXISTS (...). Nothing multiplies a resource, so the number is the population.

Follow-up

  • The filter changes from 'any of these tags' to 'all of these tags'. Rewrite it and state what it costs relative to the ANY form.
  • A resource can be shared with the same user twice under different permissions. Does your count change, and should it?

What do you know about Amerisure and the products we build?

Medium · General Background & Motivation

Approach

  1. Lead with what you can confirm: Amerisure is a property and casualty insurer, and candidates describe its software as serving policyholders, agency partners and internal claims teams. Check its current lines of business on its own site before the call, and say nothing you cannot source.
  2. Map each user group to the kind of system it implies, such as an agent-facing portal, a claims workflow or back-office data flows. Present these as your own reading of the business, not as facts about its product list.
  3. Connect that picture to the stack candidates report for the role (C#, .NET, SQL Server, with Azure as a plus) and to the legacy-modernisation work in the role description. That turns company research into a reason you fit the role.
  4. Finish by asking which of those systems the team owns. This keeps you honest about what you could not learn from outside and opens the two-way conversation candidates describe.

Follow-up

  • Which part of an insurance workflow would you most want to work on, and why?
  • How would software for agency partners differ from software built for internal claims staff?
  • What would you want to learn first about how a policy or claim moves through the systems?

Why are you interested in this specific Software Engineer position?

Medium · General Background & Motivation

Approach

  1. Give three reasons and back each one with evidence: the work itself (C#/.NET services, SQL Server, REST APIs, modernising older systems), the insurance domain, and the collaborative, cross-functional setup candidates describe. Tie each reason to something you have already done.
  2. Line your experience up against the requirements candidates list (object-oriented C#, RESTful API design, SQL Server, Agile/Scrum) and pick one example for each, so the answer works as a summary of your fit.
  3. Name one area you want to grow into that the role offers, such as Azure App Services or Functions, or front-end work in Angular or React. This shows direction without claiming skills you lack.
  4. The answer that sinks you could be sent to any employer unchanged, or talks only about what you would gain. Rehearse until the reasons can only apply to this role.

Follow-up

  • Which of the listed responsibilities have you not done yet, and how would you close that gap?
  • Where do you see this role taking your career over the next few years?
  • What would make you turn this offer down?

What are you looking for in your next team and company?

Medium · General Background & Motivation

Approach

  1. Name two or three specific criteria and say what would show each one, for example code review on every change, engineers who own their services in production, or time set aside for mentoring and learning.
  2. Link them to the role as candidates describe it: working with product owners, QA and DevOps, plus stand-ups, sprint planning and code reviews. That shows your criteria fit how this team reportedly works.
  3. Explain what is missing in your current role in neutral, factual terms (scope, stack, ownership). Criticising your current employer costs more than it gains.
  4. Turn each criterion into a question you will ask in the team conversations, so the answer leads straight into your own questions.

Follow-up

  • What are you not getting in your current role that you expect here?
  • After three months, how would you know you had picked the right team?
  • What kind of team would you not want to join?

Walk me through a recent project you are particularly proud of.

Medium · General Background & Motivation

Approach

  1. Use a fixed structure: the problem and its users, your role, the architecture (main components, data store, hosting, how it was deployed), one hard decision with its trade-off, and a measured result such as latency, defect rate, hours saved or adoption.
  2. Expect stack questions and know the details: the .NET version, how data access worked (EF Core, Dapper or stored procedures, and why), the key SQL Server tables and indexes, and how it ran (IIS, Azure App Service or containers).
  3. Say clearly which parts were yours and which were the team's. Use 'I' for your decisions and name the people you worked with on the rest.
  4. Prepare one component in depth, such as a production incident or a performance fix with before and after numbers. Listing technologies without the reasons behind them is the usual way this answer falls flat.

Follow-up

  • If you rebuilt it today, what would you change?
  • What broke in production, and how did you find the cause?
  • How was it tested, and what did the tests miss?

How have you utilized the Microsoft technology stack in your previous roles?

Medium · High-Level Technical & Architecture

Approach

  1. Go layer by layer and claim only what you have shipped: the runtime (.NET Framework or modern .NET), the web layer (ASP.NET Core Web API or MVC), data (SQL Server with EF Core, Dapper or ADO.NET), and hosting and delivery (IIS, Azure App Service or Functions, Azure DevOps or GitHub Actions pipelines).
  2. Give each layer one decision and its reason. For example: I used EF Core with AsNoTracking and projections for read-heavy endpoints, and hand-written SQL for a reporting query where the generated plan was poor.
  3. If you have moved code from .NET Framework to modern .NET, explain what changed: System.Web is gone, you get built-in dependency injection, configuration moves from web.config to appsettings.json and environment variables, and the app runs on Kestrel. Describe the order you followed, such as multi-targeting shared libraries first and then moving endpoints or services one at a time.
  4. Say where your depth ends. 'I have used Azure Functions for timer jobs but not durable orchestrations' sounds more believable than a list of every product name.

Follow-up

  • Why did you choose EF Core over Dapper (or the reverse) in that project?
  • What broke when you moved code from .NET Framework to modern .NET?
  • How did you manage configuration and secrets across environments?

Walk me through how you would design a REST API for a new internal service.

Medium · High-Level Technical & Architecture

Approach

  1. Start with the callers and their use cases, then model resources as nouns with clear ownership, for example /claims/{claimId}/notes. Use GET to read, POST to create (201 Created with a Location header), PUT or PATCH to update and DELETE to remove, and keep GET free of side effects.
  2. Plan for retries. GET, PUT and DELETE are idempotent and POST is not, so accept an Idempotency-Key header on creates and store it with the result so a repeated request returns the original response. For long-running work, return 202 Accepted with a status resource.
  3. Define errors before the success shape: 400 for malformed input, 401 vs 403 for authentication vs authorisation, 404, 409 for conflicts, 422 for validation. Use one problem-details body (RFC 9457, which ASP.NET Core supports) carrying a correlation id.
  4. Handle concurrency and lists: an ETag (a SQL Server rowversion maps well) with If-Match, returning 412 Precondition Failed when the update is stale. Prefer cursor pagination to offset on large or changing tables, and allow-list filter and sort fields.
  5. Being internal is not the same as being trusted. Use service-to-service tokens (OAuth 2.0 client credentials, for example through Microsoft Entra ID) and per-resource authorisation checks. Version the contract (/v1 or a header), publish an OpenAPI description, and add only additive changes within a version.

Follow-up

  • How would you change the contract without breaking existing callers?
  • A client retries a POST after a timeout. How do you stop it creating a duplicate record?
  • How do you page through a large result set that changes while someone is reading it?

How do you ensure the code you write is secure and performant?

Medium · High-Level Technical & Architecture

Approach

  1. Security at the data layer: always use parameterised queries, either SqlParameter or EF Core LINQ. FromSqlInterpolated turns interpolated values into parameters, while FromSqlRaw built by string concatenation is injectable. The app's database login gets only the permissions it needs.
  2. Security at the boundary: validate input at the API edge, rely on Razor's default output encoding, check authorisation on every resource access (not just authentication) so changing an id cannot expose another user's record, keep secrets out of source in Key Vault or user-secrets, and run dotnet list package --vulnerable on dependencies.
  3. Performance starts with measuring. Set a target such as p95 latency, then find where the time goes with dotnet-counters, dotnet-trace or Application Insights, and on the database side with the SQL Server execution plan and Query Store, before you change anything.
  4. Common fixes in this stack: indexes that cover the WHERE and JOIN columns, removing N+1 queries with Include or projections, AsNoTracking on read-only queries, async I/O to keep threads free, and caching only when you can explain how it is invalidated. Use BenchmarkDotNet for code-level comparisons.
  5. Back it with process and one real example: code review, Roslyn analyzers in the build, and tests that cover authorisation paths. Then tell one story from your own work with the before and after numbers.

Follow-up

  • An endpoint got slow after a release. How would you find the cause?
  • Where do you keep connection strings and API keys, and how do they reach production?
  • What is the difference between a 401 and a 403, and when does your API return each?

p99 jumped on one listing filter while p50 stayed flat

Medium · query planning · composite index · percentiles

After a release that added an owner_user_id filter to the resource listing, p99 rose from 90 ms to 1.9 s while p50 stayed at 40 ms. Traffic and row counts are unchanged. resource carries the index (tenant_id, status, updated_at DESC, resource_id DESC). The new query filters tenant_id and owner_user_id, orders by updated_at DESC, resource_id DESC, and takes 20 rows. On PostgreSQL, explain the shape of the regression, prove it from a query plan, and give the index you would add.

Approach

  1. Start from the shape. A flat p50 with a moved p99 means a subset of requests changed cost, not all of them, so the first job is naming the subset. Bucket the endpoint's latency by the tenant's row count; the natural hypothesis is that large tenants are a small share of requests and all of the tail.
  2. Get the plan for the new query on a large tenant with EXPLAIN (ANALYZE, BUFFERS). Expect an index scan over the tenant's range, a filter discarding most of it, then a Sort feeding the Limit, possibly reporting Sort Method: external merge Disk. Read actual rows on the scan node, not estimated.
  3. Explain why the existing index cannot serve it. A composite B-tree is seekable only as a left prefix, and with no equality predicate on status the scan cannot treat updated_at as an ordering, because rows in the tenant's range are ordered by status first. Everything matching must be read and sorted before LIMIT 20 can apply, so a tenant with 400,000 rows pays 400,000 rows to return 20.
  4. Add (tenant_id, owner_user_id, updated_at DESC, resource_id DESC). Equality on the first two columns leaves the index ordered by updated_at within that pair, so the plan becomes an index scan that stops after 20 rows with no Sort node. PostgreSQL can scan a B-tree backwards, so the DESC markers matter only if the two sort columns ever disagree in direction; keeping them explicit documents the order the keyset cursor depends on.

Follow-up

  • The endpoint paginates with OFFSET. What does page 500 cost with your index, and what does the keyset version cost?
  • How would you have caught this before release, given that a 10,000-row seed database produces the same plan shape at an unnoticeable cost?

Suggested practice checklist

A seven-day sequence built from the five reported rounds, the background and teamwork questions candidates report, and the C#, .NET, REST, SQL Server, Azure and networking topics. The first days build stories, the later days drill the technical conversation.

Day 1 — Map the loop and write your career story

  • List the five reported rounds in order and write one line on what each covers, marking the one you feel least ready for.
  • Write your career narrative in three parts (past, present, why this role) and say it aloud twice.
  • List six projects or incidents from your work that could become stories later.

Deliverable: A one-page loop map, a written career narrative, and a list of six story candidates.

Day 2 — Background and motivation answers

  • Read up on property and casualty insurance and who uses an insurer's systems, then write what you know about Amerisure in your own words.
  • Write answers to why this Software Engineer position and what you are looking for in your next team and company, each naming something specific.
  • Write a one-page walk-through of the project you are proudest of, covering design, your role and the result.

Deliverable: Written answers for the company-knowledge, role-interest, next-team and proudest-project questions.

Day 3 — Behavioral stories: disagreement and change

  • Write a STAR story for a disagreement with a senior engineer or manager, including the evidence you used.
  • Write a STAR story for a significant change in project scope, including how you reset expectations.
  • Add a story about a compromise made to meet a business deadline, and say it aloud.

Deliverable: Three finished STAR stories, each with a stated result, recorded aloud once.

Day 4 — Behavioral stories: feedback, support and team role

  • Write your answer on receiving code feedback, with one story where a review changed your code.
  • Write a STAR story about helping a teammate with a technical problem and a short answer on the role you take in a team.
  • Prepare a plain-language explanation of a technical issue for a non-technical colleague, and a calm answer for a teammate not pulling their weight.

Deliverable: Four written answers (feedback, helping a teammate, team role, explaining to a non-technical colleague) and one answer on an underperforming teammate.

Day 5 — C#, the Microsoft stack, Azure and networking

  • Write how you have used the Microsoft stack (projects, .NET Framework or .NET Core, Entity Framework) and how your code moved from commit to production: build, tests, pipeline stages, rollback.
  • Explain synchronous versus asynchronous C# in a short script, including a deadlock example with .Result, and the I/O-bound versus CPU-bound distinction.
  • Outline error handling and logging: global exception middleware returning ProblemDetails, structured ILogger logging (Serilog or Application Insights) with correlation ids, log levels, no swallowed exceptions; plus a migration plan: System.Web removal, built-in DI, appsettings.json, endpoint-by-endpoint moves.
  • Sketch how your .NET API runs on Azure (App Service plan and slots, Azure SQL connection, managed identity with Key Vault, Application Insights), trace a request from DNS through TLS and the load balancer to the app, and list how you would troubleshoot an app-to-SQL connection failure.

Deliverable: A Microsoft-stack and pipeline talking sheet, a spoken async explanation, an error-handling and migration outline, and an Azure hosting and request-path diagram.

Day 6 — REST design, secure and fast code, SQL Server

  • Outline a REST API for an internal service: resources, verbs, status codes, validation, authentication, versioning and error shape.
  • List your checklist for secure and performant code: input validation, parameterized queries, authentication and authorization, secrets handling, measuring before optimizing.

Deliverable: A REST API outline, a secure and performant code checklist, and a written database design and tuning story with a before-and-after measurement.

Day 7 — Full mock and questions to ask

  • Run a spoken mock through your career story, motivation answers, two behavioral stories, the async explanation and your Azure request-path sketch, back to back.
  • Write five questions to ask the team about code review, deployment pipelines, production support and the current modernization work.

Deliverable: A recorded mock run, notes on weak spots, and a list of five questions to ask.

Team fit and collaboration stories

Candidates report that the Behavioral Evaluation and the team conversations around it centre on collaboration, handling conflict, adapting to change, supporting peers and communicating with non-technical people. Prepare real episodes from your engineering work, each with your own actions and a result, so a few stories can serve many prompts.

  1. Tell me about a time you had to compromise on a technical decision to meet a business deadline.
  2. Describe a situation where you had to explain a complex technical issue to a non-technical team member.

Tell me about yourself and your journey in software engineering so far.

Medium · General Background & Motivation

Approach

  1. Use present, past, future. Open with your current role and the kind of systems you work on, then two or three earlier steps that explain how you got here, then why this Software Engineer role is the next one.
  2. Pick the thread that matches the reported role: C# and .NET services, SQL Server data work, API building and Agile teamwork. Name one outcome per step, such as a service you shipped or a query you made faster.
  3. Keep it a story of growth with a decision in each chapter, not a recitation of your resume. Credit the team where it deserves credit and state your own part plainly.
  4. End by handing the conversation over with a hook, for example the part of your background you would happily go deeper on.

Follow-up

  • Which of those roles taught you the most, and what specifically changed in how you work?
  • What part of your background is least related to this position, and how will you cover the gap?
  • Where do you want your skills to be in two or three years?

Tell me about a time you disagreed with a senior engineer or manager. How did you handle it?

Medium · Behavioral & Team Fit

Approach

  1. Choose a real technical or priority disagreement, such as a design choice, a library, or a release trade-off, where the other person was more senior. Avoid stories that turn the other person into a villain.
  2. State their position first, in terms they would accept as fair, then yours. Showing you understood their reasoning is half the answer.
  3. Describe what you did to settle it with evidence rather than opinion: a small prototype, a measured query time, a list of risks, or a request to bring in a third reviewer.
  4. Give the outcome honestly. You may have changed your mind, they may have, or you may have committed to their decision anyway; say what you did once the decision was made and how the working relationship stood afterwards.

Follow-up

  • What would you have done if they still disagreed after seeing your evidence?
  • Looking back, was there anything in your approach you would change?
  • How do you disagree when a deadline leaves no time for a prototype?

Describe a situation where you had to adapt to a significant change in project scope.

Medium · Behavioral & Team Fit

Approach

  1. Pick a change that really moved the work, such as a requirement added mid-sprint or a feature cut in half, and state in two sentences what was planned and what changed.
  2. Explain how you assessed the impact: what was already built, what had to be redone, what the new risk was, and what you told the product owner about cost and options.
  3. Show concrete adaptation: re-ordering the backlog, splitting the work into releases, hiding unfinished parts behind a flag, updating tests and acceptance criteria, and telling affected teammates and stakeholders early.
  4. Close with the result and what you changed in future planning, such as asking earlier about what could shift.

Follow-up

  • How did you decide what to drop or defer?
  • How did you tell stakeholders who had expected the original scope?
  • Did the change leave technical debt, and how did you track it?

How do you prefer to receive feedback on your code?

Medium · Behavioral & Team Fit

Approach

  1. Answer with a preference and then prove it with an episode. A solid preference is small, focused pull requests with written comments that explain the reason, and a short call or pairing session when a comment needs discussion.
  2. Tell one story where review feedback changed your code for the better, such as a missed null check, an unparameterized query, or an unclear method name, and what you changed afterwards (a test, a checklist, a habit).
  3. Show how you respond to feedback you disagree with: ask what concern sits behind it, offer your reasoning with evidence, and accept the team's convention when it is a matter of style.
  4. Mention that you give reviews the same way you like to get them, since this is a team-fit question.

Follow-up

  • Tell me about a review comment you disagreed with and what happened.
  • How would you give difficult feedback on a colleague's pull request?
  • What do you do when two reviewers give conflicting advice?

Tell me about a time you helped a teammate who was struggling with a technical problem.

Medium · Behavioral & Team Fit

Approach

  1. Choose an episode where the teammate had a real technical problem, such as an intermittent bug, a slow query or an unfamiliar framework feature, and you were not simply assigned to fix it.
  2. Show that you diagnosed before helping: you asked what they had already tried, looked at the same logs or stack trace together, and narrowed the cause with them rather than taking the keyboard.
  3. Describe what you taught or left behind, for example a debugging technique, a note in the wiki, or a test, so the teammate could handle the next one alone.
  4. Give the outcome for both the problem and the person, and mention what it cost you in time and how you balanced it with your own deadline.

Follow-up

  • What would you have done if they had been reluctant to accept help?
  • How did you balance helping with your own sprint commitments?
  • What did you learn from that teammate?

What role do you naturally take on when working in a team environment?

Medium · Behavioral & Team Fit

Approach

  1. Answer honestly with one or two roles you actually take, such as the person who clarifies requirements with the product owner, the steady reviewer, the one who writes tests and documentation, or the one who keeps the team's discussion calm.
  2. Support each role with a short example from a sprint, code review or production incident, ending with what the team gained.
  3. Show flexibility: say how your role changes when another person already fills it or when the team needs something different from you.
  4. Avoid a vague answer such as being a leader or a team player; name behaviours a colleague could verify.

Follow-up

  • What happens when the team already has someone in that role?
  • Which role do you tend to avoid, and how do you cope when it is needed?
  • How would a former teammate describe your role?

Describe your experience with database design and writing efficient SQL queries.

Medium · High-Level Technical & Architecture

Approach

  1. Tell it as two concrete episodes. First a schema you designed: the entities, keys and relationships, constraints you enforced, normalisation level and any deliberate denormalisation, and why.
  2. Second, a slow query you fixed in SQL Server or another relational database. Say how you found it (execution plan, logical reads from STATISTICS IO, a monitoring alert), what the plan showed, such as a scan or key lookup, and what you changed.
  3. Name the actual fixes: a nonclustered index with included columns, rewriting a predicate so it can use the index (no function wrapped around the column), replacing row-by-row logic with a set-based query, and fixing parameter sniffing where relevant.
  4. If you use Entity Framework, mention its pitfalls and your habits: N+1 queries caused by lazy loading, Include versus projection, AsNoTracking for read-only paths, and checking the SQL it generates.
  5. Give before-and-after evidence in your own measured terms, and the trade-off: each extra index slows writes and uses storage.

Follow-up

  • A query that was fast last week is suddenly slow. How do you investigate?
  • When would you denormalise, and what does it cost you?
  • How do you deal with a slow query generated by an ORM?