fix(understand): a network layer holds lines — valve, pump and annotation layers are no pipes

The field test ran the takeoffs on a real P&ID pair, kept outside the
repository. It showed that the default network layers took every layer the
vocabulary files under piping or electrical. That included the valve layers
(KLEPPEN, Valve_*), the pump layers (a "product pumps" layer reads as
product), and annotation layers such as pipe sizes, materials and valve
numbers. Symbol outlines and leader lines became pipe runs.

vocab.is_network_layer is now the one rule. A layer is a network layer when
it is piping or electrical at 0.9, its name names no equipment
(equipment_kind: valve, pump, tank, motor, panel, reducer), and it names no
annotation (sizes, materials, numbers, hatching, or an annotation word).
build_network's default layers, drawing_topology_check and the topo_*
focuses all use it, so they agree on which lines are the network.

Sixteen parametrized cases pin it, across symbol, annotation, pipe and cable
layers.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01FKFStjEFzpGyLq5bMpWxTd
This commit is contained in:
Umut CAN
2026-09-24 15:57:17 +03:00
co-authored by Claude Opus 5.5
parent ba41428c88
commit 307ccc799f
5 changed files with 79 additions and 22 deletions
+2 -2
View File
@@ -53,7 +53,7 @@ from collections.abc import Iterable
from dataclasses import dataclass
from engineering.understand.snapshot import EntityRecord, Pt, Snapshot
from engineering.understand.vocab import classify_layer
from engineering.understand.vocab import classify_layer, is_network_layer
__all__ = [
"DEFAULT_TOL",
@@ -219,7 +219,7 @@ def network_layers(snap: Snapshot) -> list[dict]:
for name in sorted(names):
meaning = classify_layer(name)
confidence = float(meaning.get("confidence") or 0.0)
if meaning.get("discipline") in NETWORK_DISCIPLINES and confidence >= NETWORK_CONFIDENCE:
if is_network_layer(name):
rows.append(
{
"layer": name,