使用Bot Framework和DirectLine集成测试(1)

· 2 分钟阅读

自从我在一家公司工作一段时间后,我就被分配从事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 存储库中。