1. 需求背景与适用场景
1.1 需求背景
Smartbi AIChat 提供了多种使用方式,供用户自由选择。如果常用PC端,我们有基于PC浏览器的AIWeb页面;如果常用手机,我们有基于手机的App或者使用手机浏览器访问的AIChatView页面;我们还提供了基于钉钉、企微、飞书等IM的使用页面。
但是,这些都是Smartbi AIChat平台内置的使用页面,页面样式和操作方式是基于产品内置好的。如果用户想把自然语言查询集成到用户自己的APP里面,或者集成到用户其他的平台里面,我们内置的页面样式可能不太符合用户的要求,集成起来就不自然。
为了让用户在使用Smartbi自然语言查询的时候,可以自定义前端页面,我们提供了基于Java语言实现的RestFul API接口。本文主要就是介绍如何使用Smartbi AIChat的接口实现自己的前端页面。提供了多种使用方式,供用户自由选择。如果常用PC端,我们有基于PC浏览器的AIWeb页面;如果常用手机,我们有基于手机的App或者使用手机浏览器访问的AIChatView页面;我们还提供了基于钉钉、企微、飞书等IM的使用页面。但是,这些都是AIChat平台内置页面,页面样式和操作方式是基于产品内置好的。如果要把AIChat集成到客户自己的APP里,或者集成到其他平台中,Smartbi AIChat内置页面样式可能不符合要求。 为了让客户在使用AIChat的时候可以自定义前端页面,我们提供了 Restfull API 接口。本文主要就是介绍如何使用 AIChat 接口实现客户自己的前端页面。
1.2 适用场景2 适用场景
使用Smartbi AIChat 提供的API适合以下场景开发:提供的API适合以下应用场景的开发:
- 觉得Smartbi内置的对话界面不好看,可以使用Smartbi扩展包机制重新开发使用界面觉得Smartbi AIChat内置对话界面不好看,可以使用Smartbi扩展包机制重新开发使用界面。
- 需要将对话嵌入到集团内部APP中,可以定制Android/IOS原生界面,或者嵌入自定义H5页面IOS原生界面,或者嵌入自定义H5页面。
- 需要嵌入到其他的Web平台中,可以定制H5页面需要嵌入到其他的Web平台中,可以定制H5页面。
- 需要嵌入其聊天工具中(如:钉钉、微信等),可以定制符合聊天工具要求的页面需要嵌入其聊天工具中(如钉钉、企业微信、飞书等),可以定制符合聊天工具要求的页面。
- 其他使用场景,可以咨询Smartbi客服团队,获取支持其他使用场景,可以咨询Smartbi客服团队,获取支持。
2.
...
【用户自定义对话界面-逻辑架构图】
说明:
- 用户自定义界面,可以脱离Smartbi,嵌入在第三方平台里面,包括:
- 第三方Web应用
- 第三方Android应用
- 第三方IOS应用
如果是Web页面,推荐使用Smartbi扩展包方式开发集成页面。这样可以避免跨域问题。如果需要在第三方应用中开发,需要做对所有API做服务端转发。
3. API说明
Smartbi AIChat二次开发,提供的是标准Restful API。只需要登录后,执行查询就可以了。所以,只需要2个API就可以完成需要的操作。
示例代码请参考:DemoCodeDemoCode
4.接口说明
4.1 登录AIChat
4.1.1 接口说明
...
...
值
...
技术架构
用户自定义对话界面的逻辑架构图如下。
- 用户自定义界面,可以脱离Smartbi AIChat,嵌入在第三方平台里面,包括:
- 第三方Web应用。
- 第三方Android应用。
- 第三方IOS应用。
- 如果第三方系统也是Web页面,推荐使用Smartbi扩展包方式开发集成页面,这样可以避免跨域问题。如果需要在第三方非Web应用中开发,需要对所有API做服务端转发。
3. 界面集成
可以把 Smartbi AIChat 对话界面,整体集成嵌入到第三方系统中。
值 | |
---|---|
URL路径 | http:// |
Smartbi-server:port/smartbi/ |
vision/aichat/ |
proxy/ |
#/ |
请求方式
POST
请求参数
userName
password
smartbiServer
casLoginUrl
loginMethod
4.1.2 接口参数说明
URL参数名
说明
是否必填
输入参数
userName
登录账号
必填
password
登录密码
必填
smartbiServer
Smartbi服务器地址;该AIChat服务器第一次登录Smartbi,必填;以后选填;不填则使用之前已经登录过的Smartbi服务器
选填
casLoginUrl
如果Smartbi是使用CAS登录方式,则需要填入该值;该AIChat服务器第一次登录Smartbi,必填;以后选填;不填则使用之前已经登录过的Cas认证服务器
选填
loginMethod
使用的登录方法;枚举值
login
loginWithCas
普通登录使用login;如果是Cas登录则使用loginWithCas
默认情况下都可以不填GET请求 示例:http://10.10.35.110:9070/smartbi/vision/aichat/proxy/#/ | |
集成说明 | 本地址必须登录后再使用。可以跳过登录步骤,直接打开v3的界面。 |
参数 | 无 |
4. API 接口说明
AIChat 提供的是标准 Restfull API 接口,登录后直接调用就可以了,在最简单情况下只需要两步就可以完成需要的操作。
示例代码请参考: DemoCodeDemoCode 、 示例程序下载 锚 _AIChat_Login_Method _AIChat_Login_Method
4.1 登录AIChat
- 接口说明
名称 | 值 |
---|---|
请求地址 | http://Smartbi-AIChat-server:port/aiweb/api/v1/login |
请求方式 | POST |
请求参数 | userName password smartbiServer casLoginUrl loginMethod |
- 接口参数说明
URL参数名 | 说明 | 是否必填 | |
---|---|---|---|
输入参数 | userName | 登录账号 | 必填 |
password | 登录密码 | 必填 | |
smartbiServer | Smartbi服务器地址。该AIChat服务器第一次登录Smartbi,必填;以后选填;不填则使用之前已经登录过的Smartbi服务器。 | 选填 | |
casLoginUrl | 如果Smartbi是使用CAS登录方式,则需要填入该值;该AIChat服务器第一次登录Smartbi,必填;以后选填;不填则使用之前已经登录过的CAS认证服务器。 | 选填 | |
loginMethod | 使用的登录方法,枚举值。普通登录使用login;如果是CAS登录则使用loginWithCas,默认情况下都可以不填。
| 选填 | |
返回值 | { |
...
- 接口返回值说明
返回参数名 | 返回值说明 |
---|---|
code | 接口调用是否成功;0 - |
表示成功;负数为错误码。 | |
message | 错误描述,code=0 |
时,该内容为空。 |
token |
登录方法特有内容,这个非常重要,后续接口需要传递该值以验证登录。 | |
result | 调用接口的返回内容,登录接口的返回内容说明如下:
|
|
|
|
...
|
- 调用示例(PostMan调用截图)
4.2 查询接口(异步)
名称 | 描述 | 默认值 | |
---|---|---|---|
接口路径 | http:// |
Smartbi-AIChat-server:port/aiweb/api/v3/conv/query | |||
接口说明 | V3版本查询方法 -- 异步方法 -- |
SSE请求。 | |||
header | token | 登录key,使用login方法获取;login方法请参考:登录AIChat | |
接口参数 | convId | 会话Id | |
datasetId | 数据模型Id | ||
question | 用户问题 | ||
queryType | 查询类型:
| 建议使用:analysis | |
id |
本次对话id
从外部传入才能做点赞点踩本次对话id,从外部传入用户才能使用“点赞”、“点踩”等功能。 | |
need_inquiry |
本次查询是否需要使用反问功能
本次查询是否需要使用反问功能。 | 默认值:true |
返回内容 |
返回SSE对象,前端处理
返回SSE对象,前端处理。SSE返回报文样例: ... SSE |
接口会返回很多条这样的报文,具体原理请自行百度。请手工拼接返回报文 "response_message" 和 "execution_result" 部分内容;response_type 表示当前这条报文的返回内容是啥。 |
- 参考代码:
锚 DemoCode DemoCode
服务端调用可参照以下示例代码(可展开源码阅读):
代码块 | ||||||||||
---|---|---|---|---|---|---|---|---|---|---|
| ||||||||||
public class GradleTest { public static void main(String[] args) throws Exception { String server = "http://域名:端口/smartbi"; String user = "user"; String password = "password"; ObjectMapper mapper = new ObjectMapper(); Map<String, String> cookies = new HashMap<>(); boolean useRmiLogin = true; HttpRequest request = null; if (useRmiLogin) { String params = mapper.writeValueAsString(Arrays.asList(user, password)); request = HttpRequest.post(server + "/vision/RMIServlet") .form("className", "UserService") .form("methodName", "login") .form("params", params); try (HttpResponse response = request.execute()) { for (HttpCookie cookie : response.getCookies()) { cookies.put(cookie.getName(), cookie.getValue()); } } } else { // 以下的登录方式为使用openresoruce.jsp 等的URL访问方式 // 适用于修改了 Smartbi 的登录方式,不能直接通过 RMIServlet 用户密码登录 // I402882c701552f492f49736e01552f4df2c50013 是产品的一个内置报表,可根据需要修改 request = HttpRequest.get(server + "/vision/openresource.jsp?" + "resid=I402882c701552f492f49736e01552f4df2c50013&user=" + user + "&password=" + URLEncoder.encode(password, "UTF-8")); try (HttpResponse response = request.execute()) { for (HttpCookie cookie : response.getCookies()) { cookies.put(cookie.getName(), cookie.getValue()); } } } System.out.println(toCookie(cookies)); request = HttpRequest.post(server + "/vision/aichat/proxy/api/v1/login") .cookie(toCookie(cookies)) .form("userName", user) .form("smartbiServer", server) .form("loginMethod", "login") .form("cookie", toCookie(cookies)); String token = null; try (HttpResponse response = request.execute()) { for (HttpCookie cookie : response.getCookies()) { cookies.put(cookie.getName(), cookie.getValue()); } JsonNode tree = mapper.readTree(response.body()); token = tree.get("token").asText(); } // Thread.sleep(5000); // 旧版本由于存在问题,需要 sleep。 新版本后不需要 request = HttpRequest.post(server + "/vision/aichat/proxy/api/v3/conv/query_sync") .cookie(toCookie(cookies)) .header("token", token) // 数据模型ID .form("datasetId", "Iff808081018354c854c8f0fa018354cbde880001") // 对话ID .form("convId", UUID.randomUUID().toString()) // 问句 .form("question", "车均价 ") // 分析模式 .form("queryType", "analysis") // 问句的ID .form("id", UUID.randomUUID().toString()) .form("pageSize", "10000") .form("showRows", "1000") .form("need_inquiry", "false") .form("onlyQueryChart", "false") .form("autoRecommendedChart", "false"); try (HttpResponse response = request.execute()) { System.out.println(new String(response.bodyBytes(), "UTF-8")); } } private static String toCookie(Map<String, String> cookies) throws IOException { StringBuilder buff = new StringBuilder(); for (Entry<String, String> entry : cookies.entrySet()) { buff.append(URLEncoder.encode(entry.getKey(), "UTF-8")); buff.append('='); buff.append(URLEncoder.encode(entry.getValue(), "UTF-8")); buff.append(';'); } return buff.toString(); } } |
4.3 查询接口(同步)
名称 | 描述 | 默认值 | |
---|---|---|---|
接口路径 | http:// |
Smartbi-AIChat-server:port/aiweb/api/v3/conv/query_sync | |||
接口说明 | V3版本查询方法 -- |
同步方法。 | |||
header | token | 登录key,使用login方法获取;login方法请参考:登录AIChat | |
接口参数 | convId | 会话Id | |
datasetId | 数据模型Id | ||
question | 用户问题 | ||
queryType | 查询类型: |
| 建议使用:analysis |
id |
本次对话id,从外部传入用户才能使用“点赞”、“点踩”等功能。 |
从外部传入才能做点赞点踩
need_inquiry |
本次查询是否需要使用反问功能
本次查询是否需要使用反问功能。 | 默认值:true |
返回内容 |
返回查询结果(JSON),前端处理: { code=0,表示返回正确(result是返回结果);否则message就是错误提示。 |
4.4 中断查询
名称 | 描述 | 默认值 | |
---|---|---|---|
接口路径 | http:// |
Smartbi-AIChat-server:port/aiweb/api/v3/conv/stop_stream | ||
接口说明 |
异步query方法情况下,中断当前查询。 | |||
header | token | 登录key,使用login方法获取;login方法请参考:登录AIChat | |
接口参数 | convId | 会话Id | |
返回内容 | { |
4.5 新建查询对话
名称 | 描述 | 默认值 | |
---|---|---|---|
接口路径 | http:// |
Smartbi-AIChat-server:port/aiweb/api/v3/conv/new | ||
接口说明 |
新建查询对话。 | |||
header | token | 登录key,使用login方法获取;login方法请参考:登录AIChat | |
接口参数 | convId | 会话Id | |
返回内容 | { |
4.6 关闭查询对话
名称 | 描述 | 默认值 | |
---|---|---|---|
接口路径 | http:// |
Smartbi-AIChat-server:port/aiweb/api/v3/conv/close | |||
接口说明 | 关闭查询对话 -- |
结束本次多轮对话。 | |||
header | token | 登录key,使用login方法获取;login方法请参考:AIChat登录 | |
接口参数 | convId | 会话Id | |
返回内容 | { |
4.7 获取本次对话推荐数据模型
名称 | 描述 | 默认值 | |
---|---|---|---|
接口路径 | http:// |
Smartbi-AIChat-server:port/aiweb/api/v3/conv/recommend_dataset | ||
接口说明 |
获取本次对话推荐数据模型。 | |||
header | token | 登录key,使用login方法获取;login方法请参考:登录AIChat | |
接口参数 | convId | 会话Id | |
question | 用户提问 | ||
datasetId | 当前数据模型id | ||
返回内容 | { |
4.
...
8 获取本次对话的详细查询步骤和内容
名称 | 描述 | 默认值 | |
---|---|---|---|
接口路径 | http:// |
Smartbi-AIChat-server:port/aiweb/#/testTool?answerid=${id} GET请求 |
示例:
示例: http://10.10.35.110:9070/aiweb/#/testTool2?answerid=01fc76d5-7ec4-4fad-8216-d4b829ac740c | ||
接口说明 |
获取本次对话的详细查询步骤和内容。
|
| |||
接口参数 | id | 本次对话Id | |
返回内容 |
查询步骤说明html页面。 |
4.
...
9 获取当前用户可以使用的数据模型列表
名称 | 描述 | 默认值 | |
---|---|---|---|
接口路径 | http:// |
Smartbi-AIChat-server:port/aiweb/proxy/aibus/get_using_ |
themes | ||
接口说明 |
获取当前用户可以使用的数据模型列表。 | |||
header | token | 登录key,使用login方法获取;login方法请参考:登录AIChat | |
接口参数 | |||
返回内容 | { |
数据模型themeID |
"title": 数据模型名称别名
"desc": 数据模型概览
"type": 数据类型
"recommendQuestion": 推荐问句
"lastBuildTime": 最近构建时间
}]}
...
数据模型名称 |
4.10 获取当前用户会话历史
名称 | 描述 | 默认值 | |
---|---|---|---|
接口路径 | http:// |
Smartbi-AIChat-server:port/aiweb/proxy/admin/v3/db/conv/get_list_by_user | |||
接口说明 | 获取当前用户可以使用的数据模型列表 | ||
header | token | 登录key,使用login方法获取;login方法请参考:登录AIChat | |
接口参数 | userName | 当前用户名 | |
返回内容 | { |
4.
...
11 打开对话历史
名称 | 描述 | 默认值 | |
---|---|---|---|
接口路径 | http:// |
Smartbi-AIChat-server:port/aiweb/proxy/admin/v3/db/conv/get_by_convid | ||
接口说明 |
获取当前用户可以使用的数据模型列表。 | |||
header | token | 登录key,使用login方法获取;login方法请参考:登录AIChat | |
接口参数 | convId | 会话Id | |
返回内容 | { |
4.
...
12 删除对话历史
名称 | 描述 | 默认值 | |
---|---|---|---|
接口路径 | http:// |
Smartbi-AIChat-server:port/aiweb/proxy/admin/v3/db/conv/remove_by_convid | ||
接口说明 |
获取当前用户可以使用的数据模型列表。 | |||
header | token | 登录key,使用login方法获取;login方法请参考:登录AIChat | |
接口参数 | convId | 会话Id | |
返回内容 | { |
5.界面集成
名称
描述
默认值
URL路径
/smartbi/vision/AIChatV3.html
GET请求
示例:
http://10.10.35.110:9070/smartbi/vision/AIChatV3.html
集成说明
本地址为bi里面的地址,必须登录bi后再使用。可以跳过登录步骤,直接打开v3的界面
参数