如何使 DialogFlow Google 代理响应并确认 Firebase 的字段更改


'use strict';
const functions = require('firebase-functions');
const admin = require('firebase-admin');
const {WebhookClient} = require('dialogflow-fulfillment');
process.env.DEBUG = 'dialogflow:*'; // enables lib debugging statements
admin.initializeApp({
credential: admin.credential.applicationDefault(),
databaseURL: "https://my_db.firebaseio.com/",
});
var database = admin.database();
var transition = database.ref('/stage');

exports.dialogflowFirebaseFulfillment = functions.https.onRequest((request, response) => {
console.log('Inside :) yessssssss !');
const agent = new WebhookClient({ request, response });

function moveToStage (agent) {
transition.set('2');
agent.add('Welcome to xx console. Please accept the notification on your watch');
}

transition.on('value', (snapshot) => {
console.log("Reading value succesfully from firebase");
console.log(snapshot.val());
if(snapshot.val() == '3'){
agent.add('Thank you for granting me the access.');
// OR
// response.setHeader('Content-Type','applicaiton/json');
// response.send(JSON.stringify({"fulfillmentText": 'Thank you for granting me the access.'}));
}
});

let intentMap = new Map();
intentMap.set('welcome_and_ask_to_sync', moveToStage);
agent.handleRequest(intentMap);
});

我有一个意向welcome_and_ask_to_sync,它已经激活了webhook。当Intent由成功的语音输入触发时,它会用来自代理的文本/语音进行响应,并更新相应firebase DB中的字段stage

现在,在某些情况下,另一个外部应用程序会更新firebaseDB中的stage字段。

没有这一部分在履行代码中,wtahces改变

transition.on('value', (snapshot) => {
console.log("Reading value succesfully from firebase");
console.log(snapshot.val());
if(snapshot.val() == '3'){
agent.add('Thank you for granting me the access.');
// OR
// response.setHeader('Content-Type','applicaiton/json');
// response.send(JSON.stringify({"fulfillmentText": 'Thank you for granting me the access.'}));
}
});

这里的意图是让谷歌主页说出一些东西,比如Thank you for granting me the access.

注意:我不需要被解雇的意图(很抱歉之前的混乱(。我只需要谷歌家庭语音代理来确认这个变化/触发

现在,当我观察日志时,我看到它在这里断裂agent.add('Thank you for granting me the access.');

错误日志有点像:

Error: Can't set headers after they are sent. at ServerResponse.OutgoingMessage.setHeader (_http_outgoing.js:356:11) at transition.on (/user_code/index.js:36:22) at /user_code/node_modules/firebase-admin/node_modules/@firebase/database/dist/index.node.cjs.js:4465:22 at exceptionGuard (/user_code/node_modules/firebase-admin/node_modules/@firebase/database/dist/index.node.cjs.js:691:9) at EventList.raise (/user_code/node_modules/firebase-admin/node_modules/@firebase/database/dist/index.node.cjs.js:9727:17) at EventQueue.raiseQueuedEventsMatchingPredicate_ (/user_code/node_modules/firebase-admin/node_modules/@firebase/database/dist/index.node.cjs.js:9681:41) at EventQueue.raiseEventsForChangedPath (/user_code/node_modules/firebase-admin/node_modules/@firebase/database/dist/index.node.cjs.js:9665:14) at Repo.onDataUpdate_ (/user_code/node_modules/firebase-admin/node_modules/@firebase/database/dist/index.node.cjs.js:12770:26) at PersistentConnection.onDataPush_ (/user_code/node_modules/firebase-admin/node_modules/@firebase/database/dist/index.node.cjs.js:12070:18) at PersistentConnection.onDataMessage_ (/user_code/node_modules/firebase-admin/node_modules/@firebase/database/dist/index.node.cjs.js:12064:18)

因此,基本问题仍然存在:我如何让代理说出/更新文本响应并确认DB的字段更改

简单的答案是你不能——当然不是你现在的做法。

一旦响应从webhook发送回Dialogflow,HTTPS连接就会关闭,任何进一步的回复都会生成您看到的错误。

此外,AoG和Dialogflow使用的对话模型是,用户必须始终发起每一轮对话。奥格不可能在这一点上"宣布"什么。这会被认为有点侵入性。

你可以通过谷歌上的Actions发送通知,当用户确认通知时,Actions会重新启动对话。然而,通知只发送给智能手机,而不是扬声器。因此,这可能无法满足您的需求。

如果你只希望在初次发送后很快进行一些更新,你可能想看看在等待更多更新时,是否可以使用媒体响应以"暂停音乐"来保持对话。当"暂停音乐"结束时,它将向您的Action发送一个事件,您可以重新启动暂停音乐或回复。在这种情况下,您不会使用.on()方法来接收更新,但必须在每次媒体播放结束时检查是否有未发送的更新。

最新更新