Files
Atomizer/projects/hydrotech-beam/studies/01_doe_landscape
Antoine 0e459028fe Fix: FEM part lookup (exclude _i.prt), hole_count unit (Constant not mm), add file logging
- solve_simulation.py: FEM finder now excludes idealized parts, falls back to loading .fem
- solve_simulation.py: hole_count written as [Constant] not [MilliMeter] in .exp
- run_doe.py: dual logging to console + results/doe_run.log
2026-02-11 14:17:43 +00:00
..
2026-02-10 08:00:22 +00:00

Study: 01_doe_landscape — Hydrotech Beam

See ../../README.md for project overview.

Purpose

Map the design space of the Hydrotech sandwich I-beam to identify feasible regions, characterize variable sensitivities, and prepare data for Phase 2 (TPE optimization). This is Phase 1 of the two-phase strategy (DEC-HB-002).

Quick Facts

Item Value
Objective Minimize mass (kg)
Constraints Tip displacement ≤ 10 mm, Von Mises stress ≤ 130 MPa
Design variables 4 (3 continuous + 1 integer)
Algorithm Phase 1: LHS DoE (50 trials + 1 baseline)
Total budget 51 evaluations
Constraint handling Deb's feasibility rules (Optuna constraint interface)
Status Code complete — ready for execution

Design Variables (confirmed via NX binary introspection)

ID NX Expression Range Type Baseline Unit
DV1 beam_half_core_thickness 1040 Continuous 25.162 mm
DV2 beam_face_thickness 1040 Continuous 21.504 mm
DV3 holes_diameter 150450 Continuous 300 mm
DV4 hole_count 515 Integer 10

Usage

Prerequisites

pip install -r requirements.txt

Requires: Python 3.10+, optuna, scipy, numpy, pandas.

Development Run (stub solver)

# From the study directory:
cd projects/hydrotech-beam/studies/01_doe_landscape/

# Run with synthetic results (for pipeline testing):
python run_doe.py --backend stub

# With verbose logging:
python run_doe.py --backend stub -v

# Custom study name:
python run_doe.py --backend stub --study-name my_test_run

Production Run (NXOpen on Windows)

# On dalidou (Windows node with NX):
python run_doe.py --backend nxopen --model-dir "C:/path/to/syncthing/Beam"

Resume Interrupted Study

python run_doe.py --backend stub --resume --study-name hydrotech_beam_doe_phase1

CLI Options

Flag Default Description
--backend stub stub (testing) or nxopen (real NX)
--model-dir Path to NX model files (required for nxopen)
--study-name hydrotech_beam_doe_phase1 Optuna study name
--n-samples 50 Number of LHS sample points
--seed 42 Random seed for reproducibility
--results-dir results/ Output directory
--resume false Resume existing study
-v false Verbose (DEBUG) logging

Files

File Description
run_doe.py Main entry point — orchestrates the DoE study
sampling.py LHS generation with stratified integer sampling
geometric_checks.py Pre-flight geometric feasibility filter
nx_interface.py NX automation module (stub + NXOpen template)
requirements.txt Python dependencies
OPTIMIZATION_STRATEGY.md Full strategy document
results/ Output directory (CSV, JSON, Optuna DB)

Output Files

After a study run, results/ will contain:

File Description
doe_results.csv All trials — DVs, objectives, constraints, status
doe_summary.json Study metadata, statistics, best feasible design
optuna_study.db SQLite database (Optuna persistence, resume support)

Architecture

run_doe.py
  ├── sampling.py          Generate 50 LHS + 1 baseline
  │     └── scipy.stats.qmc.LatinHypercube
  ├── geometric_checks.py  Pre-flight feasibility filter
  │     ├── Hole overlap:  span/(n-1) - d ≥ 30mm
  │     └── Web clearance: 500 - 2·face - d > 0
  ├── nx_interface.py      NX solver (stub or NXOpen)
  │     ├── NXStubSolver   → synthetic results (development)
  │     └── NXOpenSolver   → real NX Nastran SOL 101 (production)
  └── Optuna study
        ├── SQLite storage (resume support)
        ├── Enqueued trials (deterministic LHS)
        └── Deb's feasibility rules (constraint interface)

Pipeline per Trial

Trial N
  │
  ├── 1. Suggest DVs (from enqueued LHS point)
  │
  ├── 2. Geometric pre-check
  │     ├── FAIL → record as infeasible, skip NX
  │     └── PASS ↓
  │
  ├── 3. NX evaluation
  │     ├── Update expressions (exact NX names)
  │     ├── Rebuild model
  │     ├── Solve SOL 101
  │     └── Extract: mass (p173), displacement, stress
  │
  ├── 4. Record results + constraint violations
  │
  └── 5. Log to CSV + Optuna DB

Phase 1 → Phase 2 Gate Criteria

Before proceeding to Phase 2 (TPE optimization), these checks must pass:

Check Threshold Action if FAIL
Feasible points found ≥ 5 Expand bounds or relax constraints (escalate to CEO)
NX solve success rate ≥ 80% Investigate failures, fix model, re-run
No systematic crashes at bounds Visual check Tighten bounds away from failure region

Key Design Decisions

  • Baseline as Trial 0 — LAC lesson: always validate baseline first
  • Pre-flight geometric filter — catches infeasible geometry before NX (saves compute, avoids crashes)
  • Stratified integer sampling — ensures all 11 hole_count levels (5-15) are covered
  • Deb's feasibility rules — no penalty weight tuning; feasible always beats infeasible
  • SQLite persistence — study can be interrupted and resumed
  • No surrogates — LAC lesson: direct FEA via TPE beats surrogate + L-BFGS

NX Integration Notes

The nx_interface.py module provides:

  • NXStubSolver — synthetic results from simplified beam mechanics (for pipeline testing)
  • NXOpenSolver — template for real NXOpen Python API integration (to be completed on Windows)

Expression names are exact from binary introspection. Critical: beam_lenght has a typo in NX (no 'h') — use exact spelling.

Outputs to extract from NX:

Output Source Unit Notes
Mass Expression p173 kg Direct read
Tip displacement SOL 101 results mm TBD: sensor or .op2 parsing
Max VM stress SOL 101 results MPa ⚠️ pyNastran returns kPa — divide by 1000

References


Code: 🏗️ Study Builder (Technical Lead) | Strategy: Optimizer Agent | 2026-02-10