Back to blog
Engineering

Deterministic policy evaluation: how we built a fail-closed governance engine

A deep dive into the policy engine architecture - priority-based resolution, scope hierarchies, and why HARD_DENY short-circuits everything.

AK

Ankit Kumar Panda

CTO, Governax

Code on a dark screen representing policy engine architecture and deterministic evaluation

The core of any governance platform is its policy engine - the component that evaluates rules against actions and produces a deterministic outcome. Getting this right is not just a technical challenge. It is a trust challenge. If the engine is unpredictable, nobody will rely on it.

Here is how we built the Governax policy engine, and why we made the architectural choices we did.

The fundamental principle: fail-closed

The Governax policy engine is fail-closed. This means that if anything goes wrong during evaluation - a rule cannot be parsed, a data source is unavailable, an unexpected condition arises - the engine blocks the action. It does not guess, it does not fall back to a permissive default, and it does not ask a human to decide in the moment.

Fail-closed is the only safe default for a governance engine. The alternative - fail-open, where ambiguity results in allowing the action - creates exactly the kind of governance gaps that the platform is designed to prevent.

Policy structure

Every policy in Governax is a structured object with these components:

  • Conditions - A set of predicates that determine whether the policy applies to a given action. Conditions can reference action type, monetary value, department, geography, and any custom attribute.
  • Priority - An integer that determines evaluation order. Higher-priority policies are evaluated first. This allows organisations to layer general policies with specific overrides.
  • Scope - The organisational boundary within which the policy applies. Scopes can be global, departmental, regional, or team-level. Narrower scopes override broader ones when priorities are equal.
  • Effect - The outcome if the policy matches: ALLOW, DENY, or HARD_DENY.
  • HARD_DENY: the short-circuit

    HARD_DENY is a special effect that short-circuits the entire evaluation pipeline. When a policy with HARD_DENY matches, no further policies are evaluated. The action is blocked immediately, regardless of what other policies might say.

    Why is this necessary? Consider a scenario where an employee attempts to approve their own expense report. A general policy might allow expense approvals under a certain threshold. But a separation-of-duties policy with HARD_DENY blocks self-approval absolutely. Without short-circuit semantics, the general policy could theoretically override the separation-of-duties check - a critical governance failure.

    Priority-based resolution

    When multiple policies match a given action, the engine resolves them by priority. The highest-priority matching policy determines the outcome. If two policies share the same priority, scope is used as a tiebreaker - narrower scope wins.

    This resolution strategy is deterministic. Given the same set of policies and the same action context, the engine will always produce the same result. There is no randomness, no heuristic weighting, and no machine learning involved in the decision.

    Evaluation pipeline

    The full evaluation pipeline runs in this order:

  • Action classification - The incoming action is classified by type (financial, HR, IT, legal, etc.) and its attributes are extracted.
  • Policy retrieval - All policies that could potentially apply are retrieved, filtered by scope and action type.
  • Condition evaluation - Each retrieved policy's conditions are evaluated against the action's attributes.
  • Priority resolution - Matching policies are sorted by priority. HARD_DENY policies are checked first.
  • Outcome determination - The highest-priority matching policy's effect becomes the action's governance outcome.
  • Outcome recording - The result, including which policies were evaluated and which matched, is written to the decision ledger.
  • The entire pipeline executes synchronously. There are no callbacks, no deferred evaluations, and no eventual consistency. When the pipeline returns, the outcome is final.

    Why determinism matters

    A non-deterministic governance engine is worse than no governance engine at all. If the same action can produce different outcomes depending on timing, load, or hidden state, the organisation cannot predict or explain its own governance behaviour. This makes compliance impossible and erodes trust in the system.

    Every architectural decision in the Governax policy engine is oriented toward one goal: given the same inputs, produce the same output, every time, with no exceptions.