使用Bot Framework和DirectLine集成测试(1)
自从我在一家公司工作一段时间后,我就被分配从事Bot Framework的集成测试工作。
我在小组中的工作是使机器人尽可能稳定,但首先,什么是 Bot Framework?
构建、连接、部署和管理智能机器人,以便在网站、应用程序、Cortana、Microsoft Teams、Skype、Slack、Facebook Messenger 等上与用户自然交互。快速开始使用完整的机器人构建环境,同时只需为您使用的内容付费。
您可以在此处找到有关 Bot Framework 的更多信息。
以下解释不会涵盖Bot Framework如何工作的所有基本信息,如果您不明白,请去查看官方文档。
为什么需要集成测试?
需要集成测试,因为每当我的一位同事推送修复、新功能甚至新错误时,该测试都会在将代码推送到生产之前运行,如果任何测试失败,代码将不会进入生产,这意味着最终用户不会遇到错误。
机器人集成测试?
我确实相信在机器人中,集成测试非常重要。你不可能拥有一个机器人,其中的某些菜单不起作用,或者某些功能不返回任何内容。
公司正在为他们的客户使用机器人,因为他们不希望人们忙于解决他们的问题,如果机器人可以帮助用户,其他员工将能够利用他们的时间做更重要的事情。
解决方案概述。
为了完成这项工作,我在 Visual Studio 中使用了一个测试项目,该项目将使用 WebClient 作为 API Rest 和一个 Json 文件,我们将在其中存储我们的案例。
JSON 文件
{
"secret": "direct-line-secret",
"directlineGenerateTokenEndpoint": "https://directline.botframework.com/v3/directline/tokens/generate",
"directlineConversationEndpoint": "https://directline.botframework.com/v3/directline/conversations/",
"entries": [
{
"name": "DecirHola",
"request": {
"type": "message",
"text": "Hola",
"from": {
"id": "default-user",
"name": "User"
},
"locale": "es",
"textFormat": "plain",
"timestamp": "2018-04-09T08:04:37.195Z",
"channelData": {
"clientActivityId": "1523261059363.6264723268323733.0"
},
"entities": [
{
"type": "ClientCapabilities",
"requiresBotState": true,
"supportsTts": true,
"supportsListening": true
}
],
"id": "61hacck8j6jg"
},
"response": {
"type": "message",
"timestamp": "2018-04-09T08:04:37.901Z",
"localTimestamp": "2018-04-09T09:04:37+01:00",
"serviceUrl": "http://localhost:50629",
"channelId": "emulator",
"from": {
"id": "j98bbdf097a",
"name": "Bot"
},
"conversation": {
"id": "eabcie4be8ak"
},
"recipient": {
"id": "default-user"
},
"locale": "es",
"text": "No tengo respuesta para eso.",
"attachments": [],
"entities": [],
"replyToId": "61hacck8j6jg",
"id": "47me557ikbf7"
},
"assert": "Request.Text == Response.Text"
}
]
}
如您所见,我们有:
- 直线秘密 -> 来自已发布机器人的秘密
- Directline 令牌生成端点 -> 使用秘密获取令牌的端点
- 直接对话端点 -> 端点以便进行对话
- 条目 -> 测试用例
- 请求 -> 我们发送到对话的内容
- 响应 -> 我们期望得到什么
- 断言 -> 我们在比较什么
反序列化
我们已经拥有完美格式化的 json 文件,现在我们必须将其加载到解决方案中,因此我们将使用 JSON.NET 和一些类。首先,我们有条目集合,其中包含所有内容,然后我们为每个集合提供一个条目列表。
/// <summary>
/// Object to parse from the file
/// </summary>
public class TestEntriesCollection
{
/// <summary>
/// DirectLine Secret
/// </summary>
[JsonProperty("secret")]
public string Secret { get; set; }
/// <summary>
/// Endpoint to get the token using the secret for DirectLine
/// </summary>
[JsonProperty("directlineGenerateTokenEndpoint")]
public string DirectLineGenerateTokenEndpoint { get; set; }
/// <summary>
/// Endpoint for a conversation in DirectLine
/// </summary>
[JsonProperty("directlineConversationEndpoint")]
public string DirectLineConversationEndpoint { get; set; }
/// <summary>
/// Entries list
/// </summary>
[JsonProperty("entries")]
public List<TestEntry> Entries { get; set; }
}
这是具有测试用例的名称、请求、响应和断言的对象。
public class TestEntry
{
/// <summary>
/// Entry name
/// </summary>
[JsonProperty("name")]
public string Name { get; set; }
/// <summary>
/// Activity requested by the entry
/// </summary>
[JsonProperty("request")]
public Activity Request { get; set; }
/// <summary>
/// Activity response expected by the entry
/// </summary>
[JsonProperty("response")]
public Activity Response { get; set; }
/// <summary>
/// Assert value in string
/// </summary>
[JsonProperty("assert")]
public string Assert { get; set; }
}
测试用例中从json解析为对象
有了解析对象的类,这很容易,因为我们需要作为对象来读取。
// Load entries from file
var path = System.IO.File.ReadAllText(@"C:\data.json");
// Deserialize to object
var data = JsonConvert.DeserializeObject<TestEntriesCollection>(path);
现在有了这个集合,我们将能够循环它并使用例如 foreach 来获取信息。
foreach (TestEntry entry in data.Entries)
{
....
}
这就是这部分的全部内容,下一部分将包括 DirectLine 的授权,请记住所有代码都存储在我的 github 中的 this 存储库中。