Top
Adaptive Cards

Microsoft Message Cards – the ultimate guide


In the first part of the series I wrote a general overview of Message and Adaptive Cards, their brief history and purpose. This part is focused only on Message Cards – the technology from which it all begun and that is still available to use although recommendation is to move to Adaptive Cards.

Message Cards – introduction

Message Cards are created using a declarative JSON-format code. Then the definition is parsed by the SDK into a nice looking part of UI.

They can be used today still in Outlook (both Desktop and Browser based):

Message Card in Outlook
Message Card in Outlook

I doubt if it will be ever possible to use them in Outlook Mobile (Adaptive Cards are already there), plus in Microsoft Teams, sent by Flow or Bot, or via any application through a defined webhook:

Message Card in Microsoft Teams
Message Card in Microsoft Teams

JSON code that defines card is full of options. However it’s main structure consist of two areas: Card definition and Sections.

{
    "@type": "MessageCard",
    "@context": "https://schema.org/extensions",
    "summary": "",
    "themeColor": "",
    "title": "Card created: \"This is just a test\"",
    "sections": [
        {
                  …
        },
        "potentialAction": [
            {
                    …
            }
        ]
    ]
}
Areas in the Message Card
Areas in the Message Card

In Card’s information section you can define basics of your card. These are:

  1. title
  2. summary – property used by Outlook.
  3. themeColor – this is the colorful line on the left of your card. According to documentation, it is advised to use it to brand them e.g. to your organizational colors, but not to indicate status.
  4. hideOriginalBody – again, property used by Outlook.
  5. text – an additional block of text displayed using a regular font below title.

In Section, you can build blocks of data:

  1. facts –  a construct allowing to display data in organized way – a table.
  2. activity – constructed from image, title, subtitle and text.
  3. text – again, a block of text
  4. image 
  5. heroImage – different from regular image, as it displays full-width on a card.
  6. potentialAction – block dedicated for actions (described below). Can also be defined outside “Section” area.

Remember!

You can only use once each type of property in a single “Section” object, however you can have multiple objects (since Section is an array). Moreover – images cannot be defined via URI. It has to be a path to a physical image anonymously accessible (or where currently logged in user has access).

For Potential actions you can choose between the following types of actions:

  1. OpenUri
  2. HttpPost
  3. ActionCard
  4. InvokeAddInCommand
  5. ActionRequest (new version of old Transaction)

Again, there can be more than one action, since potentialAction is an array.

Anytime you would like to use “text” property remember, you can use markdown to format it too! (https://docs.microsoft.com/en-us/outlook/actionable-messages/message-card-reference#text-formatting)

There are two interesting types of actions: ActionCard, which allows to display a “sub card” with form fields and other actionable items. And ActionRequest – activity allowing payment functionalities right from the card, without a need for pushing user to leave our app.

For more information about the Message Cards structure, I recommend reading the documentation:

Important!

Note, that Message Cards are getting deprecated and replaced by their younger successor: Adaptive Cards. Microsoft recommends to migrate where possible from Message to Adaptive Cards format: https://docs.microsoft.com/en-us/outlook/actionable-messages/adaptive-card

Message Cards administration

Please note that administrator can disable rendering of Message Cards both in Outlook and Teams, by using Set-OrganizationConfig cmdlet: https://docs.microsoft.com/en-us/powershell/module/exchange/organization/set-organizationconfig

Working exampe (aka demo ;))

The solution I am about to show you is connecting SharePoint workflows (using 3rd party solution – Nintex) and Microsoft Teams, making this process running in a truly digital workplace experience mode. Let’s see how it works:

  1. In SharePoint user is creating an item, that requires approval
  2. Workflow assigns a task and in that moment it also sends, via a Teams webhook, prepared Message Card JSON.
  3. Approver therefore can complete a task any way he likes: through a native, SharePoint task, via an Actionable Message in Outlook or using Microsoft Teams.
  4. Let’s focus on Teams – approver decides, and clicks related outcome.
  5. Message Card is refreshed and instead of the previous form, now shows a confirmation information.

The workflow

SharePoint workflow is created with Nintex. It is quite simple: once an item is created it assignes a task to approver and in the same time it creates a Message Card in Teams for approval using that channel:

Nintex Workflow assigning task and sending Message Card
Nintex Workflow assigning task and sending Message Card

Posting a Message Card to Microsoft Teams

To be able to post a Message Card you must first create a Webhook for a channel. To do that first go to “Manage team” page of a team you want to post a message to:

Adding webhook to Teams, part 1
Adding webhook to Teams, part 1

Next go to “Apps” tab and click the “More apps” button:

Adding webhook to Teams, part 2
Adding webhook to Teams, part 2

Next type “Webhook” in the search menu and click the tile that appears:

Adding webhook to Teams, part 3
Adding webhook to Teams, part 3

Then click the button “Open” and after that select the channel, to which you want to post a Message Card and finally the button “Set up”:

Adding webhook to Teams, part 4
Adding webhook to Teams, part 4

Finally define webhook’s name (it will be displayed as the author of all messages), upload icon (avatar) and hit “Create”:

Adding webhook to Teams, part 5
Adding webhook to Teams, part 5

After it is created, copy the generated URL and “Done”:

Adding webhook to Teams, part 6
Adding webhook to Teams, part 6

Important!

The URL is the one that the “Web request” action in my workflow will use to post message to.

Next what has to be defined is the Message Card JSON. I have created a code using the Playground and then put dynamic values inside it, so that once workflow replaces them with actual data, the Card is really adjusted to the particular needs. Withing the “potentialActions” section I put buttons to Approve/ Reject request, which once clicked are executing HttpPOST action and is sending , along with the Outcome and Comments, SharePoint Task ID:

{
    "@@type": "ActionCard",
    "name": "Approve",
    "inputs": [
        {
            "@@type": "TextInput",
            "id": "ApprovalComment",
            "isMultiline": true,
            "title": "Comment (optional)"
        }
    ],
    "actions": [
        {
            "@@type": "HttpPOST",
            "name": "Submit",
            "target": "FLOW URL",
            "headers": [
                {
                    "name": "content-type",
                    "value": "application/json"
                },
                {
                    "name": "authorization",
                    "value": ""
                }
            ],
            "bodyContentType": "application/json",
            "body": "{\"approved\":true, \"comment\":\"{{ApprovalComment.value}}\", \"taskID\":10"
        }
    ]
}

In the end, posted Message Card looks like below:

Message Card posted by Nintex via webhook
Message Card posted by Nintex via webhook

Registering the outcome and refresing the Card

To handle actions from Message Card I decided to use Microsoft Flow that is triggered on incoming Web Request, using the following schema:

Microsoft Flow trigger for incoming web request
Microsoft Flow trigger for incoming web request
{
    "type": "object",
    "properties": {
        "name": {
            "type": "string"
        },
        "inputParameters": {
            "type": "array",
            "items": {
                "type": "object",
                "properties": {
                    "id": {
                        "type": "string"
                    },
                    "value": {
                        "type": "string"
                    }
                },
                "required": [
                    "id",
                    "value"
                ]
            }
        },
        "actionId": {
            "type": "string"
        },
        "potentialAction": {
            "type": "string"
        },
        "integrationId": {
            "type": "string"
        },
        "meta": {
            "type": "string"
        },
        "clientInfo": {
            "type": "object",
            "properties": {
                "locale": {
                    "type": "string"
                },
                "country": {
                    "type": "string"
                },
                "platform": {
                    "type": "string"
                },
                "clientVersion": {
                    "type": "string"
                }
            }
        }
    }
}

Next I am parsing property “Body” to get outcome, comment and taskID, using the following schema:

Parsing "Body" from Message Card
Parsing “Body” from Message Card

Next, based on the outcome, Flow is either updating Task Item to “Approved” or “Rejected”:

Microsoft Flow updating SharePoint task
Microsoft Flow updating SharePoint task

Now the “key” functionality: response being sent to the Message Card. As it can be read here: https://docs.microsoft.com/en-us/outlook/actionable-messages/message-card-reference#refresh-cards and here: https://docs.microsoft.com/en-us/outlook/actionable-messages/message-card-reference#reporting-an-actions-execution-success-or-failure to update a Card it has to receive a request with the following Header keys:

  1. CARD-UPDATE-IN-BODY – true|false, whether to replace card contents
  2. CARD-ACTION-STATUS – message shown as comment, below the card.

If key “CARD-UPDATE-IN-BODY” is set to “true” Card is expecting contents of a new card to be sent out. To build the Message Card to replace “Request” one, try to put as much details in the “body” parameter of the “Request” card so that later you can use them in the Flow to build the “Confirmation” one 🙂

Important!

If you see “@” in any attribute of the Message Card JSON body in your Flow, escape it with additional “@”, to make it double “@@”. Without that you will not be able to save/ execute the Flow.

Working solution

Below you can find animation showing how the whole solution works!

Message Card in Teams
Message Card in Teams

What I learnt?

  1. You can’t mention anyone using Message Card
  2. You can’t post Message Card in a private message
  3. You can’t get user context who clicks the button and pass it to Flow

Thank you for reaching that far! This post is a second one in series in which you can learn about:

  1. Introduction to Adaptive Cards
  2. Message Cards – case study and how-to
  3. Adaptive Cards – case study and how-to
  4. What’s ahead in 2.0 (hopefully with examples :))

Would you like to learn more about Adaptive Cards? Contact me or leave a comment.


Tomasz Poszytek

Hi, I am Tomasz. I am expert in the field of process automation and business solutions' building using Power Platform. I am Microsoft MVP and Nintex vTE.

15 Comments
  • Ashtosh

    I want to update a Sharepoint list item once submit button in adaptive card is clicked I have list item Id in adaptive card body.

    September 16, 2019 at 8:23 am Reply
    • Tomasz Poszytek

      Today that is not possible to be done using Teams and Microsoft Flow for posting a card. You have to create your own Bot or write your own app using Adaptive Cards SDK.

      September 16, 2019 at 8:25 am Reply
  • Martin Zutter

    Hi Tomasz
    Is it possible to save the message card Text to a file, excel, csv or SharePoint-List?
    This is an example:
    {“text”:{“DataInterface”:”Data-InterfacePRiOT-SCI-Space-DataHub”,”value”:25.7,”datasource”:”PoC-Data”,”operationscenter”:”69COSEWSD”,”airtemperature”:25.7,”airhumidity”:22}}

    This is kind of a “data import”. The goal is to visualize it in Power BI.
    Thanks a lot and sorry, english is not my “mother language”

    April 8, 2020 at 8:14 am Reply
    • Tomasz Poszytek

      Hi. Adaptive Cards are yet not supported in Power Bi. This is not even on a roadmap… Instead you can use HTML and display it using the HTML visualisation.

      April 8, 2020 at 8:32 pm Reply
  • Cristiano

    Hello, I have a problem, I’m using the MenssageCard, but the words that contain underscore (_) lose it when it arrives at Teams, example:

    “text”: router_BA_SDR

    teams displays:
    routerBASDR

    what could be happening?

    April 23, 2020 at 2:48 am Reply
    • Tomasz Poszytek

      I don’t really know what could the reason. If you put string inside quotes, like “key”: “value” then it should be sent together with underscores.

      April 27, 2020 at 10:25 am Reply
  • Steven

    Great article. I have managed to format some notifications in MS Teams using the MessageCard type now.
    One question, do you know if you can @mention someone as part of sending this over to teams. The icing on the cake would be someone being pinged they have a mention in a channel as a result of this.

    April 29, 2020 at 5:57 am Reply
  • Gurinder

    How to send message card in outgoing webhook,
    Do I need to attach it as an attachment in the json sent by teams which I deserialize via Newtonsoft and attach card inside attachment section as it is a collection of attachments.
    or only the message card json.
    I am using Azure functions at present able to send very simple message
    {
    “type”:”message “,
    “text”:”hello”
    }
    Looking to expand on it to send message card but don’t know how to structure it as mentioned above should the card be attached inside attachment section of original json post to azure function via team or message card json it self,
    Thanks you for help,
    Gurinder

    May 1, 2020 at 3:01 am Reply
    • Tomasz Poszytek

      I actually don’t understand what you’re trying to achieve. Basically if you try to send Message Card from Azure Function, via a webhook to Teams, you need to post the JSON as a Body of your POST request. The JSON must be formatted according to the examples: https://messagecardplayground.azurewebsites.net/ (try eg. Flow Approval example).

      May 2, 2020 at 10:03 pm Reply
      • Gurinder

        Thank you for reply I really appreciate,
        I was trying to send a card via Azure function but didn’t want to put raw json in it,but since have successfully created a card and post it to teams.
        Once again thanks reply.

        May 2, 2020 at 11:02 pm Reply
  • Steven

    Hey,
    In Flow, do you know how to parse out the title from the message card.
    I send over an email address as the MessageCard Summary, which in flow I turn into a variable and then use that as the mention – but I want to also refer to the title from the messagecard, I cannot see how to parse that out from the message that is received in teams

    Do you have a suggestion?

    May 26, 2020 at 5:23 am Reply

Post a Comment

This site uses Akismet to reduce spam. Learn how your comment data is processed.