Skip to content
PYD ENTERPRISES

Enterprise guide · DMN 1.5

Decision tables for people who inherit COBOL.

Decision Model and Notation turns procedural rules into tables business owners can read and engines can execute. This guide covers the parts that matter when the rules come out of legacy code.

DECISION REQUIREMENTS DIAGRAM · AUTO RATING

PremiumDriver age factorTerritory factorDriver ageGood studentZIP code
DecisionInput dataInformation requirement

The standard

Three layers, one model.

DMN is an Object Management Group standard for describing business decisions so that people can review them and engines can execute them. Version 1.5 is the current release. It has three layers, and extracted legacy rules use all three.

Decision requirements diagrams (DRDs) show the structure: which decisions depend on which input data and on which other decisions. A rating engine is a DRD with a premium decision at the top, factor decisions below it, and policy and driver data at the bottom. Business knowledge models package reusable logic, and knowledge sources record the authority behind a decision, such as a rate filing or a regulation.

Decision tables are the workhorse. Each row is a rule: input entries on the left, output entries on the right, and a hit policy that says what happens when more than one row matches. Nested IF statements and EVALUATE blocks map naturally onto them.

FEEL, the Friendly Enough Expression Language, fills the cells and the formula decisions. It has ranges, lists, contexts, date arithmetic and a deliberately simple null semantics: most operations on a missing value return null rather than failing, which is convenient for authors and dangerous for extracted rules that relied on a default.

For legacy work, the value of DMN is not the notation. It is that a rule extracted from a 1988 program becomes an artifact with a defined meaning, testable in an engine and readable by the people who own the policy.

Hit policies

Seven ways to resolve overlapping rules.

The hit policy is the single most important property of an extracted table. Choose it to match the legacy semantics first and readability second.

CodePolicyTypeSemanticsFor extracted legacy rules
UUniqueSingle hitRules must not overlap. At most one rule matches any input; overlapping matches make the result invalid.Preferred target for extracted rules once disjointness is proven. Each row reads on its own.
AAnySingle hitRules may overlap, but every matching rule must produce the same output. Differing outputs are an error.Useful when several legacy branches converge on the same value, such as several waivers that all set the fee to zero.
PPrioritySingle hitRules may overlap with different outputs. The output listed first in the output column's ordered values wins.Fits severity or tiering logic where the most restrictive outcome wins. Requires an explicit ordered list of output values.
FFirstSingle hitRules are evaluated in order and the first match wins.Faithful to COBOL EVALUATE and IF ... ELSE IF chains when the order cannot be removed. Reviewers must read rows in sequence.
CCollectMultiple hitAll matching outputs, in no guaranteed order. Optional aggregators: + sum, < min, > max, # count.Additive surcharges and discounts, or lists of applicable edits and reason codes.
RRule orderMultiple hitAll matching outputs as a list in rule order.When downstream code consumes results in the sequence the legacy program produced them.
OOutput orderMultiple hitAll matching outputs as a list sorted by the output column's priority order.Ranked results, such as every applicable reason code ordered by severity.

Interactive

Same table, eleven answers.

One discount table, evaluated live under every hit policy and Collect aggregator. Pick Gold with an order of $1,200 and watch Unique fail while First, Priority and Collect each return something different.

Customer tier

Decision: Order discount · hit policy U

4 of 5 match
#TierOrder amountDiscount
R1"Gold">= 100015%
R2"Gold"-10%
R3->= 10005%
R4"Silver"-5%
R5--0%

Output values in priority order: 15%, 10%, 5%, 0%. Inputs: tier as string, amount as number.

UNIQUE · RESULT

invalid

4 rules matched (R1, R2, R3, R5). A Unique table must not overlap.

No overlap allowed: at most one rule may match any input. If several match, the table is invalid for that input.

FEEL basics

Enough FEEL to review an extracted table.

Input cells hold unary tests: a comparison, a range, a list of values, a negated list or a dash for any value. Ranges use square brackets for inclusive and round brackets for exclusive bounds, so [21..25) means 21 up to but not including 25.

Formula decisions use literal expressions. FEEL numbers are decimal, not binary floating point, which is why extracted money arithmetic can be expressed exactly. Rounding is explicit: round half up(x, 2) matches COBOL ROUNDED, while decimal(x, 2) rounds half to even.

Watch not(...). A legacy ELSE catches every value, including invalid codes. not("B", "P") preserves that; listing the declared 88-level values instead silently narrows the rule.

FEEL in decision tables and literal expressionsText
1// Unary tests: what goes in an input cell
2< 21 // less than 21
3[21..25) // 21 inclusive to 25 exclusive
4"B", "P" // either value
5not("B", "P") // any other value, including codes nobody declared
6- // irrelevant: matches anything
7null // input is missing
8
9// Literal expressions: decisions that are formulas
10round half up(basePremium * territoryFactor, 2)
11if goodStudent then 0.90 else 1.00
12date("2026-01-01") <= policy.effectiveDate
13sum(for c in claims return c.paidAmount)

From procedure to table

How nested IFs become rows.

Each path through the decision becomes a row whose input entries are that path's conditions. The interesting rows are the ones nobody expected.

CLMPRC07.cbl · 2400-COPAYCOBOL
1 2400-COPAY.
2 IF PLAN-HMO
3 IF SVC-EMERGENCY AND NOT CLM-ADMITTED
4 MOVE 250.00 TO WS-COPAY
5 ELSE
6 IF SVC-SPECIALIST
7 MOVE 40.00 TO WS-COPAY
8 ELSE
9 MOVE 20.00 TO WS-COPAY
10 END-IF
11 END-IF
12 ELSE
13 MOVE ZERO TO WS-COPAY
14 END-IF.

Decision: Copay · hit policy UNIQUE

5 rules
#PlanServiceAdmittedCopay
R1"HMO""ER"false250.00
R2review"HMO""ER"true20.00
R3"HMO""SPEC"-40.00
R4"HMO"not("ER","SPEC")-20.00
R5not("HMO")--0.00

R2: an emergency visit that leads to admission falls into the inner ELSE and is charged the 20.00 office copay. The path is real; whether it is policy is a question for the plan owner.

  1. 01

    Enumerate paths

    Walk the control-flow graph of the paragraph from entry to every assignment of the output field.

  2. 02

    Collect conditions

    Each path's branch predicates, resolved through 88-levels, become the input entries for one row.

  3. 03

    Pick the hit policy

    Disjoint paths give a Unique table naturally. Order-dependent EVALUATE logic stays First until proven.

  4. 04

    Attach the source

    Every row keeps the file and line range of its path, so reviewers can check it against the code.

Validation

Before a table reaches production.

Five checks, in order. PYD ENTERPRISES runs the first two on export; the rest belong in your delivery pipeline.

  1. 1Validate against the DMN 1.5 schemaCheck the exported XML against the OMG DMN 1.5 XSD before anything else. Schema errors usually mean a typeRef or namespace mismatch, and every engine will reject them.
  2. 2Analyze the table for gaps and overlapsRun static decision table analysis. Drools ships a DMN validator that reports gaps and overlapping rules, and modeling tools flag structural problems. A Unique table with an overlap is a defect; a gap means some input returns null.
  3. 3Deploy into the target engineImport into the engine your services will call, such as Camunda or Drools, and confirm every hit policy you used is supported there. Not every engine implements Priority and Output order.
  4. 4Run the equivalence fixtures through the engineEvaluate the generated fixtures through the engine's own API (Camunda's decision evaluation REST endpoint, or the KIE DMN runtime in Drools) and compare results to the legacy program's outputs at the legacy field's scale.
  5. 5Sign off rule by ruleBusiness owners approve each row beside its source lines. Rewrites the extractor made, such as converting First to Unique, are listed with their justification and approved explicitly.

Common extraction pitfalls

Seven ways a correct-looking table is wrong.

  • 01Dropping order dependenceAn EVALUATE converted to a Unique table without proving the WHEN conditions are disjoint changes behavior wherever they overlap. Keep First, or prove and rewrite.
  • 02Losing the default rowWHEN OTHER and the final ELSE are rules. Leaving them out turns a defined result into null, and null propagates silently through FEEL arithmetic.
  • 03Ignoring the data divisionRange boundaries depend on the PICTURE clause. [25..69] is complete for PIC 9(03) and leaves a gap for PIC 9(03)V9.
  • 04Changing roundingCOBOL ROUNDED rounds half away from zero. FEEL decimal() rounds half to even. Use round half up() and round where the COBOL rounds, not once at the end.
  • 05Hard-coding table-driven valuesFactors read from VSAM or DB2 tables belong in a data source with effective dates, not frozen into output cells on the day of extraction.
  • 06Mixing plumbing into decisionsAbend paths, return codes for I/O errors and logging are not business outputs. Keep them out of decision tables and document them as interface behavior.
  • 07Comparing padded stringsPIC X fields carry trailing spaces and EBCDIC collation. Trim and normalize before string tests, and never translate alphanumeric range tests without checking the collating sequence.

FAQ

Questions from architecture reviews.

Which DMN version should we target?

DMN 1.5 is the current OMG release and the one PYD ENTERPRISES exports. It is backward compatible in most practical respects with 1.3 and 1.4 models, and mainstream engines support the decision table and FEEL features covered in this guide. Confirm specific function support, such as the rounding functions added in 1.4, in your engine's documentation.

Should every extracted rule become a decision table?

No. Decisions with discrete conditions and outputs suit tables. Calculations suit literal FEEL expressions or boxed contexts, and orchestration logic (which program runs next) belongs in the service or workflow, not in DMN. PYD ENTERPRISES exports formulas and tables separately for that reason.

Unique or First for extracted COBOL logic?

Start from First, because it matches the COBOL semantics exactly. Convert to Unique only when the extractor or an analyst can prove the conditions are disjoint for every possible input, considering field types. Unique tables are easier for business owners to review and to change safely.

Can actuaries and analysts edit the exported tables directly?

Yes, in any DMN modeler. Changes should go back through the equivalence suite: a modified row produces new expected values, and the old fixtures are kept as superseded so the change is documented as a decision rather than a regression.

Get your decision tables from the code, not from memory.

Run PYD ENTERPRISES on up to 100,000 lines in your VPC and export DMN 1.5 tables with every row linked to its source lines.