This notebook implements a multi-agent system where specialized AI agents collaborate to analyze an uploaded Excel file. It is the original Gradio-based version of the multi-agent demo, designed around a single-button workflow: you upload your data, type your questions, click one button, and all four agents run in sequence.
How the agents work together:
Agent 1 (Data Architect) examines the uploaded Excel file and generates a logical database schema
Agent 2 (SQL Developer) converts that schema into SQLite tables and loads the data
Agent 3 (RAG Analyst) answers your questions using retrieval-augmented generation over the raw data
Agent 4 (Evaluator) compares the SQL-based and RAG-based answers and scores their similarity
This contrasts with the multi-input version (multi_agent_multi_human_db.ipynb), which separates the workflow into distinct steps with separate buttons for each phase. The single-input design is simpler to use but gives less visibility into intermediate results. Both versions demonstrate the same core concept: different AI agents can specialize in different tasks and hand off work to each other.
# 1. INSTALL DEPENDENCIES
!pip install -q gradio openai pandas chromadb openpyxl langchain-community langchain-openai git+https://github.com/KarAnalytics/llm_cascade.git sentence-transformersIGNORE THE ABOVE ERRORS AND PROCEED, the code will still execute. These errors are specific to google colab.
import os
import sqlite3
import pandas as pd
import gradio as gr
import chromadb
Setting Up the LLM and Database¶
We initialize the LLM cascade (which automatically finds whichever API key you have configured) and set up SQLite for structured queries and ChromaDB for vector-based retrieval. This dual-database approach is what makes the SQL-vs-RAG comparison possible: the same data lives in both a relational database and a vector store, and we can compare the answers each approach produces.
from llm_cascade import get_cascade
llm = get_cascade()
# --- GLOBAL STATE & DB CONFIG ---
DB_NAME = 'agent_database.db'
CHROMA_CLIENT = chromadb.Client()LLM Cascade - available providers:
+ Gemini model=gemini-2.5-flash
+ Ollama model=kimi-k2.5:cloud
+ Groq model=llama-3.3-70b-versatile
+ HuggingFace model=meta-llama/Llama-3.3-70B-Instruct
+ Cohere model=command-a-03-2025
+ OpenRouter model=meta-llama/llama-3.3-70b-instruct:free
+ OpenAI model=gpt-4o-mini
Not configured (skipped):
- Grok (xAI) (set XAI_API_KEY)
# --- AGENT LOGIC ---
def agent_1_ingest(file_path):
'''Data Ingestion & Logical Schema Identification'''
xl = pd.ExcelFile(file_path)
sheet_data = ''
data_map = {}
for sheet in xl.sheet_names:
df = pd.read_excel(file_path, sheet_name=sheet)
data_map[sheet] = df
cols = ', '.join([f'{col} ({dtype})' for col, dtype in zip(df.columns, df.dtypes)])
sheet_data += f'Sheet Name: {sheet}' + chr(10) + f'Columns detected: {cols}' + chr(10) + chr(10)
# Prompting for Bulleted Logical Schema ONLY
prompt = f'Analyze these sheets and provide a logical database schema. Use ONLY bullet points. Identify suggested Primary Keys and Foreign Keys:' + chr(10) + sheet_data
system_prompt = 'You are a Data Architect. Output a logical schema in bulleted text. Do NOT write SQL code.'
response = llm.generate(prompt, system_prompt=system_prompt)
return response.text, data_map
def agent_2_sql_developer(logical_schema, data_map):
'''SQL Developer Agent: Create & Populate'''
# 1. Generate DDL
prompt = f'Based on this logical schema, write SQLite CREATE TABLE statements:' + chr(10) + logical_schema
system_prompt = 'Return ONLY raw SQL CREATE TABLE statements. No explanation.'
response = llm.generate(prompt, system_prompt=system_prompt)
ddl_resp = response.text.replace('```sql', '').replace('```', '')
# 2. Execute DDL and Insert Data immediately
if os.path.exists(DB_NAME): os.remove(DB_NAME)
conn = sqlite3.connect(DB_NAME)
cursor = conn.cursor()
try:
cursor.executescript(ddl_resp)
# Match dataframes to newly created tables
for table, df in data_map.items():
# Basic cleanup: remove spaces from sheet names for SQL safety
clean_table_name = table.replace(' ', '_')
df.to_sql(clean_table_name, conn, if_exists='replace', index=False)
conn.commit()
status = 'Database Ready: Tables created and data inserted.'
except Exception as e:
status = f'Database Error: {str(e)}'
finally:
conn.close()
return ddl_resp, status
def process_queries(queries_text, logical_schema, data_map):
'''Handles multiple queries and runs Agent 2, 3, and 4 for each.'''
queries = [q.strip() for q in queries_text.split(chr(10)) if q.strip()]
results = []
conn = sqlite3.connect(DB_NAME)
for q in queries:
# Agent 2: SQL Approach
sql_gen_prompt = 'Schema:' + chr(10) + logical_schema + chr(10) + 'Query: ' + q + chr(10) + 'Generate ONLY the SQL SELECT statement. Table names might have underscores.'
response = llm.generate(sql_gen_prompt)
sql_query = response.text.replace('```sql', '').replace('```', '')
try:
sql_data = pd.read_sql_query(sql_query, conn).to_string()
except Exception as e:
sql_data = f'SQL Execution Error: {str(e)}'
# Agent 3: RAG Approach
context = chr(10).join(['Table ' + k + ':' + chr(10) + v.head(20).to_string() for k, v in data_map.items()])
rag_prompt = 'Data Context:' + chr(10) + context + chr(10) + 'User Question: ' + q + chr(10) + 'Answer the question based on the data provided.'
response = llm.generate(rag_prompt)
rag_res = response.text
# Agent 4: Similarity Scorer Only
eval_prompt = 'Compare these two answers and provide ONLY a Similarity Score (0-100%).' + chr(10) + 'Answer A: ' + sql_data + chr(10) + 'Answer B: ' + rag_res
system_prompt = 'You are a calculator. Output only a percentage score.'
response = llm.generate(eval_prompt, system_prompt=system_prompt)
score = response.text
results.append('QUERY: ' + q + chr(10) + 'SQL Result: ' + sql_data + chr(10) + 'RAG Result: ' + rag_res + chr(10) + 'SIMILARITY SCORE: ' + score + chr(10) + '-' * 40)
conn.close()
return chr(10).join(results)
# --- WORKFLOW CONTROLLER ---
def run_app(file, queries):
logical_schema, data_map = agent_1_ingest(file.name)
ddl, db_status = agent_2_sql_developer(logical_schema, data_map)
comparison_results = process_queries(queries, logical_schema, data_map)
return logical_schema, ddl, db_status, comparison_resultsThe Agent Functions¶
The code above defines the core logic for all four agents. Agent 1 reads the Excel file and asks the LLM to propose a database schema. Agent 2 takes that schema and generates DDL (CREATE TABLE statements), then loads the actual data. For each user query, Agent 2 also generates a SQL SELECT statement, Agent 3 answers the same question using RAG over the raw data, and Agent 4 scores how similar the two answers are. This pipeline runs end-to-end with a single function call -- the orchestration is handled by the run_app wrapper.
# --- GRADIO UI ---
with gr.Blocks(theme=gr.themes.Monochrome()) as demo:
gr.Markdown("# 🤖 Agentic SQL vs. RAG Comparison")
with gr.Row():
file_input = gr.File(label="Upload Excel File")
query_input = gr.Textbox(label="Business Queries (One per line)", lines=5,
placeholder="How many sales in North?\nWho is the top employee?")
run_btn = gr.Button("🚀 Process All Agents", variant="primary")
with gr.Tabs():
with gr.TabItem("Data Architecture (Agent 1 & 2)"):
out_schema = gr.Markdown(label="Logical Schema (Agent 1)")
out_ddl = gr.Code(label="Generated DDL (Agent 2)", language="sql")
out_status = gr.Textbox(label="DB Population Status")
with gr.TabItem("Comparative Results (Agent 2, 3 & 4)"):
out_comparison = gr.Textbox(label="The Showdown Results", lines=20)
run_btn.click(
run_app,
inputs=[file_input, query_input],
outputs=[out_schema, out_ddl, out_status, out_comparison]
)
demo.launch()/tmp/ipykernel_6238/297498658.py:2: DeprecationWarning: The 'theme' parameter in the Blocks constructor will be removed in Gradio 6.0. You will need to pass 'theme' to Blocks.launch() instead.
with gr.Blocks(theme=gr.themes.Monochrome()) as demo:
It looks like you are running Gradio on a hosted Jupyter notebook, which requires `share=True`. Automatically setting `share=True` (you can turn this off by setting `share=False` in `launch()` explicitly).
Colab notebook detected. To show errors in colab notebook, set debug=True in launch()
* Running on public URL: https://3fc4aa289497fecaa4.gradio.live
This share link expires in 1 week. For free permanent hosting and GPU upgrades, run `gradio deploy` from the terminal in the working directory to deploy to Hugging Face Spaces (https://huggingface.co/spaces)
The Gradio Interface¶
The Gradio UI provides a simple two-input interface: upload an Excel file on the left, type your business questions (one per line) on the right, and click the Process button. Results appear in two tabs -- one showing the schema and DDL from Agents 1 and 2, the other showing the side-by-side SQL vs. RAG comparison from Agents 3 and 4. If you do not have an Excel file on hand, download this sample dataset and upload it: SUPPLIER_PARTS.xlsx (click Download raw file on the GitHub page). When running in Google Colab, Gradio automatically creates a public share link so you can access the interface from any browser.
Key takeaways¶
Specialized agents with distinct system prompts (Architect, SQL Developer, RAG Analyst, Evaluator) can be chained into a single end-to-end pipeline.
Dual-path answering -- the same question is answered via SQL and via RAG -- surfaces disagreements that a single approach would silently hide.
An evaluator agent that scores similarity between the two answers is a cheap, LLM-based form of cross-validation you can add to any pipeline.
Single-input UX trades visibility for simplicity: one click runs every agent, but you see less of what happens between them than in a stepwise interface.
SQLite plus ChromaDB side by side gives a clean substrate for comparing structured retrieval against semantic retrieval over the same dataset.
Run the code¶
To run this notebook, copy the URL below into your browser’s address bar. The link opens the notebook directly in Google Colab. (If your PDF viewer makes the URL clickable and lands on a broken page, copy the full text manually -- the viewer may have truncated the link at a line break.)
https://colab.research.google.com/github/KarAnalytics/code_demos/blob/main/MultiAgent_DB_single_human_input.ipynb