An EXPERIMENTAL(read not finished yet) visual interface for running commands as a directed acyclic graph (DAG). The output of one command node can be piped as the input to subsequent nodes. Made it to experiment with small model workflows locally while having a visual aspect to it.
The state of the graph (including command outputs) is captured after each full execution cycle ("epoch"), allowing you to step back and forth through the history using a slider to observe how data flows and changes.
Note: for higher performance script instead of ollama, checkout my brutebench repo. it has a high throughput setup with ray serve.
- Python 3.x
- Flask: (
pip install Flask) - (Optional)
uv: A fast Python package installer and resolver (for the suggested run command). - (For Demo)
ollama: If you want to run the default demo graph, you need Ollama installed and running with the specified models (gemma3:1b,qwen2.5:1.5b,llama3.2:1b,llama3:1b). See ollama.com.
- Clone the repository:
git clone <your-repo-url> cd tokenbender
- Install dependencies:
- Using
pip:pip install Flask
- Using
- Start the Flask Server:
- Using
uv:(Note: Theuv run --with flask app.py
--with flaskmight be specific to how you've set upuvor project files. Ifapp.pydirectly imports Flask,uv run app.pymight suffice afteruv pip install Flask) OR If you just want to run the script directly after installing Flask:# Ensure Flask is installed: pip install Flask python app.py - This will start the server, typically on
http://127.0.0.1:5001.
- Using
NOTE: if you want to see the simple demo on mac, you can pass a --bootstrap flag.
To define your own workflow:
- Edit the
app.pyfile. - Modify the
bootstrap_graph()function.- Use
graph.add_node(<node_id>, "<your shell command>")to add command nodes. Node IDs can be strings or numbers. - Use
graph.add_edge(<source_node_id>, <target_node_id>)to define the data flow dependencies.
- Use
- Restart the Flask server.
Example: Simple Echo Workflow
def bootstrap_graph():
graph.add_node("A", "echo 'Hello from A'")
graph.add_node("B", "echo 'Input was:' - ; cat - ; echo 'End of B'") # Reads stdin
graph.add_node("C", "echo 'Input was:' - ; cat - ; echo 'End of C'") # Reads stdin
graph.add_node("D", "wc -c") # Reads stdin from B and C
graph.add_edge("A", "B")
graph.add_edge("A", "C")
graph.add_edge("B", "D")
graph.add_edge("C", "D")