Develop Task Modules For MS Teams With Yo Teams

Overview

 
Task modules enable us to implement modal popup experiences in MS Teams applications. In this article, we will create task modules in a custom Microsoft Teams app using Yo Teams.
 

Task Modules overview

 
Task modules help to implement popup in MS Teams applications. Inside the popup you can run any of the below,
  • Custom HTML and JavaScript code
  • Iframe based widgets
  • Adaptive cards
From the MS Teams' point of view, task modules can be considered as a tab inside a popup. The task modules can be invoked from any of the below,
  • Channel and personal tab: Any button or link can invoke a task module by opening a popup.
  • Bot: Button on cards sent from the bot can invoke a task module.
  • Deeplink: You can compose a deeplink to invoke a task module.
Prerequisites
 
Install below to get started,
  • Node.js - v10.* or higher
  • NPM (gets installed with Node.js) - v6.* or higher
  • Gulp - v4.* or higher
  • Yeoman - v3.* or higher
  • Yeoman Generator for Microsoft Teams - v2.13.0 or higher
  • Visual Studio Code
Install Yeoman, Gulp, and Typescript compiler globally with NPM.
  1. npm install yo gulp-cli typescript -g  
Install generator-teams globally with NPM.
  1. npm install generator-teams -g  
If you wish to install preview version of the generator, use the below command.
  1. npm install generator-teams@preview --g  

Implement task modules with Yo Teams

 
Let us generate a solution with Yo Teams.
 
On the command prompt, type the below command.
  1. yo teams  
Follow the wizard to set up the solution.
 
Develop Task Modules For MS Teams With Yo Teams
 
On the command prompt, type code . to open the solution in visual studio code.
 

Use the latest version of Teams manifest and SDK

 
Run the below command to ensure the project is using the latest version of Teams manifest & SDK.
  1. npm i @microsoft/teams-js  
Modifications to manifest.json
 
Under the manifest folder, open the manifest.json file and make the below changes,
  • Change the $schema property to https://developer.microsoft.com/en-us/json-schemas/teams/v1.7/MicrosoftTeams.schema.json
  • Change the manifestVersion property to 1.7.
Modifications to gulp.config.js
 
Under the root folder, open the gulp.config.js file and make below changes,
 
Add the following to the SCHEMAS property.
  1. {  
  2.     version: "1.7",  
  3.     schema: "https://developer.microsoft.com/en-us/json-schemas/teams/v1.7/MicrosoftTeams.schema.json"  
  4. }  

Test the personal tab

 
Before customizing the tab, let us test it without any customizations applied.
 
From the command prompt, navigate to the root folder for the project and execute the below command:
  1. gulp ngrok-serve  
Develop Task Modules For MS Teams With Yo Teams
 
Open a browser and navigate to the ngrok URL displayed in the console:
 
Develop Task Modules For MS Teams With Yo Teams
Update the URL in the browser to load the tab created from the scaffolding process.
 
Develop Task Modules For MS Teams With Yo Teams
Now, let us try to load the tab in MS Teams. In the browser, navigate to here.
 
Using the app bar navigation menu, select the More added apps button. Then select More apps.
 
Develop Task Modules For MS Teams With Yo Teams
 
Select Upload a custom app > Upload for me or my teams.
 
Upload the app package (a ZIP file) from the project's ./package folder.
 
Develop Task Modules For MS Teams With Yo Teams
 
Click Add.
 
Develop Task Modules For MS Teams With Yo Teams
 
The app will be displayed in MS Teams as below,
 
Develop Task Modules For MS Teams With Yo Teams
 

Adaptive Cards

 
Adaptive Cards are a cross-product specification for various Microsoft products including Bots, Outlook, Teams, and Windows. An Adaptive Card is represented as a JSON object. The JSON string defines all the controls, text, and actions that the hosting application will use to render the card.
 
Below is a JSON example of an Adaptive Card that contains an input box and a single submit button,
  1. {  
  2.   "$schema""http://adaptivecards.io/schemas/adaptive-card.json",  
  3.   "type""AdaptiveCard",  
  4.   "version""1.0",  
  5.   "body": [  
  6.     {  
  7.       "type""Container",  
  8.       "items": [  
  9.         {  
  10.           "type""TextBlock",  
  11.           "text""YouTube Video Selector",  
  12.           "weight""bolder",  
  13.           "size""extraLarge"  
  14.         }  
  15.       ]  
  16.     },  
  17.     {  
  18.       "type""Container",  
  19.       "items": [  
  20.         {  
  21.           "type""TextBlock",  
  22.           "text""Enter the ID of a YouTube video to show in the task module player.",  
  23.           "wrap"true  
  24.         },  
  25.         {  
  26.           "type""Input.Text",  
  27.           "id""youTubeVideoId",  
  28.           "value"""  
  29.         }  
  30.       ]  
  31.     }  
  32.   ],  
  33.   "actions": [  
  34.     {  
  35.       "type""Action.Submit",  
  36.       "title""Update"  
  37.     }  
  38.   ]  
  39. }  
Add above json content by creating a file at src\app\scripts\youTubePlayerTab\YouTubeSelectorCard.json
 

Using Adaptive Cards in Microsoft Teams task modules

 
Once we have an Adaptive card ready, we will create a task module to display it and handle the submission action.
 
Open the file src\app\scripts\youTubePlayerTab\YouTubePlayerTab.tsx
 
Update the render method as below,
  1. public render() {  
  2.         return (  
  3.             <Provider theme={this.state.theme}>  
  4.                 <Flex column gap="gap.smaller">  
  5.                     <Header>Task Module Demo</Header>  
  6.                     <Text>YouTube Video ID:</Text>  
  7.                     <Input value={this.state.youTubeVideoId} disabled></Input>  
  8.                     <Button content="Change Video ID (AdaptiveCard)" onClick={this.onChangeVideoAdaptiveCard}></Button>  
  9.                     <Button content="Show Video" primary onClick={this.onShowVideo}></Button>  
  10.                     <Text content="(C) Copyright Contoso" size="smallest"></Text>  
  11.                 </Flex>  
  12.             </Provider>  
  13.         );  
  14.     }  
Implement onChangeVideoAdaptiveCard method as below,
  1. private onChangeVideoAdaptiveCard = (event: React.MouseEvent<HTMLButtonElement>): void => {  
  2.         // load adaptive card  
  3.         const adaptiveCard: any = require("./YouTubeSelectorCard.json");  
  4.         // update card with current video ID  
  5.         adaptiveCard.body.forEach((container: any) => {  
  6.             if (container.type === "Container") {  
  7.                 container.items.forEach((item: any) => {  
  8.                     if (item.id && item.id === "youTubeVideoId") {  
  9.                         item.value = this.state.youTubeVideoId;  
  10.                     }  
  11.                 });  
  12.             }  
  13.         });  
  14.   
  15.         const taskModuleInfo = {  
  16.             title: "YouTube Video Selector",  
  17.             card: adaptiveCard,  
  18.             width: 350,  
  19.             height: 250  
  20.         };  
  21.   
  22.         const submitHandler = (err: string, result: any): void => {  
  23.             this.setState(Object.assign({}, this.state, {  
  24.                 youTubeVideoId: result.youTubeVideoId  
  25.             }));  
  26.         };  
  27.   
  28.         microsoftTeams.tasks.startTask(taskModuleInfo, submitHandler);  
  29.     }  
Implement onShowVideo method as below,
  1. private onShowVideo = (event: React.MouseEvent<HTMLButtonElement>): void => {  
  2.         const taskModuleInfo = {  
  3.             title: "YouTube Player",  
  4.             url: this.appRoot() + `/youTubePlayerTab/player.html?vid=${this.state.youTubeVideoId}`,  
  5.             width: 1000,  
  6.             height: 700  
  7.         };  
  8.         microsoftTeams.tasks.startTask(taskModuleInfo);  
  9. }  
  10.   
  11. private appRoot(): string {  
  12.         if (typeof window === "undefined") {  
  13.             return "https://{{HOSTNAME}}";  
  14.         } else {  
  15.             return window.location.protocol + "//" + window.location.host;  
  16.         }  
  17.     }  
Test the solution
 
On the command prompt, type below command.
  1. gulp ngrok-serve  
Develop Task Modules For MS Teams With Yo Teams
 

Summary

 
Task modules enable us to implement modal popup experiences in MS Teams applications. Yo Teams helps to build task modules with ease.
 
References
 
The code developed during this article can be found  here.