# To do

Open work and deliberately unsupported behavior. [decisions.md](decisions.md) records the effective design choices. Current type-system and compiler priorities are in the [FEEL assessments](https://github.com/FeeJai/BDM/blob/main/apps/feel/README.md#documentation-and-deep-dives); the items here concern the DMN layer.

## The TCK nodes that fail

The authoritative node lists are [known failures](https://github.com/FeeJai/BDM/blob/main/apps/bdm_tck/test/fixtures/tck/dmn_known_failures.txt), [flag mismatches](https://github.com/FeeJai/BDM/blob/main/apps/bdm_tck/test/fixtures/tck/dmn_flag_mismatches.txt), and the [baseline](https://github.com/FeeJai/BDM/blob/main/apps/bdm_tck/test/fixtures/tck/dmn_baseline.txt). Run `mix run scripts/dmn_tck.exs` in `apps/bdm_tck` for fresh counts. The remaining categories include:

- [ ] **External functions** (0076, 14 nodes). They fail by default and pass with the opt-in `DmnJava.Extension` (DD-37; all 14 pass, `literal_001` only through a comparator tolerance for a TCK value truncated to 8 decimals). Not done: instance methods and constructors, the kinds `PMML` and `ONNX`, a precompiled class instead of the source that is compiled at start, parallel calls per sidecar, and FEEL extensions when parsing a literal expression (such as a function whose name has several words).
- [ ] **Research 0076 `literal_001` and flag it upstream.** The TCK expects `Math.cos(123)` as `-0.88796890`, the value truncated to 8 decimals (not rounded, which would give `-0.88796891`), and `Value.same?/3` accepts a truncated result under `doubles: true` to get around it. DMN 1.6 gives no rule for it: Table 47 maps `number` to `BigDecimal` only, §10.3.2.13.3 says results are converted "when possible", and A4-27 of the spec notes calls the precision of a Java double implementation-defined. To do: see how the other TCK runners compare it (a tolerance, or a failure), then open an issue on dmn-tck/tck asking for the full double or a stated tolerance; drop the truncation tolerance if the TCK changes.

## Resource limits and API boundaries

The completed loader and guard repairs are recorded in DD-23, and the error values for the entry points and their options in DD-36 and DD-39. Remaining work:

- [ ] **Reduce preparation and evaluation costs within the existing containment policy.** Loading, compilation and complete evaluations already use shared workers by default (DD-15): five seconds, 128 MiB heap and bounded transfers. FEEL's per-unit limits still apply; there is no general step quota. The preflight clock, the walk over every selected expression and the source maps of data-only extensions are done (DD-44); a contained TCK call costs about 60 µs more than a trusted one on the interpreter (128 µs against 68 µs) and about 40 µs more on the BEAM backend (106 µs against 69 µs). What is left is measured in `apps/tck_eval` and `bench_payload.exs`: copying the dependency view and checking its size (about 3 µs per KB), spawning a process for each call, and copying the compiled model back out of the worker on load (15–30 % of a load). Neither keeping the model where the worker can read it without copying (`:persistent_term` or ETS) nor a reusable worker has been tried; both change how calls are isolated from each other and need a design of their own. Profile repeated type environments and required large inputs before adding another limit or planning layer. Applications still own concurrency and artifact retention.
- [ ] **Decide whether `Dmn.compile(model, backend: :beam)` should require `sandbox: false`.** FEEL's APIs refuse the BEAM backend in a worker because the modules and atoms it makes outlive the worker (FEEL D-221); DMN's compiler asks for the backend itself inside its own worker, so DD-41 is accepted there. Either the DMN option stays the caller's trust decision (as now documented), or it adopts FEEL's rule, and the TCK harness's `ours-beam` row would then pass `sandbox: false` for the compile.
- [ ] **The types of each model include the item definitions of every model it reaches.** A set of 64 models that import one another has 64 sets of types, each with the definitions of all the others, so memory grows with the number of models times the item definitions of the graph (`max_import_bytes` bounds the second factor, not the product).
- [ ] **Every element holds a copy of its namespace URI** (DD-35). `max_uri_length` bounds the size of a copy, so the worst case is `max_elements` copies. Sharing one binary among the elements of a declaration would make the URI cost only once, at the price of looking up the prefix in scope for each element; this is unnecessary while the limit holds.

## Validation and imports

- [ ] **Preserve resolved scope in additional table proofs** (DD-43). Scope-dependent entries currently remain unknown rather than acquiring different builtin meanings when reparsed. Recover precision only through an interface that retains model/local bindings and extension semantics; keep wildcard/inputValues handling aligned with prepared IR. Universal revalidation of reported witnesses against original entries and input domains is also open work.

## What recursion leaves (DD-22)

- [ ] **More precise recursive analysis and relations.** Guarded recursive data declarations now retain finite graphs and check all finite descendants and component constraints at runtime. Static analysis uses a finite structural upper bound and keeps checks whose recursive target is not proved. Complete recursive subtyping/equivalence remains open; graph-projected functions and complete-callee paths can retain broad recursive call bounds. Alias-only cycles and cycles through function signatures are intentional compile errors, not incomplete descendant validation. Extend the independent finite-tree oracle pool to generated mutual graphs and larger declaration families before broadening proof rules. FEEL's explicit legacy `recursive: :any` remains an approximate opt-in; DMN's recursion feature uses guarded validation instead (DD-22).

## What the engine does not do yet

- [ ] **A persisted `Dmn.Compiled` format.** `Dmn.compile/2` prepares for the interpreter, or for the BEAM backend when the caller chooses `backend: :beam` (DD-41), and returns an ordinary in-memory artifact, not a supported serialization format; a BEAM-compiled model also refers to modules loaded in this VM only. Cross-release persistence needs an explicit representation and invalidation contract; regenerate models on upgrade.
- [ ] **Expression languages other than FEEL** (`https://www.omg.org/spec/DMN/uninterpreted/20140801`, PMML, XPath) are a diagnostic.
- [ ] **A decision service that uses decisions of another model.** A service is made up only of decisions from its own model.
- [ ] **Parse multi-word FEEL extension names in literal expressions.** DMN extensions already provide `feel_extensions/0`, and the compiler forwards those to FEEL preparation (DD-37). Fragment parsing does not receive them yet, so an added multi-word function name is not grouped as one name there. Keep extension selection under host control.

## Compatibility and maintenance

- [ ] **Automatic selection of legacy type aliases.** DD-28 implements the three DMN 1.1 temporal names through `features: [:dmn_1_1_types]`. Decide whether a model's namespace should select that extension automatically; keep caller-selected behavior explicit.

Intentional boundaries are not pending features: cycles through decisions remain errors, input conversion occurs where a value is read (DD-13), and descriptive/diagram elements do not affect evaluation.
