Before you write a big simulator, you should be able to answer: - What mission are we building? - What constraints matter most? - What is our delta-v ((v)) budget and mass budget? - What are the biggest risks / unknowns?
What you’ll build here
A simple mission requirements sheet (as a Python dict + table)
A first-pass delta-v ((v)) budget (order-of-magnitude, not perfect)
A first-pass mass model using the rocket equation
A small trade table: how assumptions change feasibility
Important note
This is an educational template. Real mission design is more detailed — but the structure is real.
Code
import numpy as npimport pandas as pdimport matplotlib.pyplot as pltfrom IPython.display import displayplt.style.use("dark_background")G0 =9.80665# m/s^2print("Environment ready. Let's plan a mission like an engineer.")
Environment ready. Let's plan a mission like an engineer.
1) Pick a mission (multi‑agency examples)
A capstone should be ambitious, but it must be bounded.
Here are a few example mission types (you can rename these to match NASA/ESA/JAXA/CNSA/ISRO/Roscosmos programs you’re studying): - LEO satellite mission (comms, navigation, Earth observation) - GEO communications satellite (large energy, long operations) - Lunar mission (orbiter, lander, crewed gateway support) - Mars transfer mission (cargo or crewed transfer)
We’ll store a “mission requirements sheet” as structured data.
Code
MISSION_LIBRARY = {"LEO Earth observation satellite": {"agency_context": "Examples: NASA Landsat, ESA Sentinel, ISRO Cartosat (varies by mission).","crewed": False,"payload_kg": 1200,"target": "Sun-synchronous-ish LEO (simplified)","delta_v_budget_m_s": {"launch_to_leo": 9400,"orbit_raise_and_phasing": 150,"stationkeeping_lifetime": 200,"deorbit_disposal": 150, },"max_g": 6.0,"notes": "LEO is crowded: debris mitigation and disposal matter.", },"GEO communications satellite": {"agency_context": "Examples: commercial + national GEO operators; ESA/NASA launches are common.","crewed": False,"payload_kg": 6000,"target": "GEO (simplified)","delta_v_budget_m_s": {"launch_to_leo_equivalent": 9400,"transfer_to_geo": 4300,"stationkeeping_lifetime": 1500,"graveyard_orbit": 20, },"max_g": 6.0,"notes": "Large energy requirement. Often uses an upper stage or onboard electric propulsion.", },"Lunar cargo lander": {"agency_context": "Examples: NASA CLPS, JAXA SLIM, CNSA Chang'e landers (varies by mission).","crewed": False,"payload_kg": 3000,"target": "Lunar surface (simplified)","delta_v_budget_m_s": {"launch_to_leo": 9400,"trans_lunar_injection": 3200,"lunar_orbit_insertion": 900,"descent_and_landing": 1900, },"max_g": 8.0,"notes": "No atmosphere: landing is propulsive. Precision + guidance matter.", },"Mars cargo transfer": {"agency_context": "Examples: NASA/ESA robotic Mars missions; future cargo/crewed concepts.","crewed": False,"payload_kg": 20000,"target": "Mars transfer + surface arrival (simplified)","delta_v_budget_m_s": {"launch_to_leo": 9400,"trans_mars_injection": 3600,"midcourse_corrections": 50,"entry_descent_landing": 1500, },"max_g": 5.0,"notes": "Mars has an atmosphere, so some energy can be removed aerodynamically.", },}mission_name ="Lunar cargo lander"# try changing thismission = MISSION_LIBRARY[mission_name]# Flatten to a quick table for readabilitybudget_rows = [(k, v) for k, v in mission["delta_v_budget_m_s"].items()]df_req = pd.DataFrame( {"field": ["agency_context", "target", "crewed", "payload_kg", "max_g", "notes"],"value": [ mission["agency_context"], mission["target"], mission["crewed"], mission["payload_kg"], mission["max_g"], mission["notes"], ], })df_dv = pd.DataFrame(budget_rows, columns=["phase", "delta_v_m_s"])print("Mission:", mission_name)display(df_req)display(df_dv)
Mission: Lunar cargo lander
field
value
0
agency_context
Examples: NASA CLPS, JAXA SLIM, CNSA Chang'e l...
1
target
Lunar surface (simplified)
2
crewed
False
3
payload_kg
3000
4
max_g
8.0
5
notes
No atmosphere: landing is propulsive. Precisio...
phase
delta_v_m_s
0
launch_to_leo
9400
1
trans_lunar_injection
3200
2
lunar_orbit_insertion
900
3
descent_and_landing
1900
2) Build a delta-v budget (and identify the biggest terms)
A delta-v budget is just a list of velocity changes you expect to need.
Key idea: - If you forget a major term, your design will look “fine”… until it fails.
We’ll sum the phases and plot which parts dominate.
Code
dv = df_dv.copy()dv["delta_v_km_s"] = dv["delta_v_m_s"] /1000total_dv =float(dv["delta_v_m_s"].sum())print(f"Total delta-v budget: {total_dv/1000:.2f} km/s")fig, ax = plt.subplots(figsize=(10.5, 4.2))ax.barh(dv["phase"], dv["delta_v_km_s"], color="#00d4ff", alpha=0.85)ax.set_title(f"Delta-v budget by phase — {mission_name}\nTotal: {total_dv/1000:.2f} km/s")ax.set_xlabel("delta-v (km/s)")ax.grid(True, axis="x", alpha=0.25)# Show labels at bar endsfor i, row in dv.iterrows(): ax.text(row["delta_v_km_s"] +0.05, i, f"{row['delta_v_km_s']:.2f}", va="center")plt.tight_layout()plt.show()
Total delta-v budget: 15.40 km/s
3) Convert delta-v into a mass ratio (rocket equation)
The Tsiolkovsky rocket equation connects mission difficulty (delta-v) to how much propellant you need:
[v = I_{sp} g_0 ()]
Where: - (I_{sp}): specific impulse (seconds) - (g_0): standard gravity (9.80665 m/s²) - (m_0): initial mass (dry + payload + propellant) - (m_f): final mass (dry + payload)
We’ll use this for a first-pass estimate. Real vehicles use staging, engine throttling, gravity losses, and many other details.