cswork / libraryOpen practice workspace

Interview guides · Walmart Labs

Walmart Labs Software Engineer Interview Guide

Walmart Labs Software Engineer interview guide: online assessment, DSA and design deep-dive, hiring manager round, reported questions and a 7-day plan.

Interviewing at Walmart Labs

  • Practice bank: 30+ questions
  • Rounds: 3
  • Typical prep: 2–4 weeks
  • Interview reports: 6

Interview rounds

RoundQuestions
Online Assessment3
Technical Screen23
Onsite4

How hard is the Walmart Labs Software Engineer interview?

DifficultyShareQuestions
Easy13%4
Medium77%23
Hard10%3

What Walmart Labs actually tests for

TopicShareQuestions
Coding & Algorithms50%15
System Design27%8
Behavioral & Leadership13%4
Software Engineering Fundamentals10%3

The 60-second brief

Candidate notes for the Walmart Labs Software Engineer role describe work inside a large retail system: payment systems, search and microservices that sit behind how customers discover, purchase and receive products. The reported interview questions follow the same themes: payment processing and ledger design, scenario-based system design, and a question on integrating AI into existing project workflows, alongside medium-level graph, hashing, string and dynamic programming problems. Prepare to write clean code and to defend architecture choices within the same loop.

Walmart Labs candidates report 3 rounds · ≈ 3-5 weeks. The stages below are what candidates describe, not a published process.

What a Software Engineer does at Walmart Labs

Alongside the payment and ledger prompts, back-end commerce problems stand out: designs where concurrent writes, retries and money have to stay correct.

Language depth is part of the preparation too. The candidate notes use Java and Spring Boot as the example stack and mention configuration, property files and profile setup. The bank also includes Spring Boot questions and an object-oriented Shape interface exercise. If you work in another language, prepare the equivalents: how your framework wires dependencies, loads configuration per environment and runs background work.

The Walmart Labs interview process

Walmart Labs candidates report 3 rounds · ≈ 3-5 weeks. The stages below are what candidates describe, not a published process.

Online Assessment

Candidates report the online assessment as the first stage, covering coding and basic framework proficiency. The candidate notes do not say which problems appear in it. Prepare from the reported coding questions as a whole: medium-level problems in grid connectivity, hashing, sliding window and dynamic programming. For the framework part, prepare your primary stack at the level of everyday use. The candidate notes use Java and Spring as the example, including configuration, property files and profile setup.

What it evaluates

  • Choosing the structure that fits each problem family: BFS/DFS or union-find for grids, a hash set for consecutive runs, a last-seen index map for non-repeating windows, a one-dimensional DP array for minimum-coin problems
  • Edge cases handled in code rather than mentioned afterwards: empty input, a single element, duplicates, and an impossible target that must return a sentinel such as -1
  • Framework basics explained plainly: how configuration is loaded, how an environment-specific profile overrides it, and how components are wired together

How to prepare

  • Practise medium problems from the reported coding families under a timer, writing each from an empty file and stating its time and space complexity before you run it
  • For Spring or your own stack, explain aloud: where application properties live, how a profile such as dev or prod changes them, how a value is injected into a bean, and what happens when a required property is missing
  • Keep a short list of test inputs per family (single cell, all water, all land, duplicates, an empty string, a target smaller than the smallest coin) and run them before you call a solution finished

Technical Deep-Dive

Candidates report this stage as covering data structures and algorithms, low-level design and high-level design. Reported design questions include payment processing, a ledger system that includes schema and functional and non-functional requirements, scenario-based system design, and integrating AI into existing project workflows. Candidates do not tie any of them to a specific round, so treat them as design practice in general. Open every design prompt by stating functional requirements, then non-functional requirements (latency, throughput, consistency), and only then the schema and services. For the algorithm part, be ready to explain why you picked a structure and what it costs in time and space.

What it evaluates

  • Requirements stated before any schema: what the system must record, which operations are allowed, and which non-functional targets you are assuming
  • Schema and storage choices tied to access patterns, including when a relational store fits a money path better than a NoSQL one and why
  • Scalability patterns used for a stated reason (caching, load balancing, message queues), with the consistency trade-off each one introduces named
  • Low-level design that stays extensible: interfaces and classes that absorb a new variant without editing every caller, as in the bank's Shape interface exercise

How to prepare

  • As design practice, design a double-entry ledger end to end: append-only entries in integer minor units, a transaction that must balance to zero, balances derived or cached from entries, and an idempotency key on every externally triggered write
  • Walk a payment through authorise, capture, refund and a timed-out call to a processor, and say which states are terminal and how a retry is made safe
  • Practise one scenario-based design where a requirement changes halfway through (a new region, a tenfold traffic increase, a new payment method) and redraw only the part that changes
  • Do one low-level design in code: an interface, two implementations and a caller that does not branch on type

Hiring Manager Round

Candidates report the hiring manager round as the final stage, focused on fit, project history and leadership potential. The candidate notes say it covers past projects, how you handle team conflict and your approach to technical leadership, with deep questions on why you made particular technical decisions, and they warn against treating it as a formality. Candidates also report behavioral questions without tying them to a round: team conflict, ambiguous requirements, a challenging project from your resume and your role in it, and balancing technical debt against feature delivery. Stories prepared for those also cover the project and conflict ground described for this round.

What it evaluates

  • Whether you can explain the why behind a technical decision on your resume: the option you rejected and the constraint that ruled it out
  • How you handle a conflict inside a team: what the disagreement was about, what evidence settled it, and what the working relationship looked like afterwards
  • Whether your account of a challenging project separates your contribution from the team's
  • Your approach to technical leadership: a decision you drove, how you brought others along, and what you would change next time

How to prepare

  • Go through every bullet on your resume and write the technical challenge, your decision and the outcome for each; be ready to be asked about any of them
  • Prepare STAR stories for the four reported behavioral questions, each with a decision you made yourself, the alternative you rejected, and a measurable result
  • Prepare an answer on AI usage: a specific place you used or would use AI tools in your development work, what it improved, and where you checked its output

Questions Walmart Labs candidates report

Data structures and algorithms

State the bound, then read your own code against it, because the cost you forgot is usually inside a call you did not write. A membership test against a list is linear while the same test against a set is expected constant, so one of those inside a loop turns a linear scan quadratic. Taking a slice copies the elements wherever slices are values rather than views. Repeated string concatenation is quadratic wherever strings are immutable, unless you accumulate into a builder or a list and join once. None of that is visible in the shape of the algorithm, and all of it is visible in the runtime.

  • Longest Consecutive Subsequence
  • Longest non-repeated substring

System design and architecture

A design is a set of promises about what happens when something is slow, down, or delivered twice, and that is the part usually left unsaid. For each dependency, say what the system does when it is unavailable: serve stale data, reject the write, or accept it and settle later. For each relaxation of consistency, describe the anomaly a user would actually notice, in the product's own words, rather than naming a consistency model and moving on. The separator is volunteering the failure behaviour as part of the design instead of producing it only when pushed.

  • Integration of AI into existing project workflows
  • Design a payment processing system
  • Scenario-based system design questions

Behavioural and engineering judgement

Every question in this category has a number in it somewhere, and engineers routinely tell the story without one. What the outage cost, what the delay cost, what the rewrite consumed in engineer-weeks against what it saved, and who absorbed it when it was not users: the on-call rotation, another team's quarter, the support queue. You will rarely have an exact figure, and an estimate with its method stated beats both a precise-sounding invention and silence. Say how you got to it and what it leaves out. That is the sentence that makes the follow-up about whether it was worth doing answerable at all.

  • How do you balance technical debt with feature delivery?
  • How do you handle ambiguity in project requirements?

Practice exercises with worked solutions

The prompts above tell you what gets asked.

Decide which facts an invoice line copies instead of joining

invoice_line_item already denormalises tenant_id, which is reachable through invoice_id, and stores amount_minor even though quantity times unit_price_micros would recompute it. A reviewer asks you to normalise both away, and separately asks whether the tenant's legal name and billing address should be copied onto the invoice header. Decide each case. For every field you keep denormalised, name the read pattern or the invariant that justifies it, the anomaly the copy can develop, and the mechanism that prevents that anomaly here.

How a strong candidate works it

  • Split the question into two kinds of copy, because they fail differently. A copy of a currently mutable fact is a cache: it drifts and needs invalidation. A copy of a fact frozen at write time is not a cache at all, it is the record of what happened, and normalising it away destroys information the source no longer holds.
  • Keep tenant_id on the line. It costs 8 bytes, it leads every index on the table so no read is ever accidentally cross-tenant, and it turns a wrong join into an empty result rather than another tenant's money. Prevent the drift structurally: a unique constraint on invoice (invoice_id, tenant_id) plus a composite foreign key from the line on (invoice_id, tenant_id) makes a mismatched pair impossible, so the database enforces agreement instead of a code review.
  • Keep amount_minor. Rounding must happen exactly once, at a named site, with a stated mode (half-even here). If readers recompute from quantity and unit_price_micros, every reader owns a rounding decision, and half-up and half-even diverge systematically across thousands of lines rather than cancelling out. A check constraint can bound the stored value but deliberately cannot re-derive it.
  • Copy the legal name and billing address onto the invoice header, written once and never updated. The statement must show what was true when it was sealed, and the tenant record will change afterwards. This is a snapshot for the same reason source_rollup_watermark is stored per line: without it, nobody can reconstruct what the customer was told.
  • Name the read pattern that pays for all of it. Rendering, dispute response and export are per-tenant, per-period reads over thousands of lines that would otherwise join back to slowly changing dimensions that no longer hold the historical value. The write side is a once-per-period batch, so the extra columns cost nothing that matters.
  • Concede the case where the reviewer is right: a mutable operational attribute such as the tenant's current plan name has no business on a line. If a report wants it, join. If a statement needs the plan as of the period, that is another snapshot and it belongs on the header with the rest.

Follow-ups

  • Write the composite foreign key and the unique constraint it requires on the parent. What does it cost on every line insert, and what does it do to a bulk load?
  • A tenant is renamed after being invoiced. Which rows change, and what does the customer see on last quarter's PDF?
  • Where does currency live, and what breaks if a tenant's billing currency changes between two periods?

Paginate a tenant's delivery export without skipping rows

A customer exports webhook_delivery: delivery_id (bigint identity), subscription_id, tenant_id, event_id, status, attempt_count, next_attempt_at, created_at, delivered_at, updated_at. The endpoint runs select ... where tenant_id = $1 order by created_at desc limit 100 offset $2, and customers report rows missing from exports taken while new deliveries are being inserted. Write the replacement query and the index that supports it, paging a tenant's deliveries newest first at constant cost per page. State why updated_at cannot be the cursor column.

How a strong candidate works it

  • Name the defect precisely. OFFSET is a position in a result set that is recomputed on every request, so a row inserted ahead of the window shifts everything back by one and the next page starts after a row the client never received. Nothing errors and no identifier gap appears, so the loss is silent.
  • Replace the position with a value predicate over a stable, unique, indexed ordering: where tenant_id = $1 and (created_at, delivery_id) < ($2, $3) order by created_at desc, delivery_id desc limit 100. The row comparison is load-bearing: created_at alone is not unique, so ties straddling a page boundary are dropped or repeated, which is the same bug in a smaller window.
  • Index (tenant_id, created_at, delivery_id). PostgreSQL scans a btree in either direction, so an all-DESC ORDER BY is served by an ASC index read backwards and no DESC modifiers are needed; they only matter when the ORDER BY mixes directions. Confirm the plan has no Sort node above the index scan, or the LIMIT stops being an early exit.
  • Price both forms: keyset is one index descent plus 100 adjacent leaf entries per page, constant regardless of depth, while OFFSET still produces and discards every skipped row, so page N costs time proportional to N times the page size and a deep page on a large table goes from milliseconds to seconds.
  • Rule out updated_at as the cursor from the precondition, not from taste: a cursor column must never change value for a row already paged past. updated_at moves on every delivery attempt, so a row the client already emitted re-enters a later page and is exported twice. created_at and delivery_id are immutable, which is the whole qualification.

Expected result (20 min): A keyset query using the row comparison (created_at, delivery_id) < ($2, $3) with order by created_at desc, delivery_id desc limit 100, backed by (tenant_id, created_at, delivery_id) scanned backwards; plus the statement that OFFSET drops rows under concurrent insert and costs time proportional to the offset, and that updated_at is disqualified because it mutates on retry.

Check yourself

  • Buffer counts for page 500 are the same order of magnitude as page 1.
  • Every id present before the walk is returned exactly once when only inserts run concurrently.
  • The query plan shows no Sort node above the index scan.
  • Two rows sharing a created_at value to the microsecond are both returned across the page boundary.

Follow-ups

  • The client wants a snapshot as of one instant rather than a live tail. Compare a repeatable-read transaction held open, an added created_at <= $snapshot bound, and a materialised export table.
  • A retention job deletes deliveries older than 90 days. What does a client mid-walk see, and does keyset pagination help at all?
  • The customer wants to resume an export from yesterday's last cursor. What must be true of the cursor for that to be safe?

Seal an hour under late data with bounded memory

Metering ingest reads 256 partitions at 10,000 to 40,000 events/second. Events carry occurred_at and ingested_at, and during a producer replay the gap between them is hours. Seal each UTC hour once no more than 50 parts per million of that hour's eventual quantity can still arrive, using memory that does not grow with the size of the replay. Define the watermark, the lateness parameter and how you measure it, the structure holding open hours, and the write that performs the seal. State what an idle partition does to your watermark.

How a strong candidate works it

  • Two clocks, two jobs. Bucket by occurred_at, because that is the hour the customer is billed for, and advance the watermark on ingested_at, because that is what the fold has consumed and what source_max_ingested_at records. Conflating them is what makes late data invisible.
  • The global watermark is the min over partitions of each partition's committed ingested_at, not the max: the fold is trustworthy only as far as the slowest partition. The consequence is that one idle partition pins the watermark forever and nothing seals, so an idle partition must promote its watermark to wall clock after a stated idle timeout, and that timeout becomes a correctness parameter, because a partition that is slow rather than idle gets sealed past.
  • Choose the lateness L from the measured distribution of ingested_at - occurred_at, weighted by quantity rather than by event count. The target is 50 ppm of the hour's quantity, and a replay is rare in events while carrying disproportionate mass, so an event-weighted quantile picks an L that is comfortably wrong at exactly the moment it matters.
  • Measure that quantile in bounded memory. A Greenwald-Khanna summary gives epsilon-approximate quantiles in O((1/epsilon) log(epsilon n)) space; a t-digest costs more per merge but has relative error that tightens at the tails, which is the half of the distribution you are reading at p99.99. Keep a separate summary per tenant class, because one tenant's batch importer is not the population.
  • Hold open hours in a min-heap keyed by hour_start. When the watermark advances, pop every hour with hour_end + L < W and seal it: O(log H_open) per advance and O(1) amortised per event to touch its bucket. Memory is open hours multiplied by distinct (tenant, workspace, sku) keys, so cap the number of simultaneously open hours and spill the oldest into usage_rollup_hourly as status='open' with a revision bump. While an hour is open the row is upsertable, so the store is your overflow.
  • The seal itself is a conditional write: update ... set status='sealed', sealed_at=now() where status='open' returning .... Two sealers race on every restart, and the loser must see zero rows and stop rather than write a second value. After the seal, an event for that hour is not an upsert but an adjustment, and source_max_ingested_at is what proves it arrived afterwards.

Expected result (40 min): The quantity-weighted p99.99 is hours larger than the event-weighted one. Choosing L from the event-weighted number lets roughly the tail's 3% of quantity land after the seal, 600 times the 50 ppm target. With the min watermark and no idle timeout, the stalled partition blocks all sealing; with a 60-second timeout, the stall is sealed past and its events arrive late.

Check yourself

  • Post-seal quantity as a fraction of the hour's total is at or below 50 ppm at the chosen L, measured rather than assumed.
  • The second sealer's update reports zero rows affected and writes nothing.
  • Heap size equals the number of open hours and does not grow with the replay's event count.

Follow-ups

  • A replay starts during the sealing window for a period you are about to close. What do you do, and what is the customer-visible consequence of each option?
  • Your measured quantity-weighted p99.99 lateness is six hours and the invoice must be issued at 02:00 UTC on the first. How do you reconcile those two numbers?
  • How would you detect that L has drifted before it costs you an hour's quantity?

Per-tenant rate limiting that holds across one hundred pods

The same gateway enforces each tenant's plan rate limit in requests/second and its monthly quota. Traffic is heavily skewed: a handful of tenants exceed all others combined, while a small tenant's requests may all land on one of the 120 pods. Both limits must hold in aggregate rather than per pod, per credential or per region, and the check may add at most 2 ms at p99. Specify the algorithm, where the state lives, the exact operation performed per request, and the behaviour when the counter store is unreachable - separately for the rate limit and the quota.

How a strong candidate works it

  • Do the arithmetic on per-pod buckets before discarding them, and be precise about which half fails. Giving each pod rate/N keeps the sustained aggregate correct - 120 buckets of 5 rps sum to the 600 rps limit - but a tenant whose traffic all lands on one pod is throttled at 5 rps, a hundred and twentieth of what it pays for. The over-admission comes from burst depth, not sustained rate: if each pod carries a full bucket depth B, the aggregate burst is 120B against a limit that intended to allow B.
  • Move the rate limit to a shared counter accessed in exactly one atomic round trip - a token bucket or GCRA as a single server-side script returning allow/deny plus a retry-after - never a read followed by a write. Keep the key tenant-scoped and region-local; a globally shared counter costs a cross-region round trip that alone exceeds the 2 ms budget, so shard the global limit per region in proportion to observed regional share and accept that a tenant whose traffic shifts regions is briefly throttled until the shards rebalance.
  • Cut round trips for the largest tenants with leased tokens: a pod leases 50 at a time and spends them locally, reducing counter round trips by 50x at the cost of bounded over-admission of pods x lease_size, which is 6,000 requests in the worst case here. Shrink the lease for tenants with small limits, where that bound would swamp the limit itself.
  • Treat the quota as a different problem, not a longer window. It is a count that other in-flight requests are changing, so select-the-usage-then-insert is write skew: read-committed permits it and repeatable read permits it too, because snapshot isolation is exactly what allows two transactions to read a consistent count and both write. Enforce it inside one statement - an atomic increment whose returned value is compared, or UPDATE ... SET used = used + $1 WHERE used + $1 <= limit RETURNING - or with a constraint that makes the surplus write fail.
  • Write the unavailability policy per limit rather than one policy for both. The rate limit fails open to a conservative local bucket, because it protects capacity and failing closed turns a counter blip into a total outage. The quota fails open for tenants whose last known usage was well below the cap and closed for those at or above it, since that is the only decision with revenue attached, and reconciles from the usage ledger on recovery - which is why the monthly counter must be re-seedable from that ledger rather than being the only copy.

Expected result (30 min): A per-region shared token bucket keyed (tenant, region, window) executed as one atomic script at roughly one sub-millisecond intra-region round trip; the monthly quota enforced by a single atomic increment-and-compare that is re-seedable from the usage ledger; leases only for high-limit tenants with over-admission bounded at 120 x 50 = 6,000 requests; the rate limit failing open to a conservative local bucket and the quota failing closed only above the last known cap.

Check yourself

  • Separate the two halves of the local-bucket claim: sustained aggregate is correct at rate/N per pod, burst is not. If your answer says local buckets let a tenant exceed its sustained rate, the arithmetic does not support it.
  • Re-read your quota check and confirm no branch reads the counter and then writes it. If the predicate is not inside the write or enforced by a constraint, the race is still there.
  • Compare worst-case lease over-admission against the smallest tenant limit you apply leases to. If 6,000 exceeds that tenant's per-minute allowance, the lease size is wrong for that tier.

Follow-ups

  • One tenant is 40% of all traffic and its counter key lands on a single shard. What do you change, and what does that cost in accuracy?
  • Clients receive 429s and retry. What stops the well-behaved ones from synchronising into a herd?
  • A tenant reports being throttled below its limit. Which evidence do you produce, and does your design emit it today?

A rare job-run overwrite that logging makes disappear

About one job run in fifty thousand records billable_seconds matching no observed sandbox lifetime, and a few rows show worker_id changing after finished_at was already set. It does not reproduce: debug logging around the terminal write made it vanish for two weeks before it returned. Runs last from 200 ms to 30 minutes, the lease is 60 seconds and is renewed while a run executes. Give an ordered checklist, the mechanism, and a fix that makes the illegal write impossible rather than merely rarer.

How a strong candidate works it

  • Mine the evidence instead of chasing a repro: select rows where updated_at is later than finished_at, or where a terminal status was written twice, and join them to attempt history to recover both writer identities. The defect has already happened tens of times and the rows are the recording.
  • State the signature before measuring it. If the cause is a lease that expired while the original worker was stalled, affected runs should cluster where the gap between the last renewal and the terminal write exceeds the lease, and should correlate with worker pause metrics rather than with workload shape.
  • Read the disappearance honestly. Logging inside the window changed the timing and lowered the probability; it is evidence about how narrow the window is, not a fix. Reproduce by widening the window on purpose, shortening the lease and injecting a pause between sandbox exit and the terminal write, rather than by adding more instrumentation.
  • Name the mechanism precisely: the lease expires during a stall such as a long garbage-collection pause or a brief partition, the run is re-dispatched, and the original worker then wakes and writes its terminal state over the new attempt's row. A lease alone cannot stop this, because the check and the write are separated by the stall.
  • Fix by fencing the write itself: UPDATE job_run SET status = $2, finished_at = $3, billable_seconds = $4 WHERE run_id = $1 AND status = 'running' AND lease_token = $5, with zero rows affected interpreted as having been fenced rather than as success. The token lives on the row so the store arbitrates, not the worker's memory.
  • Keep the state machine honest: a retry inserts a new row pointing at parent_run_id rather than resetting the old one, and a run whose worker vanished terminates as lost with billable_seconds null, because recording failure asserts an outcome nobody observed and then bills and retries on that assertion.

Follow-ups

  • The supervisor also emits a usage event on completion. What does the fenced worker do about the event it already emitted, and how does metering absorb it?
  • Lease renewal is itself a network call. What happens when a renewal times out, and how does the worker decide whether it still holds the lease?
  • Why is lengthening the lease past the longest legitimate run the wrong lever, and what breaks if you do it anyway?

Unblock an engineer on a job run that finished twice

An engineer two weeks into the team brings you a job_run row showing status succeeded with an exit_code written by a worker declared dead ten minutes earlier; the retry attempt also shows succeeded. They have spent a day adding logging and are no closer. You have twenty minutes and you do not want to take the keyboard. Describe how you unblock someone: the question you ask first, what you let them find themselves, the concept you name and when, and how you check the next day that they own the fix rather than having watched you produce it.

How a strong candidate works it

  • Ask what they expect rather than what they see: which statement set status to succeeded, and what did it check before writing? That question points directly at the update's WHERE clause, which is where the answer lives, and it costs them nothing to answer, so it does not read as a test.
  • Let them build the timeline themselves from the row: queued_at, started_at, leased_until, finished_at and worker_id, on both the original run and the retry. Two different worker_ids with a lease expiry between them tells the whole story, and they will see it before you say it.
  • Name the concept once the evidence has earned it. A lease bounds time; it does not prevent a write. The store has to reject a stale writer, which means the update carries a fencing token the row compares — update job_run set status = 'succeeded' where run_id = $1 and lease_token = $2 and status = 'running' — and a long garbage-collection pause or a brief partition is enough to produce what they are looking at.
  • Point at the second, less obvious half and let them decide it: 'lost' exists in the status enum precisely so a run whose worker vanished is not recorded as failed, because failed asserts an outcome nobody observed and the system then bills and retries on that assertion. Ask them what these two rows should have said.
  • Leave them with the next step rather than the patch — a test that kills the first worker after the sandbox exits and before the row is written — and say when you are available again, so the offer is real rather than polite.
  • Check ownership the next day by what they produced, not by asking if it went well: a test that reproduces the window proves they understood it; a test that only asserts the new WHERE clause proves they copied it. Ask them to explain it to a third person and listen for whether the explanation is theirs.

Follow-ups

  • They propose a longer lease instead of a token. What do you say, and what breaks when legitimate runs last thirty minutes?
  • How can you tell whether your explanation landed or they simply deferred to you?
  • The same engineer hits a variant of this next month. What did you fail to teach the first time?

Where candidates lose points

Drawing ledger or payment tables before stating functional and non-functional requirements

The reported ledger question explicitly includes schema and FR/NFR, so let requirements drive the schema. Start with functional requirements: post a transfer, reverse it, query a balance and its history. Then give non-functional ones: no money created or lost, a full audit trail, strong consistency on the write path, and latency and throughput targets you state as assumptions. Only then draw tables, and point to the requirement each column serves.

A payment design where a retried or timed-out request can charge twice

Treat a timeout to a payment processor as an unknown outcome, not a failure. Give each external request an idempotency key enforced by a unique constraint, model the payment as a state machine with explicit terminal states, and reconcile unknown outcomes by querying the processor before any retry. Record money as integer minor units in append-only ledger entries rather than updating a floating-point balance in place.

Stopping at a correct but slow version of a reported coding problem

For Number of Islands 2, re-running a full DFS after every added cell costs O(m x n) per addition. Use union-find: add the cell as a new component, union with each land neighbour, and decrement the count only on a successful union. Skip cells that are already land. For Longest Consecutive Subsequence, a hash set gives O(n) if you only start counting from numbers whose predecessor is absent. Sorting is O(n log n). State the brute force first, then move to the version that meets the bound.

Solving the online assessment's coding problems but stalling on framework basics

Candidates report the online assessment covers basic framework proficiency as well as coding. If your stack is Java and Spring Boot, rehearse how properties are loaded, how profiles override them per environment, how values and beans are injected, and how a service runs background work. If your stack is different, prepare the same four answers for your framework so none of them is a surprise.

Describing what the system did in the hiring manager round instead of what you decided

Candidate notes say this round asks deep questions on why you made technical decisions, so a tour of the architecture leaves the main question unanswered. For each project story, name the decision that was yours, the option you rejected and the constraint that ruled it out. For conflict and technical-debt prompts, say what you actually chose to defer or push back on, and what would have made you change your mind.

Breadth then depth, for a generalist facing a mixed loop

Four days sample coding, design, fundamentals and the practical rounds at deliberately shallow depth, which is enough to surface the topics you did not know were in scope. That map, rather than a guess made on day one, decides where the last three days go.

Day 1 — Coding: grids and graphs

  • Solve Number of Islands with BFS and then DFS, and state why both are O(m x n).
  • Solve Number of Islands 2 (Island Counting II in the bank) with union-find using path compression and union by size. Test a repeated addition and cells that join two existing islands at once.
  • Solve the bank's Course Schedule cycle detection to cover directed graphs, using either Kahn's algorithm or three-colour DFS.

Deliverable: Three working solutions with complexities written above each and a list of the edge cases you tested.

Day 2 — Coding: hashing, strings and dynamic programming

  • Solve Longest Consecutive Subsequence in O(n) with a hash set, counting only from numbers whose predecessor is absent, and explain why sorting is slower.
  • Solve the longest non-repeated substring with a sliding window and a last-seen index map, then the bank's Shortest Unique-Character Substring for contrast.
  • Solve Coin Change (minimum coins, return -1 when unreachable) and the bank's count-ways variant. Explain why the coins loop must be the outer loop when counting combinations.

Deliverable: Five solutions, each preceded by a one-line brute force and its complexity, then the optimised version.

Day 3 — Timed coding and framework basics

  • Pick two unseen medium problems from the families in days 1 and 2 and solve each in a plain editor with no autocomplete, running your own edge-case inputs before stopping.
  • Answer aloud the framework basics for your stack: configuration and property files, environment profiles, dependency injection, and background work (the bank has Spring Boot questions if Java is your stack).
  • Do the bank's Shape interface exercise as a small low-level design warm-up: one interface, two implementations, and a caller that does not branch on type.

Deliverable: Two timed solutions with notes on where you slowed down, plus a one-page framework cheat sheet written from memory.

Day 4 — High-level design: payments and the ledger

  • Design a ledger system in the order the reported question implies: functional requirements, non-functional requirements, then schema. Use double-entry, append-only entries and integer minor units.
  • Design a payment processing system: authorise, capture, refund, the timeout path, idempotency keys and reconciliation against the processor.
  • Read the drill on which facts an invoice line copies instead of joining (drill-sql-1) and apply its snapshot and rounding reasoning to your ledger schema.

Deliverable: Two one-page designs, each opening with an FR/NFR list and ending with the failure you designed hardest for.

Day 5 — High-level design: scenario-based problems and AI integration

  • Take one bank prompt (real-time inventory service or read- and write-heavy product catalog) and design it. Then change one requirement mid-way and redraw only what changes.
  • Work through the guide's rate-limiting exercise (drill-design-4) and compare your quota check against its atomic write.
  • Prepare a design answer on integrating AI into an existing project workflow: where the model call sits, what happens when it is slow or wrong, and how you would measure whether it helped.

Deliverable: One scenario design showing before and after the requirement change, plus a short written answer on AI integration.

Day 6 — Behavioral stories and resume

  • Write STAR stories for the four reported behavioral questions: team conflict, ambiguous requirements, a challenging project and your role in it, and technical debt against feature delivery.
  • For every resume bullet, note the technical challenge, the decision you made, the rejected alternative and the outcome.
  • Prepare one debugging story using the bank's Troubleshooting a System Issue prompt as a model: the evidence you gathered, the fix, and when you escalated.

Deliverable: Four STAR stories that each name a decision you made, and an annotated resume you can defend line by line.

Day 7 — Full mock of the three reported rounds

  • Mock the online assessment, which candidates say covers coding and basic framework proficiency. The mix is your own practice choice: one timed medium coding problem and five framework questions.
  • Mock the technical deep-dive, which candidates say covers DSA, low-level design and high-level design. As your own practice set, use one algorithm problem, one short low-level design and one high-level design opened with FR/NFR; candidates do not say which design question comes in which round.
  • Mock a hiring manager conversation using day 6's stories, and ask the interviewer to probe why you made each decision.
  • Redo the guide's worked keyset pagination exercise (drill-sql-2) cold, then check it against the listed checks.

Deliverable: Notes from all three mocks listing the weakest answer in each, and a one-page card of the rules you can state without reading them.