Design a Refund Workflow as a Directed Acyclic Graph
Quick Overview
Design a durable refund workflow as a directed acyclic graph with safe retries and concurrent steps. Handle idempotent side effects, partial-refund limits, crash recovery, asynchronous status, and manual intervention.
Design a Refund Workflow as a Directed Acyclic Graph
Company: DoorDash
Role: Software Engineer
Category: System Design
Difficulty: medium
Interview Round: Onsite
# Design a Refund Workflow as a Directed Acyclic Graph
Design a workflow engine representation for automatically refunding a user. Model the work as a directed acyclic graph so that steps with satisfied prerequisites can run, independent steps may run concurrently, and a failed or retried step does not accidentally issue the refund twice.
Extend the design to support a partial refund. Then address a workflow that may take long enough that the user should not wait on one synchronous request for completion.
### Constraints & Assumptions
- A refund has a stable workflow identifier and may be retried after a worker or network failure.
- The requested refund amount must be validated against the refundable amount before money-moving work begins.
- External side effects cannot be assumed to participate in one database transaction with workflow state.
### Clarifying Questions to Ask
- Which refund steps are pure computation and which call systems with external side effects?
- Can several partial refunds be issued against the same original payment?
- What user-visible states are required while a slow workflow is pending or needs intervention?
```hint Persist transitions before relying on them
An in-memory queue alone cannot tell a replacement worker which nodes completed before a crash.
```
```hint Give side effects stable identities
A retry is safe when the same logical node uses the same idempotency key rather than creating a new refund attempt.
```
### What a Strong Answer Covers
- A persisted DAG definition plus per-workflow node states and dependency counts.
- Atomic claiming, retry policy, idempotency keys, and recovery from worker crashes.
- Partial-refund validation that prevents cumulative refunds from exceeding the refundable balance.
- Asynchronous initiation with status polling or notifications for slow execution.
- Compensation or manual-review states for failures that cannot be rolled back automatically.
### Follow-up Questions
- How would two concurrent partial-refund requests avoid overspending the remaining refundable balance?
- How would you add a new workflow node without corrupting already-running instances?
- What evidence would let an operator explain why one refund is still pending?
Quick Answer: Design a durable refund workflow as a directed acyclic graph with safe retries and concurrent steps. Handle idempotent side effects, partial-refund limits, crash recovery, asynchronous status, and manual intervention.
Design a Refund Workflow as a Directed Acyclic Graph
DoorDash
Aug 2, 2026, 12:00 AM
mediumSoftware EngineerOnsiteSystem Design
0
0
Design a Refund Workflow as a Directed Acyclic Graph
Design a workflow engine representation for automatically refunding a user. Model the work as a directed acyclic graph so that steps with satisfied prerequisites can run, independent steps may run concurrently, and a failed or retried step does not accidentally issue the refund twice.
Extend the design to support a partial refund. Then address a workflow that may take long enough that the user should not wait on one synchronous request for completion.
Constraints & Assumptions
A refund has a stable workflow identifier and may be retried after a worker or network failure.
The requested refund amount must be validated against the refundable amount before money-moving work begins.
External side effects cannot be assumed to participate in one database transaction with workflow state.
Clarifying Questions to Ask Guidance
Which refund steps are pure computation and which call systems with external side effects?
Can several partial refunds be issued against the same original payment?
What user-visible states are required while a slow workflow is pending or needs intervention?
What a Strong Answer Covers Guidance
A persisted DAG definition plus per-workflow node states and dependency counts.
Atomic claiming, retry policy, idempotency keys, and recovery from worker crashes.
Partial-refund validation that prevents cumulative refunds from exceeding the refundable balance.
Asynchronous initiation with status polling or notifications for slow execution.
Compensation or manual-review states for failures that cannot be rolled back automatically.
Follow-up Questions Guidance
How would two concurrent partial-refund requests avoid overspending the remaining refundable balance?
How would you add a new workflow node without corrupting already-running instances?
What evidence would let an operator explain why one refund is still pending?