agent_bridge (macula_neuroevolution v0.28.0)
View SourceAgent Bridge - Orchestrates the Sense→Think→Act Cycle.
This module ties together agent definition, sensors, actuators, and environment to run complete evaluation episodes. It is the integration point between domain-defined behaviours and the neuroevolution engine.
The bridge answers the question: "HOW do all the pieces fit together?"
Overview
The agent bridge:
- Registers sensors and actuators for an agent type
- Validates that topology matches I/O counts
- Orchestrates the sense→think→act cycle
- Slices inputs/outputs correctly for each sensor/actuator
Bridge Configuration
A bridge config specifies all components of an agent:
Config = #{
definition => my_agent_definition,
sensors => [vision_sensor, hearing_sensor, energy_sensor],
actuators => [movement_actuator, signal_actuator],
environment => hex_arena_env
}Sense→Think→Act Cycle
Each tick, the bridge executes:
1. SENSE: For each sensor, call read/2 → collect inputs
2. THINK: Feed inputs to neural network → get outputs
3. ACT: For each actuator, slice outputs → call act/3 → collect actions
4. APPLY: For each action, call environment:apply_action/3Input/Output Slicing
Sensors and actuators are processed in registration order:
Sensors: [vision(18), hearing(4), energy(1)] → Inputs: [0..17, 18..21, 22]
Actuators: [movement(7), signal(1)] → Outputs: [0..6, 7]Topology Validation
The bridge validates that:
- Sum of sensor input_counts == topology inputs
- Sum of actuator output_counts == topology outputs
This catches configuration errors before training begins.
See also: agent_actuator, agent_definition, agent_environment, agent_sensor.
Summary
Types
Neural network (from macula_tweann).
Functions
Processes outputs through all actuators.
Creates and validates a new bridge configuration.
Runs a complete evaluation episode.
Collects inputs from all sensors.
Executes one complete sense→think→act cycle.
Validates a bridge configuration.
Types
-type agent_state() :: map().
-type env_state() :: map().
-type network() :: term().
Neural network (from macula_tweann).
-type validated_bridge() :: #{definition := module(), sensors := [{module(), non_neg_integer(), pos_integer()}], actuators := [{module(), non_neg_integer(), pos_integer()}], environment := module(), evaluator => module(), total_inputs := pos_integer(), total_outputs := pos_integer(), topology := {pos_integer(), [pos_integer()], pos_integer()}}.
Functions
-spec act(Bridge, Outputs, AgentState, EnvState) -> Actions when Bridge :: validated_bridge(), Outputs :: [float()], AgentState :: agent_state(), EnvState :: env_state(), Actions :: [map()].
Processes outputs through all actuators.
Slices the output vector and calls each actuator's act/3. Returns a list of actions to apply.
-spec new(Config) -> {ok, ValidatedBridge} | {error, Reason} when Config :: bridge_config(), ValidatedBridge :: validated_bridge(), Reason :: term().
Creates and validates a new bridge configuration.
Returns a validated bridge with computed I/O offsets, or an error if validation fails.
Example:
Config = #{
definition => my_agent,
sensors => [vision_sensor, energy_sensor],
actuators => [movement_actuator],
environment => arena_env
},
{ok, Bridge} = agent_bridge:new(Config).
-spec run_episode(Bridge, Network, EnvConfig) -> Result when Bridge :: validated_bridge(), Network :: network(), EnvConfig :: map(), Result :: {ok, float(), map()} | {ok, map()} | {error, term()}.
Runs a complete evaluation episode.
Executes the full episode lifecycle: 1. Initialize environment 2. Spawn agent 3. Loop: tick → sense → think → act → apply actions 4. Extract metrics when terminal 5. Calculate fitness if evaluator is configured
Returns: - {ok, Fitness, Metrics} if evaluator is configured - {ok, Metrics} if no evaluator (backward compatible)
-spec sense(Bridge, AgentState, EnvState) -> Inputs when Bridge :: validated_bridge(), AgentState :: agent_state(), EnvState :: env_state(), Inputs :: [float()].
Collects inputs from all sensors.
Calls each sensor's read/2 in order and concatenates the results. Returns a flat list of floats ready for the neural network.
-spec sense_think_act(Bridge, Network, AgentState, EnvState) -> {Inputs, Outputs, Actions} when Bridge :: validated_bridge(), Network :: network(), AgentState :: agent_state(), EnvState :: env_state(), Inputs :: [float()], Outputs :: [float()], Actions :: [map()].
Executes one complete sense→think→act cycle.
This is the core function called each tick: 1. Sense: Collect inputs from all sensors 2. Think: Evaluate neural network 3. Act: Convert outputs to actions
Returns the list of actions to apply to the environment.
-spec validate(Config) -> {ok, ValidatedBridge} | {error, Reason} when Config :: bridge_config(), ValidatedBridge :: validated_bridge(), Reason :: term().
Validates a bridge configuration.
Checks:
- All modules implement their respective behaviours
- Sum of sensor inputs matches topology inputs
- Sum of actuator outputs matches topology outputs