ai物联网工程师

tech2022-09-11  125

ai物联网工程师

If you’re keen to learn more on AI, check out our screencast Microsoft Cognitive Services and the Text Analytics API, for AI sentiment in your bot.

如果您想了解有关AI的更多信息,请查看我们的截屏视频Microsoft Cognitive Services和Text Analytics API ,了解您机器人中的AI情绪。

The potential of a personal assistant gets exciting when it has access to personal data and the real world via the Internet of Things. New possibilities arise — from requesting your assistant turn on your lights to asking it how well you slept. We’ll be connecting your Api.ai assistant to the Jawbone Up API as an example of this.

当个人助理可以通过物联网访问个人数据和现实世界时,其潜力会变得令人兴奋。 出现了新的可能性-从要求您的助手打开灯光到询问您的睡眠状况如何。 作为示例,我们将把您的Api.ai助手连接到Jawbone Up API。

Note: this article was updated in 2017 to reflect recent changes to Api.ai.

注意:本文于2017年更新,以反映对Api.ai的最新更改。

您需要什么 (What You’ll Need)

This article builds upon a variety of concepts we’ve already covered in previous articles here at SitePoint. In order to follow along with this tutorial comfortably, you’ll need the following.

本文基于SitePoint先前文章中已经介绍的各种概念。 为了舒适地遵循本教程,您需要以下内容。

An Api.ai agent connected to a simple HTML web app. See this article if you’d like to understand this process. Otherwise, you can download the code from this guide and use it too.

连接到简单HTML Web应用程序的Api.ai代理。 如果您想了解此过程,请参阅本文 。 否则,您可以从本指南中下载代码并使用它。

An agent that has been taught the entity of “sleep”. We created this in Empowering Your Api.ai Assistant with Entities. It should understand concepts like “how much sleep did I have last night?” and “how much REM sleep did I get?” If you’re looking to adapt this to your own IoT device, you’ll need to have created your own custom entity that understands your IoT functionality.

已被告知“睡眠”实体的代理。 我们是在通过实体为您的Api.ai助手赋权的过程中创建的。 它应该理解诸如“昨晚我睡了多少时间”之类的概念。 和“我获得了多少REM睡眠?” 如果您想使其适应自己的物联网设备,则需要创建自己的自定义实体,以了解您的物联网功能。

A general knowledge of Node.js and running a Node server. Without it, you won’t be able to get the server running!

Node.js和运行节点服务器的一般知识。 没有它,您将无法使服务器运行!

Knowledge of how to use the Jawbone UP API (or another API you intend to use). We’ve covered the Jawbone Up API previously in Connecting to the Jawbone Up API with Node.js, and I’ll be referring to sections from that article throughout.

了解如何使用Jawbone UP API(或您打算使用的其他API)。 之前,我们在使用Node.js连接到Jawbone Up API中已经介绍了Jawbone Up API,并且我将始终引用该文章的各个部分。

An SSL certificate to run your site on HTTPS. You’ll need this if working with the Jawbone Up API. As mentioned at the start of this series, overall it’s a bit easier to do a lot of this on HTTPS. We cover how to set up a self signed certificate on the Jawbone Up API article if you’re interested, but it’s not the easiest option these days. You can do it really easily using Let’s Encrypt as mentioned in the first article in the series. Glitch.com also provides a great prototyping environment that comes with HTTPS by default.

用于在HTTPS上运行您的站点的SSL证书。 如果使用Jawbone Up API,则需要此功能。 正如本系列文章开头提到的,总体上,在HTTPS上执行许多操作要容易一些。 如果您有兴趣,我们将在Jawbone Up API文章中介绍如何设置自签名证书 ,但这不是当前最简单的选择。 您可以使用本系列第一篇文章中提到的“让我们加密”来真正轻松地做到这一点。 默认情况下, Glitch.com还提供了HTTPS随附的出色原型开发环境。

代码 (The Code)

All code for this demo is available for you to download and use however you please! You can find it all on GitHub.

您可以下载和使用此演示的所有代码,请您随意使用! 您可以在GitHub上找到所有内容 。

运作方式 (How This Works)

Your Api.ai assistant is already connected to a simple web app that accepts statements via the HTML5 Speech Recognition API. From here, you need to add a new bit of functionality that listens for a specific action from your Api.ai agent. In your case, this is the action of “sleepHours”.

您的Api.ai助手已经连接到一个简单的Web应用程序,该应用程序通过HTML5语音识别API接受语句。 从这里开始,您需要添加一些新功能,以侦听来自Api.ai代理的特定操作。 在您的情况下,这是“ sleepHours”的动作。

Whenever your JavaScript detects this action, it triggers a separate call to your Node.js app to ask the Jawbone API for that data. Once the web app receives this data, your web app turns it into a nice sentence and reads it out — giving your assistant a whole new range of intelligence!

每当您JavaScript检测到此操作时,它都会触发对Node.js应用的单独调用,以要求Jawbone API提供该数据。 Web应用程序接收到这些数据后,您的Web应用程序会将其变成一个漂亮的句子并读出来-为您的助手提供全新的智能范围!

您的项目结构 (Your Project Structure)

I’ve adjusted the app from the initial HTML-only structure to one that uses EJS views so that you can switch pages in your web app when logging into the Jawbone Up API via OAuth. In reality, you only really have one page, but this method allows you to add more in future if needed for other IoT devices. This single view is at /views/index.ejs. You then have your Node server in the root folder as server.js and certificate files in root too. To keep things relatively simple and contained, all front-end JavaScript and CSS is inline. Feel free to move these into CSS and JS files as you prefer, minify them and make them pretty.

我已经将应用程序从最初的仅HTML结构调整为使用EJS视图的结构,以便在通过OAuth登录Jawbone Up API时可以在Web应用程序中切换页面。 实际上,您实际上只有一页,但是此方法允许您将来在其他物联网设备需要时添加更多页面。 该单一视图位于/views/index.ejs 。 然后,将节点服务器作为server.js放在根文件夹中,并将证书文件也放在根目录中。 为了使事情相对简单和包含内容,所有前端JavaScript和CSS都是内联的。 随意将它们随意移动到CSS和JS文件中,将它们缩小并使其漂亮。

响应JavaScript中的Api.ai操作 (Responding to Api.ai Actions in JavaScript)

As you might remember from the previous article, when Api.ai returns a response, it provides a JSON object that looks like so:

您可能还记得上一篇文章,当Api.ai返回响应时,它提供了一个JSON对象,如下所示:

{ "id": "6b42eb42-0ad2-4bab-b7ea-853773b90219", "timestamp": "2016-02-12T01:25:09.173Z", "result": { "source": "agent", "resolvedQuery": "how did I sleep last night", "speech": "I'll retrieve your sleep stats for you now, one moment!", "action": "sleepHours", "parameters": { "sleep": "sleep" }, "metadata": { "intentId": "25d04dfc-c90c-4f55-a7bd-6681e83b45ec", "inputContexts": [], "outputContexts": [], "contexts": [], "intentName": "How many hours of @sleep:sleep did I get last night?" } }, "status": { "code": 200, "errorType": "success" } }

Within that JSON object there are two bits of data you need to use — action and parameters.sleep:

在该JSON对象中,您需要使用两位数据action和parameters.sleep :

"action": "sleepHours", "parameters": { "sleep": "sleep" },

action is the name you gave to the Api.ai action that the user has triggered. In the case of your sleep example, you named it “sleepHours”. parameters contain the variables in your sentence that can change a few details. In the case of sleep, your parameter tells you what type of sleep — “sleep”, “deep sleep”, “light sleep” or “REM sleep” (or just “REM”).

action是您为用户触发的Api.ai操作指定的名称。 在您的睡眠示例中,您将其命名为“ sleepHours”。 parameters包含句子中的变量,可以更改一些细节。 在睡眠的情况下,您的参数告诉您什么类型的睡眠-“睡眠”,“深度睡眠”,“轻度睡眠”或“ REM睡眠”(或简称为“ REM”)。

Initially, in an earlier article on Api.ai, the prepareResponse() function took the JSON response from Api.ai, put the whole thing into your debug text field on the bottom right and took out Api.ai’s verbal response to display in the web app. You completely relied on what your Api.ai agent said, without adding any of your own functionality:

最初,在之前有关Api.ai的文章中, prepareResponse()函数从Api.ai接收JSON响应,将整个内容放入右下角的调试文本字段中,并取出Api.ai的口头响应以显示在网络应用。 您完全依赖Api.ai代理所说的内容,而无需添加任何自己的功能:

function prepareResponse(val) { var debugJSON = JSON.stringify(val, undefined, 2), spokenResponse = val.result.speech; respond(spokenResponse); debugRespond(debugJSON); }

This time around, keep an eye out for the action field and run your own function called requestSleepData() if the action contains "sleepHours". Within this function, pass in the sleep parameter so you know what type of sleep is being requested:

这一次,请注意action字段,如果该动作包含"sleepHours" ,请运行您自己的名为requestSleepData()的函数。 在此函数中,传入sleep参数,以便您知道请求哪种类型的睡眠:

function prepareResponse(val) { var debugJSON = JSON.stringify(val, undefined, 2), spokenResponse = val.result.speech; if (val.result.action == "sleepHours") { requestSleepData(val.result.parameters.sleep); } else { respond(spokenResponse); } debugRespond(debugJSON); }

Within requestSleepData(), request all sleep data from your Node.js server and then filter it by looking at the very first value in the returned array of data (data.items[0].details): this would be last night’s sleep. Within these details, you have data.items[0].details.rem with your REM sleep, data.items[0].details.sound with your deep sleep, data.items[0].details.light with your light sleep and data.items[0].details.duration with the combined amount of sleep recorded:

在requestSleepData() ,从Node.js服务器请求所有睡眠数据,然后通过查看返回的数据数组中的第一个值( data.items[0].details )进行data.items[0].details :这将是昨晚的睡眠。 在这些细节,你有data.items[0].details.rem与REM睡眠, data.items[0].details.sound与你的深度睡眠, data.items[0].details.light与浅睡眠和data.items[0].details.duration与记录的总睡眠时间:

function requestSleepData(type) { $.ajax({ type: "GET", url: "/sleep_data/", contentType: "application/json; charset=utf-8", dataType: "json", success: function(data) { console.log("Sleep data!", data); if (data.error) { respond(data.error); window.location.replace("/login/jawbone"); } switch (type) { case "REM sleep": respond("You had " + toHours(data.items[0].details.rem) + " of REM sleep."); break; case "deep sleep": respond("You had " + toHours(data.items[0].details.sound) + " of deep sleep."); break; case "light sleep": respond("You had " + toHours(data.items[0].details.light) + " of light sleep."); break; case "sleep": respond("You had " + toHours(data.items[0].details.duration) + " of sleep last night. That includes " + toHours(data.items[0].details.rem) + " of REM sleep, " + toHours(data.items[0].details.sound) + " of deep sleep and " + toHours(data.items[0].details.light) + " of light sleep."); break; } }, error: function() { respond(messageInternalError); } }); }

toHours() is a crude and quick function that formats your times into sentences like “1 hour, 53 minutes and 59 seconds”:

toHours()是一种粗略而快捷的函数,可将您的时间格式化为“ 1小时53分59秒”之类的句子:

function toHours(secs) { hours = Math.floor(secs / 3600), minutes = Math.floor((secs - (hours * 3600)) / 60), seconds = secs - (hours * 3600) - (minutes * 60); hourText = hours + (hours > 1 ? " hours, " : " hour, "); minuteText = minutes + (minutes > 1 ? " minutes " : " minute "); secondText = seconds + (seconds > 1 ? " seconds" : " second"); return hourText + minuteText + "and " + secondText; }

As you’ll see when looking into the requestSleepData() function, the end result is a call to respond() — the same function that previously took Api.ai’s voice response. You reuse your existing functionality to bring speech to your own response, allowing your assistant to tell the user this information once it’s ready.

正如您在查看requestSleepData()函数时所看到的那样,最终结果是调用了response respond() ,该函数先前与Api.ai的语音响应相同。 您可以重用现有功能,以使语音响应自己的React,使您的助手在准备好信息后就可以告诉用户。

One last aspect of your front-end JavaScript to point out is error handling. If you have an issue with how Jawbone returns data (usually due to not being logged into the service), your server responds with a JSON value in the format of {"error" : "Your error message"}. The assistant sees this and automatically takes the user to your OAuth login page:

要指出的前端JavaScript的最后一个方面是错误处理。 如果您对Jawbone返回数据的方式有疑问(通常是由于未登录服务),则服务器将以{"error" : "Your error message"}格式返回JSON值。 助手会看到此情况,并自动将用户带到您的OAuth登录页面:

if (data.error) { respond(data.error); window.location.replace("/login/jawbone"); }

您的Node.js服务器 (Your Node.js Server)

Your Node.js server is based on the one used in Connecting to the Jawbone UP API with Node.js. If any of the code looks confusing, feel free to refer to that earlier article, as it explains all about connecting to the Jawbone API via OAuth and setting up an HTTPS server to run it. If you don’t have a Jawbone Up, the same concepts can be used for other IoT devices. You would just need to add your own methods of responding to GET requests with different data (and you may not need to worry about OAuth). The Jawbone Up data here is just an example.

您的Node.js服务器基于使用Node.js连接到Jawbone UP API中使用的服务器 。 如果任何代码看起来令人困惑,请随时参考该较早的文章,因为它解释了有关通过OAuth连接到Jawbone API以及设置HTTPS服务器以运行它的所有内容。 如果您没有Jawbone Up,则可以将相同的概念用于其他IoT设备。 您只需要添加自己的方法即可使用不同的数据来响应GET请求(并且您不必担心OAuth)。 这里的Jawbone Up数据只是一个例子。

Your Jawbone data has been adjusted from the earlier article to provide a simple JSON response rather than formatting it all into a table template view. The variables of up and options have been moved to global variables so that they can be reused in multiple requests to the API (in that other SitePoint example, we only requested data in one big chunk each time).

您的Jawbone数据已根据上一篇文章进行了调整,以提供简单的JSON响应,而不是将其全部格式化为表格模板视图。 up和options变量已移至全局变量,以便可以在对API的多次请求中重复使用(在另一个SitePoint示例中,我们每次仅请求一大块数据)。

To log into the Jawbone API via OAuth, the user can go to /login/jawbone. However, as you saw above, they don’t need to know to do this. Your assistant can also redirect them if it notices they aren’t logged in. You could also add a new intent into your Api.ai agent that understands the phrase “log me into my Jawbone Up data”, if you wanted to make this truly seamless. Your login route in Node.js looks like so:

要通过OAuth登录Jawbone API,用户可以转到/login/jawbone 。 但是,正如您在上面看到的,他们不需要知道这样做。 您的助手也可以重定向到它们,如果发现它们尚未登录。您还可以在Api.ai代理中添加一个新意图,该意图可以理解“将我登录到我的Jawbone Up数据中”这一短语,如果您想真正做到这一点的话无缝。 您在Node.js中的登录路线如下所示:

app.get("/login/jawbone", passport.authorize("jawbone", { scope: ["basic_read","sleep_read"], failureRedirect: "/" }) );

Once you’ve logged into the Jawbone API via passport.use("jawbone", new JawboneStrategy()), assign this access to your up variable and direct the user to /barry. You could redirect the user to any path of your choice, as long as it’s different from your root directory (that seemed to just cause an endless struggle for my server). I chose /barry, as I named my assistant Barry and thought it self explanatory (the page shows the exact same index view and thus isn’t different in any way). You could also use this as a way of providing a different view for users who have logged into their Jawbone device successfully if you so desire. Once logged in, the user can go back to the root https://localhost:5000 page and use Up functionality as well.

通过passport.use("jawbone", new JawboneStrategy())登录到Jawbone API后,将此访问权限分配给您的up变量,并将用户定向到/barry 。 您可以将用户重定向到您选择的任何路径,只要它与您的根目录不同即可(这似乎为我的服务器带来了无尽的麻烦)。 我选择了/barry ,因为我命名了助手Barry并认为它可以自我解释(该页面显示了完全相同的索引视图,因此在任何方面都没有区别)。 如果您愿意,也可以使用此方法为成功登录其Jawbone设备的用户提供不同的视图。 登录后,用户可以返回到根https://localhost:5000页面并使用Up功能。

发回您的物联网数据 (Sending Back Your IoT Data)

Your retrieval of Jawbone data is done in a very simple way upon receiving a GET request for /sleep_data. Check if the up variable is defined: if not, your user hasn’t logged in and you tell the web app this so that it can perform the redirection and tell the user they’ll need to log in. Do the same thing if Jawbone returns any errors when you call up.sleeps.get() and if jawboneData.items isn’t defined:

收到对/sleep_data的GET请求后,可以非常简单的方式检索Jawbone数据。 检查是否定义了up变量:如果未定义,则您的用户尚未登录,您将此通知Web应用程序,以便它可以执行重定向并告诉用户他们需要登录。如果Jawbone,请执行相同的操作当您调用up.sleeps.get()且未定义jawboneData.items时,将返回任何错误:

app.get("/sleep_data", function(req, resp) { if (up !== undefined) { up.sleeps.get({}, function(err, body) { if (err) { console.log("Error receiving Jawbone UP data"); resp.send({"error": "Your sleep tracker isn't talking to me. Let's try logging in again."}); } else { var jawboneData = JSON.parse(body).data; if (jawboneData.items) { resp.send(jawboneData); } else { console.log("Error: " + jawboneData); resp.send({"error": "Your sleep tracker isn't talking to me. Let's try logging in again."}); } } }); } else { console.log("Up is not ready, lets ask to log in."); resp.send({"error": "Your sleep tracker isn't talking to me. Let's try logging in again."}); } });

The errors here could be caused by other factors too, but to keep it simple, I’m focusing on getting them to try logging in again. In a production level app, you’d want to look into various causes and adjust your response.

这里的错误也可能是由其他因素引起的,但是为了简单起见,我专注于让他们尝试再次登录。 在生产级应用程序中,您需要调查各种原因并调整响应。

If all is well and you receive a valid response, send it as a JSON response back to the web app to read and parse through nicely:

如果一切正常,并且您收到了有效的响应,请将其作为JSON响应发送回Web应用程序,以很好地阅读和解析:

if (jawboneData.items) { resp.send(jawboneData); }

With the web app and your Node.js server working together, you should be able to retrieve sleep data from your Jawbone Up device now. So let’s give it a go.

在Web应用程序和Node.js服务器协同工作的情况下,您现在应该能够从Jawbone Up设备检索睡眠数据。 因此,让我们开始吧。

行动中 (In Action)

Run your server with the usual node server.js. Remember that you’ll need to have run npm install for your npm modules and will need to have a certificate on your server to run it via HTTPS.

使用通常的node server.js运行服务器。 请记住,您需要为npm模块运行npm install ,并且需要在服务器上具有证书才能通过HTTPS运行它。

Visiting https://localhost:5000 in your web browser should bring you to your AI assistant. (If you’re using a service like Glitch, you’ll have a Glitch URL instead.) Ask it how much sleep you’ve had:

在网络浏览器中访问https://localhost:5000应该会带您进入AI助手。 (如果您使用的是诸如Glitch之类的服务,则将改为使用Glitch URL。)询问您已睡了多少时间:

Turns out you aren’t logged in yet. It directs you to the Jawbone Up OAuth login screen. Log in and agree to provide access to your data, then click “Agree”:

原来您尚未登录。 它会将您定向到Jawbone Up OAuth登录屏幕。 登录并同意提供对您的数据的访问,然后单击“同意”:

If you ask it this time around, you’ll receive the right answer:

如果您这次要求这样做,您将获得正确的答案:

You can also ask it something more specific, such as “How much REM did I get?” to test out the parameters:

您还可以询问一些更具体的信息,例如“我获得了多少REM?” 测试参数:

结论 (Conclusion)

That concludes quite a varied exploration of Api.ai’s capabilities for now! You could expand upon this example to allow it to understand date ranges (e.g. “How much sleep did I get on Tuesday?”) or to format the time slightly better (notice a slight bug in one of the responses?). You might have much nicer and shorter ways of phrasing the responses too. Personalize it — make it your own!

到目前为止,对Api.ai的功能进行了各种各样的探索 ! 您可以扩展此示例,以使其理解日期范围(例如“星期二我睡了多少时间?”)或略微改善时间格式(注意其中一个响应中的错误)。 您也可能有更好和更短的短语表达方式。 个性化-自己制作!

As you can see, by using these methods you can connect up any Node.js compatible or web API compatible service to your Node.js server, hook it up to an intent in your Api.ai agent and teach it all sorts of things! You could connect up plenty of IoT devices via IFTTT, connect up your LIFX smart lights via IFTTT or even connect up your very own Nodebot. Possibilities are limited only by the devices you have at your disposal!

如您所见,通过使用这些方法,您可以将任何与Node.js兼容或与Web API兼容的服务连接到Node.js服务器,将其与Api.ai代理中的意图挂钩并进行各种操作! 您可以通过IFTTT连接大量物联网设备,通过IFTTT 连接LIFX智能灯,甚至可以连接自己的Nodebot 。 可能性仅受您拥有的设备限制!

If you’ve been following along and building your own personal assistant using Api.ai, I’d love to hear how you went! What have you connected it to? Let me know in the comments below, or get in touch with me on Twitter at @thatpatrickguy.

如果您一直在使用Api.ai并建立自己的私人助理,我很想听听您的情况! 您连接了什么? 在下面的评论中让我知道,或者在Twitter上通过@thatpatrickguy与我联系 。

Give your AI the human touch with a sentiment tool. Check out our screencasts on the Microsoft Cognitive Services and the Text Analytics API.

使用情感工具让您的AI具有人性化的感觉。 查看我们有关Microsoft Cognitive Services和Text Analytics API的截屏视频。

翻译自: https://www.sitepoint.com/how-to-connect-your-api-ai-assistant-to-the-iot/

ai物联网工程师

相关资源:2020年中国智能物联网(AIoT)白皮书.pdf
最新回复(0)