#mention via incoming webhook in MS Teams - microsoft-teams

I'm trying to mention a user from an incoming webhook.
I tried a few iterations via Postman of
{
"text": "test #user"
}
or
{
"text": "test #user#email.com"
}
but none of these seem to work.
Is this simple but very important thing just not possible?
Thanks.

I'm afraid this isn't possible yet - the only way to do # mentions is by using the full Bot Framework APIs.
You're not the only one to have asked for this though, so I'll get it on the backlog.

This is now supported and documented here (https://learn.microsoft.com/en-us/microsoftteams/platform/task-modules-and-cards/cards/cards-format?tabs=adaptive-md%2Cconnector-html#user-mention-in-incoming-webhook-with-adaptive-cards).
Sample:
{
"type": "message",
"attachments": [
{
"contentType": "application/vnd.microsoft.card.adaptive",
"content": {
"type": "AdaptiveCard",
"body": [
{
"type": "TextBlock",
"size": "Medium",
"weight": "Bolder",
"text": "Sample Adaptive Card with User Mention"
},
{
"type": "TextBlock",
"text": "Hi <at>Adele UPN</at>, <at>Adele AAD</at>"
}
],
"$schema": "http://adaptivecards.io/schemas/adaptive-card.json",
"version": "1.0",
"msteams": {
"entities": [
{
"type": "mention",
"text": "<at>Adele UPN</at>",
"mentioned": {
"id": "AdeleV#contoso.onmicrosoft.com",
"name": "Adele Vance"
}
},
{
"type": "mention",
"text": "<at>Adele AAD</at>",
"mentioned": {
"id": "87d349ed-44d7-43e1-9a83-5f2406dee5bd",
"name": "Adele Vance"
}
}
]
}
}
}]
}

If it helps anybody, after looking in to this and seeing it couldn't be done (still!?), a workaround for me was to change the channel notification settings to banner + feed for all new posts for relevant users in the channel. This eliminates the need to use the tag (if tagging the team).

It is supported in Teams now, however the sample code does not work in Microsoft card playground, I didn't know the code actually worked until I tried in Postman.

Related

Body always empty when answering an invoke

I have a live Microsoft Teams application with a couple of working functionalities. Right now I am working on a new feature where the user clicks on a button in a previously sent adaptive card and I will open another adaptive card with a form for the user to fill. I am using this documentation as a base, which has a really similar example as to what I am trying to achieve here.
Since I am working with an adaptive card the button that will open my form card is an Action.Submit button with "msteams": {"type': 'task/fetch"} inside its data. When I click that button I receive the correct invoke call, the body looks like this:
{
"type": "invoke",
"timestamp": "2021-02-01T20:19:34.327Z",
"localTimestamp": "2021-02-01T15:19:34.327-05:00",
"id": "f:955407977095344101",
"channelId": "msteams",
"serviceUrl": "https://smba.trafficmanager.net/amer/",
"from": {
"id": "censured",
"name": "censured",
"aadObjectId": "censured"
},
"conversation": {
"conversationType": "personal",
"tenantId": "censured",
"id": "censured"
},
"recipient": {
"id": "censured",
"name": "Tcensured"
},
"entities": [
{
"locale": "censured",
"country": "censured",
"platform": "censured",
"timezone": "censured",
"type": "clientInfo"
}
],
"channelData": {
"tenant": {
"id": "censured"
},
"source": {
"name": "message"
},
"legacy": {
"replyToId": "censured"
}
},
"replyToId": "censured",
"value": {
"commandId": "reply_feedback",
"requested_feedback_id": 1,
"type": "composeExtension/fetchTask"
},
"locale": "censured",
"localTimezone": "censured"
}
It seems like the invoke call is correct, so the next step is to answer the call with my adaptive card. However, it doesn't matter what I answer this call with, when I inspect the invoke call in my browser the answer is always empty, even if I answer with a really simple task response like (which I got from the documentation)
{
"task": {
"type": "continue",
"value": {
"title": "Task module title",
"height": 500,
"width": "medium",
"url": "https://contoso.com/msteams/taskmodules/newcustomer",
"fallbackUrl": "https://contoso.com/msteams/taskmodules/newcustomer"
}
}
}
Or even
{
"task": {
"type": "message",
"value": "Test"
}
}
I still get an empty response on the front-end side. I am fairly confident that I am properly answering the call on my side with data, I have a lot of other features in this same application working so I don't think it is some problem where I am actually giving an empty body from my side. Maybe for the specific invoke call I need to answer things in a different manner?
Obs: I am using Python with no SDKs, so I build Adaptive Cards and interpret the requests on my application.

Microsoft Teams bot: Card including Action.OpenUrl with task deeplink

For our bot in Teams, using the Microsoft Bot Framework, I want the bot to send a card with a button that, when clicked, will open a task module through a deep link
Deep link:
https://teams.microsoft.com/l/task/<BOT_ID>?fallbackUrl=https://google.com&completionBotId=<BOT_ID>&height=large&width=large&title=Title&card=<card>
Where <card> comes from the example in the docs:
{
"type": "AdaptiveCard",
"body": [
{
"type": "TextBlock",
"text": "Here is a ninja cat:"
},
{
"type": "Image",
"url": "http://adaptivecards.io/content/cats/1.png",
"size": "Medium"
}
],
"version": "1.0"
}
URL encode the JSON to: %7B%0A%20%20%20%20%22type%22%3A%20%22AdaptiveCard%22%2C%0A%20%20%20%20%22body%22%3A%20%5B%0A%20%20%20%20%20%20%20%20%7B%0A%20%20%20%20%20%20%20%20%20%20%20%20%22type%22%3A%20%22TextBlock%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%22text%22%3A%20%22Here%20is%20a%20ninja%20cat%3A%22%0A%20%20%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%20%20%20%7B%0A%20%20%20%20%20%20%20%20%20%20%20%20%22type%22%3A%20%22Image%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%22url%22%3A%20%22http%3A%2F%2Fadaptivecards.io%2Fcontent%2Fcats%2F1.png%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%22size%22%3A%20%22Medium%22%0A%20%20%20%20%20%20%20%20%7D%0A%20%20%20%20%5D%2C%0A%20%20%20%20%22version%22%3A%20%221.0%22%0A%7D
We then have deep link:
https://teams.microsoft.com/l/task/<BOT_ID>?fallbackUrl=https://google.com&completionBotId=<BOT_ID>&height=large&width=large&title=Title&card=%7B%0A%20%20%20%20%22type%22%3A%20%22AdaptiveCard%22%2C%0A%20%20%20%20%22body%22%3A%20%5B%0A%20%20%20%20%20%20%20%20%7B%0A%20%20%20%20%20%20%20%20%20%20%20%20%22type%22%3A%20%22TextBlock%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%22text%22%3A%20%22Here%20is%20a%20ninja%20cat%3A%22%0A%20%20%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%20%20%20%7B%0A%20%20%20%20%20%20%20%20%20%20%20%20%22type%22%3A%20%22Image%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%22url%22%3A%20%22http%3A%2F%2Fadaptivecards.io%2Fcontent%2Fcats%2F1.png%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%22size%22%3A%20%22Medium%22%0A%20%20%20%20%20%20%20%20%7D%0A%20%20%20%20%5D%2C%0A%20%20%20%20%22version%22%3A%20%221.0%22%0A%7D
Finally, send message through Bot Framework API:
POST https://smba.trafficmanager.net/emea/v3/conversations/<conv_id>/activities
Body:
{
"recipient": {
"id": "29:1uuzUvFTkcseXZ1Q2wOva1inGkpH1SqbHwqdXjG8MhUa8mkFsdUnvrgn4FnPbX8CwBl_GwDHSQGIlRSPKczwUFg"
},
"type": "message",
"text": "Hi 👋<br/><br/>What do you need?",
"textFormat": "xml",
"attachments": [
{
"contentType": "application/vnd.microsoft.card.adaptive",
"content" : {
"$schema": "http://adaptivecards.io/schemas/adaptive-card.json",
"type": "AdaptiveCard",
"version": "1.0",
"actions": [{
"type": "Action.OpenUrl",
"title": "Display task",
"url": "https://teams.microsoft.com/l/task/<BOT_ID>?fallbackUrl=https://google.com&completionBotId=<BOT_ID>&height=large&width=large&title=Title&card=%7B%0A%20%20%20%20%22type%22%3A%20%22AdaptiveCard%22%2C%0A%20%20%20%20%22body%22%3A%20%5B%0A%20%20%20%20%20%20%20%20%7B%0A%20%20%20%20%20%20%20%20%20%20%20%20%22type%22%3A%20%22TextBlock%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%22text%22%3A%20%22Here%20is%20a%20ninja%20cat%3A%22%0A%20%20%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%20%20%20%7B%0A%20%20%20%20%20%20%20%20%20%20%20%20%22type%22%3A%20%22Image%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%22url%22%3A%20%22http%3A%2F%2Fadaptivecards.io%2Fcontent%2Fcats%2F1.png%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%22size%22%3A%20%22Medium%22%0A%20%20%20%20%20%20%20%20%7D%0A%20%20%20%20%5D%2C%0A%20%20%20%20%22version%22%3A%20%221.0%22%0A%7D"
}],
"body": []}}]}
The message appears in Teams as expected, but when clicking the button nothing happens. What am I doing wrong?
The issue was that I was sending my bot id instead of my app id for the APP_ID parameter.
I don't understand this in the docs though:
Note that it's valid for APP_ID and BOT_APP_ID to be the same, and in many cases will be if an app has a bot since it's recommended to use that as an app's ID if there is one.
How is one supposed to achieve this?

AdaptiveCard not rendering in Bot Framework Emulator / Web Chat

Really hoping someone can help out on this.
I'm trying to achieve - a no-code chat bot using QnAMaker.ai and Azure Bot Services with AdaptiveCards to serve rich content.
I have a knowledgebase set up and published, I have a bot in Azure set up to serve that content and it seems to work okay at the first stage.
Now I'm trying to add AdaptiveCards without opening and editing the solution in VSCode - I really want to keep all this contained in a no-code solution.
I Googled how to add custom cards/content and found this post by LiveTiles - excellent - I thought, I can just add minified JSON and it will render what I want - lovely stuff!
However; despite there being a live output render on the LiveTiles site, when I take that JSON I cannot get it to render through either Web Chat or the Bot Framework Emulator.
I've tried...
Copy/pasting the raw JSON into a QnAPair
{
"contentType": "application/vnd.microsoft.card.adaptive",
"content": {
"type": "AdaptiveCard",
"version": "1.0",
"body": [
{
"type": "Image",
"url": "",
"size": "stretch",
"selectAction": {
"type": "Action.OpenUrl",
"title": "Test",
"url": "https://www.livetiles.nyc/"
}
},
{
"type": "TextBlock",
"text": "This is an adaptive card - if this renders it means it's worked!",
"wrap": true
}
],
"actions": [
{
"type": "Action.Submit",
"title": "Let's get started!",
"url": "Let's get started!"
}
]
}
}
Copy/pasting minified JSON into a QnAPair
{"contentType":"application/vnd.microsoft.card.adaptive","content":{"type":"AdaptiveCard","version":"1.0","body":[{"type":"Image","url":"","size":"stretch","selectAction":{"type":"Action.OpenUrl","title":"Test","url":"https://www.livetiles.nyc/"}},{"type":"TextBlock","text":"This is an adaptive card - if this renders it means it's worked!","wrap":true}],"actions":[{"type":"Action.Submit","title":"Let's get started!","url":"Let's get started!"}]}}
Making a Source Excel File (which includes the JSON) and adding that to the knowledge base
All my attempts end up with the bot spitting the actual JSON at me when I ask it. Not the lovely rendered card I wanted.
Renders on the LiveTiles site:
Doesn't render on the Emulator
Or on the Web Chat
In QnAMaker.ai Test Function
Really hoping someone can offer some insight or advice to this.
Please try below json it works for me ,
{
//"contentType": "application/vnd.microsoft.card.adaptive",
//"content": {
"type": "AdaptiveCard",
"version": "1.0",
"body": [
{
"type": "Image",
"url": "",
"size": "stretch",
"selectAction": {
"type": "Action.OpenUrl",
"title": "Test",
"url": "https://www.livetiles.nyc/"
}
},
{
"type": "TextBlock",
"text": "This is an adaptive card - if this renders it means it's worked!",
"wrap": true
}
],
"actions": [
{
"type": "Action.Submit",
"title": "Let's get started!",
"url": "Let's get started!"
}
]
//}
}
I have added a screenshot below please check
code for send card as an attachment :
var cardAttachment = Common.CreateAdaptiveCardAttachment();
await turnContext.SendActivityAsync(MessageFactory.Attachment(cardAttachment), cancellationToken);

Action.OpenUrl in Adaptive card, Confirmation for opening the URl

I am using Microsoft bot framework, i have requirement to open URL after clicking button. I have achieve that by using Adaptive card. URL is opening in button click.
I need to implement confirmation option, when user click on button, pop should come and ask for confirmation of opening the URL.
I tried that it is working in emulator but in web it not working. it simply opens the URL without asking the confirmation.
My bot will be used in web.
I have refer https://adaptivecards.io/samples/
below is my code for adaptive card
"$schema": "http://adaptivecards.io/schemas/adaptive-card.json",
"type": "AdaptiveCard",
"version": "1.0",
"actions": [
{
"type": "Action.OpenUrl",
"title": "Action.OpenUrl",
"url": "https://adaptivecards.io"
}
]
Thanks
Sanjeev Gautam
This happens only in Local Emulator,
For this to happen in browser you need to handle it differently, You can use the same adaptive cards to get this happen, I have mentioned one sample below for your reference
{
"$schema": "http://adaptivecards.io/schemas/adaptive-card.json",
"type": "AdaptiveCard",
"version": "1.0",
"body": [
{
"type": "TextBlock",
"text": "This is Vinay Jayaram Helping you to open a URL"
}
],
"actions": [
{
"type": "Action.ShowCard",
"title": "https://adaptivecards.io",
"card": {
"type": "AdaptiveCard",
"body": [
{
"type": "TextBlock",
"text": "Are You sure you want to open this link?"
}
],
"actions": [
{
"type": "Action.OpenUrl",
"title": "YES",
"url": "https://adaptivecards.io"
}
],
"$schema": "http://adaptivecards.io/schemas/adaptive-card.json"
}
}
]
}
Looks like this:
Onclick:
Reference: https://adaptivecards.io/explorer/Action.ShowCard.html
Let me know if this works fine for you. Happy Coding

Detect the speaker of Google Home or Amazon's Alexa

I would like to detect who is interacting with my agent.
For example I read that Alexa should be able to detect different users. The Google Home advertisement also let me think that it should detect who is talking. So how can I see who is talking?
In slack it seems to be easier since it is well known who is writing. However I cannot see who I get the current user.
I found out how to detect the user in slack: If you implement that hook you will get this example json:
{
"id": "f7912345-e21c-450f-a8ca-d01e38012345",
"timestamp": "2016-12-20T06:53:51.071Z",
"result": {
"source": "agent",
"resolvedQuery": "echo hallo welt",
"speech": "",
"action": "",
"actionIncomplete": false,
"parameters": {
"myInput": "hallo welt"
},
"contexts": [{
"name": "generic",
"parameters": {
"slack_user_id": "U0AT12345",
"myInput": "hallo welt",
"slack_channel": "D3DR12345",
"myInput.original": "hallo welt"
},
"lifespan": 4
}],
"metadata": {
"intentId": "06212345-06a0-40fe-bbeb-9189db412345",
"webhookUsed": "true",
"webhookForSlotFillingUsed": "false",
"intentName": "Response"
},
"fulfillment": {
"speech": "",
"messages": [{
"type": 0,
"speech": ""
}]
},
"score": 0.75
},
"status": {
"code": 200,
"errorType": "success"
},
"sessionId": "10612345-c681-11e6-af08-875120912345",
"originalRequest": {
"source": "slack_testbot",
"data": {
"channel": "D3DR12345",
"match": ["echo hallo welt"],
"text": "echo hallo welt",
"team": "T04H12345",
"type": "message",
"event": "direct_message",
"user": "U0AT12345",
"ts": "1482216830.000005"
}
}
}
So in case of slack you can access result->contexts[0]->paramaters->slack_user_id.
Google Home does not (at least currently) have a way to handle multiple users on the same device.
Google Home keeps improving (even removing development hurdles I've faced with their recent updates). It can now be trained to know your voice vs someone else's voice.
Tomato, tomahto. Google Home now supports multiple users

Resources