跪拜 Guibai
← Back to the summary

A BI Developer Bolted a Natural-Language AI Assistant Onto SmartBI in One Day Without Writing a Single Line of Frontend Code

Done! No frontend skills, spent one day installing an AI agent on the company's BI system!

As a BI/data developer, I've always had a pain point: business people have to come to me every time they need data, asking me to write SQL and drag reports. Simple questions like sales amounts and regional sales volumes get repeated dozens of times a day. I've always wanted to add a natural language data query AI assistant to the company's SmartBI system, but the thought of writing a frontend chat interface, doing backend APIs, handling server deployment, and dealing with cross-origin authentication always felt like too much trouble, so I put it off for over half a year.

Until I recently discovered EdgeOne Makers. From registering an account to getting it running locally, and then embedding a floating window into SmartBI, it took a total of one day. I didn't write a single line of frontend code and got the AI agent installed. This article lays out the complete steps and all the pitfalls I encountered; you can follow along and succeed too.


I want to share this case because from start to finish, I was just copying and pasting, and basically, AI helped me check and correct errors. The moment I finally got the agent working successfully, my scalp tingled. EdgeOne Makers is just too good!!!

Let's first look at the final effect~

1. Complete Implementation Steps from Zero to One (Follow Along and You'll Succeed)

Preparation


Step 1: Create an EdgeOne Makers Project

  1. Open the EdgeOne Makers console: https://edgeone.cloud.tencent.com/makers

image.png 2. Create a new project and select the 'OpenAI Agents Starter Template (Python version)'

  1. Choose a git platform; I chose Gitee here, then click 'Create Now'.

  1. Wait 1 minute, and the project is initialized. It comes with a chat interface, session memory, streaming output, and a tool-calling framework. No need to write your own frontend.


Step 2: Set Up the Local Development Environment

  1. First, install the EdgeOne CLI tool:
npm install -g edgeone
  1. Pull the project locally and enter the project directory.

  1. Install dependencies:
npm install
  1. Windows users must set the encoding first (otherwise, emojis will cause a GBK encoding error later):
set PYTHONUTF8=1
  1. Start the local development service:
edgeone makers dev
  1. After a successful start, open http://localhost:8088 to see the default chat interface, which comes with sample tools like weather and translation. The startup is slow; wait until you see 'running at xxx'.


Step 3: Configure SmartBI Environment Variables

Create a .env file in the project root directory and configure the SmartBI connection information:

# AI Gateway Configuration (auto-generated after project creation, no need to change)
AI_GATEWAY_API_KEY=your_API_KEY
AI_GATEWAY_BASE_URL=your_gateway_address
AI_GATEWAY_MODEL=@makers/deepseek-v4-flash

# SmartBI Configuration
SMARTBI_BASE_URL=http://your_SmartBI_address:port/smartbi
SMARTBI_TOKEN=your_SmartBI_personal_access_token
PYTHONUTF8=1

Generate the SmartBI personal access token in 'Personal Center - Personal Access Token'; query permissions are sufficient. ⬇️⬇️⬇️


In the data model section, add a test dataset for subsequent agent testing.

-- Sales test data (Oracle version, UNION ALL constructs a temporary dataset, all fields in Chinese)
SELECT 
    "Order Date",
    "Order Number",
    "Region",
    "Province",
    "City",
    "Product Category",
    "Product Name",
    "Sales Quantity",
    "Unit Price",
    "Sales Amount",
    "Profit",
    "Customer Type",
    "Sales Channel",
    "Salesperson"
FROM (
    -- January Sales Data
    SELECT DATE '2026-01-05' AS "Order Date", 'DD20260105001' AS "Order Number", 'East China' AS "Region", 'Jiangsu' AS "Province", 'Nanjing' AS "City",
           'Fish Products' AS "Product Category", 'Spicy Small Dried Fish' AS "Product Name", 120 AS "Sales Quantity", 3.5 AS "Unit Price",
           420.00 AS "Sales Amount", 126.00 AS "Profit", 'Old Customer' AS "Customer Type", 'Distributor' AS "Sales Channel", 'Zhang San' AS "Salesperson" from dual 
    UNION ALL
    SELECT DATE '2026-01-08', 'DD20260108001', 'South China', 'Guangdong', 'Guangzhou',
           'Bean Products', 'Saucy Thick Dried Tofu', 200, 2.8, 560.00, 156.80, 'New Customer', 'Online', 'Li Si' from dual 
    UNION ALL
    SELECT DATE '2026-01-12', 'DD20260112001', 'North China', 'Beijing', 'Beijing',
           'Meat Snacks', 'Spicy Dried Meat', 80, 5.0, 400.00, 120.00, 'Old Customer', 'Offline', 'Wang Wu' from dual 
    UNION ALL
    SELECT DATE '2026-01-15', 'DD20260115001', 'Southwest', 'Sichuan', 'Chengdu',
           'Vegetarian Snacks', 'Konjac Shuang', 150, 2.5, 375.00, 105.00, 'Old Customer', 'Distributor', 'Zhao Liu' from dual 
    UNION ALL
    SELECT DATE '2026-01-20', 'DD20260120001', 'Central China', 'Hunan', 'Changsha',
           'Fish Products', 'Braised Small Dried Fish', 300, 3.5, 1050.00, 315.00, 'New Customer', 'Online', 'Zhang San' from dual 

    -- February Sales Data
    UNION ALL
    SELECT DATE '2026-02-03', 'DD20260203001', 'East China', 'Shanghai', 'Shanghai',
           'Meat Snacks', 'Five-Spice Dried Meat', 100, 5.0, 500.00, 150.00, 'Old Customer', 'Offline', 'Li Si' from dual 
    UNION ALL
    SELECT DATE '2026-02-07', 'DD20260207001', 'South China', 'Guangdong', 'Shenzhen',
           'Fish Products', 'Sweet and Sour Small Dried Fish', 180, 3.5, 630.00, 189.00, 'Old Customer', 'Online', 'Wang Wu' from dual 
    UNION ALL
    SELECT DATE '2026-02-12', 'DD20260212001', 'North China', 'Shandong', 'Jinan',
           'Bean Products', 'Spicy Thick Dried Tofu', 250, 2.8, 700.00, 196.00, 'New Customer', 'Distributor', 'Zhao Liu' from dual 
    UNION ALL
    SELECT DATE '2026-02-18', 'DD20260218001', 'Southwest', 'Chongqing', 'Chongqing',
           'Vegetarian Snacks', 'Sour and Spicy Kelp Knots', 160, 2.0, 320.00, 89.60, 'Old Customer', 'Online', 'Zhang San' from dual 
    UNION ALL
    SELECT DATE '2026-02-25', 'DD20260225001', 'Central China', 'Hubei', 'Wuhan',
           'Fish Products', 'Spicy Small Dried Fish', 220, 3.5, 770.00, 231.00, 'Old Customer', 'Offline', 'Li Si' from dual 

    -- March Sales Data
    UNION ALL
    SELECT DATE '2026-03-02', 'DD20260302001', 'East China', 'Zhejiang', 'Hangzhou',
           'Vegetarian Snacks', 'Spicy Konjac Shuang', 140, 2.5, 350.00, 98.00, 'New Customer', 'Online', 'Wang Wu' from dual 
    UNION ALL
    SELECT DATE '2026-03-09', 'DD20260309001', 'South China', 'Fujian', 'Fuzhou',
           'Meat Snacks', 'Shredded Dried Meat', 90, 6.0, 540.00, 162.00, 'Old Customer', 'Distributor', 'Zhao Liu' from dual 
    UNION ALL
    SELECT DATE '2026-03-15', 'DD20260315001', 'North China', 'Tianjin', 'Tianjin',
           'Bean Products', 'Pickled Pepper Dried Tofu', 170, 2.8, 476.00, 133.28, 'Old Customer', 'Offline', 'Zhang San' from dual 
    UNION ALL
    SELECT DATE '2026-03-20', 'DD20260320001', 'Southwest', 'Yunnan', 'Kunming',
           'Fish Products', 'Braised Small Dried Fish', 110, 3.5, 385.00, 115.50, 'New Customer', 'Online', 'Li Si' from dual 
    UNION ALL
    SELECT DATE '2026-03-28', 'DD20260328001', 'Central China', 'Henan', 'Zhengzhou',
           'Vegetarian Snacks', 'Crispy Lotus Root Slices', 200, 2.2, 440.00, 123.20, 'Old Customer', 'Distributor', 'Wang Wu' from dual 

    -- April Sales Data
    UNION ALL
    SELECT DATE '2026-04-04', 'DD20260404001', 'East China', 'Jiangsu', 'Suzhou',
           'Fish Products', 'Spicy Small Dried Fish', 280, 3.5, 980.00, 294.00, 'Old Customer', 'Online', 'Zhao Liu' from dual 
    UNION ALL
    SELECT DATE '2026-04-10', 'DD20260410001', 'South China', 'Guangdong', 'Dongguan',
           'Meat Snacks', 'Spicy Dried Meat', 130, 5.0, 650.00, 195.00, 'New Customer', 'Offline', 'Zhang San' from dual 
    UNION ALL
    SELECT DATE '2026-04-16', 'DD20260416001', 'North China', 'Hebei', 'Shijiazhuang',
           'Bean Products', 'Five-Spice Dried Tofu', 210, 2.8, 588.00, 164.64, 'Old Customer', 'Distributor', 'Li Si' from dual 
    UNION ALL
    SELECT DATE '2026-04-22', 'DD20260422001', 'Southwest', 'Sichuan', 'Chengdu',
           'Fish Products', 'Sweet and Sour Small Dried Fish', 190, 3.5, 665.00, 199.50, 'Old Customer', 'Online', 'Wang Wu' from dual 
    UNION ALL
    SELECT DATE '2026-04-29', 'DD20260429001', 'Central China', 'Hunan', 'Changsha',
           'Vegetarian Snacks', 'Konjac Shuang', 320, 2.5, 800.00, 224.00, 'New Customer', 'Offline', 'Zhao Liu' from dual 

    -- May Sales Data
    UNION ALL
    SELECT DATE '2026-05-05', 'DD20260505001', 'East China', 'Shanghai', 'Shanghai',
           'Meat Snacks', 'Shredded Dried Meat', 150, 6.0, 900.00, 270.00, 'Old Customer', 'Online', 'Zhang San' from dual 
    UNION ALL
    SELECT DATE '2026-05-11', 'DD20260511001', 'South China', 'Guangxi', 'Nanning',
           'Fish Products', 'Spicy Small Dried Fish', 160, 3.5, 560.00, 168.00, 'New Customer', 'Distributor', 'Li Si' from dual 
    UNION ALL
    SELECT DATE '2026-05-18', 'DD20260518001', 'North China', 'Beijing', 'Beijing',
           'Vegetarian Snacks', 'Sour and Spicy Kelp Knots', 240, 2.0, 480.00, 134.40, 'Old Customer', 'Offline', 'Wang Wu' from dual 
    UNION ALL
    SELECT DATE '2026-05-23', 'DD20260523001', 'Southwest', 'Guizhou', 'Guiyang',
           'Bean Products', 'Saucy Thick Dried Tofu', 130, 2.8, 364.00, 101.92, 'Old Customer', 'Online', 'Zhao Liu' from dual 
    UNION ALL
    SELECT DATE '2026-05-30', 'DD20260530001', 'Central China', 'Jiangxi', 'Nanchang',
           'Fish Products', 'Braised Small Dried Fish', 170, 3.5, 595.00, 178.50, 'New Customer', 'Distributor', 'Zhang San' from dual 

    -- June Sales Data
    UNION ALL
    SELECT DATE '2026-06-03', 'DD20260603001', 'East China', 'Zhejiang', 'Ningbo',
           'Fish Products', 'Spicy Small Dried Fish', 260, 3.5, 910.00, 273.00, 'Old Customer', 'Offline', 'Li Si' from dual 
    UNION ALL
    SELECT DATE '2026-06-08', 'DD20260608001', 'South China', 'Guangdong', 'Guangzhou',
           'Meat Snacks', 'Five-Spice Dried Meat', 140, 5.0, 700.00, 210.00, 'Old Customer', 'Online', 'Wang Wu' from dual 
    UNION ALL
    SELECT DATE '2026-06-15', 'DD20260615001', 'North China', 'Shandong', 'Qingdao',
           'Vegetarian Snacks', 'Crispy Lotus Root Slices', 200, 2.2, 440.00, 123.20, 'New Customer', 'Distributor', 'Zhao Liu' from dual 
    UNION ALL
    SELECT DATE '2026-06-21', 'DD20260621001', 'Southwest', 'Chongqing', 'Chongqing',
           'Bean Products', 'Spicy Thick Dried Tofu', 280, 2.8, 784.00, 219.52, 'Old Customer', 'Online', 'Zhang San' from dual 
    UNION ALL
    SELECT DATE '2026-06-28', 'DD20260628001', 'Central China', 'Hubei', 'Wuhan',
           'Fish Products', 'Spicy Small Dried Fish', 350, 3.5, 1225.00, 367.50, 'Old Customer', 'Offline', 'Li Si' from dual 
) t

Right-click the dataset to view its properties; you can see the dataset ID, which will be used later.

Step 4: Write the SmartBI Query Tool

Create a smartbi_tool.py file in the agents/chat/ directory. This is the core tool file; only two tools are needed:

import os
import json
import requests
from agents import function_tool
from typing import Annotated

SMARTBI_BASE_URL = os.getenv("SMARTBI_BASE_URL", "")
SMARTBI_TOKEN = os.getenv("SMARTBI_TOKEN", "")

def _get_headers():
    return {
        "Authorization": f"Bearer {SMARTBI_TOKEN}",
        "Content-Type": "application/json"
    }

# Tool 1: Get a list of all datasets
@function_tool
def list_datasets() -> str:
    """Get a list of all available datasets/data models in SmartBI"""
    if not SMARTBI_TOKEN or not SMARTBI_BASE_URL:
        return "Error: Environment variables not configured"
    url = f"{SMARTBI_BASE_URL}/api/catalog/getCatalogElement/DEFAULT_TREENODE"
    try:
        resp = requests.post(url, headers=_get_headers(), timeout=30)
        if resp.status_code != 200:
            return f"Failed to get catalog, HTTP {resp.status_code}"
        return json.dumps(resp.json(), ensure_ascii=False, indent=2)[:3000]
    except Exception as e:
        return f"Exception getting catalog: {str(e)}"

# Tool 2: Query data
@function_tool
def query_dataset(
    dataset_id: Annotated[str, "Dataset ID"],
    fields: Annotated[str, "Fields to query, separated by English commas, use Chinese names, e.g., Order Date, Region, Sales Amount"],
    limit: Annotated[int, "Number of rows to return, default 20"] = 20
) -> str:
    """Query data from a specified dataset, using Chinese field names"""
    if not SMARTBI_TOKEN or not SMARTBI_BASE_URL:
        return "Error: Environment variables not configured"
    safe_limit = min(limit, 100)
    field_list = [f.strip() for f in fields.split(",") if f.strip()]
    url = f"{SMARTBI_BASE_URL}/smartbix/api/augmentedQuery/data/"
    payload = {
        "dataSetId": dataset_id,
        "rows": field_list,
        "columns": [],
        "filters": []
    }
    try:
        resp = requests.post(url, json=payload, headers=_get_headers(), timeout=30)
        if resp.status_code != 200:
            return f"Query failed, HTTP {resp.status_code}: {resp.text[:500]}"
        data = resp.json()
        iterator = data.get("iterator", [])
        result = []
        for row in iterator[:safe_limit]:
            obj = {}
            for idx, cell in enumerate(row):
                field_name = field_list[idx] if idx < len(field_list) else f"field_{idx}"
                obj[field_name] = cell.get("displayValue") or cell.get("value")
            result.append(obj)
        return json.dumps({
            "success": True,
            "total": len(iterator),
            "returned": len(result),
            "data": result
        }, ensure_ascii=False, indent=2)
    except Exception as e:
        return f"Query exception: {str(e)}"

TOOLS = [list_datasets, query_dataset]

Step 5: Configure the Agent

Modify agents/chat/index.py to register the tools we wrote and configure the prompt:

# Keep other imports unchanged, add the tool import
from .smartbi_tool import TOOLS as smartbi_tools

agent = Agent(
    name="SmartBI Data Assistant",
    instructions="""
You are a SmartBI data query assistant, helping users query data in the SmartBI system.

Workflow:
1. When a user asks a data-related question, first call list_datasets to see all available datasets.
2. After finding the corresponding dataset, directly call query_dataset to query the data.
3. Use Chinese for field names. Common fields include: Order Date, Order Number, Region, Province, City, Category, Product Name, Quantity, Unit Price, Sales Amount, Profit, Customer Type, Channel, Salesperson.
4. After a successful query, perform simple summary statistics on the data and return the results in natural language.

Notes:
- Do not call get_dataset_schema; query directly using Chinese field names.
- If a query fails, try again with a few other common fields.
- Bold key numbers.
""",
    # Add our tools
    tools=[get_weather, get_clothing_advice, translate_text, text_statistics] + smartbi_tools,
    model=llm_model,
)

The other SSE streaming output code doesn't need to be changed; the template has already written it.


Step 6: Configure iframe Cross-Origin

Because the chat interface needs to be embedded into SmartBI via iframe, modify vite.config.ts to allow cross-origin and iframe embedding:

import { defineConfig } from 'vite'

export default defineConfig({
  server: {
    port: 8088,
    host: '0.0.0.0',
    headers: {
      'X-Frame-Options': 'ALLOWALL',
      'Content-Security-Policy': "frame-ancestors 'self' http://your_SmartBI_address:* http://localhost:*"
    },
    cors: true
  }
})

Also modify index.html, adding a crypto polyfill at the very beginning of the head to be compatible with HTTP intranet environments:

<script>
if (!window.crypto) window.crypto = {};
if (!window.crypto.randomUUID) {
  window.crypto.randomUUID = function() {
    return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, function(c) {
      var r = Math.random() * 16 | 0, v = c == 'x' ? r : (r & 0x3 | 0x8);
      return v.toString(16);
    });
  };
}
</script>

Step 7: Write the Floating Window Injection Script (No Need to Modify SmartBI Source Code)

The most convenient embedding method is a bookmarklet. No need to modify any SmartBI code, no need to install Tampermonkey. Just click a bookmark to bring up the floating window: (I'll explain why this method was chosen later; actually, the best way is to write the project code into SmartBI's index page.)

  1. Right-click on the browser's bookmark bar -> Add page

  1. Name: AI Data Assistant
  2. Paste the following complete code into the URL field (supports drag-to-resize from the top-left corner):
javascript:(function(){if(window.__aiAssistantLoaded)return;window.__aiAssistantLoaded=true;const AGENT_URL="http://your_local_IP:8088";let isOpen=false;let isResizing=false;let startX,startY,startW,startH;const btn=document.createElement('div');btn.innerHTML='💬 AI Data Assistant';btn.style.cssText='position:fixed;right:20px;bottom:20px;width:120px;height:44px;background:linear-gradient(135deg,#1677ff 0%,#722ed1 100%);color:white;border-radius:22px;display:flex;align-items:center;justify-content:center;cursor:pointer;box-shadow:0 4px 16px rgba(22,119,255,0.4);z-index:999999;font-size:14px;font-weight:500;transition:all 0.3s;user-select:none;';const chatWindow=document.createElement('div');chatWindow.style.cssText='position:fixed;right:20px;bottom:76px;width:480px;height:680px;min-width:360px;min-height:480px;max-width:90vw;max-height:90vh;background:white;border-radius:12px;box-shadow:0 8px 32px rgba(0,0,0,0.18);display:none;flex-direction:column;z-index:999998;overflow:hidden;';const resizeHandle=document.createElement('div');resizeHandle.style.cssText='position:absolute;left:0;top:0;width:20px;height:20px;cursor:nesw-resize;z-index:999999;background:linear-gradient(225deg,rgba(114,46,209,0.4) 0%,transparent 60%);border-radius:12px 0 0 0;';const header=document.createElement('div');header.style.cssText='padding:14px 16px;background:linear-gradient(135deg,#1677ff 0%,#722ed1 100%);display:flex;justify-content:space-between;align-items:center;flex-shrink:0;position:relative;z-index:5;padding-left:28px;';header.innerHTML='<span style="font-weight:600;color:white;font-size:15px;">💬 AI Data Assistant</span><span class="ai-close-btn" style="cursor:pointer;color:rgba(255,255,255,0.8);font-size:18px;width:28px;height:28px;display:flex;align-items:center;justify-content:center;border-radius:6px;transition:background 0.2s;">✕</span>';const iframeWrap=document.createElement('div');iframeWrap.style.cssText='flex:1;position:relative;overflow:hidden;';const iframe=document.createElement('iframe');iframe.src=AGENT_URL;iframe.style.cssText='width:100%;height:100%;border:none;';iframe.allow='clipboard-write';const dragMask=document.createElement('div');dragMask.style.cssText='position:absolute;top:0;left:0;width:100%;height:100%;background:transparent;z-index:10;display:none;';iframeWrap.appendChild(iframe);iframeWrap.appendChild(dragMask);chatWindow.appendChild(resizeHandle);chatWindow.appendChild(header);chatWindow.appendChild(iframeWrap);document.body.appendChild(btn);document.body.appendChild(chatWindow);btn.onclick=()=>{isOpen=!isOpen;chatWindow.style.display=isOpen?'flex':'none';};const closeBtn=header.querySelector('.ai-close-btn');closeBtn.onmouseenter=()=>closeBtn.style.background='rgba(255,255,255,0.2)';closeBtn.onmouseleave=()=>closeBtn.style.background='transparent';closeBtn.onclick=(e)=>{e.stopPropagation();isOpen=false;chatWindow.style.display='none';};btn.onmouseenter=()=>{btn.style.transform='scale(1.05)';btn.style.boxShadow='0 6px 20px rgba(22,119,255,0.5)';};btn.onmouseleave=()=>{btn.style.transform='scale(1)';btn.style.boxShadow='0 4px 16px rgba(22,119,255,0.4)';};resizeHandle.addEventListener('mousedown',(e)=>{e.preventDefault();e.stopPropagation();isResizing=true;startX=e.clientX;startY=e.clientY;startW=chatWindow.offsetWidth;startH=chatWindow.offsetHeight;dragMask.style.display='block';document.body.style.cursor='nesw-resize';document.body.style.userSelect='none';});document.addEventListener('mousemove',(e)=>{if(!isResizing)return;const dx=e.clientX-startX;const dy=e.clientY-startY;let newW=startW-dx;let newH=startH-dy;newW=Math.max(360,Math.min(newW,window.innerWidth*0.9));newH=Math.max(480,Math.min(newH,window.innerHeight*0.9));chatWindow.style.width=newW+'px';chatWindow.style.height=newH+'px';});document.addEventListener('mouseup',()=>{if(isResizing){isResizing=false;dragMask.style.display='none';document.body.style.cursor='';document.body.style.userSelect='';}});})();

Before opening the AI assistant, the interface looks like this:

After clicking the bookmark to open it, it looks like this:

Step 8: Test & Go Live

  1. Restart the local service and open the SmartBI page.
  2. Click the 'AI Data Assistant' in the bookmark bar, and a floating button will appear in the bottom right corner.
  3. Click to open it and start chatting. Ask things like 'What is the total sales amount?' or 'Which region sold the best?'. The AI will automatically call the tools to query the data.

  1. After local testing is fine, deploy online with one click:
edgeone makers deploy
  1. Wait 1 minute for deployment to complete. You'll get a public URL. Replace the local IP in the bookmark with the public URL, and the whole company can use it.

2. Pitfall Log (Don't Step on the Ones I Did)

1. Windows GBK Encoding Error

2. Module Import Path Error

3. Dataset ID Pitfall

4. Field Name Pitfall

5. Metadata Interface 404

6. iframe Blocked by X-Frame-Options

7. crypto.randomUUID Error in HTTP Environment

8. Tampermonkey Script Blocked by CSP

9. CSS resize Not Working

10. Tool Parameter Type Pitfall


3. Future Optimization Plans

The tool is up and running, but it's currently just a minimum viable version. There's room for further optimization. What I can think of so far includes:

  1. Full Dynamic Dataset Support: Optimize the recursive logic of list_datasets to automatically identify all dozens of datasets. The AI would automatically match user questions to the corresponding dataset, eliminating hardcoding.
  2. Advanced Query Capabilities: Support for filter conditions, grouping and aggregation, time filtering, and year-over-year/month-over-month calculations to answer more complex business questions.
  3. Automatic Chart Generation: After querying data, automatically generate bar charts, line charts, and pie charts, eliminating the need to create reports manually.
  4. User Permission Passthrough: Obtain the identity of the currently logged-in SmartBI user and query data with corresponding permissions for data permission isolation.
  5. Formal Integration: Develop it as a SmartBI extension package that loads automatically upon login, removing the need to manually click a bookmark.
  6. Intelligent Q&A Optimization: Support for multi-turn conversations, context memory, and follow-up questions. For example, after asking about the best region, being able to ask 'Which product sold best in that region?' without repeating conditions.

4. Some Thoughts

EdgeOne Makers Has Really Lowered the Development Barrier

In the past, making an AI assistant like this would have required me to:

Altogether, it would have taken at least 3 days, not counting various environmental issues.

But with EdgeOne Makers, the frontend chat interface, session memory, streaming output, tool-calling framework, deployment, and HTTPS domain are all done for you. I only needed to write the core SmartBI query tool and tune the prompt. It was done in one day, and the free tier is sufficient for a small team. It really frees developers from repetitive infrastructure work.

AI is Changing How We Work

Before, when building a feature, we'd spend 80% of our time on 'scaffolding': writing interfaces, doing APIs, deploying, and configuring environments. Only 20% of the time was spent on actually solving business problems. Now, with AI Agent frameworks + low-code platforms, 80% of the scaffolding is done for you. We only need to focus on that 20% of core business logic.

In the future, every system will have its own AI assistant. No need to learn complex operations or memorize function menus; natural language will be the interface. Business people can ask questions directly without waiting for data developers to schedule report creation. Data developers can also be freed from repetitive data retrieval tasks to do more valuable data construction work.

I used to think AI would replace programmers. Now I realize it's not replacement, but multiplication — a programmer who knows how to use AI tools can single-handedly match the output of a small team from before. For this BI assistant, I, a backend developer, didn't write a single line of frontend code and built it in one day. That was unthinkable before. Now, when business colleagues need simple data, they don't have to ping me on DingTalk to schedule it. They just open BI, click a bookmark, and ask, 'What is the total sales amount for fish products in East China in June?' The result comes out in seconds with automatic summaries. Yesterday, after an operations colleague used it, they chased me down asking how to do it, saying they wanted to set one up for their backend too 😂


If you also want to add an AI assistant to your company's system, definitely give EdgeOne Makers a try. You can build your own AI application at zero cost; the barrier is much lower than you think.

After all, for data folks, writing fewer repetitive SQL queries for data retrieval and leaving more time for slacking off is the real deal 😎 This article has laid out all the pitfalls I stepped on and the complete, runnable code. If you follow the steps, you'll definitely be able to install an AI assistant for your company's system too.

If you find this useful, don't forget to like 👍, bookmark ⭐, and forward. If you have any questions or encounter new pitfalls, leave a comment and I'll reply~ Also, everyone is welcome to try EdgeOne Makers. There are ready-made examples now; building your own little AI tool at zero cost is really sweet.

🎊 The end, thanks for reading this far~ 🎊

First published at: https://cloud.tencent.com/developer/article/2701802?shareByChannel=link Comments and forwards are welcome!