@chatopera/sdk
Advanced tools
Comparing version 1.10.0 to 2.0.0
@@ -0,3 +1,11 @@ | ||
# 2.0.0 | ||
- 提供 `Chatbot#command` 接口,对 RestAPI 进一步封装,提高灵活性 | ||
- 将 `Chatbot` 作为成员类 `exports` 出来 | ||
- 增加 `DeprecationWarning`,以后统一使用 `Chatbot#command` 接口 | ||
- `queryString` 中增加 `sdklang=nodejs` 参数 | ||
- 调整接口的返回值为包含标准`rc`, `data`, `msg`, `error`, `status`的字段。 | ||
# 1.9.0 | ||
- 在 faq 及 conversation 检索接口中,增加 faq_best_reply 参数和 faq_sugg_reply 参数支持阀值过滤 |
117
index.d.ts
@@ -1,83 +0,9 @@ | ||
declare interface DetailResult { | ||
name: string; | ||
fallback: string; | ||
description: string; | ||
welcome: string; | ||
primaryLanguage: string; | ||
} | ||
declare interface FAQResult { | ||
id: string; | ||
score: number; | ||
post: string; | ||
reply: string; | ||
} | ||
declare interface ConversationService { | ||
provider: string; | ||
} | ||
declare interface ConversationResult { | ||
state: string; | ||
createdAt: number; | ||
string: string; | ||
topicName: string; | ||
subReplies: string[]; | ||
service: ConversationService; | ||
logic_is_fallback: boolean; | ||
logic_is_unexpected: boolean; | ||
botName: string; | ||
faq: FAQResult[]; | ||
} | ||
declare interface UserResult { | ||
userId: string; | ||
lasttime: string; | ||
created: string; | ||
} | ||
declare interface ChatResult { | ||
userId: string; | ||
textMessage: string; | ||
direction: string; | ||
service: string; | ||
created: string; | ||
} | ||
declare interface IsMuteResult { | ||
mute: boolean; | ||
} | ||
declare interface DeployConversationResult { | ||
declare interface ResponseResult { | ||
rc: number; | ||
data: any; | ||
error: string; | ||
msg: string; | ||
status: any; | ||
} | ||
declare interface IntentSlot { | ||
dictname: string; | ||
name: string; | ||
requires: boolean; | ||
val: string; | ||
} | ||
declare interface IntentSessionResult { | ||
channel: string; | ||
createdate: string; | ||
id: string; | ||
entities: IntentSlot[]; | ||
intent_name: string; | ||
resolved: boolean; | ||
uid: string; | ||
} | ||
declare interface IntentMessage { | ||
receiver: string; | ||
is_proactive: boolean; | ||
is_fallback: boolean; | ||
textMessage: string; | ||
} | ||
declare interface IntentChatResult { | ||
message: IntentMessage; | ||
session: IntentSessionResult; | ||
} | ||
declare class Chatbot { | ||
@@ -91,5 +17,10 @@ constructor( | ||
/** | ||
* 核心封装 | ||
*/ | ||
command(method: string, path: string, payload: any): Promise<ResponseResult>; | ||
/** | ||
* 获得详情 | ||
*/ | ||
detail(): Promise<DetailResult>; | ||
detail(): Promise<ResponseResult>; | ||
@@ -101,3 +32,3 @@ /** | ||
*/ | ||
faq(userId: string, textMessage: string): Promise<FAQResult[]>; | ||
faq(userId: string, textMessage: string): Promise<ResponseResult>; | ||
@@ -114,3 +45,3 @@ /** | ||
isDebug: boolean = false | ||
): Promise<ConversationResult>; | ||
): Promise<ResponseResult>; | ||
@@ -127,3 +58,3 @@ /** | ||
sortby: string = "-lasttime" | ||
): Promise<UserResult[]>; | ||
): Promise<ResponseResult>; | ||
@@ -140,3 +71,3 @@ /** | ||
page: number = 1 | ||
): Promise<ChatResult[]>; | ||
): Promise<ResponseResult>; | ||
@@ -147,3 +78,3 @@ /** | ||
*/ | ||
mute(userId: string): Promise<void>; | ||
mute(userId: string): Promise<ResponseResult>; | ||
@@ -154,3 +85,3 @@ /** | ||
*/ | ||
unmute(userId: string): Promise<void>; | ||
unmute(userId: string): Promise<ResponseResult>; | ||
@@ -161,3 +92,3 @@ /** | ||
*/ | ||
ismute(userId: string): Promise<IsMuteResult>; | ||
ismute(userId: string): Promise<ResponseResult>; | ||
@@ -168,3 +99,3 @@ /** | ||
*/ | ||
deployConversation(botarchive: string): Promise<DeployConversationResult>; | ||
deployConversation(botarchive: string): Promise<ResponseResult>; | ||
@@ -176,3 +107,3 @@ /** | ||
*/ | ||
intentSession(uid: string, channel: string): Promise<IntentSessionResult>; | ||
intentSession(uid: string, channel: string): Promise<ResponseResult>; | ||
@@ -183,3 +114,3 @@ /** | ||
*/ | ||
intentSessionDetail(sessionId: string): Promise<IntentSessionResult>; | ||
intentSessionDetail(sessionId: string): Promise<ResponseResult>; | ||
@@ -203,3 +134,3 @@ /** | ||
*/ | ||
psychSearch(query: string, threshold: number): Promise<any>; | ||
psychSearch(query: string, threshold: number): Promise<ResponseResult>; | ||
@@ -218,5 +149,5 @@ /** | ||
textMessage: string | ||
): Promise<any>; | ||
): Promise<ResponseResult>; | ||
} | ||
export = Chatbot; | ||
export = { Chatbot }; |
837
index.js
/** | ||
* Chatopera Node.js SDK | ||
* Copyright 2020 Chatopera Inc. <https://www.chatopera.com>. All rights reserved. | ||
* This software and related documentation are provided under a license agreement containing | ||
* restrictions on use and disclosure and are protected by intellectual property laws. | ||
* Except as expressly permitted in your license agreement or allowed by law, you may not use, | ||
* copy, reproduce, translate, broadcast, modify, license, transmit, distribute, exhibit, perform, | ||
* publish, or display any part, in any form, or by any means. Reverse engineering, disassembly, | ||
* or decompilation of this software, unless required by law for interoperability, is prohibited. | ||
*/ | ||
const debug = require("debug")("chatopera:sdk:index"); | ||
const request = require("superagent"); | ||
const utils = require("./lib/utils"); | ||
const fs = require("fs"); | ||
const Q = require("@chatopera/q"); | ||
const generate = require("./lib/generate-authorization"); | ||
const basePath = "/api/v1/chatbot"; | ||
const fs = require("fs"); | ||
const { deprecate } = require("util"); | ||
// 处理JSON返回值 | ||
// TODO request.parse['application/json'] 有bug, 否则用它更好 | ||
function successHandler(res) { | ||
return new Promise((resolve, reject) => { | ||
let { rc, data, error, err, msg, message } = res.body; | ||
if (rc === 0) { | ||
// omit chatbotID | ||
if (data) { | ||
if (data.chatbotID) { | ||
delete data.chatbotID; | ||
} else if (Array.isArray(data)) { | ||
for (let x in data) { | ||
delete data[x].chatbotID; | ||
} | ||
} | ||
} | ||
resolve(data); | ||
} else { | ||
// check the possible error message | ||
reject(new Error(error || err || msg || message)); | ||
} | ||
}); | ||
} | ||
// 常量 | ||
const BASE_PATH = "/api/v1/chatbot"; | ||
const K_CHATBOT_ID = "chatbotID"; | ||
const depCode = (fnName, day) => { | ||
return "chatopera/sdk <chatbot#" + fnName + "> " + day; | ||
}; | ||
/** | ||
* 处理异常返回 | ||
* @param {*} err | ||
* 聊天机器人 | ||
* 构造函数 | ||
* @param {*} clientId | ||
* @param {*} clientSecret | ||
* @param {*} host | ||
*/ | ||
function failHandler(err) { | ||
return Promise.reject(err); | ||
function Chatbot(clientId, clientSecret, host = "https://bot.chatopera.com") { | ||
debug( | ||
"constructor: host %s, clientId %s, clientSecret %s", | ||
host, | ||
clientId, | ||
clientSecret | ||
); | ||
if (clientId) { | ||
this.clientId = clientId; | ||
this.clientSecret = clientSecret; | ||
this.baseEndpoint = `${BASE_PATH}/${this.clientId}`; | ||
} else { | ||
// null, false, blank or undefined. | ||
throw new Error("Chatbot: Unexpected clientId"); | ||
} | ||
if (host) { | ||
if (host.endsWith("/")) host = host.substr(0, host.length - 1); | ||
this.host = host; | ||
} else { | ||
throw new Error("Chatbot: Unexpected host"); | ||
} | ||
} | ||
/** | ||
* 聊天机器人 | ||
* 核心接口 | ||
* @param {*} method | ||
* @param {*} path | ||
* @param {*} payload | ||
*/ | ||
class Chatbot { | ||
/** | ||
* 构造函数 | ||
* @param {*} clientId | ||
* @param {*} clientSecret | ||
* @param {*} host | ||
*/ | ||
constructor(clientId, clientSecret, host = "https://bot.chatopera.com") { | ||
debug( | ||
"constructor: host %s, clientId %s, clientSecret %s", | ||
host, | ||
clientId, | ||
clientSecret | ||
); | ||
Chatbot.prototype.command = function (method, path, payload, headers, attach) { | ||
let deferred = Q.defer(); | ||
let endpoint = this.baseEndpoint + path; | ||
if (!!clientId) { | ||
this.clientId = clientId; | ||
this.clientSecret = clientSecret; | ||
// 处理参数 | ||
method = method.toUpperCase(); | ||
if (path) { | ||
let splits = path.split("&"); | ||
if (splits.length > 1 && path.includes("?")) { | ||
path += "&sdklang=nodejs"; | ||
} else { | ||
// null, false, blank or undefined. | ||
throw new Error("Chatbot: Unexpected clientId"); | ||
path += "?sdklang=nodejs"; | ||
} | ||
if (!!host) { | ||
if (host.endsWith("/")) host = host.substr(0, host.length - 1); | ||
this.host = host; | ||
} else { | ||
throw new Error("Chatbot: Unexpected host"); | ||
} | ||
} else { | ||
path = "/?sdklang=nodejs"; | ||
} | ||
/** | ||
* 获得详情 | ||
*/ | ||
detail() { | ||
let endpoint = `${basePath}/${this.clientId}`; | ||
return request | ||
.get(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "application/json") | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.GET, | ||
endpoint | ||
) | ||
) | ||
.then(successHandler, failHandler); | ||
// 发送请求 | ||
let req = request(method, this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set( | ||
"Content-Type", | ||
headers && headers["Content-Type"] | ||
? headers["Content-Type"] | ||
: "application/json" | ||
) | ||
.set( | ||
"Accept", | ||
headers && headers["Accept"] ? headers["Accept"] : "application/json" | ||
) | ||
.set( | ||
"Authorization", | ||
generate(this.clientId, this.clientSecret, method, endpoint) | ||
); | ||
if (attach && attach instanceof Array) { | ||
for (let x of attach) { | ||
req.attach(x["filename"], x["filepart"]); | ||
} | ||
} else if (payload) { | ||
req.send(payload); | ||
} | ||
/** | ||
* 检索知识库 | ||
*/ | ||
faq(userId, textMessage, faq_best_reply, faq_sugg_reply) { | ||
let endpoint = `${basePath}/${this.clientId}/faq/query`; | ||
return request | ||
.post(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "application/json") | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.POST, | ||
endpoint | ||
) | ||
) | ||
.send({ | ||
req.then( | ||
(res) => { | ||
if (res.body && res.body.rc === 0) { | ||
// omit chatbotID | ||
if (res.body.data) { | ||
if (res.body.data[K_CHATBOT_ID]) { | ||
delete res.body.data[K_CHATBOT_ID]; | ||
} else if (res.body.data instanceof Array) { | ||
// fastest loop | ||
// https://www.incredible-web.com/blog/performance-of-for-loops-with-javascript/ | ||
for (let i = res.body.data.length - 1; i >= 0; i--) { | ||
delete res.body.data[i][K_CHATBOT_ID]; | ||
} | ||
} | ||
} | ||
} | ||
deferred.resolve(res.body); | ||
}, | ||
(err) => { | ||
debug("[command] method %s, path %s, Error %s", method, path, err); | ||
deferred.reject({ | ||
rc: 100, | ||
error: err, | ||
}); | ||
} | ||
); | ||
return deferred.promise; | ||
}; | ||
/** | ||
* 获得详情 | ||
*/ | ||
Chatbot.prototype.detail = function () { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command("GET", "/"); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("detail", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
/** | ||
* 检索知识库 | ||
*/ | ||
Chatbot.prototype.faq = function ( | ||
userId, | ||
textMessage, | ||
faq_best_reply, | ||
faq_sugg_reply | ||
) { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command("POST", "/faq/query", { | ||
fromUserId: userId, | ||
@@ -132,41 +174,28 @@ query: textMessage, | ||
faq_best_reply: faq_best_reply, | ||
}) | ||
.then(successHandler, failHandler); | ||
} | ||
}); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("faq", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
/** | ||
* 查询多轮对话 | ||
* @param {*} userId | ||
* @param {*} textMessage | ||
* @param {*} isDebug | ||
*/ | ||
conversation( | ||
userId, | ||
textMessage, | ||
faq_best_reply, | ||
faq_sugg_reply, | ||
isDebug = false | ||
) { | ||
debug("conversation userId %s, textMessage %s", userId, textMessage); | ||
let endpoint = `${basePath}/${this.clientId}/conversation/query`; | ||
return request | ||
.post(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "application/json") | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.POST, | ||
endpoint | ||
) | ||
) | ||
.send({ | ||
/** | ||
* 查询多轮对话 | ||
* @param {*} userId | ||
* @param {*} textMessage | ||
* @param {*} isDebug | ||
*/ | ||
Chatbot.prototype.conversation = function ( | ||
userId, | ||
textMessage, | ||
faq_best_reply, | ||
faq_sugg_reply, | ||
isDebug = false | ||
) { | ||
debug("conversation userId %s, textMessage %s", userId, textMessage); | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command("POST", "/conversation/query", { | ||
fromUserId: userId, | ||
@@ -177,260 +206,166 @@ textMessage: textMessage, | ||
faq_sugg_reply: faq_sugg_reply, | ||
}) | ||
.then(successHandler, failHandler); | ||
} | ||
}); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("conversation", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
/** | ||
* 查询用户列表 | ||
* @param {*} limit | ||
* @param {*} page | ||
* @param {*} sortby | ||
*/ | ||
users(limit = 50, page = 1, sortby = "-lasttime") { | ||
let endpoint = | ||
basePath + | ||
"/" + | ||
this.clientId + | ||
`/users?page=${page}&limit=${limit}&sortby=${sortby}`; | ||
return request | ||
.get(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "application/json") | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.GET, | ||
endpoint | ||
) | ||
) | ||
.then(successHandler, failHandler); | ||
} | ||
/** | ||
* 查询用户列表 | ||
* @param {*} limit | ||
* @param {*} page | ||
* @param {*} sortby | ||
*/ | ||
Chatbot.prototype.users = function ( | ||
limit = 50, | ||
page = 1, | ||
sortby = "-lasttime" | ||
) { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command( | ||
"GET", | ||
`/users?page=${page}&limit=${limit}&sortby=${sortby}` | ||
); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("users", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
/** | ||
* 获得聊天历史记录 | ||
* @param {*} userId | ||
* @param {*} limit | ||
* @param {*} page | ||
*/ | ||
chats(userId, limit = 50, page = 1) { | ||
let endpoint = | ||
basePath + | ||
"/" + | ||
this.clientId + | ||
`/users/${userId}/chats?page=${page}&limit=${limit}`; | ||
return request | ||
.get(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "application/json") | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.GET, | ||
endpoint | ||
) | ||
) | ||
.then(successHandler, failHandler); | ||
} | ||
/** | ||
* 获得聊天历史记录 | ||
* @param {*} userId | ||
* @param {*} limit | ||
* @param {*} page | ||
*/ | ||
Chatbot.prototype.chats = function (userId, limit = 50, page = 1) { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command( | ||
"GET", | ||
`/users/${userId}/chats?page=${page}&limit=${limit}` | ||
); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("chats", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
/** | ||
* 屏蔽一个聊天者 | ||
* @param {*} userId | ||
*/ | ||
mute(userId) { | ||
let endpoint = `${basePath}/${this.clientId}/users/${userId}/mute`; | ||
return request | ||
.post(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "application/json") | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.POST, | ||
endpoint | ||
) | ||
) | ||
.then(successHandler, failHandler); | ||
} | ||
/** | ||
* 屏蔽一个聊天者 | ||
* @param {*} userId | ||
*/ | ||
Chatbot.prototype.mute = function (userId) { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command("POST", `/users/${userId}/mute`); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("mute", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
/** | ||
* 取消屏蔽一个聊天者 | ||
* @param {*} userId | ||
*/ | ||
unmute(userId) { | ||
let endpoint = `${basePath}/${this.clientId}/users/${userId}/unmute`; | ||
return request | ||
.post(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "application/json") | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.POST, | ||
endpoint | ||
) | ||
) | ||
.then(successHandler, failHandler); | ||
} | ||
/** | ||
* 取消屏蔽一个聊天者 | ||
* @param {*} userId | ||
*/ | ||
Chatbot.prototype.unmute = function (userId) { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command("POST", `/users/${userId}/unmute`); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("unmute", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
/** | ||
* | ||
* @param {*} userId | ||
*/ | ||
ismute(userId) { | ||
let endpoint = `${basePath}/${this.clientId}/users/${userId}/ismute`; | ||
return request | ||
.post(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "application/json") | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.POST, | ||
endpoint | ||
) | ||
) | ||
.then(successHandler, failHandler); | ||
} | ||
/** | ||
* | ||
* @param {*} userId | ||
*/ | ||
Chatbot.prototype.ismute = function (userId) { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command("POST", `/users/${userId}/ismute`); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("ismute", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
deployConversation(botarchive) { | ||
let exist = fs.existsSync(botarchive); | ||
if (!exist) { | ||
return reject(new Error("File not exist.")); | ||
} | ||
Chatbot.prototype.deployConversation = function (botarchive) { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
let exist = fs.existsSync(botarchive); | ||
if (!exist) { | ||
throw new Error("File not exist."); | ||
} | ||
let endpoint = `${basePath}/${this.clientId}/conversation/droplet/import`; | ||
return request | ||
.post(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "multipart/form-data") | ||
.set("Accept", "application/json") | ||
.attach("droplet", botarchive) | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.POST, | ||
endpoint | ||
) | ||
) | ||
.then(successHandler, failHandler); | ||
} | ||
return self.command( | ||
"POST", | ||
"/conversation/droplet/import", | ||
null, | ||
{ | ||
"Content-Type": "multipart/form-data", | ||
}, | ||
[ | ||
{ | ||
filename: "droplet", | ||
filepart: botarchive, | ||
}, | ||
] | ||
); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("deployConversation", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
intentSession(uid, channel) { | ||
let endpoint = `${basePath}/${this.clientId}/clause/prover/session`; | ||
debug("intentSession: %s", this.host + endpoint); | ||
return request | ||
.post(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "application/json") | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.POST, | ||
endpoint | ||
) | ||
) | ||
.send({ uid: uid, channel: channel }) | ||
.then(successHandler, failHandler); | ||
} | ||
Chatbot.prototype.intentSession = function (uid, channel) { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command("POST", "/clause/prover/session", { | ||
uid: uid, | ||
channel: channel, | ||
}); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("intentSession", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
intentSessionDetail(sessionId) { | ||
let endpoint = `${basePath}/${this.clientId}/clause/prover/session/${sessionId}`; | ||
debug("intentSessionDetail: %s", this.host + endpoint); | ||
return request | ||
.get(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.GET, | ||
endpoint | ||
) | ||
) | ||
.then(successHandler, failHandler); | ||
} | ||
Chatbot.prototype.intentSessionDetail = function (sessionId) { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command("GET", `/clause/prover/session/${sessionId}`); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("intentSessionDetail", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
intentChat(sessionId, uid, textMessage) { | ||
let endpoint = `${basePath}/${this.clientId}/clause/prover/chat`; | ||
return request | ||
.post(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "application/json") | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.POST, | ||
endpoint | ||
) | ||
) | ||
.send({ | ||
Chatbot.prototype.intentChat = function (sessionId, uid, textMessage) { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command("POST", "/clause/prover/chat", { | ||
fromUserId: uid, | ||
@@ -441,35 +376,27 @@ session: { id: sessionId }, | ||
}, | ||
}) | ||
.then(successHandler, failHandler); | ||
} | ||
}); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("intentChat", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
/** | ||
* Skills: 心理咨询聊天 | ||
* @param {*} channel | ||
* @param {*} channelId | ||
* @param {*} userId | ||
* @param {*} textMessage | ||
*/ | ||
psychChat(channel, channelId, userId, textMessage) { | ||
let endpoint = `${basePath}/${this.clientId}/skills/psych/chat`; | ||
return request | ||
.post(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "application/json") | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.POST, | ||
endpoint | ||
) | ||
) | ||
.send({ | ||
/** | ||
* Skills: 心理咨询聊天 | ||
* @param {*} channel | ||
* @param {*} channelId | ||
* @param {*} userId | ||
* @param {*} textMessage | ||
*/ | ||
Chatbot.prototype.psychChat = function ( | ||
channel, | ||
channelId, | ||
userId, | ||
textMessage | ||
) { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command("POST", "/skills/psych/chat", { | ||
channel: channel, | ||
@@ -479,40 +406,32 @@ channelId: channelId, | ||
textMessage: textMessage, | ||
}) | ||
.then(successHandler, failHandler); | ||
} | ||
}); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("psychChat", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
/** | ||
* Skills: 心理咨询查询 | ||
* @param {*} query | ||
* @param {*} threshold | ||
*/ | ||
psychSearch(query, threshold) { | ||
let endpoint = `${basePath}/${this.clientId}/skills/psych/search`; | ||
return request | ||
.post(this.host + endpoint) | ||
.set("X-Requested-With", "XMLHttpRequest") | ||
.set("Expires", "-1") | ||
.set( | ||
"Cache-Control", | ||
"no-cache,no-store,must-revalidate,max-age=-1,private" | ||
) | ||
.set("Content-Type", "application/json") | ||
.set("Accept", "application/json") | ||
.set( | ||
"Authorization", | ||
generate( | ||
this.clientId, | ||
this.clientSecret, | ||
utils.HTTP_METHOD.POST, | ||
endpoint | ||
) | ||
) | ||
.send({ | ||
/** | ||
* Skills: 心理咨询查询 | ||
* @param {*} query | ||
* @param {*} threshold | ||
*/ | ||
Chatbot.prototype.psychSearch = function (query, threshold) { | ||
let self = this; | ||
let fn = deprecate( | ||
() => { | ||
return self.command("POST", "/skills/psych/search", { | ||
query: query, | ||
threshold: threshold || 0.2, | ||
}) | ||
.then(successHandler, failHandler); | ||
} | ||
} | ||
}); | ||
}, | ||
"use `Chatbot#command` API instead, removed in 2020-10", | ||
depCode("psychSearch", "2020-07-18") | ||
); | ||
return fn(); | ||
}; | ||
exports = module.exports = Chatbot; | ||
exports = module.exports = { | ||
Chatbot, | ||
}; |
@@ -0,1 +1,11 @@ | ||
/** | ||
* Chatopera Node.js SDK | ||
* Copyright 2020 Chatopera Inc. <https://www.chatopera.com>. All rights reserved. | ||
* This software and related documentation are provided under a license agreement containing | ||
* restrictions on use and disclosure and are protected by intellectual property laws. | ||
* Except as expressly permitted in your license agreement or allowed by law, you may not use, | ||
* copy, reproduce, translate, broadcast, modify, license, transmit, distribute, exhibit, perform, | ||
* publish, or display any part, in any form, or by any means. Reverse engineering, disassembly, | ||
* or decompilation of this software, unless required by law for interoperability, is prohibited. | ||
*/ | ||
const crypto = require("crypto"); | ||
@@ -5,8 +15,5 @@ const debug = require("debug")("chatopera:sdk:generator"); | ||
const hmacSha1 = (secret, text) => | ||
crypto | ||
.createHmac("sha1", secret) | ||
.update(text) | ||
.digest("hex"); | ||
crypto.createHmac("sha1", secret).update(text).digest("hex"); | ||
const json2base64 = obj => | ||
const json2base64 = (obj) => | ||
Buffer.from(JSON.stringify(obj), "utf8").toString("base64"); | ||
@@ -13,0 +20,0 @@ |
@@ -17,3 +17,3 @@ "use strict"; | ||
Object.defineProperty(global, tempDirectorySymbol, { | ||
value: fs.realpathSync(os.tmpdir()) | ||
value: fs.realpathSync(os.tmpdir()), | ||
}); | ||
@@ -20,0 +20,0 @@ } |
@@ -0,1 +1,11 @@ | ||
/** | ||
* Chatopera Node.js SDK | ||
* Copyright 2020 Chatopera Inc. <https://www.chatopera.com>. All rights reserved. | ||
* This software and related documentation are provided under a license agreement containing | ||
* restrictions on use and disclosure and are protected by intellectual property laws. | ||
* Except as expressly permitted in your license agreement or allowed by law, you may not use, | ||
* copy, reproduce, translate, broadcast, modify, license, transmit, distribute, exhibit, perform, | ||
* publish, or display any part, in any form, or by any means. Reverse engineering, disassembly, | ||
* or decompilation of this software, unless required by law for interoperability, is prohibited. | ||
*/ | ||
const archiver = require("archiver"); | ||
@@ -8,3 +18,3 @@ const fs = require("fs"); | ||
*/ | ||
exports.getTimestamp = function() { | ||
exports.getTimestamp = function () { | ||
var now = new Date(); | ||
@@ -27,3 +37,3 @@ return ( | ||
*/ | ||
exports.zipDirectory = function(source, out) { | ||
exports.zipDirectory = function (source, out) { | ||
const archive = archiver("zip", { zlib: { level: 9 } }); | ||
@@ -35,3 +45,3 @@ const stream = fs.createWriteStream(out); | ||
.directory(source, false) | ||
.on("error", err => reject(err)) | ||
.on("error", (err) => reject(err)) | ||
.pipe(stream); | ||
@@ -43,12 +53,1 @@ | ||
}; | ||
/** | ||
* Shortcuts for HTTP Methods | ||
*/ | ||
exports.HTTP_METHOD = { | ||
POST: "POST", | ||
GET: "GET", | ||
DELETE: "DELETE", | ||
PUT: "PUT", | ||
PATCH: "PATCH" | ||
}; |
{ | ||
"name": "@chatopera/sdk", | ||
"version": "1.10.0", | ||
"description": "Official sdk of Chatopera", | ||
"version": "2.0.0", | ||
"description": "Official sdk of Chatopera services, https://bot.chatopera.com", | ||
"main": "index.js", | ||
@@ -18,17 +18,18 @@ "bin": { | ||
], | ||
"author": "Chatopera <http://chatopera.com>", | ||
"license": "Apache 2.0", | ||
"author": "Chatopera <info@chatopera.com>", | ||
"license": "SEE LICENSE IN LICENSE", | ||
"bugs": { | ||
"url": "https://github.com/chatopera/conversation-sampleapp/issues" | ||
}, | ||
"homepage": "https://docs.chatopera.com/", | ||
"homepage": "https://bot.chatopera.com/", | ||
"dependencies": { | ||
"archiver": "^3.0.0", | ||
"commander": "^2.20.0", | ||
"@chatopera/q": "^1.0.1", | ||
"archiver": "^4.0.2", | ||
"commander": "^5.1.0", | ||
"debug": "^4.1.1", | ||
"inquirer": "^6.3.1", | ||
"superagent": "^5.0.5" | ||
"inquirer": "^7.3.2", | ||
"superagent": "^5.3.1" | ||
}, | ||
"devDependencies": { | ||
"ava": "^0.25.0", | ||
"ava": "^3.10.1", | ||
"dotenv": "^8.2.0" | ||
@@ -35,0 +36,0 @@ }, |
133
README.md
@@ -23,3 +23,3 @@ <p align="center"> | ||
``` | ||
var Chatbot = require("@chatopera/sdk"); | ||
var Chatbot = require("@chatopera/sdk").Chatbot; | ||
@@ -64,6 +64,16 @@ var chatbot = new Chatbot(*ClientId*, *Secret* [, ServiceProvider]); | ||
### 高级封装接口 | ||
`command`接口是实例化一个 Chatbot 对象后,最核心的调用 Chatbot 各种服务的接口。 | ||
``` | ||
var resp = await chatbot.command(METHOD, PATH, PAYLOAD); | ||
``` | ||
其中,`METHOD` 是调用 HTTPRequest 时的 method, 有效值包含 `POST, PUT, DELETE, HEAD, GET`;`PATH` 是 HTTPRequest 中的 URL path 参数,PAYLOAD 是 JSONArray 或 JSONObject 作为 HTTPRequest 的 Body。 | ||
### 获得聊天机器人实例 | ||
``` | ||
var Chatbot = require("@chatopera/sdk"); | ||
var Chatbot = require("@chatopera/sdk").Chatbot; | ||
var chatbot = new Chatbot(*ClientId*, *Secret*); | ||
@@ -83,7 +93,10 @@ | ||
{ | ||
"name": "bar", | ||
"fallback": "我不明白您的意思。", | ||
"description": "", | ||
"welcome": "你好!我是机器人客服。", | ||
"primaryLanguage": "zh_CN" | ||
"rc": 0, | ||
"data": { | ||
"name": "bar", | ||
"fallback": "我不明白您的意思。", | ||
"description": "", | ||
"welcome": "你好!我是机器人客服。", | ||
"primaryLanguage": "zh_CN" | ||
} | ||
} | ||
@@ -110,12 +123,15 @@ ``` | ||
{ | ||
"state": "default", | ||
"createdAt": 1540796868205, | ||
"string": "白天天气晴好,早晚会感觉偏凉,午后舒适、宜人。", | ||
"topicName": "weather", | ||
"subReplies": [], | ||
"service": { | ||
"provider": "conversation" | ||
}, | ||
"logic_is_fallback": false, | ||
"botName": "bar" | ||
"rc": 0, | ||
"data": { | ||
"state": "default", | ||
"createdAt": 1540796868205, | ||
"string": "白天天气晴好,早晚会感觉偏凉,午后舒适、宜人。", | ||
"topicName": "weather", | ||
"subReplies": [], | ||
"service": { | ||
"provider": "conversation" | ||
}, | ||
"logic_is_fallback": false, | ||
"botName": "bar" | ||
} | ||
} | ||
@@ -143,11 +159,14 @@ ``` | ||
``` | ||
[ | ||
{ | ||
"id": "AWa-Ogcaf3EIFA_CgZ3o", | ||
"score": 0.747, | ||
"post": " 停效期间的保单是否能办理减保?", | ||
"reply": " 停效期间的保单可以办理减保" | ||
}, | ||
... | ||
] | ||
{ | ||
"rc": 0, | ||
"data": [ | ||
{ | ||
"id": "AWa-Ogcaf3EIFA_CgZ3o", | ||
"score": 0.747, | ||
"post": " 停效期间的保单是否能办理减保?", | ||
"replies": {"rtype": "plain", "content": " 停效期间的保单可以办理减保""} | ||
}, | ||
... | ||
] | ||
} | ||
``` | ||
@@ -193,10 +212,13 @@ | ||
``` | ||
[ | ||
{ | ||
"userId": "张三", | ||
"lasttime": "2018-10-29T07:07:47.812Z", | ||
"created": "2018-10-29T05:02:13.084Z" | ||
}, | ||
... | ||
] | ||
{ | ||
"rc": 0, | ||
"data": [ | ||
{ | ||
"userId": "张三", | ||
"lasttime": "2018-10-29T07:07:47.812Z", | ||
"created": "2018-10-29T05:02:13.084Z" | ||
}, | ||
... | ||
] | ||
} | ||
``` | ||
@@ -215,12 +237,15 @@ | ||
``` | ||
[ | ||
{ | ||
"userId": "张三", | ||
"created": "2018-10-29T05:29:41.833Z", | ||
"textMessage": "白天天气晴好,早晚会感觉偏凉,午后舒适、宜人。", | ||
"direction": "outbound", | ||
"service": "conversation", | ||
"confidence": 1 | ||
} | ||
] | ||
{ | ||
"rc": 0, | ||
"data": [ | ||
{ | ||
"userId": "张三", | ||
"created": "2018-10-29T05:29:41.833Z", | ||
"textMessage": "白天天气晴好,早晚会感觉偏凉,午后舒适、宜人。", | ||
"direction": "outbound", | ||
"service": "conversation", | ||
"confidence": 1 | ||
} | ||
] | ||
} | ||
``` | ||
@@ -238,4 +263,10 @@ | ||
返回值为空 | ||
返回值为 JSONObject | ||
``` | ||
{"rc":0,"data":{}} | ||
``` | ||
`rc` 等于 0 代表接口调用成功。 | ||
### 取消屏蔽 | ||
@@ -249,4 +280,10 @@ | ||
返回值为空 | ||
返回值为 JSONObject | ||
``` | ||
{"rc":0,"data":{}} | ||
``` | ||
`rc` 等于 0 代表接口调用成功。 | ||
### 查看用户是否被屏蔽 | ||
@@ -260,6 +297,6 @@ | ||
返回值为 Boolean | ||
返回值为 JSONObject | ||
``` | ||
[true|false] | ||
{"rc":0,"data":{"mute":false}} | ||
``` | ||
@@ -266,0 +303,0 @@ |
Major refactor
Supply chain riskPackage has recently undergone a major refactor. It may be unstable or indicate significant internal changes. Use caution when updating to versions that include significant changes.
Found 1 instance in 1 package
Misc. License Issues
License(Experimental) A package's licensing information has fine-grained problems.
Found 1 instance in 1 package
Environment variable access
Supply chain riskPackage accesses environment variables, which may be a sign of credential stuffing or data theft.
Found 1 instance in 1 package
Unidentified License
License(Experimental) Something that seems like a license was found, but its contents could not be matched with a known license.
Found 1 instance in 1 package
Deprecated
MaintenanceThe maintainer of the package marked it as deprecated. This could indicate that a single version should not be used, or that the package is no longer maintained and any new vulnerabilities will not be fixed.
Found 1 instance in 1 package
59045
17
0
460
6
1
1
80
909
9
1
+ Added@chatopera/q@^1.0.1
+ Added@chatopera/q@1.0.1(transitive)
+ Addedansi-escapes@4.3.2(transitive)
+ Addedansi-regex@5.0.1(transitive)
+ Addedansi-styles@4.3.0(transitive)
+ Addedarchiver@4.0.2(transitive)
+ Addedasync@3.2.6(transitive)
+ Addedchalk@4.1.2(transitive)
+ Addedcli-cursor@3.1.0(transitive)
+ Addedcli-width@3.0.0(transitive)
+ Addedcolor-convert@2.0.1(transitive)
+ Addedcolor-name@1.1.4(transitive)
+ Addedcommander@5.1.0(transitive)
+ Addedcompress-commons@3.0.0(transitive)
+ Addedemoji-regex@8.0.0(transitive)
+ Addedfigures@3.2.0(transitive)
+ Addedget-intrinsic@1.2.7(transitive)
+ Addedhas-flag@4.0.0(transitive)
+ Addedinquirer@7.3.3(transitive)
+ Addedis-fullwidth-code-point@3.0.0(transitive)
+ Addedmimic-fn@2.1.0(transitive)
+ Addedmute-stream@0.0.8(transitive)
+ Addedonetime@5.1.2(transitive)
+ Addedrestore-cursor@3.1.0(transitive)
+ Addedstring-width@4.2.3(transitive)
+ Addedstrip-ansi@6.0.1(transitive)
+ Addedsupports-color@7.2.0(transitive)
+ Addedtype-fest@0.21.3(transitive)
+ Addedzip-stream@3.0.1(transitive)
- Removedansi-escapes@3.2.0(transitive)
- Removedansi-regex@3.0.14.1.1(transitive)
- Removedansi-styles@3.2.1(transitive)
- Removedarchiver@3.1.1(transitive)
- Removedasync@2.6.4(transitive)
- Removedchalk@2.4.2(transitive)
- Removedcli-cursor@2.1.0(transitive)
- Removedcli-width@2.2.1(transitive)
- Removedcolor-convert@1.9.3(transitive)
- Removedcolor-name@1.1.3(transitive)
- Removedcommander@2.20.3(transitive)
- Removedcompress-commons@2.1.1(transitive)
- Removedfigures@2.0.0(transitive)
- Removedget-intrinsic@1.3.0(transitive)
- Removedhas-flag@3.0.0(transitive)
- Removedinquirer@6.5.2(transitive)
- Removedis-fullwidth-code-point@2.0.0(transitive)
- Removedmimic-fn@1.2.0(transitive)
- Removedmute-stream@0.0.7(transitive)
- Removedonetime@2.0.1(transitive)
- Removedrestore-cursor@2.0.0(transitive)
- Removedstring-width@2.1.1(transitive)
- Removedstrip-ansi@4.0.05.2.0(transitive)
- Removedsupports-color@5.5.0(transitive)
- Removedzip-stream@2.1.3(transitive)
Updatedarchiver@^4.0.2
Updatedcommander@^5.1.0
Updatedinquirer@^7.3.2
Updatedsuperagent@^5.3.1