Skip to main content
Back to The LibraryFor Product Leaders

Show the Problem, Not the Roadblock

"That discount needs VP approval. Here's the button."

The Architecture Series · 8 minute read · By Ed | Founder & CEO, DealiOS


Your sales rep just built a deal with a 15% discount. They hit "save." The system says "Invalid discount."

That's it. "Invalid discount." No context. No explanation. No "this discount exceeds your authority but here's who can approve it." Just a wall.

The rep has two choices: guess what went wrong, or ping their manager on Slack. Both waste time. Both erode trust in the system. And the next time the system says "no," the rep's instinct will be to find a workaround instead of working within it.

You didn't build a guardrail. You built a wall. And people go around walls.

You didn't build a guardrail. You built a wall. And people go around walls.


Walls vs. Windows

There are two ways to tell someone they've hit a limit.

"Invalid discount."

Or: "This discount brings the deal margin to 28%, which is below the 35% floor for the Growth tier. VP approval required. [Route for Approval]"

Same rule. Same enforcement. One builds compliance. The other builds resentment.

The difference isn't cosmetic. It's architectural. The first approach treats business rules as binary gates: pass or fail. The second treats business rules as information layers: compute freely, annotate the results, let humans make informed decisions. The first approach assumes the user's intent was wrong. The second assumes the user's intent was fine but they lacked context about the constraints.

This distinction matters because of what happens next. The rep who sees "Invalid discount" learns to avoid the system. They build the deal in a spreadsheet, find the maximum discount they can apply without triggering the error, and submit a technically valid but strategically suboptimal deal. The system's constraint was respected. The business objective behind the constraint was undermined.

The rep who sees the margin impact, the floor, the tier, and the approval path learns something. They learn that this deal's margin is thin. They learn where the threshold is. They learn who can approve exceptions. Next time, they structure the deal differently. Not because the system blocked them, but because the system educated them.

Jakob Nielsen identified this thirty years ago as Usability Heuristic #9: help users recognize, diagnose, and recover from errors (Nielsen Norman Group). Error messages should be expressed in plain language, communicate the problem, and provide a path to resolution. Thirty years later, most enterprise software still shows "Invalid discount." The heuristic is older than most of the engineers building these systems. The systems haven't caught up.


The Compute-Then-Annotate Pattern

The architectural pattern that makes informative constraints possible is compute-then-annotate. It's a two-pass system, and the separation between passes is the key insight.

Pass 1: Compute everything. The discount engine computes every combination the user requested. Percentage discounts, volume discounts, term-based discounts, bundling discounts, fixed-amount discounts, per-line-item discounts, stackable combinations, non-stackable overrides, anti-compounding rules. The engine doesn't care about policy. It doesn't know what's allowed. It calculates what the numbers would be if every request were granted.

This is critical. The engine produces a complete financial picture of the deal as the user built it. Every line item, every subtotal, every margin calculation, every downstream consequence. The user's intent is fully expressed in math before any policy evaluation occurs.

Pass 2: Annotate with policy. A separate guardrails layer runs against the computed output. It doesn't recompute. It evaluates. Each violation is typed and categorized:

  • BELOW_MARGIN_FLOOR: The computed margin falls below the minimum for this pricing tier. Severity: error (blocks finalization without approval).
  • EXCEEDS_MAX_DISCOUNT: The aggregate discount exceeds the maximum allowable percentage. Severity: error.
  • STACKING_VIOLATION: Discounts were applied in a way that violates the workspace's stacking policy. Severity: warning.

Three violations. That's it. Not six. Not twelve. Three. Each one maps to a specific financial constraint that the business actually enforces. The temptation is always to add more violation types because more feels more complete. But every violation type you add is a message the user has to read, evaluate, and decide whether to act on. Three violations that carry clear meaning and actionable context beat twelve that create noise.

Each annotation carries the computed context: the actual margin number, the floor it violates, the discount percentage applied, the policy that was breached. The violation is a complete sentence, not a code.

Compute freely, annotate with policy, show the user exactly what happened and what they can do about it.

The two-pass separation matters because it preserves the user's work. A system that validates on input and blocks computation never lets the user see the full picture of what they were trying to build. They can't evaluate whether the deal they envisioned is close to viable or wildly unrealistic. They can't see which constraint they're hitting and by how much. They're navigating in the dark, bumping into walls they can't see, guessing where the edges are.

Compute-then-annotate shows the user exactly where they are, exactly which lines they've crossed, and exactly what it would take to either fix the deal or get the exception approved.


Approval Chains as Routing, Not Blocking

The logical extension of informative violations is informative approvals. When a deal violates a constraint that requires approval, the system doesn't block submission. It routes it.

Blocking says: "You can't do this." Routing says: "You can do this, and here's the path."

The approval chain architecture is sequential and multi-step, with cascading resolution logic that eliminates dead ends:

1. Specific user resolution: The violation specifies an approver (e.g., the deal owner's direct manager). 2. Role-based resolution: If the specific user is unavailable (out of office, deactivated, over-capacity), the system resolves to anyone with the required role within the relevant scope (e.g., any VP Sales in the same region). 3. Fallback resolution: If role-based resolution fails, the system escalates to all workspace administrators.

The cascading logic means the system always finds someone to route to. It doesn't send an approval request into the void and hope. It resolves to a specific person. If that person can't be found, it widens to anyone with the right role. If that fails, workspace admins catch everything that falls through.

The rep sees all of this. They know who the approval went to. They know the fallback path. They can follow up with context ("I submitted a deal with a margin exception because the client is displacing a competitor's three-year contract; here's the strategic justification"). The approval isn't a gate they're waiting behind. It's a conversation they're participating in.

This changes behavior. A rep who understands the approval process structures better exception requests. They preemptively include justification. They learn which deal structures require approval and start building deals that either avoid the exception or arrive with a ready-made case. The system's constraints become navigational tools, not obstacles.


The Error Taxonomy

Not all violations are equal, and treating them equally is its own form of information destruction.

The two-tier severity model (error and warning) maps to two different user experiences:

Errors block finalization. The deal cannot be submitted for signature until the violation is resolved (either by modifying the deal or by obtaining approval). Errors are reserved for constraints that carry direct financial consequences. A margin below the floor is an error because it creates a deal the business doesn't want to honor. A discount exceeding the maximum is an error because it produces a financial outcome that wasn't authorized.

Warnings inform without blocking. The user can proceed, but they should know something. A stacking violation is a warning because it might indicate a mistake (the rep didn't realize two discounts were being applied) or it might indicate a deliberately structured deal. The user decides. The system flags it and trusts the human to evaluate.

Two tiers. Not three, not five. The temptation to add more severity levels is real. "What about informational? What about advisory?" Every tier you add dilutes the ones that matter. When a rep sees an error, it should mean something. When they see a warning, it should mean something different. If you have five severity levels, the rep has to learn a taxonomy before they can act on the message. Two tiers, clear meaning, immediate action.

NNG's research on hostile error patterns confirms this: premature, aggressive, and disproportionate error messaging degrades trust and increases cognitive load (Nielsen Norman Group, 2024). Users who encounter a warning styled as an error pause, re-read, and question whether something went wrong. Users who encounter routine information presented as a warning start ignoring all warnings. Calibrated severity isn't a nice-to-have. It's a trust architecture.


Why AI Makes This Harder (and More Important)

Everything above applies to traditional rule-based systems. AI adds a layer of complexity that makes the compute-then-annotate pattern even more critical.

When AI generates a proposal, it's producing numbers, language, and structure simultaneously. If the AI generates a discount that violates a margin floor, the violation is embedded in the generated output. A system that validates after generation can catch it. A system that validates before generation prevents the AI from even considering certain deal structures, which constrains its ability to explore creative solutions.

The compute-then-annotate pattern applied to AI generation means: let the AI build the complete deal it thinks is best, including aggressive discounts, creative bundling, and unconventional term structures. Then run the guardrails. The AI might produce a deal with a 12% margin because the competitive dynamics justify it. That deal shouldn't be silently blocked. It should be computed, annotated with the margin violation, and routed for VP approval with the AI's strategic rationale included.

This is where the pattern connects to the companion paper on deterministic math (Library #1, "The Calculator Must Win the Argument"). The AI proposes the deal structure. The deterministic engine computes the financials. The guardrails layer annotates violations. The approval chain routes exceptions. Each layer does one job. No layer overrides another. The AI doesn't see invisible walls. It sees the full picture, constraints included, the same way the human user does.


The Universal Principle

The show-the-violation pattern extends beyond discount engines into every domain where systems enforce constraints on human behavior.

Compliance. A compliance check that says "Document not compliant" teaches nothing. A compliance check that says "Section 4.2 references pricing terms that are no longer current. The approved language for this contract type is [link]. Updating this section resolves the compliance flag" teaches the user how to fix the document and why the constraint exists.

Permissions. A permission error that says "Access denied" creates a support ticket. A permission error that says "This action requires Editor access on the workspace. Your current role: Viewer. The workspace owner is [name]. [Request Access]" resolves itself.

Content moderation. A content flag that says "Content rejected" creates frustration. A content flag that says "This section includes a ROI projection without a source citation. Company policy requires all quantitative claims to include methodology. [Add Citation] or [Remove Claim]" turns moderation into coaching.

In every case, the pattern is the same: compute freely, annotate with policy, show the user exactly what happened and what they can do about it. Transparency about constraints builds more trust than enforcement of constraints. A rep who understands why a deal needs approval structures better deals. A writer who understands why a section was flagged produces better content. A user who understands why access was denied requests it from the right person.

The wall says "no." The window says "not yet, and here's why, and here's how."

Build windows.

The takeaway: The wall says "no." The window says "not yet, and here's why, and here's how." Transparency about constraints builds more trust than enforcement of constraints.


References

1. Nielsen Norman Group. Usability Heuristic #9: Help Users Recognize, Diagnose, and Recover from Errors. Error messages should be expressed in plain language, precisely indicate the problem, and constructively suggest a solution. 2. Nielsen Norman Group. (2024). Hostile Patterns in Error Messages. Research on how premature, aggressive, and disproportionate error messaging increases cognitive load and degrades user trust in systems. 3. Nielsen Norman Group. Usability Heuristic #5: Error Prevention. Prevent problems by eliminating error-prone conditions or presenting confirmation before consequential actions. 4. Discount engine architecture (compute-then-annotate pattern, typed violations, two-tier severity model, cascading approval chains) based on DealiOS production implementation. 5. Library #1, "The Calculator Must Win the Argument," for the deterministic engine architecture that produces the computed outputs the guardrails layer evaluates. 6. Library #11, "Scoring Trust Without a Model," for the broader philosophy of encoding domain logic rather than relying on probabilistic inference for business-critical decisions.


This paper is part of The Architecture Series by Ed, Founder & CEO of DealiOS. For the weekly series and more technical deep-dives, visit dealios.app/library.

See how these principles come together. Explore the platform →