{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "## Remote model interface\n", "This tutorial demonstrates how to use larvaworld's remote model interface. This allows interfacing larvaworld modules with arbitrary external processes and programs - for example an external neural simulator. In the present example a larva agent will use a neuron model running in brian2 to process olfactory information.\n", "\n", "This notebook provides a detailed description of the general setup and steps needed. The full code is located in the examples/brian2-interface/ folder. \n", "\n", "This type of setup requires two components that need to be run as separate processes:\n", "- a model server\n", "- a larvaworld experiment\n", "\n", "To run this you need to run two scripts in parallel via two terminals:\n", "\n", "Terminal 1 (run model server):\n", "```(bash)\n", "python3 server.py\n", "```\n", "\n", "Terminal 2 (launch larvaworld experiment):\n", "```(bash)\n", "python3 larvaworld_launcher.py\n", "```\n", "\n", "## Setup and code structure\n", "The example for this mode of operation involves 6 python files. All of which can be found inside the `examples/brian2-interface/` folder of larvaworld.\n", "\n", "The sections below will walk through all the main files and provide explanations of their purpose and other remarks related to the implementation. While this is a simple example - the general setup and structure holds true for any more complicated setups that can be developed.\n", "\n", "### larvaworld_launcher.py\n", "This file is the main entrypoint to execute the larvaworld simulation. It will setup a larvaworld experiment that will use a custom implementation `sensors.LocalOlfactor` for the OSNOlfactor module. This custom behavioral module performs the following tasks:\n", "- create a Python dict with concentration values sensed from the environment at the current simulation time step\n", "- create a `BrianInterfaceMessage` instance with that data\n", "- send that message object to the model server and wait for a response\n", "- parse the response from the model server and use its values as the output of the OSN module\n", "\n", "It follows and uses the same patterns that have been introduced in detail as part of the **library interface** and **custom module** tutorial.\n", "\n", "### server.py\n", "This file implements the model server for executing a brian2 model each time a message is received from the larvaworld simulation.\n", "The model server is a program that spins up a network server which listens for incoming message of type `larvaworld.lib.ipc.BrianInterfaceMessage`. This object contains all the data that is being exchanged between a model server and larvaworld.\n", "To make implementation easier larvaworld provides the functionality for starting up such a server through the `larvaworld.lib.ipc.Server` class. It takes care of all the heavy lifting and only requires implementation of a handler function that gets called each time a BrianInterfaceMessage is being received.\n", "\n", "The source code of a fully working example can be found in `examples/brian2-interface/server.py`. In this file you will find:\n", "- a main entrypoint that is executed when the script is being run\n", "- a handler function `server_process_request` to process incoming messages\n", "- a `process_model` function that executes a brian2 model using the data available in the received `BrianInterfaceMessage`\n", "\n", "### server_runnable.py\n", "This file contains the main logic to execute a brian2 model instance:\n", "- warmup the model when it is being first run\n", "- restore model state from a previous simulation step\n", "- prepare the input to the model (convert concentration values to current)\n", "- execute the model for a given duration\n", "- snapshot / save the state of the brian2 model\n", "- compute / collect the output data of the model to be send back to larvaworld\n", "\n", "The file is commented and generates a lot of terminal output to see what is happening.\n", "It can serve as a skeleton for custom implementations.\n", "\n", "Important to highlight is the need to perform snapshotting of model state after each run - that is after each simulation step performed in larvaworld which triggers a model execution. Because our brian2 model is time-dependent and maintains state over time (in the form of membrane potential and spike-frequency adaptation).\n", "If one would omit snapshotting model state the neuron model would always behave like it has been freshly initialized.\n", "\n", "Another important aspect is the warmup phase. Whenever the brian2 model gets executed for the first time - we run it for a certain period of time with some constant input. This will drive the model parameters to a equilibrium state and ensures that no artifacts will be present.\n", "\n", "\n", "### model.py\n", "This file contains the brian2 model definition. For this example it is a single OSN neuron using a conductance-based LiF model with spike-frequency adaptation. The neuron receives input as current injection. That current is derived from a concentration value transmitted from the larvaworld experiment and transformed into a current by applying a Hill function.\n", "\n", " " ] } ], "metadata": { "kernelspec": { "display_name": "Python 3 (ipykernel)", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.13.2" } }, "nbformat": 4, "nbformat_minor": 4 }