TeX 93.9%
Python 6%
1% --- Python execution sandbox: isolation boundary + IPC ---2\begin{figure}[htbp]3\centering4\begin{tikzpicture}[vqfont]56% ---- Server side ----7\node[vqblue, text width=2.6cm, minimum height=2.0cm] (srv) at (0,0)8 {\textbf{Server}\\\vqsmall \texttt{spawn} child\\ write stdin\\ read stdout};910% ---- Child inner stages ----11\node[vqgreen, text width=4.5cm] (ns) at (8.0,2.05)12 {\textbf{Build namespace}\\\vqsmall 17 libs $\cdot$ \texttt{save\_excel}/\texttt{save\_word} $\cdot$ \texttt{fmp} client $\cdot$ context vars};13\node[vqorange, text width=4.5cm] (ex) at (8.0,0.35)14 {\textbf{\texttt{exec(code, ns)}}\\\vqsmall \texttt{stdout}/\texttt{stderr} $\to$ string buffers $\cdot$ optional \texttt{main()}};15\node[vqpurple, text width=4.5cm] (cap) at (8.0,-1.35)16 {\textbf{Figure capture}\\\vqsmall \texttt{get\_fignums} $\to$ PNG @150\,dpi $\to$ base64};1718\draw[vqarr] (ns) -- (ex);19\draw[vqarr] (ex) -- (cap);2021% Child container22\begin{scope}[on background layer]23 \node[vqband, fill=VQInk!4, draw=VQInk!35, line width=0.5pt, dashed,24 fit=(ns)(ex)(cap), inner sep=10pt] (child) {};25\end{scope}26\node[vqsmall, anchor=north west, text=VQInk!70] at (child.north west)27 {\textbf{Child Python process}~~\vqtiny(\texttt{PYTHONUNBUFFERED}, 90\,s timeout, Agg backend)};2829% ---- IPC arrows across the boundary ----30\draw[vqflow] (srv.east) to[out=25,in=180]31 node[vqtag, pos=0.5, above]{stdin: \texttt{\{code, context, key\}}} (ns.west);32\draw[vqflow, draw=VQTeal!80!black] (cap.west) to[out=180,in=-25]33 node[vqtag, pos=0.5, below]{stdout: \texttt{\{output, figures[], files[]\}}} (srv.east);3435% Isolation boundary marker36\draw[VQRed!70!black, line width=0.7pt, dash pattern=on 3pt off 2pt]37 (3.0,2.8) -- (3.0,-2.3);38\node[vqtag, text=VQRed!70!black, fill=white] at (3.0,-2.6) {process isolation};3940\end{tikzpicture}41\caption{\textbf{The Python execution sandbox.} The server runs model-authored code in a separate42interpreter, not in process. It serializes one JSON request to the child's standard input; the43child builds an execution namespace (scientific libraries, artifact helpers, a market-data client,44and any context variables), runs the code with output redirected into string buffers, then sweeps45all live matplotlib figures into base64-encoded PNGs and returns a single JSON response. A46non-zero exit or empty output is surfaced as an error so the model can revise. The dashed boundary47is the process-isolation line; the red marker emphasizes that a crash or timeout cannot reach the48server.}49\label{fig:sandbox}50\end{figure}51