Security News
Node.js EOL Versions CVE Dubbed the "Worst CVE of the Year" by Security Experts
Critics call the Node.js EOL CVE a misuse of the system, sparking debate over CVE standards and the growing noise in vulnerability databases.
finochat-botkit
Advanced tools
机器人框架主要基于Matrix聊天协议接入FinoChat应用并通过FSM(有限状态机)管理会话状态,以及FinoChat ConvoUI协议扩展实现的聊天机器人。
npm install finochat-botkit
nodejs版本要求为v9.4.0
config.js说明
module.exports = {
// 以下配置接口和机器人账号仅供演示测试用
homeserver: process.env.HOMESERVER || "https://api.finolabs.club",
loginUrl: process.env.LOGIN_URL || "https://api.finolabs.club/api/v1/registry/botlogin",
fcid: process.env.FCID || "@test-bot:finolabs.club",
password: process.env.PASSWORD || "123456",
ENABLE_MONITOR: process.env.ENABLE_MONITOR || false
logLevel: 'debug',
timeout: 30000,
routelist: [],
whitelist: [],
blacklist: [],
};
const botkit = require('finochat-botkit');
const States = {
INIT: 'INIT',
STEP1: 'STEP1',
STEP2: 'STEP2'
};
继承botkit.Bot类
class demoBot extends botkit.Bot
引入状态机和匹配 API
// 引入状态机API
const { startWith, when, goto, stay, stop } = botkit.DSL(fsm);
// 引入匹配API
const { match, BodyCase, ActionCase, CommandCase, DefaultCase } = botkit.Matcher;
状态机API基本用法
// 初始化状态,接收一个状态参数
startWith(States.INIT);
// 描述某个状态,接收一个状态参数,返回一个asnyc回调函数
// sender发送消息的用户信息,content用户发送的消息体(注意:content.body才是消息体文本内容)
when(States.STEP1)(asnyc (sender, content) => {
// 机器人发送消息接口,第一个参数为房间ID,第二个参数为JSON消息体
bot.sendMessage(sender.roomId, { body: 'hello from bot' });
// 机器人发送文本消息接口,第一个参数为房间ID,第二个参数为具体文本
bot.sendMessage(sender.roomId, 'hello from bot');
// 描述状态转移,全部都可以链式调用withConvoMsg方法给用户附带发送消息,其中goto接收下一个状态作为参数
return stop()/stay()/goto(States.STEP2).withConvoMsg('Hi there!');
});
匹配API基本用法
when(States.STEP1)(asnyc (sender, content) => {
// 匹配函数,接收第一个参数(content消息体)和其他具体匹配方法作为后续参数传入
return match(content,
// 普通聊天文本消息匹配,支持字符串和正则表达式,匹配成功后做对应的逻辑处理
BodyCase('Hey bot!')(() => {
return goto(States.STEP1).withConvoMsg('Hi there!');
})
);
});
new demoBot(require('config')).run();
// 引入机器人框架依赖
const botkit = require('finochat-botkit');
// 定义状态机的各种状态
const States = {
INIT: 'INIT',
STEP1: 'STEP1',
STEP2: 'STEP2'
};
// 创建自己的机器人
class demoBot extends botkit.Bot {
// 机器人被邀请加入房间
onJoinRoom(bot, roomId, userId, displayName) {
return `亲,我是DemoBot【roomId: ${roomId}, userId: ${userId}, displayName: ${displayName}】`;
}
// 用户被邀请加入房间
onUserJoinRoom(bot, roomId, userId, displayName) {
return this.onJoinRoom(bot, roomId, userId, displayName);
}
// 用户当前视图切换入房间
onUserEnterRoom(bot, roomId, userId, displayName) {
return this.onJoinRoom(bot, roomId, userId, displayName);
}
// 会话超时结束
onTimeout(bot, roomId, userId, displayName) {
return `会话结束【roomId: ${roomId}, userId: ${userId}, displayName: ${displayName}】`;
}
// 状态机定义函数, 主要的逻辑写在这里
describe(fsm, bot) {
/**
* 状态机 DSL
* startWith 描述状态机的初始状态和初始 data,只需调用一次
* when 描述某个状态下,发生Event时,Bot业务执行与状态迁移的细节
* goto 用于生成when()函数的返回值,返回 nextState
* stay goto(CurrentState)的另一种形式,停留在本状态
* stop goto(Done)的另一种形式,结束会话
*/
const { startWith, when, goto, stay, stop } = botkit.DSL(fsm);
/**
* matcher API
* BodyCase 匹配普通聊天中的string, 支持变长 pattern(String or RegExp type)
* ActionCase 匹配convoUI消息的action,支持变长 pattern(String or RegExp type)
* CommandCase 匹配convoUI消息的command类型,支持变长pattern(String or RegExp type)
* DefaultCase 模式匹配的Default分支
*/
const { match, BodyCase, ActionCase, CommandCase, DefaultCase } = botkit.Matcher;
// 初始化状态
startWith(States.INIT);
// INIT状态描述
when(States.INIT)(async (sender, content) => {
// 匹配函数,接收第一个参数(content消息体)和其余参数(消息匹配方法)
return match(content,
// 匹配消息成功后回调,返回客户端消息(withConvoMsg方法)并转移到STEP1状态
BodyCase('Hey bot!')(() => {
return goto(States.STEP1).withConvoMsg('Hi there!');
})
);
});
when(States.STEP1)(async (sender, content) => {
return match(content,
ActionCase('action1')(() => {
return goto(States.STEP2).withConvoMsg('U r in Step2 now');
}),
DefaultCase(() => {
// ConvoUI工厂方法创建Assist消息
const ui = botkit.ConvoFactory.ui()
// body文本在ConvoUI无法渲染时显示,类似HTML中img标签的alt提示属性
.setBody('assist demo')
// Layout工厂方法创建带两个按钮的Assist消息
.setPayload(
botkit.LayoutFactory.assist().setTitle('assist').addItems(
botkit.ActionFactory.button('button1', 'action1')
botkit.ActionFactory.button('button2', 'action2')
)
);
return stay().withConvoMsg(ui);
})
);
});
when(States.STEP2)(async (sender, content) => {
return match(content,
BodyCase('apple')(() => {
return stop().withConvoMsg('You can buy an Apple product in https://www.apple.com/');
})
);
});
}
}
// 机器人运行
new demoBot(require('config')).run();
状态机describe()
的方法体内可以使用如下两种方式共享变量(session scope)
using()
. 这里建议通过 spread-rest
语法构造 immutable object 对象。后续会方便利用到状态跟踪,重演,TimeTravel Debugging 等很多玩法。在回调函数内,可以不借助 matcher API,通过判断 content 或者 data 的具体细节来控制分支走向, 获得最大的灵活度:
when(MyStates.IDLE)(async (sender, content, data) => {
if(content.body === "step1") {
return goto(MyStates.STEP1).withConvoMsg({body: "I goto step1!"});
} else if (content.body === "开始业务2") {
return goto(MyStates.STEP2)
}
return stay().withConvoMsg({body: "Stay!"});
});
FAQs
finochat bot framework
We found that finochat-botkit demonstrated a not healthy version release cadence and project activity because the last version was released a year ago. It has 1 open source maintainer collaborating on the project.
Did you know?
Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.
Security News
Critics call the Node.js EOL CVE a misuse of the system, sparking debate over CVE standards and the growing noise in vulnerability databases.
Security News
cURL and Go security teams are publicly rejecting CVSS as flawed for assessing vulnerabilities and are calling for more accurate, context-aware approaches.
Security News
Bun 1.2 enhances its JavaScript runtime with 90% Node.js compatibility, built-in S3 and Postgres support, HTML Imports, and faster, cloud-first performance.