vibe coding an orbital mechanics simulation to try out claude code
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 

7.9 KiB

Test Plan: Invalid Parent Assignment Bug

Overview

Comprehensive test suite to capture and validate parent-child relationship bugs in orbital mechanics simulation.

Date: January 20, 2026 Status: Complete (Tests 1-3 resolved) Related: docs/mission_planning.md FIXME section


Bug Diagnosis

Root Cause Identified

The Bug (Fixed): In tests/configs/earth_mars_simple.toml, spacecraft had placeholder values:

  • position = {1.496e11, 0, 0} (IDENTICAL to Earth)
  • velocity = {0, 0, 0} (zero velocity)
  • SOI = ~17.3 meters (calculated from mass=1kg)

What Happened:

  1. Config loaded with spacecraft at Earth's exact position
  2. During find_dominant_body(1) for Earth:
    • Checks all bodies
    • Finds spacecraft at distance = 0
    • 0 < 17.3 is TRUE
    • Sets Earth's parent to spacecraft!

Why Test Failed But GUI Failed Worse:

  • Test calls initialize_spacecraft_leo() → spacecraft moved to proper LEO orbit (200km from Earth)
  • GUI never called this → placeholder values caused immediate bug

Solution Implemented

Config Validation in src/config_loader.cpp:

  • Added validation loop after parsing bodies, before initialize_bodies()
  • Validates that distance between body and parent ≥ parent.radius + body.radius
  • Provides clear error message with actual and required distances
  • Prevents loading invalid configs with bodies too close to their parents

Config Fix in tests/configs/earth_mars_simple.toml:

  • Changed spacecraft position from 1.496e11 (same as Earth) to 1.49606571e11
  • This places spacecraft at proper LEO altitude: Earth position + 6,571,000 m
  • 6,571 km = Earth radius (6,371 km) + 200 km altitude

Test Cases

Test Case 1: Earth→Spacecraft Parent Switch

Purpose: Directly detect when Earth's parent becomes spacecraft (the exact bug from FIXME)

Actual Result: PASSES

How It Was Fixed:

  • Config validation now rejects bodies starting at parent's position
  • Spacecraft properly positioned at LEO altitude (6,571 km from Earth center)
  • find_dominant_body() never finds spacecraft at distance=0
  • Earth's parent remains Sun throughout simulation

Config: tests/configs/earth_mars_simple.toml

Key Assertion:

REQUIRE(sim->bodies[EARTH_IDX].parent_index != SPACECRAFT_IDX);

Test Case 2: Mass Hierarchy Validation

Purpose: Validate that massive bodies never become children of small bodies

Actual Result: PASSES

How It Was Fixed:

  • Config validation ensures proper parent-child distance
  • Mass hierarchy preserved throughout simulation
  • Earth never becomes child of spacecraft or other bodies

Config: tests/configs/earth_mars_simple.toml

Key Assertions:

// Parent must be more massive
REQUIRE(mass_ratio >= 1.0);

// For planets: parent should be significantly more massive
if (not spacecraft) {
    REQUIRE(mass_ratio >= 1000.0);
}

// Massive bodies should never have small bodies as parents
if (child_mass > 1e20) { // Planet-scale
    REQUIRE(parent_mass > child_mass);
}

Test Case 3: Config Placeholder Validation

Purpose: Detect invalid config initialization (bodies starting too close together)

Actual Result: PASSES

How It Was Fixed:

  • Test updated to use radius-based validation (matches config_loader logic)
  • Spacecraft now at proper LEO position: 6,571,000 m from Earth center
  • Validation: distance (6,571,000 m) ≥ Earth.radius + spacecraft.radius (6,372,000 m)
  • Config validation catches any bodies positioned within parent's radius

Config: tests/configs/earth_mars_simple.toml

Key Assertion:

double min_distance = sim->bodies[EARTH_IDX].radius + sim->bodies[SPACECRAFT_IDX].radius;
REQUIRE(distance >= min_distance); // parent.radius + body.radius

Test Case 4: Mutual SOI - Similar Mass Planets

Purpose: Edge case: two Earth-like planets positioned within each other's SOI

Actual Result: STILL FAILS (separate issue, not fixed by spacecraft validation)

Config: tests/configs/mutual_soi_close.toml

Setup:

  • PlanetA: mass = 5.972e24 kg, position = {1.496e11, 0, 0}
  • PlanetB: mass = 5.972e24 kg, position = {1.501e11, 0, 0}
  • Separation: 5e8 meters (500 million km)
  • Planet SOI: ~9.25e8 meters (925 million km)
  • Both planets within each other's SOI

Why This Fails:

  • Both planets start with parent=0 (Sun)
  • Both are within each other's SOI
  • find_dominant_body() logic selects closest body within SOI
  • Result: PlanetA selects PlanetB as parent, PlanetB selects PlanetA as parent
  • Config validation passes (both are ≥ parent.radius + body.radius from Sun)

Key Assertions:

// Both should orbit Sun (not each other)
REQUIRE(sim->bodies[PLANET_A_IDX].parent_index == SUN_IDX);
REQUIRE(sim->bodies[PLANET_B_IDX].parent_index == SUN_IDX);

// Planets should never have each other as parents
for (int parent : history.planet_a_parents) {
    REQUIRE(parent != PLANET_B_IDX);
}
for (int parent : history.planet_b_parents) {
    REQUIRE(parent != PLANET_A_IDX);
}

Expected Behavior (Option A):

  • Both planets should continue orbiting Sun
  • Neither should become other's parent
  • This requires future fix to find_dominant_body() logic (mass hierarchy check)

Test Matrix

Test Case Config Tests Expected (Before Fix) Actual Result
1. Earth→Spacecraft earth_mars_simple.toml Parent assignment FAIL PASS
2. Mass Hierarchy earth_mars_simple.toml Mass ratios FAIL PASS
3. Config Validation earth_mars_simple.toml Separation distance FAIL PASS
4. Mutual SOI mutual_soi_close.toml Edge case behavior FAIL FAIL (separate issue)

Implementation

Test File

tests/test_invalid_parent_assignment.cpp

Test Config Files

  • tests/configs/earth_mars_simple.toml (existing)
  • tests/configs/mutual_soi_close.toml (new)

Build Integration

Add to CMakeLists.txt or Makefile test targets


Implementation Summary

Solution Applied (Jan 20, 2026):

  1. Config validation in src/config_loader.cpp:

    • Validates parent-child distances before initialization
    • Requires distance ≥ parent.radius + body.radius
    • Prevents loading invalid configs
  2. Config fix in tests/configs/earth_mars_simple.toml:

    • Spacecraft position corrected to proper LEO altitude
    • Position: 1.49606571e11 m (Earth position + 6,571,000 m offset)
    • Velocity calculated by initialize_bodies() using semi_major_axis = 6.571e6
  3. Test updates in tests/test_invalid_parent_assignment.cpp:

    • Test 3 updated to use radius-based validation
    • Matches config_loader validation logic

Future Work

Current Status

Tests 1-3 are now passing. Test 4 continues to fail, documenting a separate mutual SOI issue.

Potential Fixes for Test 4

  1. Add mass hierarchy check to find_dominant_body()
  2. Prevent mutual SOI assignments for similar-mass bodies
  3. Detect and reject invalid configs at load time
  4. Implement proper N-body interaction or restricted 3-body solution

Enhanced Detection

  • SOI overlap detection at config load time
  • Automatic correction of invalid parent assignments
  • Validation warnings for edge cases

References

  • docs/mission_planning.md:125-135 - FIXME section describing bug (now resolved)
  • src/config_loader.cpp:138-157 - Config validation implementation
  • tests/configs/earth_mars_simple.toml - Corrected spacecraft position (LEO altitude)
  • src/simulation.cpp:64-107 - find_dominant_body() implementation
  • src/simulation.cpp:212-233 - initialize_bodies() implementation
  • tests/test_invalid_parent_assignment.cpp - Test suite implementation

Commits

  • 0239cc1 - Add test suite for invalid parent assignment bugs
  • 899fa3b - Add config validation for parent-child distances