# Microsoft Teams

{% hint style="info" %}
BEFORE YOU START: **Confirm your Microsoft Teams license allows custom apps before starting this set up.**

* Confirm the plan they have and understand if custom apps are allow and if with any limits.
* Publishing custom StackAI agents to Microsoft Teams requires the organization to have a Microsoft 365 plan that supports custom app sideloading (Microsoft 365 Business Basic or higher; free and Teams Essentials tiers do not support this).&#x20;
  {% endhint %}

Use Microsoft Teams to expose a workflow inside your workspace.

You can deploy a Teams bot to Azure in two ways:

1. [Automated Deployment (PowerShell)](#automated-deployment-powershell)
2. [Manual Deployment (Azure Portal)](#manual-deployment)

If you plan to use multiple agents, use the [automated deployment flow.](#automated-deployment-powershell)

## Automated Deployment (PowerShell)

Use the `deploy_teams_bot.ps1` script to automate the Azure setup.

Read the [overview](#overview), review and prepare the [prerequisites](#prerequisites), and then follow the [deployment steps](#deployment-steps).

### Overview

The `deploy_teams_bot.ps1` script automates:

* Azure AD app registration for a single-tenant app
* Azure Bot Service creation
* Teams app manifest package generation
* Optional upload to your organization's Teams app catalog

The script also includes:

* Pre-flight validation
* Rollback support
* Idempotency, so it is safe to re-run
* Dry-run mode
* Detailed logging

## Prerequisites

#### 1. Deployment script

Download `deploy_teams_bot.ps1`.&#x20;

{% file src="/files/GX12oytmn8pYPJFI7VHF" %}

#### 2. Required software

{% tabs %}
{% tab title="Option A: Azure Cloud Shell" %}
This is the easiest option. It requires no local installation.
{% endtab %}

{% tab title="Option B: Local installation" %}

* **Azure CLI**: install from <https://aka.ms/installazurecli>
* **Az PowerShell Module**: install with:

```powershell
Install-Module -Name Az -Scope CurrentUser
```

{% endtab %}
{% endtabs %}

#### 3. Required permissions

<table><thead><tr><th width="397.71875">Permission</th><th>Purpose</th></tr></thead><tbody><tr><td>Azure AD: Application Developer or Global Admin</td><td>Create app registrations</td></tr><tr><td>Azure Subscription: Contributor</td><td>Create bot resources</td></tr><tr><td>Teams Admin (optional)</td><td>Required only for <code>-uploadToOrgCatalog</code></td></tr></tbody></table>

#### 4. Icon Files

To deploy the chatbot, two icon files must be provided: `color.png` and `outline.png`. The table below outlines the specifications for these files:

<table><thead><tr><th width="112.2421875">Icon Type</th><th width="113.6484375">File Name</th><th width="357.3515625">Requirements</th><th data-type="files">Example Files</th></tr></thead><tbody><tr><td>Color</td><td>color.png</td><td>192x192 pixels, PNG format, max 1000 KB</td><td><a href="/files/BUDk6vwL2PotsUeU58fb">/files/BUDk6vwL2PotsUeU58fb</a></td></tr><tr><td>Outline</td><td>outline.png</td><td>32x32 pixels, PNG format, white with transparency</td><td><a href="/files/Z1c9DseHCmg8gJMPZURb">/files/Z1c9DseHCmg8gJMPZURb</a></td></tr></tbody></table>

#### 5. Bot Configuration

There are two options:&#x20;

{% tabs %}
{% tab title="Use a configuration file (Recommended)" %}
Create a `bot-config.json` file and update it with your values:

```json
{
  "botName": "MyCompanyBot",
  "teamsDisplayName": "My Company Assistant",
  "botDescription": "My company's customer support assistant",
  "resourceGroup": "rg-bots",
  "location": "westus",
  "subscriptionId": "12345678-1234-1234-1234-123456789012",
  "messagingEndpoint": "https://api.stack-ai.com/msft-teams/YOUR_BOT_ID/messages?api_key=YOUR_API_KEY",
  "colorIconPath": "color.png",
  "outlineIconPath": "outline.png"
}
```

{% endtab %}

{% tab title="Basic deployment" %}

<pre class="language-powershell"><code class="lang-powershell"><strong>.\deploy_teams_bot.ps1 `
</strong>  -botName "MyCompanyBot" `
  -teamsDisplayName "My Company Assistant" `
  -botDescription "My company's customer support assistant" `
  -resourceGroup "rg-bots" `
  -subscriptionId "12345678-1234-1234-1234-123456789012" `
  -messagingEndpoint "https://api.stack-ai.com/msft-teams/YOUR_BOT_ID/messages?api_key=YOUR_API_KEY"
</code></pre>

{% endtab %}
{% endtabs %}

**Script parameters**

{% tabs %}
{% tab title="Required parameters" %}

| Parameter            | Description                                                                   |
| -------------------- | ----------------------------------------------------------------------------- |
| `-botName`           | Azure resource name. Use 3-63 characters, letters, numbers, and hyphens only. |
| `-resourceGroup`     | Azure resource group name                                                     |
| `-subscriptionId`    | Azure subscription ID in GUID format                                          |
| `-messagingEndpoint` | HTTPS endpoint for Teams messages. Use your Stack AI endpoint.                |
| {% endtab %}         |                                                                               |

{% tab title="Optional parameters" %}

| Parameter             | Default                          | Description                                             |
| --------------------- | -------------------------------- | ------------------------------------------------------- |
| `-teamsDisplayName`   | Same as `botName`                | Display name shown in Teams                             |
| `-botDescription`     | `"[teamsDisplayName] Teams bot"` | Description shown in Teams                              |
| `-location`           | `westus`                         | Azure region, such as `westus` or `westeurope`          |
| `-colorIconPath`      | `color.png`                      | Path to the 192x192 color icon                          |
| `-outlineIconPath`    | `outline.png`                    | Path to the 32x32 outline icon                          |
| `-configFile`         | -                                | JSON config file path. CLI values override file values. |
| `-outputFile`         | -                                | Save credentials to a JSON file                         |
| `-logFile`            | -                                | Save detailed logs                                      |
| `-uploadToOrgCatalog` | `$false`                         | Upload to the organization Teams app catalog            |
| `-noRollback`         | `$false`                         | Disable automatic rollback on failure                   |
| `-dryRun`             | `$false`                         | Validate without creating resources                     |
| {% endtab %}          |                                  |                                                         |
| {% endtabs %}         |                                  |                                                         |

### Deployment Steps

#### 1. Prepare your environment

* Make sure the [prerequisites](#prerequisites) are installed and configured.
* Gather your Azure subscription details from the **Subscriptions** section in Azure.

<figure><img src="/files/NSGYL8vAnMYBa343xB5r" alt=""><figcaption></figcaption></figure>

* Go to StackAI Interface.&#x20;
  1. Select the Microsoft Teams Interface option in the options menu.
  2. Copy your **Messaging Endpoin**t from the StackAI deployment interface.

     <figure><img src="/files/ns9kyakBs2QsWkQ1KYGo" alt=""><figcaption></figcaption></figure>
* Validate your configuration

Run a dry run before you create resources:

```powershell
.\deploy_teams_bot.ps1 -configFile "bot-config.json" -dryRun
```

The dry run checks:

* Input parameters
* Prerequisites and permissions
* Icon file requirements
* Azure resource access

#### 2. Run the deployment

* Go to [https://shell.azure.com](https://shell.azure.com/).
* Select the **PowerShell** environment.
* Upload the [`deploy_teams_bot.ps1`](#id-1.-deployment-script)., [icon files](#id-3.-icon-files), and [`bot-config.json`.](#use-a-configuration-file-recommended)
* Run the script:

```powershell
.\deploy_teams_bot.ps1 -configFile "bot-config.json"
```

If validation succeeds, you can also save credentials and logs:

```powershell
.\deploy_teams_bot.ps1 `
  -configFile "bot-config.json" `
  -outputFile "credentials.json" `
  -logFile "deployment.log"
```

#### 3. Save the credentials

The script prints credentials when it finishes:

```
=== Configuration for Stack AI Platform ===
  Bot Name:           MyCompanyBot
  Teams Display Name: My Company Assistant
  App ID:             a1b2c3d4-e5f6-7890-abcd-ef1234567890
  Tenant ID:          12345678-1234-1234-1234-123456789012
  Client Secret:      abc123def456ghi789jkl012mno345pqr678
  Messaging Endpoint: https://api.stack-ai.com/msft-teams/...
  App Package:        C:\path\to\MyCompanyBot.zip
```

{% hint style="warning" %}
Save the client secret immediately. Azure will not show it again.
{% endhint %}

#### 4. Configure the Stack AI interface

1. Open the **Interface** tab for the workflow you want to publish as a Microsoft Teams chatbot.
2. Enter the **App ID**, **Tenant ID**, and **Client Secret** from the script output.
3. Verify that the messaging endpoint matches.

<figure><img src="/files/2YV3PBnTqS8D5vamMnuk" alt=""><figcaption></figcaption></figure>

#### 5. Upload the app to Teams

Open Microsoft Teams.

**Option A: Organization catalog**

Use this option if you ran the script with `-uploadToOrgCatalog`.

1. Go to **Apps** > **Built for your org**.
2. Find and install your bot.

**Option B: Manual upload**

1. Go to **Apps** > **Manage your apps** > **Upload a custom app**.
2. Select **Upload for \[your organization]** or **Upload for me or my teams**.
3. Upload the `[BotName].zip` file.

If you need a bot in group messages, it needs to be uploadedto the whole org instead of making it a personal app.&#x20;

<figure><img src="/files/62DaJVeLYCsiBBlufWIw" alt="" width="325"><figcaption></figcaption></figure>

#### 6. Test the bot

1. Start a new chat with the bot in Teams.
2. Send a test message.
3. Confirm that the bot responds correctly.

### Advanced usage

#### Full deployment with all options

```powershell
.\deploy_teams_bot.ps1 `
  -botName "ProductionBot" `
  -teamsDisplayName "Production Assistant" `
  -botDescription "Production customer support bot with AI assistance" `
  -resourceGroup "rg-prod-bots" `
  -location "westus" `
  -subscriptionId "12345678-1234-1234-1234-123456789012" `
  -messagingEndpoint "https://api.stack-ai.com/msft-teams/YOUR_BOT_ID/messages?api_key=YOUR_API_KEY" `
  -colorIconPath "assets/bot-color.png" `
  -outlineIconPath "assets/bot-outline.png" `
  -outputFile "prod-credentials.json" `
  -logFile "prod-deployment.log" `
  -uploadToOrgCatalog
```

#### Update an existing bot

The script is idempotent, so you can safely run it again:

```powershell
.\deploy_teams_bot.ps1 -configFile "bot-config.json"
```

If the script finds existing resources, it prompts you:

```
⚠ Existing resources detected!
Continue and update existing resources? (Y/N)
```

Type `Y` to update the existing bot.

#### Export credentials to JSON

```powershell
.\deploy_teams_bot.ps1 `
  -configFile "bot-config.json" `
  -outputFile "secure-credentials.json"
```

{% hint style="warning" %}
Keep exported credential files secure. Do not commit them to source control.
{% endhint %}

### Rollback behavior

If deployment fails, the script prompts you to roll back:

```
!!! Deployment failed at: [Step Name] !!!
Would you like to rollback and delete created resources? (Y/N)
```

* Type `Y` to delete resources created during this run
* Type `N` to leave resources for manual inspection
* Use `-noRollback` to disable rollback prompts

The script only deletes resources it created during the current run. It does not delete pre-existing resources.

### Troubleshooting

#### View full help

```powershell
Get-Help .\deploy_teams_bot.ps1 -Full
```

#### View examples

```powershell
Get-Help .\deploy_teams_bot.ps1 -Examples
```

## Manual Deployment

### 1. Open Azure Portal

Open Azure Portal and start the application setup.

[Go to Azure Portal](https://portal.azure.com/#home)

### 2. Create a new app registration

Go to **App registrations** and click **New registration**.

### 3. Register the application

Enter an app name, select **Accounts in any organizational directory**, and click **Register**.

### 4. Copy the Application ID

After registration, the Microsoft Entra ID overview page opens.

Copy the **Application (client) ID** and save it for later.

### 5. Add web authentication

1. In the left menu, under **Manage**, select **Authentication**.
2. Under **Web**, select **Add URI**.
3. Enter `https://token.botframework.com/.auth/web/redirect`.
4. Click **Save**.

### 6. Configure the redirect URI

Add your redirect URI and enable **Access tokens** and **ID tokens**.

Use this redirect URI:

```
{BASE_INFERENCE_URL}/auth-end
```

### 7. Create a client secret

1. In the left menu, under **Manage**, select **Certificates & secrets**.
2. Under **Client secrets**, select **+ New client secret**.
3. Enter a description and click **Add**.
4. Copy the secret value immediately.

### 8. Add API permissions

1. In the left menu, select **API permissions**.
2. Click **+ Add a permission** and select **Microsoft Graph**.
3. Select **Application permissions**.
4. Expand **User** and select `User.Read.All`.
5. Click **Add permissions**.

### 9. Add the Application ID URI

1. In the left menu, under **Manage**, select **Expose an API**.
2. Set the **Application ID URI** to `api://api.stack-ai.com/<APP_ID>`.
3. Click **Save**.

### 10. Add a scope

1. In the left menu, under **Manage**, select **Expose an API**.
2. Click **+ Add a scope**.
3. Enter `access_as_user` for the scope name.
4. Under **Who can consent?**, select **Admins and users**.

Use these values:

* **Admin consent display name**: `Teams can access the user's profile`
* **Admin consent description**: `Allows Teams to call the app's web APIs as the current user`
* **User consent display name**: `Teams can access the user profile and make requests on the user's behalf`
* **User consent description**: `Enable Teams to call this app's APIs with the same rights as the user`
* **State**: `Enabled`

Then click **Add scope**.

### 11. Add authorized client applications

1. In the left menu, under **Manage**, select **Expose an API**.
2. Under **Authorized client applications**, click **+ Add a client application**.
3. Add both Teams client IDs:
   * Teams mobile or desktop: `1fec8e78-bce4-4aaf-ab1b-5451cc387264`
   * Teams web: `5e3ce6c0-2b1f-4285-8d4b-75ee78787346`
4. Select the authorized scopes checkbox.
5. Click **Add application**.

### 12. Create the Azure Bot resource

1. Go to **Home** and click **+ Create a resource**.
2. Search for `Azure Bot`.
3. Select **Azure Bot** and click **Create**.

Use these settings:

* **Bot handle**: your bot name
* **Subscription**: your Azure subscription
* **Resource group**: select an existing group or create a new one
* **Pricing**: `F0 Free`
* **Microsoft App ID type**: `Single Tenant`
* **Creation type**: `Use existing app registration`
* **App ID**: the Application ID you copied earlier

### 13. Add the Microsoft Teams channel

1. In the left menu, select **Channels**.
2. Under **Available Channels**, select **Microsoft Teams**.
3. Accept the Terms of Service and click **Apply**.

### 14. Add the messaging endpoint

1. In the left menu, under **Settings**, select **Configuration**.
2. Set the messaging endpoint to:

```
https://api.stack-ai.com/msft-teams/<YOUR_PROJECT_ID>/messages?api_key=<YOUR_API_KEY>
```

3. Replace `<YOUR_PROJECT_ID>` with the workflow ID from your URL.
4. Replace `<YOUR_API_KEY>` with your API key.
5. Click **Apply**.

### 15. Save the Stack AI interface

Return to Stack AI and save the interface configuration.

<figure><img src="/files/splqk82dD0ZdFFL3koJP" alt=""><figcaption></figcaption></figure>

### 16. Upload the app to Teams

1. Open Microsoft Teams.
2. In the left sidebar, click **Apps**.

<figure><img src="/files/17JR9MeOiv74pwlJJlKH" alt=""><figcaption></figcaption></figure>

3. Go to **Manage your apps**.

<figure><img src="/files/YPoAF4tcgbi7kLjQ4kNT" alt=""><figcaption></figcaption></figure>

4. Click **Upload an app** and choose the upload option you want.

You need a package that contains:

* `manifest.json`
* `color.png`
* `outline.png`

Use the template below for `manifest.json`.

Replace:

* `"botId"` with the Microsoft App ID from step 4
* `"id"` with a unique UUID for this Teams app package

```json
{
  "$schema": "https://developer.microsoft.com/json-schemas/teams/v1.19/MicrosoftTeams.schema.json",
  "manifestVersion": "1.19",
  "version": "1.0.0",
  "id": "<YOUR_APP_ID>",
  "developer": {
    "name": "Stack AI",
    "websiteUrl": "https://www.stack-ai.com",
    "privacyUrl": "https://www.stack-ai.com/privacy",
    "termsOfUseUrl": "https://www.stack-ai.com/terms"
  },
  "name": {
    "short": "Stack AI Bot",
    "full": "Stack AI Bot"
  },
  "description": {
    "short": "Stack AI Microsoft Teams bot",
    "full": "Stack AI Microsoft Teams bot"
  },
  "icons": {
    "outline": "outline.png",
    "color": "color.png"
  },
  "accentColor": "#ffffff",
  "bots": [
    {
      "botId": "<YOUR_APP_ID>",
      "needsChannelSelector": false,
      "isNotificationOnly": false,
      "supportsFiles": true,
      "scopes": [
        "personal",
        "team",
        "groupChat"
      ]
    }
  ],
  "authorization": {
    "permissions": {
      "resourceSpecific": [
        {
          "name": "ChannelMessage.Read.Group",
          "type": "Application"
        }
      ]
    }
  },
  "webApplicationInfo": {
    "id": "<YOUR_APP_ID>",
    "resource": "api://botid-<YOUR_APP_ID>"
  },
  "permissions": [],
  "validDomains": [
    "api.stack-ai.com"
  ]
}
```

### 17. Add the app to a channel

1. Open the channel where you want to use the bot.
2. Click **Apps**.

<figure><img src="/files/r4Co3x421BAz3IZ74B68" alt=""><figcaption></figcaption></figure>

3. Select your app and add it to the channel.
4. Mention the bot with `@` followed by its name.

If you update the workflow later, publish it again so Teams uses the latest version.


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.stackai.com/interface-and-deployment/end-user-interfaces/microsoft-teams.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
