Reproducing Memory Inside a Live Drone Control Loop

A simulated drone -- 2D position and altitude, raycast obstacle sensing, wind, battery drain, walls it can actually crash into -- wired into the vaas-x ingest/query/outcome loop in real time. Below is how to reproduce it end to end, including a controlled ablation that found a genuine, reproducible limitation in how memory competed for the decision.

Requirements: a VAAS-X API key, pip install vaas-x.

The architecture: memory suggests, deterministic rules decide

Every control step: canonicalize the drone's state to text, query memory for similar past situations, and add the recalled action to a candidate pool alongside a local heuristic controller, a few purpose-built maneuvers (settle near the goal, brake, escape a close obstacle), and small perturbations. Every candidate is scored by simulating it forward a few steps and penalizing collisions, close clearance, and wasted energy. A hard-coded veto function rejects any candidate -- retrieved or not -- that violates a safety rule. Probabilistic retrieval proposes; deterministic rules and simulated rollout decide.

from vaasx import Bootstrap

brain = Bootstrap(api_key="YOUR_API_KEY", device_id="drone_01")

state_text = "Drone navigation state. goal_dist=6.0m goal_dz=-1.5m yaw_err=0.2rad " \
             "vxy=0.5 vz=0.0 yaw=-0.8 battery=0.85 wind=(1.0,-0.5) gps=good " \
             "hazard=clear obstacles_front=15.0m left=15.0m right=15.0m back=13.5m"

hits = brain.query(state_text, k=7)
# hits[i]["text"] carries the recalled state+action+outcome; parse the
# "Control: thrust=... yaw_rate=... climb=..." substring out of it and add
# it to your candidate pool alongside your own controller's proposal.

brain.ingest([{
    "state": {"text": state_text},
    "action": {"text": "Control: thrust=0.72 yaw_rate=0.31 (left) climb=-0.20 (down)"},
    "outcome": {"text": "Outcome: success no_collision dist_to_goal=1.9 energy=0.013 arrived", "success": True},
}])

# If the executed action came from a retrieved episode, report back on it
brain.outcome(hits[0]["id"], success=True, delta=0.12)

Run it yourself: seed, then close the loop

The full simulation (dynamics, walls, raycasting, the heuristic controller, veto rules, rollout scoring) and the memory-integration layer are two separate files -- the simulation has no vaas-x dependency at all.

# One 40-step episode:
py public_sdk_drone.py

# Adaptive loop -- policy shifts trust in memory vs. local control based on
# whether each episode succeeded, and that policy update is itself written
# back as a queryable episode:
py public_sdk_drone.py --loop --episodes 10 --steps 40

Each step makes 2-3 API calls (query, ingest, sometimes outcome); a free or lower tier's per-key burst limit can be exhausted by a tight loop with no pacing. The script paces itself between steps and retries with exponential backoff on any 429/503/502, so it degrades gracefully rather than crashing -- worth building into any real integration that calls the resolver in a loop, not just this demo.

The ablation: does memory actually change the outcome?

A fair test needs a controlled comparison, not just a summary number. This runs the identical episode count twice, back to back, on the same wall layout and the same random draws -- once with the memory candidate allowed to compete for the decision, once with it excluded entirely from an otherwise identical candidate pool and scoring pipeline.

py public_sdk_drone.py --ablation --episodes 10 --steps 40

# Or, to rerun just the baseline arm on its own (e.g. resuming a partial run
# without re-ingesting into the memory-enabled device):
py public_sdk_drone.py --baseline-only --episodes 10 --steps 40

First attempt: both arms produced byte-identical trajectories. The cause was in how memory had been seeded -- entirely from the same local heuristic controller it was competing against, so retrieval had nothing genuinely different to offer. Fixed by seeding 24% of prior episodes from a distinct exploration policy instead, and rerun.

What we found, reported honestly

Both arms still finished at 4 wins out of 10 -- and were still episode-for-episode identical. Across 20 full episodes (232 total control steps combined), the memory candidate won the internal decision exactly once. The reason: the scoring bonus meant to favor a recalled action is a small, fixed number, while the rollout cost function it competes against has a much larger dynamic range -- a single collision alone costs 400 points in that scoring. A recalled action transplanted onto a new state essentially never beats a controller purpose-built for that exact state by less than the bonus, so the discount rarely if ever changes which candidate wins.

This is a faithful port of the original prototype's own scoring formula, not something introduced while porting it to the public SDK -- which means it's a genuine, previously-unmeasured property of this specific design, not a flaw in retrieval itself. We can't even say whether what memory recalled was good; it essentially never got the chance to be chosen. The generalizable lesson: in any "propose from memory, then score by simulation" pattern, the bonus that lets memory override a local controller has to be calibrated against the actual scale of the scoring function it's competing inside, or memory will structurally never participate no matter how good retrieval is.

Scope

What this reproduces: the ingest/query/outcome path running unmodified inside a real-time control loop against a resolver over the network, and a controlled, reproducible ablation methodology that can isolate exactly what a memory-augmented decision system is and isn't doing. What it does not show: that retrieval-augmented control outperforms a well-tuned local controller in this environment -- on this evidence, it didn't get the chance to. This is a simulated drone, not flight-tested hardware, and the scoring-calibration issue found here is specific to this rollout-scoring design, not a general claim about memory-augmented control.

More guides: Reproduction Guides. Full reference: Developer Guide. Technical writeup: Robotics & Autonomy whitepaper.