World Simulation¶
Mission simulation tiers — single-sat (Tier 1), multi-sat handover (Tier 2), and network traffic (Tier 3).
Tier 1: Simple World Sim¶
SimpleWorldSim
¶
Tier 1 world simulation: single satellite to terminal time-series.
Evaluates a snapshot link budget at each time step along a pre-computed satellite pass, applying operational policy checks (minimum elevation) and collecting margin, throughput, and outage statistics.
Examples:
>>> sim = SimpleWorldSim()
>>> result = sim.run(link_inputs, trajectory, OpsPolicy(), env)
>>> result.summary["availability"]
0.95
Source code in src/opensatcom/world/sim.py
run
¶
Run the Tier 1 simulation over a satellite pass.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
link_inputs
|
LinkInputs
|
Link configuration (terminals, antennas, propagation, RF chain). |
required |
trajectory
|
PrecomputedTrajectory
|
Pre-computed satellite trajectory with elevation, azimuth, and range arrays. |
required |
ops
|
OpsPolicy
|
Operational constraints (min elevation, max scan angle). |
required |
env
|
StaticEnvironmentProvider
|
Environment provider for propagation conditions at each step. |
required |
doppler_hz
|
ndarray or None
|
Pre-computed Doppler shift time series in Hz. If provided, included in the output. |
None
|
Returns:
| Type | Description |
|---|---|
WorldSimOutputs
|
Time-series results with margin, throughput, outage mask, and scalar summary statistics. |
Source code in src/opensatcom/world/sim.py
34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 | |
Tier 2: Multi-Sat World Sim¶
MultiSatWorldSim
¶
Tier 2 world simulation: multiple satellites with handover.
Evaluates link budget for each satellite at each timestep, applies handover policy to select serving satellite, and produces combined time-series output.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
handover_policy
|
HandoverPolicy | None
|
Handover policy. Defaults to hysteresis-based with values from OpsPolicy. |
None
|
Source code in src/opensatcom/world/multisim.py
run
¶
Run multi-satellite simulation.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
link_inputs
|
LinkInputs
|
Base link inputs (shared antenna, RF chain, scenario). |
required |
trajectories
|
dict[str, PrecomputedTrajectory]
|
Satellite trajectories keyed by satellite ID. |
required |
ops
|
OpsPolicy
|
Operational policy with min elevation and handover hysteresis. |
required |
env
|
StaticEnvironmentProvider
|
Environment conditions provider. |
required |
Returns:
| Type | Description |
|---|---|
MultiSatWorldSimOutputs
|
Combined time-series output including per-satellite contact times and handover events. |
Source code in src/opensatcom/world/multisim.py
69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 | |
MultiSatWorldSimOutputs
dataclass
¶
Outputs from multi-satellite simulation, extends WorldSimOutputs.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
base
|
WorldSimOutputs
|
Base world simulation outputs (time-series margins, throughput, etc.). |
required |
selected_sat_id
|
list[str]
|
Satellite ID selected at each timestep. |
required |
handover_times_s
|
list[float]
|
Simulation times (seconds) at which handovers occurred. |
required |
n_handovers
|
int
|
Total number of handovers during the simulation. |
required |
per_sat_contact_s
|
dict[str, float]
|
Cumulative contact time (seconds) per satellite ID. |
required |
Tier 3: Network World Sim¶
NetworkWorldSim
¶
Tier 3 world simulation: multi-satellite with traffic scheduling.
At each timestep: 1. Evaluate link per satellite (via MultiSatWorldSim) 2. Compute available capacity from link margin + modem 3. Schedule traffic across users based on demand and capacity 4. Record per-user throughput and satisfaction metrics
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
scheduler
|
str
|
Scheduler type: "proportional_fair" (default) or "round_robin". |
'proportional_fair'
|
Source code in src/opensatcom/world/network_sim.py
run
¶
Run network simulation with traffic scheduling.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
link_inputs
|
LinkInputs
|
Base link inputs (antenna, RF chain, scenario). |
required |
trajectories
|
dict[str, PrecomputedTrajectory]
|
Satellite trajectories keyed by satellite ID. |
required |
ops
|
OpsPolicy
|
Operational policy with min elevation and handover hysteresis. |
required |
env
|
StaticEnvironmentProvider
|
Environment conditions provider. |
required |
traffic_profile
|
TrafficProfile
|
Time-varying traffic demand profile for all users. |
required |
Returns:
| Type | Description |
|---|---|
NetworkSimOutputs
|
Network-level outputs including per-user throughput allocation and satisfaction metrics. |
Source code in src/opensatcom/world/network_sim.py
74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 | |
NetworkSimOutputs
dataclass
¶
Outputs from network-level simulation, extends MultiSatWorldSimOutputs.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
base
|
MultiSatWorldSimOutputs
|
Underlying multi-satellite simulation outputs. |
required |
per_user_throughput_mbps
|
dict[str, ndarray]
|
Allocated throughput (Mbps) time-series per user ID. |
required |
total_capacity_mbps
|
ndarray
|
Total available link capacity (Mbps) at each timestep. |
required |
user_satisfaction
|
dict[str, float]
|
Fraction of total demand served over the simulation, per user ID (0.0 = none served, 1.0 = fully served). |
required |
Providers¶
StaticEnvironmentProvider
¶
Returns fixed propagation conditions for all timesteps.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
conditions
|
PropagationConditions
|
Static conditions returned at every time step. |
required |
Source code in src/opensatcom/world/providers.py
conditions
¶
Return the static propagation conditions.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
t_s
|
float
|
Simulation time in seconds (unused). |
required |
terminal_a
|
Terminal
|
First terminal (unused). |
required |
terminal_b
|
Terminal
|
Second terminal (unused). |
required |
Returns:
| Type | Description |
|---|---|
PropagationConditions
|
The fixed conditions provided at construction. |
Source code in src/opensatcom/world/providers.py
PrecomputedTrajectory
¶
Trajectory provider from pre-computed pass data.
Stores az/el/range arrays directly — no ECEF conversion needed. The states_ecef method returns dummy states (the WorldSim uses the az/el/range directly via get_geometry).
Source code in src/opensatcom/world/providers.py
from_arrays
classmethod
¶
Construct from raw numpy arrays.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
times_s
|
ndarray
|
Time stamps in seconds. |
required |
elev_deg
|
ndarray
|
Elevation angles in degrees. |
required |
az_deg
|
ndarray
|
Azimuth angles in degrees. |
required |
range_m
|
ndarray
|
Slant ranges in metres. |
required |
Returns:
| Type | Description |
|---|---|
PrecomputedTrajectory
|
Trajectory wrapping the provided arrays. |
Source code in src/opensatcom/world/providers.py
states_ecef
¶
Return dummy ECEF states (not used by SimpleWorldSim).
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
t0_s
|
float
|
Start time in seconds. |
required |
t1_s
|
float
|
End time in seconds. |
required |
dt_s
|
float
|
Time step in seconds. |
required |
Returns:
| Type | Description |
|---|---|
list of StateECEF
|
Placeholder states with zero position vectors. |
Source code in src/opensatcom/world/providers.py
get_geometry
¶
Get geometry for a given timestep index.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
idx
|
int
|
Time step index into the pass data arrays. |
required |
Returns:
| Type | Description |
|---|---|
tuple of (float, float, float)
|
|
Source code in src/opensatcom/world/providers.py
PrecomputedPassData
dataclass
¶
Pre-baked pass data: arrays of time, elevation, azimuth, range.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
times_s
|
ndarray
|
Time stamps in seconds, shape |
required |
elev_deg
|
ndarray
|
Elevation angles in degrees, shape |
required |
az_deg
|
ndarray
|
Azimuth angles in degrees, shape |
required |
range_m
|
ndarray
|
Slant ranges in metres, shape |
required |
Handover¶
HandoverPolicy
¶
Hysteresis-based handover policy.
Selects the satellite with the best metric (margin or elevation).
A handover from the current satellite only occurs if a candidate
exceeds the current satellite's metric by hysteresis_db and
the hysteresis timer (hysteresis_s) has elapsed since the last
handover.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
hysteresis_db
|
float
|
Minimum margin advantage (dB) for a candidate to trigger handover. |
3.0
|
hysteresis_s
|
float
|
Minimum time (seconds) between handovers. |
5.0
|
metric
|
str
|
Selection metric: "margin" or "elevation". |
'margin'
|
Source code in src/opensatcom/world/handover.py
reset
¶
Reset handover state for a new simulation run.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
initial_sat_idx
|
int
|
Index of the initially selected satellite (default 0). |
0
|
Returns:
| Type | Description |
|---|---|
None
|
|
Source code in src/opensatcom/world/handover.py
evaluate
¶
Evaluate handover decision at one timestep.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
t_s
|
float
|
Current simulation time in seconds. |
required |
sat_ids
|
list[str]
|
Satellite identifiers. |
required |
metrics
|
list[float]
|
Per-satellite metric values (margin_db or elevation_deg). |
required |
visible
|
list[bool]
|
Per-satellite visibility flags (above min elevation). |
required |
Returns:
| Type | Description |
|---|---|
HandoverDecision
|
|
Source code in src/opensatcom/world/handover.py
HandoverDecision
dataclass
¶
Result of a handover evaluation at one timestep.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
selected_sat_idx
|
int
|
Index of the selected satellite in the candidate list. |
required |
selected_sat_id
|
str
|
Identifier of the selected satellite. |
required |
is_handover
|
bool
|
True if a handover occurred at this timestep. |
required |
margin_db
|
float
|
Link margin (dB) of the selected satellite. |
required |
all_margins_db
|
list[float]
|
Metric values for all candidate satellites at this timestep. |
required |
Schedulers¶
ProportionalFairScheduler
¶
Allocates capacity proportional to demand and channel quality.
Proportional fair: each user gets capacity proportional to their demand weighted by priority, subject to total capacity constraint.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
alpha
|
float
|
Fairness parameter. alpha=1.0 is pure proportional fair. |
1.0
|
Source code in src/opensatcom/world/scheduler.py
allocate
¶
Allocate capacity across users.
Returns dict mapping user_id to allocated Mbps. Total allocation never exceeds capacity_mbps.
Source code in src/opensatcom/world/scheduler.py
RoundRobinScheduler
¶
Simple round-robin scheduler: equal share to each user.
Each user gets capacity / n_users, capped at their demand. Remaining capacity from users whose demand is below their equal share is not redistributed.
allocate
¶
Allocate capacity equally across users.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
users
|
list[TrafficDemand]
|
List of user traffic demands to schedule. |
required |
capacity_mbps
|
float
|
Total available capacity in Mbps. |
required |
Returns:
| Type | Description |
|---|---|
dict[str, float]
|
Mapping of user_id to allocated throughput in Mbps. |
Source code in src/opensatcom/world/scheduler.py
Traffic¶
TrafficDemand
dataclass
¶
Single user traffic demand at a point in time.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
user_id
|
str
|
Unique identifier for the user. |
required |
demand_mbps
|
float
|
Requested throughput in Mbps. |
required |
priority
|
int
|
Scheduling priority (higher values = higher priority, default 0). |
0
|
lat_deg
|
float
|
User latitude in degrees (default 0.0). |
0.0
|
lon_deg
|
float
|
User longitude in degrees (default 0.0). |
0.0
|
alt_m
|
float
|
User altitude in meters (default 0.0). |
0.0
|
TrafficProfile
¶
Base class for time-varying traffic demand profiles.
demands_at
¶
Return traffic demands at a given simulation time.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
t_s
|
float
|
Simulation time in seconds. |
required |
Returns:
| Type | Description |
|---|---|
list[TrafficDemand]
|
List of per-user traffic demands at time |
Source code in src/opensatcom/world/traffic.py
ConstantTrafficProfile
¶
Bases: TrafficProfile
Traffic profile with constant demands over time.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
demands
|
list[TrafficDemand]
|
Fixed list of user demands. |
required |
Source code in src/opensatcom/world/traffic.py
demands_at
¶
Return constant traffic demands regardless of time.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
t_s
|
float
|
Simulation time in seconds (unused). |
required |
Returns:
| Type | Description |
|---|---|
list[TrafficDemand]
|
Copy of the fixed demand list. |
Source code in src/opensatcom/world/traffic.py
TimeVaryingTrafficProfile
¶
TimeVaryingTrafficProfile(base_demands, pattern='ramp', ramp_factor=2.0, burst_period_s=60.0, burst_multiplier=3.0, burst_duration_s=10.0, t_start_s=0.0, t_end_s=600.0)
Bases: TrafficProfile
Traffic profile with time-varying patterns.
Supports ramp and burst patterns per user.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
base_demands
|
list[TrafficDemand]
|
Base demand levels. |
required |
pattern
|
str
|
Pattern type: "ramp" (linear increase), "burst" (periodic spikes). |
'ramp'
|
ramp_factor
|
float
|
For "ramp": max multiplier at end of simulation. |
2.0
|
burst_period_s
|
float
|
For "burst": period in seconds between bursts. |
60.0
|
burst_multiplier
|
float
|
For "burst": demand multiplier during burst. |
3.0
|
burst_duration_s
|
float
|
For "burst": duration of each burst. |
10.0
|
t_start_s
|
float
|
Simulation start time for ramp scaling. |
0.0
|
t_end_s
|
float
|
Simulation end time for ramp scaling. |
600.0
|
Source code in src/opensatcom/world/traffic.py
demands_at
¶
Return scaled traffic demands based on the configured pattern.
For "ramp" pattern, demand scales linearly from 1.0 at
t_start_s to ramp_factor at t_end_s. For "burst"
pattern, demand is multiplied by burst_multiplier during
periodic burst windows.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
t_s
|
float
|
Simulation time in seconds. |
required |
Returns:
| Type | Description |
|---|---|
list[TrafficDemand]
|
Demand list with |