一段时间不活动后,如何从 bot 框架 sdk 发送消息?在节点中

How can I send a message from bot framework sdk after a period of inactivity? In nodejs

我正在使用适用于 Bot Framework 的 nodejs SDK 开发聊天机器人。如果他们在 5 分钟内没有写,我想向用户发送一条消息。 我没有在 bot-framework 文档中找到示例,并且在 Whosebug 中没有启动机器人的解决方案(我不需要它来开始对话)。我需要在哪里创建代码?我有一个 index.js 和一个对话框文件。如何设置计时器并在用户发送消息时重新启动它? 我正在使用直线。

谢谢

您可以通过两种不同的方式来解决这个问题,一种是针对仅使用事件的直线,另一种是针对使用 setTimeout 的所有渠道。直线解决方案需要您的网络聊天客户端上的一些代码,但后者需要您保存对话引用并启动一个新的机器人适配器。这两种方法都可行。

仅限直线

您需要设置您的网络聊天客户端以设置计时器,如果在计时器到期之前没有发送任何活动,则向您的机器人发送一个事件。您需要创建一个自定义商店来执行此操作。这是我过去使用的示例:

            const store = window.WebChat.createStore({}, function(dispatch) { return function(next) { return function(action) {
                if (action.type === 'WEB_CHAT/SEND_MESSAGE') {
                    // Message sent by the user
                    clearTimeout(interval);
                } else if (action.type === 'DIRECT_LINE/INCOMING_ACTIVITY' && action.payload.activity.name !== "inactive") {
                    // Message sent by the bot
                    clearInterval(interval);
                    interval = setTimeout(function() {
                        
                        // Notify bot the user has been inactive
                        dispatch.dispatch({
                            type: 'WEB_CHAT/SEND_EVENT',
                            payload: {
                                name: 'inactive',
                                value: ''
                            }
                        });
                        
                    }, 300000)
                }

                return next(action);
            }}});

这将向您的机器人发送一个名为 'inactive' 的事件。现在您需要设置您的机器人来处理它。所以在你的 this.onEvent 处理程序中你需要做这样的事情:

if (context.activity.name && context.activity.name === 'inactive') {
    await context.sendActivity({
        text: 'Are you still there? Is there anything else I can help you with?',
        name: 'inactive'
    });
}

所有频道

在我输入此内容时,我意识到您应该能够从您的机器人本身发出事件并放弃启动新的机器人适配器实例。但我之前没有尝试过,所以我提供了我现有的解决方案。但是您可能希望尝试在达到超时时发出非活动事件而不是下面的操作。

也就是说,这里有一个您可以在 this.onMessage 处理程序中使用的解决方案。

// Inactivity messages
// Reset the inactivity timer
clearTimeout(this.inactivityTimer);
this.inactivityTimer = setTimeout(async function(conversationReference) {
    console.log('User is inactive');
    try {
        const adapter = new BotFrameworkAdapter({
            appId: process.env.microsoftAppID,
            appPassword: process.env.microsoftAppPassword
        });
        await adapter.continueConversation(conversationReference, async turnContext => {
            await turnContext.sendActivity('Are you still there?');
        });
    } catch (error) {
        //console.log('Bad Request. Please ensure your message contains the conversation reference and message text.');
       console.log(error);
    }
}, 300000, conversationData.conversationReference);

请注意,如果您走这条路,您必须获取并保存 conversationReference,这样您就可以在计时器到期时调用 continueConversation。我通常也在我的 this.onMessage 处理程序中执行此操作,只是为了确保我始终拥有有效的对话引用。您可以使用以下代码获取它(我假设您已经定义了对话状态和状态访问器)。

const conversationData = await this.dialogState.get(context, {});
conversationData.conversationReference = TurnContext.getConversationReference(context.activity);

正如我在第一个解决方案中提到的那样,我相信您应该能够在 try 块中发送不活动事件,而不是启动 bot 适配器。如果您尝试这样做并且有效,请告诉我,以便我更新此解决方案!