Last updated on 16th July 2024
The RunnerBackend and ModelRunner classes need to be used together to setup and run a simulation that can run multiple times.
This guide assumes you have a Model created which implements simudyne.core.Model
The following imports are assumed
Imports required for multirun (Java)
import simudyne.core.runner.ModelRunner;
import simudyne.core.runner.RunResult;
import simudyne.core.runner.RunnerBackend;
The RunnerBackend class is needed to set up the ModelRunner. The default RunnerBackend can be created by using the RunnerBackend create method. This will create an instance of the RunnerBackend that can be used to run the model locally.
Create a model runner (Java)
RunnerBackend runnerBackend = RunnerBackend.create();
Create the ModelRunner for a specific model with RunnerBackend#forModel
passing the class of the model or RunnerBackend#forConfig
passing the ModelConfiguration
for the model
Create a model runner for a specific model (Java)
ModelRunner modelRunner = runnerBackend.forModel(myModel.class);
Use the ModelRunner
to set the number of ticks(steps) to run each run of the model for, and the number of runs (number of times to run the full simulation).
withInput
can optionally be used to set values of @Input
variables in the model.
Setting inputs (Java)
modelRunner
.forRuns(100)
.forTicks(50)
.withInput("{\"myBooleanInput\": false}")
.withInput("{\"myStringInput\": \"aString\"}");
To run the model and wait for the results, use ModelRunner#run
. Alternatively, the model can be run as an asynchronous process in the background. This means that while its running, the progress can be tracked.
// To run the model and wait for it to complete
RunResult runResult = modelRunner.run();
// To run the model a a background process and track the progress
Future<RunResult> runResultFuture = modelRunner.runAsync();
modelRunner.getProgress();
// Wait for final result
RunResult runResult = Await.result(runResultFuture, Duration.Inf());
A scenario is a simulation that can be setup to run a series of ticks with different input parameters for each tick. Each series can be run multiple times with a different seed.
We need to register the model and start the server.
Server.register("Game of Life", GameOfLife.class);
Server.run();
The model is now available for us to query. In this example, we will update gridSize of the Game of Life Model. We will set two runs with different seeds.
The parameters sent to the servers are:
Simulation parameters:
Scenario Parameters:
curl -X POST \
http://localhost:8080/api/simulations/scenario \
-H 'Cache-Control: no-cache' \
-H 'Content-Type: application/json' \
-d '{
"modelName": "Game of Life",
"output": {"uri": "/tmp/scenarios"},
"scenarios":[{
"seeds": [1234, 2314]
"scenarioData": {
"0": {"gridSize":10},
"10": {}
}
}]
}'
The server will return the following:
{"id":"f78057c4-f7f2-477b-bed1-3a690c7be864","name":"Game of Life","description":"","public":false,"session":"744d5b5b-ac16-4361-be3e-da5836c234bb","kind":"pojo"}
Now that this simulation has completed, go in the /tmp/scenarios/ we specified. Open the folder named as the id returned by the server, then runs. Inside are 2 files and 2 folders.
We only have one scenario, and two runs, this information is present in the folders names:
In the results.json file in each of the results folder, you can find the seed that we setup earlier as well as all data output. To have more details about the simulation output, refer to the documentation about the output directory structure.
Running a distributed multirun simulation depends on different packages and imports.
These elements can be found in the spark requirement tutorial and the spark runner tutorial tutorials.
To setup a distributed multirun, create a new instance of the SparkRunnerBackend as the RunnerBackend. All other methods are the same as for the local RunnerBackend.
Multirun with spark (Java)
RunnerBackend runnerBackend = new SparkRunnerBackend();
ModelRunner modelRunner = runnerBackend.forModel(myModel.class);
Extracting information from the RunResult
is explained in Multirun Output