mesa icon indicating copy to clipboard operation
mesa copied to clipboard

Access and modify model from Solara visualisation.

Open EwoutH opened this issue 1 year ago • 10 comments

Let's say you're running the Solara visualisation in a Jupyter notebook. Currently you can initialize the visualisation, and then it initializes a model instance from a model class.

image

However, you can currently not:

  • [ ] Start Solara with an existing model
  • [ ] Directly access the model instance, to get variables or data (like model.datacollectors.get_model_vars_dataframe())
  • [ ] Perform model methods, like model.step().

Ideally you want full control of the model, and Solara just updating whatever the current state of the model is. All the buttons in Solara should access methods that are also accessible by Python.

I think one non-ideal design choice we made is initializing the model in the JupyterViz class itself (here). If it's initialized outside there, you can just pass the model instance instead of the class.

One way of approaching is being able to directly access page.model and do things from there.

There might be some overlap with Mesa-interactive / #1805 here (cc @Corvince).

cc @rht and @maartenbreddels.

EwoutH avatar Jul 11 '24 14:07 EwoutH

If we can get something like the NetLogo Command Center in Solara that would also be amazing.

image

Just execute Python commands from a bar in your browser, in the visualisation. Things like:

model.step()
print(model.agents[0])

EwoutH avatar Jul 11 '24 14:07 EwoutH

Well that was one of my design goals for mesa interactive, so yes there are overlaps :)

Two issues are somewhat solved there. You can access the model at least from within the solar frontend, so you can easily write your own components for interactions. And those components only depend on the model - so you can "apply" those components to any model, not just the one created with mesa interactive.

But running code outside the frontend, e.g. in a different Jupiter cell doesn't yet automatically update the component plots - that's one thing I was looking into last (several months ago)

I am currently on vacation until the end of the month and then starting a new job. So time is very limited, but hopefully I can eventually port some of the ideas of mi back to mesa

Corvince avatar Jul 12 '24 05:07 Corvince

I think a crucial ingredient here is to have the mesa model emit events when things change. Maybe this example helps to get an idea how to implement this:

https://py.cafe/maartenbreddels/solara-external-model-observation

maartenbreddels avatar Jul 12 '24 07:07 maartenbreddels

I think a crucial ingredient here is to have the mesa model emit events when things change.

@EwoutH @Corvince It seems we have a good reason to add the pub-sub stuff we discussed long ago. Due to teaching and personal circumstances, I haven't been able to work on this over the last three months. There is, however, a branch with a working proof of principle. I am happy to pick this up again in the near future after my vacation break.

quaquel avatar Jul 12 '24 07:07 quaquel

Not sure if it is relevant, but I am not a fan of a push-based system. Over the years, however, a hybrid push/pull system (i.e. signals) has become more popular in the Javascript community. The key difference is, in signals, you mark derived 'state' (can also be component) as dirty. Then you schedule an update in the future for all derived state (e.g. component). Once those derived function/components execute, they pull in other derived things. This avoids issues with diamond dependencies and executing too much code, because push system always execute every dependency eagerly.

Ideally, solara's reactive variables (which are signals) would be its own library... :)

But, maybe it's overkill and otherwise I find: https://pypi.org/project/psygnal/ by @tlambert03 quite elegant.

maartenbreddels avatar Jul 12 '24 12:07 maartenbreddels

Not sure if it is relevant, but I am not a fan of a push-based system. Over the years, however, a hybrid push/pull system (i.e. signals) has become more popular in the Javascript community.

I agree

psygnal looks indeed very elegant. It also solves a particular problem we were discussing (evented containers). I'll have to give it a try after my vacation.

quaquel avatar Jul 15 '24 07:07 quaquel

There is another thing I want to adres. Currently we are using the visualisation by first creating a SolaraViz object, and then declaring it.

page = SolaraViz(
    ... # Some parameters
)

page 

Then you go to your terminal, and run solara run app.py.

I think for many users having to go to a terminal is counterintuitive, and I want to directly trigger run the Solara visualisation from the Python script. So doing something like page.run() or whatever.

I don't know if such a modification is currently easily possible, and if it conflicts with the goals listed here above. When running directly from a Python script it might be more difficult to later update a model or get data from it, or it might be easier because it's now all in a single Python script.

I would love to hear any thoughts on this. My current two priorities are:

  • Getting data back from a Mesa model running in Solara visualisation
  • Being able to run directly from a Python script (page.run() or something)

EwoutH avatar Aug 11 '24 16:08 EwoutH

I think for many users having to go to a terminal is counterintuitive, and I want to directly trigger run the Solara visualisation from the Python script. So doing something like page.run() or whatever.

See https://github.com/widgetti/solara/issues/192#issuecomment-2288780826

rht avatar Aug 14 '24 19:08 rht

For anyone interested: related discussion is happening at:

  • https://github.com/projectmesa/mesa/discussions/2236

EwoutH avatar Aug 22 '24 08:08 EwoutH

Even my code editor is now suggestion we should have something like page.run():

image

EwoutH avatar Sep 22 '24 10:09 EwoutH