node.jsbotframeworkazure-bot-service

How to send adaptive card through outlook with botFramework NodeJs


I've built a bot that sends adaptive cards through teams. I'm able to successfuly interact with the card. However, I would like to extend the functionality and make it capable to send cards through outlook as well. I have followed this steps and added the channel to the azure bot services. However, I do not know how to start sending the card because its not explained in the documentation. Here is the snipped of how I send the card to teams.

// HTTP trigger to send notification. You need to add authentication / authorization for this API. Refer https://aka.ms/teamsfx-notification for more details.
server.post(
  "/api/notificationByTeams",
  restify.plugins.queryParser(),
  restify.plugins.bodyParser(), // Add more parsers if needed
  async (req, res) => {
    let continuationToken = undefined;
    do {
      const pagedData = await notificationApp.notification.getPagedInstallations();
      let adaptiveCardData = req.body;
      const { MerlinUser, MerlinPassword, Receivers, TemplateType } = adaptiveCardData;

      //Here we get all the users receiving the notification
      const usersReceivingCardInformation = await getNotificationMembersInfoByEmail(Receivers)
      const installations = pagedData.data;
      continuationToken = pagedData.continuationToken;

      //Here we encrypt the data of the admin user
      adaptiveCardData.MerlinUser = encryptData(MerlinUser);
      adaptiveCardData.MerlinPassword = encryptData(MerlinPassword);
      adaptiveCardData.Originator = process.env.Originator;
      console.info("Llegamos a setear el originator ", adaptiveCardData.Originator);
      adaptiveCardData.UserIds = usersReceivingCardInformation.map(x => x.id);

      for (const target of installations) {
       
        if (target.type === "Person" && usersReceivingCardInformation.some(x => x.id === target.conversationReference.user.id)) {
          let selectedTemplate = selectTemplate(TemplateType);
          await target.sendAdaptiveCard(
            AdaptiveCards.declare(selectedTemplate).render({
              ...adaptiveCardData
            })
          );
        }
      }
    } while (continuationToken);

    res.json({});
  }
);

I added the outlook channels to my bot service in azure.


Solution

  • I would like to extend the functionality and make it capable to send cards through outlook as well.

    By using Microsoft Graph API, we can be able to send an adaptive card via email through Outlook.

    Here, I have added outlook channel to my azure bot service.

    enter image description here

    enter image description here

    enter image description here

    {
        "type": "AdaptiveCard",
        "body": [
            {
                "type": "TextBlock",
                "text": "Hello!",
                "size": "large"
            },
            {
                "type": "TextBlock",
                "text": "This is an adaptive card sent via email."
            },
            {
                "type": "Image",
                "url": "https://adaptivecards.io/content/cats/1.png"
            }
        ],
        "actions": [
            {
                "type": "Action.OpenUrl",
                "title": "Learn More",
                "url": "https://adaptivecards.io"
            }
        ],
        "$schema": "http://adaptivecards.io/schemas/adaptive-card.json",
        "version": "1.2"
    }
    

    enter image description here

    const msal = require('@azure/msal-node');
    const { Client } = require('@microsoft/microsoft-graph-client');
    require('isomorphic-fetch');
    
    // MSAL configuration
    const msalConfig = {
        auth: {
            clientId: 'YOUR_CLIENT_ID',
            authority: 'https://login.microsoftonline.com/YOUR_TENANT_ID',
            clientSecret: 'YOUR_CLIENT_SECRET'
        }
    };
    
    const cca = new msal.ConfidentialClientApplication(msalConfig);
    
    async function getToken() {
        const clientCredentialRequest = {
            scopes: ['https://graph.microsoft.com/.default'],
        };
        const response = await cca.acquireTokenByClientCredential(clientCredentialRequest);
        return response.accessToken;
    }
    
    async function sendAdaptiveCardEmail() {
        const accessToken = await getToken();
    
        const client = Client.init({
            authProvider: (done) => {
                done(null, accessToken);
            }
        });
    
        const adaptiveCardJson = require('./adaptiveCard.json');
    
        const email = {
            message: {
                subject: 'Adaptive Card Email',
                body: {
                    contentType: 'HTML',
                    content: 'Please see the adaptive card below.'
                },
                toRecipients: [
                    {
                        emailAddress: {
                            address: 'recipient@example.com'
                        }
                    }
                ],
                attachments: [
                    {
                        '@odata.type': '#microsoft.graph.fileAttachment',
                        name: 'adaptiveCard.json',
                        contentType: 'application/json',
                        contentBytes: Buffer.from(JSON.stringify(adaptiveCardJson)).toString('base64')
                    }
                ]
            }
        };
    
        await client.api('/me/sendMail')
            .post({ message: email.message, saveToSentItems: 'true' });
    
        console.log('Email sent successfully.');
    }
    
    sendAdaptiveCardEmail().catch(console.error);
    

    enter image description here