STAR
Cal STAR — firmware, DAQ server, and engine design
Loading...
Searching...
No Matches
flight_cases.py
Go to the documentation of this file.
1"""Shared inputs for the flight tests: the shipped 6.5 kN vehicle and its thrust curve.
2
3The curve is the one the config header states for the flat dome-regulated burn through the
4time-varying solver: thrust 6500.0 -> 6601.9 N and mdot 2.7976 -> 2.8550 kg/s, linear over
53.8978 s, split at the delivered O/F 1.5013. Using the header numbers keeps these tests off the
6engine solver, which is not what they check.
7"""
8
9from __future__ import annotations
10
11import contextlib
12import copy
13import io
14import math
15from pathlib import Path
16
17import numpy as np
18
19CONFIG = Path(__file__).resolve().parents[1] / "configs" / "ethalox_6500N.yaml"
20BURN_S = 3.8978
21OF = 1.5013
22
23
24def header_curve(n: int = 200):
25 t = np.linspace(0.0, BURN_S, n)
26 F = 6500.0 + (6601.9 - 6500.0) * t / BURN_S
27 md = 2.7976 + (2.8550 - 2.7976) * t / BURN_S
28 return t, F, md * OF / (1 + OF), md / (1 + OF)
29
30
31def shipped():
32 from engine.pipeline.io import load_config
33
34 return load_config(str(CONFIG))
35
36
38 t, F, mO, mF = header_curve()
39 return float(np.trapezoid(F, t)), float(np.trapezoid(mO, t)), float(np.trapezoid(mF, t))
40
41
42def roomy_tanks(cfg, load_factor: float = 1.001, fill: float = 0.8):
43 """Tanks sized so the curve's own propellant fills them to `fill`: no cap can bite."""
44 _, IO, IF = curve_integrals()
45 cfg.design_requirements.lox_tank_capacity_kg = None
46 cfg.design_requirements.fuel_tank_capacity_kg = None
47 for sec, h, r, m, rho in (
48 (cfg.lox_tank, "lox_h", "lox_radius", IO, cfg.fluids["oxidizer"].density),
49 (cfg.fuel_tank, "rp1_h", "rp1_radius", IF, cfg.fluids["fuel"].density),
50 ):
51 V = m * load_factor / rho / fill
52 sec.tank_volume_m3 = V
53 setattr(sec, h, V / (math.pi * getattr(sec, r) ** 2))
54 return cfg
55
56
57def fly(cfg, curve=None):
58 """ui.flight_sim.setup_flight on the curve, quietly."""
59 from scipy.interpolate import interp1d
60 from ui.flight_sim import setup_flight
61
62 t, F, mO, mF = curve or header_curve()
63 cfg = copy.deepcopy(cfg)
64 cfg.thrust.burn_time = float(t[-1])
65 f = lambda y: interp1d(t, y, bounds_error=False, fill_value=0.0) # noqa: E731
66 with contextlib.redirect_stdout(io.StringIO()):
67 return setup_flight(cfg, f(F), f(mO), f(mF))
68
69
70def fly_helpers(cfg, curve=None):
71 """The Flight tab's path: engine.optimizer.copv_flight_helpers.run_flight_simulation."""
72 from engine.optimizer.copv_flight_helpers import run_flight_simulation
73
74 t, F, mO, mF = curve or header_curve()
75 with contextlib.redirect_stdout(io.StringIO()):
76 return run_flight_simulation(copy.deepcopy(cfg), {"time": t, "thrust": F, "mdot_O": mO, "mdot_F": mF}, float(t[-1]))
header_curve(int n=200)
fly_helpers(cfg, curve=None)
fly(cfg, curve=None)
roomy_tanks(cfg, float load_factor=1.001, float fill=0.8)