Adaptive Cards

Post stanowiący pierwszą część serii opisywał ogólnie Message i Adaptive Cards, ich krótką historię i cel istnienia. Ten post koncentruje się wyłącznie na Message Cards – technologii, od której wszystko się zaczęło, i która nadal jest istnieje i działa, chociaż Microsoft zaleca migrację do Adaptive Cards.

Message Cards – wprowadzenie

Karty wiadomości są tworzone przy użyciu deklaratywnego kodu w formacie JSON. Następnie kod ten przetwarzany jest przez SDK i renderowany do atrakcyjnie wyglądającego elementu interfejsu użytkownika.

Można ich nadal używać w Outlook (zarówno wersji Desktop, jak i w przeglądarce):

Message Card in Outlook
Message Card w Outlook

Wątpię, aby stało się możliwe również używanie ich w aplikacji Outlook Mobile (w końcu Adaptive Cards są już wspierane). Message Cards mogą być także używane w Microsoft Teams – gdy przesłane do kanału poprzez Microsoft Flow lub Bot, lub za pośrednictwem dowolnej aplikacji przez zdefiniowany webhook:

Message Card in Microsoft Teams
Message Card w Microsoft Teams

Struktura JSON, która definiuje kartę, posiada wiele opcji. Jest zbudowana z dwóch, głównych obszarów: Card definition i 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
Obszary w Message Card

W części definicji Karty można ustalić podstawowe informacje na jej temat. Są to:

  1. title
  2. summary – właściwość używana i wyświetlana tylko w Outlook.
  3. themeColor – jest to kolorowa linia po lewej stronie karty. Zgodnie z dokumentacją zaleca się używania jej do stylowania ich np. do kolorów organizacji/ produktu, ale nie do wskazywania statusu.
  4. hideOriginalBody – właściwość ponownie używana jedynie przez Outlook.
  5. text – dodatkowy blok tekstu, wyświetlanego standardową czcionką poniżej tytułu karty.

W części Section można używać następujących elementów:

  1. facts –  umożliwia wyświetlanie danych w zorganizowany sposób – jako tabelka.
  2. activity – blok zbudowany z obrazu, tytułu, podtytułu i dodatkowego tekstu.
  3. text – dodatkowy blok tekstu.
  4. image 
  5. heroImage – różni się od zwykłego obrazu tym, że wyświetlany jest na całą szerokość karty.
  6. potentialAction – blok dedykowany akcjom (opisane poniżej). Akcje można również definiować poza obszarem „Sections”.

Pamiętaj!

Możesz użyć tylko raz właściwości każdego typu w pojedynczym obiekcie „Sekcja”, jednak możesz mieć wiele obiektów (ponieważ Sekcja jest tablicą). Ponadto – obrazy nie mogą być definiowane przez URI. Musisz użyć bezwzględnej ścieżki do obrazu dostępnego anonimowo (lub tam, gdzie aktualnie zalogowany użytkownik ma dostęp).

W przypadku Potential action możesz wybrać jeden z następujących rodzajów działań:

  1. OpenUri
  2. HttpPost
  3. ActionCard
  4. InvokeAddInCommand
  5. ActionRequest (nowa wersja starej Transaction)

Tutaj również – może istnieć więcej niż jedna akcja, ponieważ potentialAction to tablica.

Każdorazowo używając bloku „text” pamiętaj o tym, że możesz go teskt w nim wpisany sformatować! (https://docs.microsoft.com/en-us /outlook/actionable-messages/reference-card-reference#text-formatting)

Chciałbym zwrócić Twoją uwagę na dwa, moim zdaniem, najciekawsze typy akcji: ActionCard, która umożliwia wyświetlanie tzw. „sub-cards” z polami formularza i innymi aktywnymi elementami. Drugą jest ActionRequest – działanie umożliwiające użycie funkcjonalności płatności bezpośrednio z karty, bez potrzeby zmuszania użytkownika do opuszczenia aplikacji.

Jeśli szukasz jeszcze bardziej precyzyjnych informacji nt. struktury Message Cards, polecam przeczytanie dokumentacji:

Ważne!

Należy zauważyć, że Message Cards są już przestarzałe i zastępowane przez ich młodszego następcę: Adaptive Cards Microsoft zaleca migrację (w miarę możliwości) z formatu Message do Adaptive Cards: https://docs.microsoft.com/en-us/outlook/actionable-messages/adaptive-card

Administracja Message Cards

Warto wiedzieć, że administrator może wyłączyć mechanizm renderowania Message Cards zarówno w programie Outlook, jak i Teams, używając cmdletu Set-OrganizationConfig: https://docs.microsoft.com/en-us/powershell/module/exchange/organization/set-organizationconfig

Działający przykład (aka demo ;))

Rozwiązanie, które za chwilę zobaczysz, łączy przepływy pracy w SharePoint (zbudowane z użyciem rozwiązania firmy trzeciej – Nintex) i Microsoft Teams, dzięki czemu proces funkcjonuje w modelu „Digital Workplace”. Zobaczmy, jak to działa:

  1. W SharePoint użytkownik tworzy element, który wymaga zatwierdzenia
  2. Workflow przypisuje zadanie i w tym momencie wysyła również, za pomocą webhook, przygotowany kod JSON Message Card do Teams.
  3. Zatwierdzający może zatem wykonać zadanie w dowolny sposób: za pomocą natywnego zadania SharePoint, za pomocą Actionable Message w Outlooku lub przy użyciu karty w Microsoft Teams.
  4. Skupmy się na Teams – zatwierdzający decyduje, czy zaakceptować, czy odrzucić wniosek i klika na odpowiadający przycisk.
  5. Message Card jest odświeżana i zamiast poprzedniej treści wyświetla teraz potwierdzenie wykonania akceptacji.

Workflow

Przepływ pracy SharePoint jest stworzony za pomocą Nintex. Jest on dość prosty: po utworzeniu elementu przypisuje zadanie do zatwierdzenia, a jednocześnie tworzy Message Card i wysyła ją poprzez webhook do zatwierdzenia w wybranym kanale, w Microsoft Teams:

Nintex Workflow assigning task and sending Message Card
Nintex Workflow przypisuje zadanie i wysyła Message Card

Wysyłanie Message Card do Microsoft Teams

Aby móc opublikować Message Card, musisz najpierw utworzyć webhook dla kanału. Aby to zrobić, najpierw przejdź do strony „Manage team” w zespole, do którego chcesz wysyłać karty:

Adding webhook to Teams, part 1
Dodawanie webhook do Teams, część 1

Następnie przejdź do zakładki „Apps” i tam kliknij przycisk „More apps”:

Adding webhook to Teams, part 2
Dodawanie webhook do Teams, część 2

Następnie wpisz hasło „Webhook” w polu wyszukiwania i kliknij w kafelek, który się pojawi:

Adding webhook to Teams, part 3
Dodawanie webhook do Teams, część 3

Następnie klknij przysik „Open” i potem wybierz kanał, do którego mają być wysyłane karty. Na koniec kliknij przycisk „Set up”:

Adding webhook to Teams, part 4
Dodawanie webhook do Teams, część 4

Finalnie ustaw nazwę webhooka (będzie wyświetlana jako nazwa nadawcy wiadomości), wgraj ikonę (avatar) i naciśnij przycisk „Create”:

Adding webhook to Teams, part 5
Dodawanie webhook do Teams, część 5

Na koniec skopiuj wygenerowany URL i naciśnij przycisk „Done”:

Adding webhook to Teams, part 6
Dodawanie webhook do Teams, część 6

Ważne!

Skopiowany URL jest tym, który będzie używany przez akcję „Web request” w przepływie pracy, który posłuży do wysłania Message Card.

Następnie należy zdefiniować kod JSON Message Card. Ja swój stworzyłem za pomocą Message Cards Playground, a następnie wstawiłem do niego dynamiczne placeholdery, dzięki czemu po przepływ pracy zastąpi je rzeczywistymi danymi i karta będzie naprawdę dostosowana do konkretnych potrzeb. Korzystając z sekcji „potentialActions”, umieściłem przyciski do zatwierdzenia/ odrzucenia żądania, które po kliknięciu uruchamia akcję HttpPOST i wysyłają, wraz z decyzją i komentarzem, identyfikator zadania SharePoint:

{
    "@@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"
        }
    ]
}

Wygenerowana karta wygląda następująco:

Message Card posted by Nintex via webhook
Message Card wysłana przez Nintex poprzez webhook

Zapisywanie wyniku i odświeżanie Karty

Aby obsłużyć działania z Message Card, zdecydowałem się użyć Microsoft Flow, który jest uruchamiany przez przychodzące żądanie sieci Web, używając następującego schematu body:

Microsoft Flow trigger for incoming web request
Microsoft Flow trigger dla przychodzących zapytań HTTP
{
    "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"
                }
            }
        }
    }
}

Następnie parsuję właściwość „Body”, aby uzyskać wynik zadania, komentarz i identyfikator zadania, używając następującego schematu:

Parsing "Body" from Message Card
Przetwarzanie „Body” z Message Card

Następnie, w zależności od wyniku, Flow albo aktualizuje zadanie dla wyniku „Approved” lub „Rejected”:

Microsoft Flow updating SharePoint task
Microsoft Flow aktualizuje zadanie w SharePoint

Teraz „kluczowa” funkcjonalność: wysyłanie odpowiedzi do Message Card. Jak można przeczytać tutaj: https://docs.microsoft.com/en-us/outlook/actionable-messages/message-card-reference#refresh-cards i tutaj: https://docs.microsoft.com/en -us/outlook/actionable-messages/message-card-reference#reporting-an-actions-execution-success-or-failure w celu aktualizacji karty musi ona otrzymać żądanie z następującymi nagłówkami:

  1. CARD-UPDATE-IN-BODY – true|false, czy zastąpić aktualną treść karty, czy nie
  2. CARD-ACTION-STATUS – wiadomość pokazywana jako komentarz, poniżej karty.

Jeśli nagłówek „CARD-UPDATE-IN-BODY” jest ustawiony na „true”, karta oczekuje, że w odpowiedzi otrzyma zawartość nowej karty. Aby dynamicznie zbudować Message Card, którą zastąpisz kartę pokazującą zadanie, spróbuj zapisać jak najwięcej szczegółów dotyczących zadania w parametrze „Body” karty zadania. Potem będziesz mógł użyć ich w Flow, aby zbudować kartę wyświetlającą potwierdzenie wykonania zadania 🙂

Ważne!

Jeśli zobaczysz znak „@” w dowolnym atrybucie treści JSON Message Card w Twoim Flow, dodaj do niego dodatkowy znak „@” –> „@@”. Bez tego nie będziesz w stanie zapisać / wykonać Flow.

Działające rozwiązanie

Poniżej znajdziesz animację pokazującą, jak działa całe rozwiązanie!

Message Card in Teams
Message Card w Teams

Czego się nauczyłem?

  1. Nie możesz skorzystać z funkcji „Mention” korzystając z Message Cards
  2. Nie możesz wysłać karty w prywatnej wiadomości
  3. Nie możesz uzyskać kontekstu użytkownika, który kliknie przycisk i przekaż go do Flow

Dziękuję, że dotarłeś tak daleko! Ten post jest już drugim z serii, w której możesz dowiedzieć się o:

  1. Wprowadzenie do Adpative Cards
  2. Message Cards – case study i how-to
  3. Adaptive Cards – case study i how-to
  4. Co w planach dla wersji 2.0 (mam nadzieję, z przykładami :))

Czy chcesz dowiedzieć się więcej o kartach adaptacyjnych? Skontaktuj się ze mną lub zostaw komentarz.