Conflicts due to multiple "installationUpdate" events when installing bot in a Team

Anonymous
2024-08-17T04:05:46.2333333+00:00

I’m encountering an issue with my TeamsBot when adding it to a team's channel. Specifically, I receive two installationUpdate events:

  1. One event is triggered for the bot being installed in the team.
  2. The other event is for the personal installation (i.e., adding the bot for self).

The order of these events is not consistent. Sometimes, the first installationUpdate event is for the team installation, and sometimes it is for the personal installation.

This inconsistent order is causing conflicts in my code. I’m uncertain about how to handle user details when processing the installationUpdate events, particularly whether I should process user details in the context of the team installation or the personal installation.

Questions:

  1. How should I manage these events to avoid conflicts in my code?
  2. Is there a recommended approach for processing user details and handling the installation updates in a consistent manner?

Any guidance or best practices on managing these multiple installationUpdate events would be greatly appreciated.

Microsoft Teams | Development
{count} votes

1 answer

Sort by: Most helpful
  1. Lior Lew 0 Reputation points
    2024-10-27T12:17:54.48+00:00

    I am having the same issue. the possible scopes on my manifest are personal and team, however when I install it on the teams scope I am getting the notification on both, team and personal scopes.
    this is my code:

    import * as dotenv from 'dotenv';
    import { TeamsActivityHandler, TurnContext, MessageFactory, CardFactory } from "botbuilder";
    
    const environment = process.env.NODE_ENV || 'dev'; // Default to 'dev' if NODE_ENV is not set
    dotenv.config({ path: `env/.env.${environment}` });
    export class TeamsBot extends TeamsActivityHandler {
      private callbackUrl: string;
    
      constructor() {
        super();
        // Handle bot installation
        this.onInstallationUpdateAdd(async (context: TurnContext, next: () => Promise<void>) => {
          dotenv.config();
          const conversationType = context.activity.conversation?.conversationType;
          let configurationUrl = process.env.CONFIGURATION_URL; //base URL of Snappy integrations
          
          // Check if the app is installed in a team or personal scope
          if (conversationType === "channel") {
            // For team scope installation
            const channelId = context.activity.conversation?.id;
            const teamName = context.activity.channelData?.team?.name;
            
            // Add teamId and teamName to the configuration URL
            configurationUrl += `?teamId=${channelId}&teamName=${teamName}`;
          } else if (conversationType === "personal") {
            // For personal scope installation
            const userId = context.activity.from?.id;
    
            // Add userId and userName (or any other equivalent) to the configuration URL
            configurationUrl += `?teamId=${userId}&teamName=member-level`;
          }
    
          // Adaptive card payload
          const adaptiveCard = {        
            ..... 
            .....
          };
          console.log(`configurationUrl = ${configurationUrl}`);
          // Send the adaptive card as the welcome message
          await context.sendActivity(MessageFactory.attachment(CardFactory.adaptiveCard(adaptiveCard)));
    
          // Proceed to the next middleware or handler
          await next();
        });
      }
    }
    
    0 comments No comments

Your answer

Answers can be marked as Accepted Answers by the question author, which helps users to know the answer solved the author's problem.