The Runtime Around the Models: State, Messaging, and Deployment

For MathModelAgent, inspectability depends on more than agents and prompts. A long modeling task must remain visible while it runs, recoverable when a browser reconnects, and understandable when an operator needs to stop it. This chapter follows the runtime around the models: background execution, Redis messages, file-backed history, WebSocket delivery, frontend projections, configuration, and deployment. The goal is to identify where state lives and which operational choices determine whether the evidence chain survives contact with a real environment.

A final paper is a delayed artifact. During the hours before it exists, the user needs other signals: which stage is active, whether code is executing, whether an error occurred, whether images were created, and whether the task has finished or stopped. The backend and frontend therefore treat progress as data. That choice is valuable, but it also creates several state stores and several boundaries where information can be delayed, duplicated, or lost.

Live messages and persisted history serve different needs

The backend publishes typed system, agent, tool, and interpreter messages to a Redis channel associated with a task. A WebSocket subscribes to that channel and forwards messages to the browser. This live path is designed for immediacy. It lets the interface show a stage transition or execution result while the workflow is still running, rather than waiting for a final document.

The same backend also saves messages in a per-task JSON file. That file serves a different purpose. A live message is useful only while the connection is open and the event is flowing. Persisted history lets the frontend load what happened after a reconnect or lets a reviewer inspect the sequence after the task ends. The two paths are complementary: Redis provides a stream, while the file provides a recoverable record.

Treating them as interchangeable would create misleading expectations. A message can arrive live before the corresponding file write succeeds. A file can contain history that is no longer being streamed. A browser can reconnect and need to merge historical messages with new ones without displaying duplicates. The frontend task store therefore groups messages by task, de-duplicates them, orders them, loads history, and maintains the active WebSocket connection. These are not cosmetic details. They determine whether a user’s view is a faithful account of the task or merely the subset of events that happened to arrive in one browser session.

The message stream also carries different kinds of state. A system message can announce that a stage has started or failed. An agent message can show a Coordinator or Modeler response. A tool message can carry code input or interpreter output. The UI can therefore display progress and intermediate work without exposing every internal interaction in one undifferentiated chat transcript.

One stream becomes several working views

The frontend projects the shared message stream into views that match the roles. The planning view parses the latest Coordinator message to show the title, background, question count, and question list, then parses the Modeler message to show EDA, per-question solutions, and sensitivity analysis. The Coder view displays notebook-style execution output. The Writer view collects section messages and orders them according to the configured writing sequence.

This projection solves a real usability problem. A user trying to understand a proposed model does not need to search through code output. A user debugging a failed computation does not need to read every paragraph of paper prose.