{"id":269,"date":"2022-01-12T15:04:15","date_gmt":"2022-01-12T15:04:15","guid":{"rendered":"https:\/\/blog.citrus-lime.com\/crmc\/?p=269"},"modified":"2022-01-12T15:04:16","modified_gmt":"2022-01-12T15:04:16","slug":"creating-a-new-bot-for-teams","status":"publish","type":"post","link":"https:\/\/blog.citrus-lime.com\/crmc\/creating-a-new-bot-for-teams\/","title":{"rendered":"Creating a New Bot for Teams"},"content":{"rendered":"\n<p>This article focuses on the steps required to start developing a new Bot and taking the first steps to publishing this Bot into Teams.<\/p>\n\n\n\n<p>We are going to take you through the first steps of&nbsp;<strong>(1)&nbsp;<\/strong>creating the Web App Bot in Azure,&nbsp;<strong>(2)<\/strong>&nbsp;connecting this to the Code your Bot is going to run,&nbsp;<strong>(3)<\/strong>&nbsp;defining your Bot\u2019s Manifest and uploading into Teams, before&nbsp;<strong>(4)<\/strong>&nbsp;testing the Bot in Teams and looking forward.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">Before we start, a Quick Word on Client App IDs<\/h3>\n\n\n\n<p>Before we get started, we can take a quick look at Client IDs.<\/p>\n\n\n\n<p>These IDs identify Apps within the Microsoft Cloud and so we typically find *everything* we do has a Client ID, and that it will be one of the key variables we have to supply to facilitate communication between Apps.<\/p>\n\n\n\n<p>We saw how this works for an Azure App Registration to communicate with Dynamics, and now we will see this in action for the new Bot we create.<\/p>\n\n\n\n<p>When we create our Web App Bot in Azure &#8211; this will be given a Client ID for the Bot.&nbsp; This Client ID represents the identifier for our App (in this case, a Bot) in the Cloud \u2013 and can be used alongside the Client Secret to communicate with the App, particularly so that other Apps can pass or receive messages with the App.<\/p>\n\n\n\n<p>We can see this Client ID in Azure:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_27FEEF0A.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_759B1B8A.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p>This must then match the manifest of our Bot in Visual Studio, as this is the manifest that we pass to Teams so that the App that is Teams can communicate with the App that is our Bot to bring the two together:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_35650210.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_5C331850.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p>This allows the connection between how we publish our code into Azure to control what the Bot does for us, and how we upload the manifest into Teams to connect our Bot into Teams.<\/p>\n\n\n\n<p>With that in mind \u2013 we are going to look at this process step by step:<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">(1) Defining a New Bot Service in Azure<\/h3>\n\n\n\n<p>To get started with this approach, we can use the following steps to create ourselves a new Web App Bot and connect this into Teams:<\/p>\n\n\n\n<p>In Azure, we can create a new Bot Service and then select Web App Bot as the type of Service we want to create:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_49EA518E.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_70B867CE.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p>This will then let us set the name and parameters for our new Bot:<\/p>\n\n\n\n<p><strong>Bot Handle<\/strong><\/p>\n\n\n\n<p>The Development Name for our Bot<\/p>\n\n\n\n<p><strong>Pricing Tier<\/strong><\/p>\n\n\n\n<p>For Development purposes, we can use the F0 Free Pricing Tier.<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_30824E54.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_1E398792.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p><strong>Bot Template<\/strong><\/p>\n\n\n\n<p>Initially we can leave this as the default Echo Bot C# template<\/p>\n\n\n\n<p><strong>App ID and Password<\/strong><\/p>\n\n\n\n<p>We can leave these to auto-create so that Azure generates us a new Client ID and secret.<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_72F4F08A.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_32BED710.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p>This will then create our Bot in Azure \u2013 this is created in two components, the Web App Bot definition and behind it the App Service.<\/p>\n\n\n\n<p>We can see both in our Resources List in Azure:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_077A4009.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_1956D3D6.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p>This means that we the container that we can publish our code into directly from Visual Studio.<\/p>\n\n\n\n<p>At present this is just a \u2018generic\u2019 bot in a way and so not connected to Teams.<\/p>\n\n\n\n<p>In Azure, we can add the Channel connection to add the link between our Bot in the Cloud and Teams:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_1BFF8F87.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_22B2990A.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p>This will ask us the type of Teams we can connecting with, and confirm our consent for Teams and the Bot the exchange information.<\/p>\n\n\n\n<p>Once done, we can see the connection running for our Bot App.<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_348F2CD7.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_5033B8CD.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<h3 class=\"wp-block-heading\">(2) Deploying our Bot Project into the Bot Service<\/h3>\n\n\n\n<p>Now we have the Bot defined, we will want to publish some of our custom logic into the Bot and start seeing the Bot contribute to our Business Logic within Teams.<\/p>\n\n\n\n<p>The best place to start is a good initial HelloWorld style Bot or other Template that we use before we start adding our bespoke logic in.<\/p>\n\n\n\n<p>In a previous article in this series, we look at our starter Bot Project here and can use this Visual Studio Project to get started \u2013 there is also the Microsoft Teams Bot Example Project available via GitHub here.<\/p>\n\n\n\n<p>Once done and we have our starter Bot in Visual Studio &#8211; we can then deploy our code from Visual Studio into the Bot Service in Azure.<\/p>\n\n\n\n<p>Publishing to Azure is built into the DNA of Visual Studio these days and so is easy to manage through the options in Publish:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_3DEAF20B.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_64B9084B.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p>This will deploy our Bot to the App Service as the container for our code \u2013 which is connected to the Web App Bot that manages the chat communication and the channel connector we have setup between our Bot and Teams.<\/p>\n\n\n\n<p>We can actually test our Bot outside of Teams using the<strong>&nbsp;Test in Web Chat<\/strong>&nbsp;area in Azure and this gives us a means of Unit Testing that our code is uploading correctly and we have the foundation in place.<\/p>\n\n\n\n<p>However our Bot is looking to work with Teams and so take the Teams Message and other inputs into its execution, which means that chances are it won\u2019t do much outside of Teams!<\/p>\n\n\n\n<p>So our next step is to see the Bot in Teams.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">(3) Building our Manifest Package for Teams<\/h3>\n\n\n\n<p>Adding a Bot into Teams means connecting the intended instance of Teams to the logic running in our App Service in Azure \u2013 the Channels connection defines that our Bot is able to connect to Teams, but the Manifest Package is the Solution File that we upload into a particular Teams Instance to add our Bot into that Channel or set of Channels in a Team.<\/p>\n\n\n\n<p>To do this, we have to build our Manifest XML and package up for Teams.<\/p>\n\n\n\n<p>My preference is to do this in our Visual Studio Project so we can define the XML in the same Project as the core logic, and so we can see a Folder containing an example manifest in our starter project \u2013 but this is not absolutely necessary, the Manifest XML and Images Files can be built entirely independently of the Visual Studio Project Files depending on preference.<\/p>\n\n\n\n<p>Drilling into our XML here:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_76959C18.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_2B35F854.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p>The key element initially is ensuring we insert our Application Client ID into both the \u2018id\u2019 tag and the \u2018botid\u2019 tag \u2013 this will inform Teams on upload of the Manifest of your connection to the container in Azure.<\/p>\n\n\n\n<p>We must also supply a Short Name, Full Name and icons for the Bot.<\/p>\n\n\n\n<p>Finally we define the Commands that the Bot makes available \u2013 this is the list of commands that are shown in Teams Chat as what\u2019s possible.<\/p>\n\n\n\n<p>The article here drills into the full detail of the Manifest File in relation to a Teams Bot.<\/p>\n\n\n\n<p>However whilst we are getting up and running, the main areas for each are ensuring we have our Client ID correct and we have the details of the Bot Name and Icons ready to go.<\/p>\n\n\n\n<p>Once we have this \u2013 we can compress our Manifest files into a ZIP and use this ZIP to upload our Bot into Teams.<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_31E901D7.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_58B71817.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p><strong>Zip up the Files in our Manifest Folder and we are ready to go!<\/strong><\/p>\n\n\n\n<h3 class=\"wp-block-heading\">(4) Add our Bot to Teams<\/h3>\n\n\n\n<p>Right \u2013 we\u2019ve done all our steps to build up to getting our Bot into our instance of Microsoft Teams.<\/p>\n\n\n\n<p>We do this by opening Teams (Web or Desktop is fine here) and navigating into&nbsp;<strong>More Apps<\/strong>:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_745BA40D.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_34258A93.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p>Here we have options to add various commercial or publicly available Apps to how we use Teams.<\/p>\n\n\n\n<p>We also have an option for Upload a Customised App that allows us to add our bespoke developed App into Teams \u2013 and this is the option we want here to add our new Bot into Teams.<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_21DCC3D1.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_7AA27A9B.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\"><p><em><strong>NOTE:&nbsp;<\/strong>To do this, you will need to be a suitably powerful Admin who is allowed to add Apps to Teams in Teams Global Policy Settings \u2013 otherwise the Upload a Customised App option will not appear<\/em><\/p><\/blockquote>\n\n\n\n<p>This will ask us for our Manifest ZIP file and we can supply this to add our Bot into Teams.<\/p>\n\n\n\n<p>When it\u2019s not quite right \u2013 we will get a Parsing Error that will ask us to format the Files or Structure in our ZIP, or the XML Content in our Manifest File, and usually we will have one or two loops to get it right as any files or unexpected content will prompt Teams to reject it!<\/p>\n\n\n\n<p>But once its gone in right \u2013 we will see our App installed into Teams.<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_6859B3D9.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_6F0CBD5C.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p>We are not quite done yet as we still need to add our new Bot into 1 or more Teams. (this step can be automated using Graph API but for now, we can do manually)<\/p>\n\n\n\n<p>To add our Bot, we click on the App here and this will present an option for Add to a Team, which we can use to then select a Team and make our Bot available in all the Channels for that Team.<\/p>\n\n\n\n<p>Now we can test our Bot.<\/p>\n\n\n\n<p>Moving into a Channel in the Team, we can start a new Chat in the Channel with @SSO or the Short Name of our Bot and this talks to the Bot \u2013 this will offer us the list of commands possible for the Bot, as dictated from our Manifest File.<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_71B5790D.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_4A7B2FD8.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<blockquote class=\"wp-block-quote is-layout-flow wp-block-quote-is-layout-flow\"><p><em><strong>NOTE:&nbsp;<\/strong>We can have additional commands in the code of our Bot, just that only those well defined in the Manifest will appear to the User as \u2018what can I do\u2019.<\/em><\/p><\/blockquote>\n\n\n\n<p>We can now run our commands and see the outcome of our custom code running within Teams:<\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_38326916.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_0CEDD20F.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p>In the case of this simple example, coming from the code here:<\/p>\n\n\n\n<p><strong>Example Action<\/strong><\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_613D0812.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_3A02BEDD.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p><strong>WhoAmI Action<\/strong><\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_3CAB7A8E.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_435E8411.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p><strong>These being invoked from our central OnMessageActivityAsync Method in the main TeamsConversationBot.cs code:<\/strong><\/p>\n\n\n\n<figure class=\"wp-block-image\"><a href=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_3115BD4F.png\"><img decoding=\"async\" src=\"https:\/\/license.citruslime.com\/cs\/blogs\/crmcs\/image_thumb_5BEE2161.png\" alt=\"image\" title=\"image\" \/><\/a><\/figure>\n\n\n\n<p>This shows the connection from Teams to our logic in Azure and ultimately the code we have published to run there.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">What Next?<\/h3>\n\n\n\n<p>Looking forward, now we have our Bot added to Teams, we can update our code and simply publish to our Azure Web App to add new functionality or implement changes.<\/p>\n\n\n\n<p>Publishing to Azure being our only required step to release new changes.<\/p>\n\n\n\n<p>(so I would always recommend having Dev, Test and Live instances of your Bot so you can have an effective release cycle \u2013 particularly as any changes will be immediately published to all instances of the Bot, and this could be many Teams or even many Clients depending on how widespread your Bot is installed!)<\/p>\n\n\n\n<p>But from my side, we\u2019ve got our Bot, now we want to do something more exciting with it \u2013 and coming from my background, that means start thinking how our Bot can work with Dynamics 365 and Power Automate.<\/p>\n\n\n\n<p>So our next article here is going to take a dive into the code and how we can start adding Business Logic into our Bot.<\/p>\n\n\n\n<h3 class=\"wp-block-heading\">Further Reading<\/h3>\n\n\n\n<p><strong>Microsoft Guide for Building a Bot for Microsoft Teams &#8211;&nbsp;<\/strong><a href=\"https:\/\/docs.microsoft.com\/en-us\/microsoftteams\/platform\/build-your-first-app\/build-bot\"><strong>https:\/\/docs.microsoft.com\/en-us\/microsoftteams\/platform\/build-your-first-app\/build-bot<\/strong><\/a><\/p>\n\n\n\n<p><strong>Upload your Custom App &#8211;&nbsp;<\/strong><a href=\"https:\/\/docs.microsoft.com\/en-us\/microsoftteams\/platform\/concepts\/deploy-and-publish\/apps-upload\"><strong>https:\/\/docs.microsoft.com\/en-us\/microsoftteams\/platform\/concepts\/deploy-and-publish\/apps-upload<\/strong><\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>This article focuses on the steps required to start developing a new Bot and taking the first steps to publishing this Bot into Teams. We are going to take you through the first steps of&nbsp;(1)&nbsp;creating the Web App Bot in Azure,&nbsp;(2)&nbsp;connecting this to the Code your Bot is going to run,&nbsp;(3)&nbsp;defining your Bot\u2019s Manifest and<\/p>\n","protected":false},"author":43,"featured_media":88,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"_price":"","_stock":"","_tribe_ticket_header":"","_tribe_default_ticket_provider":"","_tribe_ticket_capacity":"0","_ticket_start_date":"","_ticket_end_date":"","_tribe_ticket_show_description":"","_tribe_ticket_show_not_going":false,"_tribe_ticket_use_global_stock":"","_tribe_ticket_global_stock_level":"","_global_stock_mode":"","_global_stock_cap":"","_tribe_rsvp_for_event":"","_tribe_ticket_going_count":"","_tribe_ticket_not_going_count":"","_tribe_tickets_list":"[]","_tribe_ticket_has_attendee_info_fields":false,"footnotes":""},"categories":[3,4],"tags":[],"class_list":{"0":"post-269","1":"post","2":"type-post","3":"status-publish","4":"format-standard","5":"has-post-thumbnail","7":"category-crm","8":"category-docdrive365"},"featured_image_src":"https:\/\/blog.citrus-lime.com\/crmc\/wp-content\/uploads\/sites\/30\/2021\/12\/DocDriveSiteimageclouds-scaled.jpg","author_info":{"display_name":"jadesmith","author_link":"https:\/\/blog.citrus-lime.com\/crmc\/author\/jadesmith\/"},"_links":{"self":[{"href":"https:\/\/blog.citrus-lime.com\/crmc\/wp-json\/wp\/v2\/posts\/269","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/blog.citrus-lime.com\/crmc\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/blog.citrus-lime.com\/crmc\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/blog.citrus-lime.com\/crmc\/wp-json\/wp\/v2\/users\/43"}],"replies":[{"embeddable":true,"href":"https:\/\/blog.citrus-lime.com\/crmc\/wp-json\/wp\/v2\/comments?post=269"}],"version-history":[{"count":1,"href":"https:\/\/blog.citrus-lime.com\/crmc\/wp-json\/wp\/v2\/posts\/269\/revisions"}],"predecessor-version":[{"id":270,"href":"https:\/\/blog.citrus-lime.com\/crmc\/wp-json\/wp\/v2\/posts\/269\/revisions\/270"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/blog.citrus-lime.com\/crmc\/wp-json\/wp\/v2\/media\/88"}],"wp:attachment":[{"href":"https:\/\/blog.citrus-lime.com\/crmc\/wp-json\/wp\/v2\/media?parent=269"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/blog.citrus-lime.com\/crmc\/wp-json\/wp\/v2\/categories?post=269"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/blog.citrus-lime.com\/crmc\/wp-json\/wp\/v2\/tags?post=269"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}