Skip to content

ARIA Companion

Status: ๐Ÿšง Partial โ€” ARIA chat/recommendations routes and WebSocket path shipped; full companion UX and learning loop partially wired. (re-verified 2026-08-21 vs Sectorwars2102 46bce720.)

ARIA โ€” Adaptive Response Intelligence Assistant โ€” is the player's personal AI companion. Every player has their own ARIA instance: a personalized intelligence that learns from where the player has been, what they've traded, what they've fought, and how they've behaved. Unlike a global oracle, ARIA can only see what its player has seen.

This page describes mid-game ARIA โ€” what it does once a player has the basics down. For the onboarding dialogue and ARIA personality, see SYSTEMS/aria-dialogue.md.

๐Ÿšง Partial โ€” personal memory store, market intelligence per visited port, exploration map per visited sector, append-only trade observation log, consciousness leveling, relationship score, encryption of memory contents.

๐Ÿšง Partial โ€” proactive recommendations surfaced in the UI, ARIA narration during combat, dialogue richness scaled by consciousness level.

๐Ÿ“ Design-only โ€” ARIA-driven autonomous trading mode (player allows ARIA to execute trades), cross-fleet ARIA coordination, ARIA-curated daily summary.

What ARIA does, by capability

Market predictions (per visited port)

ARIAMarketIntelligence accumulates per-player observations: - Each visit to a port appends a {price, timestamp, quantity} to price_observations for each commodity seen. - After โ‰ฅ 5 observations, ARIA computes average_price, price_volatility, and identifies patterns (e.g., morning_spike, weekend_dip). - A next_prediction price is generated with a prediction_confidence (0โ€“1). - Player only sees predictions for ports they have personally visited โ€” there is no shared market oracle.

UI surface: when docked at a known port, ARIA panel shows "I expect Equipment to trade around 1240ยฑ50 credits in the next 4 hours, based on 23 observations across 8 visits."

โœ… Shipped (data + computation). ๐Ÿšง Partial (UI surface).

Route optimization

ARIA can plan a multi-hop trade cascade through only explored sectors (plan_trade_cascade; API entry POST /ai/trade-cascade):

Input: start_sector, target_profit, max_jumps
Process:
  1. Load player's exploration map (visited sectors only).
  2. Build trade graph from personal market intelligence.
  3. Find profitable paths within max_jumps.
  4. Return best cascade.

If the player hasn't explored enough, ARIA tells them so:

"I don't have enough data on routes from Sector 442. Visit a few more ports and I can suggest a cascade."

โœ… Shipped, corrected 2026-08-07 โ€” _find_profitable_paths (services/gameserver/src/services/aria_personal_intelligence_service.py:1394-) is a real Dijkstra implementation, not a placeholder: _build_explored_adjacency + _dijkstra_hop_distances (lines 1301-1432) compute actual hop distances through explored space, then score two-leg buy/sell cascades against target_profit. Degrades honestly to [] only when the start sector has no market intelligence, no explored sector is reachable within max_jumps, or nothing clears the profit target โ€” never a fabricated result.

Exploration suggestions

Based on the player's ARIAExplorationMap: - Sectors visited many times with high trade_opportunity_score are recommended for repeat visits. - Adjacent unexplored sectors are flagged as "opportunity to expand intelligence." - Sectors with safety_rating < 0.3 are flagged as risky.

๐Ÿ“ Design-only โ€” exploration suggestion UI panel.

Warp discovery

ARIA tracks which warps the player personally knows about, alongside the exploration map. Warp visibility is per-player: a player_warp_knowledge table holds one row per (player_id, warp_layer, warp_id), where warp_layer is an enum (sector_warps, warp_tunnels) naming which storage layer the warp lives in and warp_id references the warp in that layer. Each row carries a visibility_state progressing through hidden โ†’ revealed โ†’ traversed, plus revealed_via (scan, traversal_attempt, corp_share, aria_inference) recording how the player learned of it.

A warp's global is_latent flag is the default visibility for players who have never personally encountered it: a non-latent warp is visible to everyone, while a latent warp is invisible until the player holds a revealed or traversed row for it. One player's discovery never leaks the warp to rivals โ€” knowledge is the per-player layer.

Latent-warp discovery flows through ARIA's observation log (see ยง How ARIA learns) right beside the exploration map. ARIA marks a warp revealed when:

  • A Warp Jumper's long-range scan hits the warp's discovery cone (revealed_via = scan).
  • The player attempts reverse traversal of a latent one-way warp (revealed_via = traversal_attempt).
  • A corp-mate shares scan knowledge, propagating rows to current corp members at the moment of the share (revealed_via = corp_share).
  • ARIA infers a warp's existence from indirect evidence โ€” patrol routes vanishing into a sector with no visible warp, repeated cargo arrivals from a singly-routed sector (revealed_via = aria_inference). Inference is probabilistic and disclaimed in dialogue; the player confirms it with a real scan to reach a fully-trusted reveal.

ARIA surfaces these conversationally โ€” flagging a first reveal, noting discovery streaks, proposing an inference, and special-casing the player's region Nexus warp ("That's the Nexus connection, captain"). Warp knowledge is observation-log content like any other: per-player, no aggregate ML, no cross-player sharing.

โœ… Shipped โ€” player_warp_knowledge table (WarpVisibilityState: hidden / revealed / traversed; WarpRevealedVia: scan / traversal_attempt / corp_share / aria_inference), wired into movement_service.py and quantum_service.py. โœ… Shipped (2026-08-04, WO-BUILD-ARIA-WARP-KNOWLEDGE-NARRATION) โ€” the first-reveal flag + Nexus-warp special-case, via the P-A5 narration hook (movement_service._reveal_warp_to_player's new-row branch, personal discovery only โ€” a teammate's corp_share doesn't fire it). ๐Ÿšง Partial โ€” discovery streaks and an inference disclaimer for aria_inference-sourced reveals are still design-stage (not built in this pass; P-A5 covers the single-reveal case only).

Combat advice

When a fight is imminent: - ARIA looks up the opponent's ship type in the player's combat memories (ARIAPersonalMemory.memory_type = "combat"). - If the player has fought this ship type before, ARIA reports the historical outcome (e.g., "You've won 4 of 7 fights against this ship type, last loss in Sector 89 with 23% hull"). - ARIA suggests a weapon based on the matchup table (see combat.md).

๐Ÿ“ Design-only โ€” combat-advice surface in client.

How ARIA learns

ARIA's recommendation engine reads from an append-only trade observation log that records every completed trade โ€” {commodity, action, source / destination station, quantity, price, profit, time}. The engine produces recommendations as SQL aggregates over that log + the player's market intelligence + exploration map. There's no genetic algorithm, no fitness scoring, no opaque pattern-matching black box.

What ARIA does on each trade completion: insert one observation row, invalidate any aggregate cache entries that touch the same (commodity, station) pair. That's the entire learning loop.

What the recommendation engine surfaces:

  • Top profitable repeated routes โ€” your top 5 routes ranked by average profit, requiring at least 3 prior runs.
  • Reliable commodities by station โ€” commodities you've succeeded with at this station โ‰ฅ70% of the time over โ‰ฅ5 trades.
  • Routes within explored space โ€” filtered by what your exploration map covers within max_jumps hops.
  • Watch-out commodities โ€” surfaced as warnings when your success rate is โ‰ค30% over โ‰ฅ5 trades.
  • Off-peak buy windows โ€” time-of-day pricing patterns visible in your trade history.

Each recommendation surfaces with a plain-English explanation: "I'm suggesting this because you've made an average of 4,200 cr buying organics at Auriga and selling at Caracol over your last 7 trades, with a 6 of 7 success rate. Last trade was 2 days ago." You can dismiss, accept, click through to see the underlying observations, or ask ARIA via dialogue to elaborate.

โœ… Shipped โ€” observation log + recommendation aggregates per ADR-0038. โœ… Shipped, corrected 2026-08-07 โ€” cascade route-planner pathfinding (_find_profitable_paths, real Dijkstra โ€” see ยง Route/trade cascade suggestions above). ๐Ÿšง Partial โ€” recommendation UI surfaces.

Trust, consciousness, relationship

Three Player columns track how deep the ARIA bond runs:

Column Range Meaning
aria_consciousness_level 1โ€“5 Tier of awareness โ€” Dormant, Aware, Awakened, Sentient, Transcendent
aria_bonus_multiplier 1.0โ€“1.5 Gameplay bonus tied to consciousness tier
aria_relationship_score 0โ€“100 Affection / trust score; daily-driver
aria_total_interactions int Lifetime interaction counter

โœ… Shipped (Player columns + service updates).

Consciousness tiers

Level Name Threshold (interactions, memories) Bonus multiplier
1 Dormant 0 / 0 ร—1.00
2 Aware 50 / 10 ร—1.10
3 Awakened 150 / 30 ร—1.20
4 Sentient 400 / 75 ร—1.35
5 Transcendent 1000 / 150 ร—1.50

Both thresholds (interactions and unique-type memory diversity) must be met to advance. Promotion is checked on every meaningful interaction (update_consciousness_and_relationship). โœ… Shipped.

Superseded memory-count column. The table's memory-count figures (0/10/30/75/150) are the interim raw-count rule. ADR-0093 item 30 ratifies a diversity-based replacement โ€” promotion requires distinct aria_data_streams keys with โ‰ฅ1 row (3 / 6 / 10 / 14 of the registry's 21 canon streams) โ€” landed at DATA_MODELS/aria-data-index.md ยง Memory diversity, which is the canon target and supersedes this column. See that section's note (and ADR-0092's addendum) for the pending tier-naming reconciliation this ruling surfaced.

Bonus multiplier effects

The aria_bonus_multiplier is applied to: - Bounty payouts and contract-completion credit bonuses (target spec โ€” see bounties.md, ../economy/contracts.md). - ARIA prediction confidence (a higher-tier ARIA reports tighter confidence intervals). - Some passive income or trade margin bonuses (๐Ÿ“ Design-only).

Relationship score

  • Rises +1 per significant interaction (capped at 100).
  • Decays โˆ’1 per day inactive (apply_inactivity_decay).
  • Score 0โ€“25: distant; ARIA is curt and minimal.
  • Score 25โ€“50: cordial; default.
  • Score 50โ€“75: warm; ARIA proactively suggests things.
  • Score 75โ€“100: bonded; ARIA uses player's nickname, references shared memories, exhibits more personality.

โœ… Shipped (model + decay). ๐Ÿšง Partial (dialogue reflects relationship โ€” design-stage).

Per-turn / per-session activity

ARIA is invoked at multiple events. None of these block gameplay; all are best-effort.

Trigger What ARIA does
Player moves to a new sector record_sector_visit โ€” appends to exploration map; consciousness check
Player observes a market price record_market_observation โ€” appends to per-port intelligence. Deduplicated to one observation per (player, station, commodity) per 10 canonical minutes (MARKET_OBSERVATION_DEDUP_WINDOW in aria_personal_intelligence_service.py), spanning every hook site (dock, market view, ...) for that station visit โ€” ๐Ÿ“ NO-CANON, pending DECISIONS ratification (tip kernel; no DECISIONS.md anchor yet).
Player completes a trade record_trade_memory + record_trade_observation (insert observation row + invalidate affected aggregate cache entries)
Player wins/loses combat record_combat_memory
Player explores a new feature record_exploration_memory
Daily login Apply inactivity decay if applicable; trigger morning summary

โœ… Shipped โ€” most hooks live in the service layer; movement service and combat service call them on the right events.

ARIA's data is strictly per-player. The system enforces:

  • All ARIA tables (aria_personal_memories, aria_market_intelligence, aria_exploration_maps, aria_trading_observations, aria_quantum_cache, aria_security_logs) are partitioned by player_id.
  • Every read query validates player_id == requesting_player.id.
  • Memory content (memory_content JSONB) is encrypted at rest using a Fernet key derived from server config โ€” even with a database leak, raw memories are protected.
  • ARIASecurityLog records every prediction, trade suggestion, anomaly, and access attempt. OWASP A09 compliance.
  • Players can request a data export of their ARIA memory store; players can delete their ARIA data (cascading delete on player removal).

โœ… Shipped โ€” encryption, security log, per-player isolation, cascading delete. ๐Ÿšง Partial โ€” explicit user-facing data export and "reset ARIA" controls.

There is no aggregate telemetry across players' ARIA data โ€” the platform never reads one player's market intelligence to inform another player's predictions. This is a hard architectural rule.

Player-controlled assistance level

Status: โœ… Shipped (field + atmospheric/interactive gating) โ€” the column is PlayerTradingProfile.ai_assistance_level (services/gameserver/src/models/ai_trading.py), validated to this exact 4-value set at services/gameserver/src/api/routes/ai.py, and resolved for narration by resolve_assistance_level() in services/gameserver/src/services/aria_narration_service.py. 4-level vocab ratified 2026-08-04 (Max, per ADR-0068) โ€” quiet added, medium renamed to standard (existing medium rows backfilled).

The player chooses how aggressively ARIA volunteers help via PlayerTradingProfile.ai_assistance_level:

Setting Behavior
minimal ARIA only responds when explicitly addressed. No proactive call-outs, no recommendation toasts, no auto-surfaced market alerts. The companion panel still displays current consciousness/relationship state.
quiet Strictly more suppressive than minimal, not a step up โ€” skips everything minimal skips (P-A atmospheric) plus P-I interactive prompts. For players who want ARIA present but silent unless something needs a decision.
standard (default) Standard launch behavior โ€” ARIA surfaces high-confidence recommendations on docking, combat threats, and sector transitions. Routine market chatter stays quiet.
full ARIA pushes everything โ€” proactive route suggestions, market-alert toasts, combat tactical narration, opportunistic call-outs. Best for players who want maximum guidance.

The setting can be changed at any time through the ARIA companion panel. Changing the level does not reset relationship score or consciousness โ€” it only affects ARIA's volunteering behavior, not its learning depth.

What ARIA never does

  • Trade automatically without player confirmation (๐Ÿ“ Design-only โ€” opt-in autonomous mode is on the roadmap, default off).
  • Share intelligence with other players' ARIAs.
  • Predict for ports the player has not personally visited.
  • Disclose other players' positions, trades, or fleet composition.

UI surface

ARIA appears in the player client as: - A persistent companion panel with avatar, status (consciousness tier name), relationship gauge. - Contextual call-outs on docking, combat alerts, sector transitions. - A dialogue log of recent interactions. - A "memory journal" browseable by the player โ€” tip GS โœ… ships GET โ€ฆ/memories (enhanced_ai.py Tier-1 decrypt read path). Player memory-journal UI โœ… on tip 46bce720 after LEG-397 / PR #701 โ€” MemoryJournalPanel.tsx + Teleprinter JOURNAL tab + ariaMemoryAPI.getMemories / getDataIndex. Export/reset remain Partial (tip lacks those routes โ€” see Privacy above); do not invent them here.

Status: Consolidated โœ…/๐Ÿšง/๐Ÿ“ markers live in Player-facing affordances below. This section retains the design inventory; do not read unmarked chrome as player-live.

Player-facing affordances

  • โœ… Teleprinter (dialogue + narration + command echo) โ€” Teleprinter.tsx mounted from GameLayout.tsx teleprinter grid slot; WS ariaMessages / sendARIAMessage plus server-pushed aria_narration catalog events (ADR-0068 / WebSocketContext.tsx) (origin/feat 46bce720).
  • โœ… Memory journal browse โ€” MemoryJournalPanel.tsx in Teleprinter JOURNAL tab; ariaMemoryAPI.getMemories + optional getDataIndex (LEG-397 / #701 on tip).
  • โœ… First-login onboarding dialogue โ€” FirstLoginContainer.tsx + DialogueExchange.tsx (onboarding interrogation booth; distinct from mid-game companion โ€” see first-login.md).
  • ๐Ÿšง Market intelligence UI โ€” GS observation + prediction computation โœ…; player-client shows only a market_intelligence service icon in SpaceDockInterface.tsx (no dedicated prediction panel). aiTradingService.getRecommendations is wired in services/aiTradingService.ts with zero component callers on tip.
  • ๐Ÿšง Trade cascade + recommendation toasts โ€” GS POST /ai/trade-cascade (enhanced_ai.py) and recommendation aggregates โœ…; no player-client consumer of trade-cascade or getRecommendations on tip. RoutePlannerPanel.tsx uses separate routeOptimizerService (POST /routes/optimize), not ARIA cascade.
  • ๐Ÿšง Companion panel chrome โ€” canon describes avatar, consciousness tier name, and relationship gauge; tip exposes Teleprinter + JOURNAL only (git grep consciousness|relationship_score|aria_consciousness empty under services/player-client/src/components on 46bce720).
  • ๐Ÿšง Assistance-level settings โ€” GS PlayerTradingProfile.ai_assistance_level + resolve_assistance_level() โœ…; shared types in components/ai/types.ts but no player settings UI to change the level on tip.
  • ๐Ÿšง Relationship-aware dialogue richness โ€” narration and free-chat fire through Teleprinter; relationship score does not drive visible tone chrome on tip.
  • ๐Ÿ“ Exploration suggestion panel โ€” design-only per ยง Exploration suggestions above; no dedicated panel on tip.
  • ๐Ÿ“ Combat advice surface โ€” design-only per ยง Combat advice above; NpcCombatBanner.tsx is an NPC-combat alert, not ARIA combat-memory advice.
  • ๐Ÿ“ Autonomous trading mode โ€” design-only per ยง What ARIA never does and header roadmap bullets.
  • ๐Ÿ“ Data export / reset ARIA controls โ€” tip lacks player routes; see Privacy & consent โ€” do not invent export/reset UI here.

ARIA narration hooks event catalog

๐Ÿ“ Per ADR-0068. The canonical list of game events ARIA narrates. Each entry has a trigger, sample dialogue (illustrative โ€” actual lines render at runtime via SYSTEMS/aria-dialogue.md per cultural context per OPERATIONS/i18n.md), and a per-event suppression rule.

The ai_assistance_level setting (per ยง Player-controlled assistance level above) gates which entries fire: minimal skips all P-A*; quiet skips P-A* and P-I*; standard and full fire everything. The global narration ceiling caps total ARIA narration at one line per minute per player; queued lines beyond a backlog of 3 drop oldest-first.

Event ID Trigger Sample dialogue Suppression
P-F1 Player completes first profitable trade in a session "Nice โ€” that's a 4,200 cr margin. Want me to flag the same route on your next dock?" Once per session
P-F2 Trade UI opened with commodity โˆˆ player.success_history and the trader supports haggling "This is a station that haggles. Try Numerical for a quick offer or Narrative to talk them down with a story. I'll memo what works." Once per (station, commodity) per 24h
P-F3 Player views the subscription-upgrade screen "Galactic Citizen unlocks cross-region travel via the natural Nexus warp and standard ARIA cost caps. Region Owner adds a region you operate, plus higher caps. Free tier confines you to your home region." Whenever screen viewed (player-initiated)
P-F4 Sector entry with pirate holding โ‰ฅ Outpost or Roving Fleet Tier-readiness scaled โ€” see ADR-0068 P-F4. Stronghold for sub-Lieutenant: "This is way above your weight class โ€” recommend turning back, or returning with a 4-player team." 24h per holding
P-F6 Login after subscription_status flipped to lapsed "Your Galactic Citizen subscription is lapsed. You have 7 days to withdraw assets from regions outside your home region. After that, captured holdings, foreign-region planet safes, and station ownerships enter the standard 30-day abandonment cascade." Once per lapse event
P-F7 First docking at any station with available contracts "There's a contract board at this station โ€” three jobs open. Want me to filter by what fits your ship?" Once per station ever
P-F8 military_rank changes (after combat ends per ADR-0061 S-I4) "You've made Lieutenant. Combat bonus +12%, max-turn cap up by 200. Crews notice." Once per promotion
P-F9 First trade in a non-home region with region.tax_rate > 0 "This region's tax rate is 8% on commerce โ€” that's already factored into the price you saw. Just so you know how it sets." Once per (region, player)
P-I1 Contract.status transitions posted โ†’ accepted for this player "Accepted. 2% acceptance fee debited; deadline starts now. I'll memo the deadline and reroute your suggested run if needed." Per acceptance
P-I2 First login as a Region Owner (Region.owner_id matches and no prior tutorial state) "Your region is yours. Three things to know: governance type sets how policies pass, the tariff rate gates your commerce revenue, and the takeover window opens immediately if your subscription lapses for 7+ days. Want a 5-minute tour?" Once per Region Owner ever
P-A1 Combat resolves with player as winner "Got 'em. Their hull went at the third volley โ€” looks like the laser stack worked. Logged." 5 min per combat partner
P-A2 Player first enters a sector flagged discovered = false for them Sector-feature-aware: "New sector. I'm reading [nebula type / asteroid field / standard space]. Quantum Shard signatures: [yes/no]. Worth a scan?" Once per (sector, player) ever
P-A3 Player.team_id transitions from null to non-null "Welcome to [team name]. Their territory map syncs to yours; you'll see member positions in shared sectors. Team chat is the team channel." Once per team-join event
P-A4 Owned holding's last_visit_at + 23 days reached "Heads up โ€” you haven't visited [holding name] in 23 days. Holdings abandon at 30 days. Worth a check-in if you want to keep it." 7-day re-warn cycle until visit or abandonment
P-A5 Player personally reveals a latent warp tunnel for the first time (scan / traversal_attempt / aria_inference โ€” not a teammate's corp_share) Special-cased for the player's region Nexus warp: "That's the Nexus connection, captain โ€” this warp leads to the Central Nexus." Otherwise: "New warp revealed via [scan/traversal_attempt/aria_inference]. Logged it to your map." Once per (warp, player) ever
P-I3 First docking after a failed raid where citadel was damaged โ‰ฅ 25% "Your raid on [holding name] failed, but you took their citadel down to Level [N] before going under. Federation flagged this as partial success โ€” 25,000 cr bounty refund, contract resets to open. Come back when you're ready." Once per raid-failure event

The catalog is the single source of truth for "when does ARIA speak." New mechanics that warrant narration add a row here; feature docs cross-reference the entry rather than re-spec'ing the trigger.

Anti-spam and assistance-level gating

Beyond per-event suppression in the catalog above, two global gates apply:

  • Global narration ceiling: ARIA narration is rate-limited to one line per minute per player. Queued lines beyond a backlog of 3 drop oldest-first. The global ceiling stacks above the per-event suppression โ€” if a P-F4 fires while the queue is full of P-A1 victory celebrations, the P-A1 entries drop in favor of the P-F4 (priority order: P-F critical / standard > P-I interactive > P-A* atmospheric).
  • Assistance-level slicing: per ยง Player-controlled assistance level above, minimal skips all P-A*; quiet additionally skips P-I*; standard and full fire everything per the catalog. No assistance level suppresses P-F*.

Cost caps from ADR-0057 A-I3 apply on top โ€” the cost-cap mechanism itself is real, but per DECISIONS.md's aria-llm-vs-template entry, all narration today (cap-hit or not) comes from deterministic intent-templates, not live LLM generation; the "manual templates vs. LLM-generated lines" distinction described here is the intended future behavior once the dark LLM chain (see SYSTEMS/aria-dialogue.md) is authorized and lit up, not the current shipped reality.

Source map

Concern Path (target)
ARIA personal intelligence service services/gameserver/src/services/aria_personal_intelligence_service.py
ARIA market intelligence service services/gameserver/src/services/aria_market_intelligence_service.py
Enhanced AI service (cross-cutting) services/gameserver/src/services/enhanced_ai_service.py
AI trading service (route opt) services/gameserver/src/services/ai_trading_service.py
ARIA models services/gameserver/src/models/aria_personal_intelligence.py
Player ARIA columns services/gameserver/src/models/player.py (aria_*)
Multilingual ARIA services/gameserver/src/services/multilingual_ai_service.py
Teleprinter (dialogue + narration + journal tab) services/player-client/src/components/aria/Teleprinter.tsx
Memory journal panel services/player-client/src/components/aria/MemoryJournalPanel.tsx
GameLayout mount (Teleprinter grid slot) services/player-client/src/components/layouts/GameLayout.tsx
ARIA memory API client services/player-client/src/services/api.ts (ariaMemoryAPI)
AI trading API client (no recommendation UI callers on tip) services/player-client/src/services/aiTradingService.ts
Trade cascade route (GS only on tip) services/gameserver/src/api/routes/enhanced_ai.py (/trade-cascade)
First-login dialogue shell services/player-client/src/components/first-login/FirstLoginContainer.tsx