microsoftgraph / microsoft-graph-comms-samples

Microsoft Graph Communications Samples
MIT License
208 stars 231 forks source link

Question: How to retrieve the details of the meeting from which a call is originated? #462

Open jong64 opened 3 years ago

jong64 commented 3 years ago

Here's the scenario providing the context for the question.

User A (Jason Carter) creates a Teams meeting and adds user B (Admin) as a participant. As you see in the following screen shot, the meeting subject/title is "Test Meeting between Jason and Admin", and the meeting description reads "Hey, this meeting is to test sample bot. I hope you can help!".

image

When the meeting completes with the two participants joining the call, the sample bot (https://github.com/microsoftgraph/microsoft-graph-comms-samples/tree/master/Samples/V1.0Samples/LocalMediaSamples/PolicyRecordingBot) is supplied with the following notification payload (showing only the relevant part here for space reason) containing some information about the meeting context.

{ "@odata.type": "#microsoft.graph.commsNotifications", "value": [ { "@odata.type": "#microsoft.graph.commsNotification", "changeType": "deleted", "resourceUrl": "/communications/calls/8f1f6300-a17c-4c2b-8fdd-bec8b165fe65", "resource": "/app/calls/8f1f6300-a17c-4c2b-8fdd-bec8b165fe65", "resourceData": { "@odata.type": "#microsoft.graph.call", "state": "terminated", "resultInfo": { "@odata.type": "#microsoft.graph.resultInfo", "code": 200, "subcode": 0, "message": "Recorder call leg has been terminated because the participant call leg has ended.. DiagCode: 0#10550" }, "chatInfo": { "@odata.type": "#microsoft.graph.chatInfo", "threadId": "19:meeting_M2RjN2RjMGQtZTNmMC00ZWJmLWFjNWUtM2U5YzBjODk4ZDA5@thread.v2", "messageId": "0" }, "meetingInfo": { "@odata.type": "#microsoft.graph.tokenMeetingInfo", "token": "eyJhbGciOiJSUzI1NiIsImtpZCI6Ik4xb25SeFM4Smk0MlVfbndJOWRaYmRrZTVpayIsInR5cCI6IkpXVCIsIng1dCI6Ik4xb25SeFM4Smk0MlVfbndJOWRaYmRrZTVpayJ9.eyJhcHBJZCI6IjZlYmQzZDc5LTFkMjctNDQyMC1hZWJhLTVlN2Y0ZTZkMWU0MyIsImNvbnZlcnNhdGlvbkNvbnRyb2xsZXIiOiJodHRwczovL2FwaS5mbGlnaHRwcm94eS50ZWFtcy5taWNyb3NvZnQuY29tL2FwaS92Mi9lcC9jb252LXVzd2UtMDguY29udi5za3lwZS5jb20vY29udi9FSEtTcVV2ZVRVS1JIQ2JPR0ZBYmx3P2k9MTA3JmU9NjM3NTc3NDIwNjMyNjI0MzkyIiwiYWN0aXZpdHlJZCI6ImQxMWQ4YTU3LTFiYTgtNDg2YS05NzgxLWU1YTE5NzgwNDFiYSIsImh0dHA6Ly9zY2hlbWFzLm1pY3Jvc29mdC5jb20vaWRlbnRpdHkvY2xhaW1zL3RlbmFudGlkIjoiMDMyMDNhMTgtMjAwMS00YTRiLThkODEtZWZhYjljMGY5NzY3IiwibmJmIjoxNjIzMDcwOTQ4LCJleHAiOjE2MjMxNTczNDgsImlzcyI6Imh0dHBzOi8vYXBpLmJvdGZyYW1ld29yay5jb20iLCJhdWQiOiJodHRwczovL2FwaS5ib3RmcmFtZXdvcmsuY29tIn0.ImSKPNeDcN18A4WMgFIJJpbY873bgpKCUhTs3c9yn5ZLkVeOsyo_pe5kFm5-GjPWNzc3uN-qGslS__NvUzK0NxgHrtSzNEu9w0W6Js_AmgszYByen8eoxN571lC5ZbNeIJVDF8yS87bIH6MczX2I5_P-aghomFYRD2LGdjTI4rS-m6sn26uj5nY3UROMZdwW9XGvxr-zhmTnc2XUbeYEtcEkkf92sCDcyQjbm1lNZAqEushHCTo5D3nqFzBxRp9qH9A9QQ5nHpROS9YY01ghbaCzgpDjFc6XVVfatwW5My2Uw9rJzexszKcv1KT6EM83ekR3A5ftNHqdeiIDpgcT1g", "organizerInfo": { "@odata.type": "#microsoft.graph.organizerInfo", "identity": { "@odata.type": "#microsoft.graph.identitySet", "user": { "@odata.type": "#microsoft.graph.identity", "id": "7231fff4-bd85-403a-b293-aae48ffa2717", "tenantId": "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX", "identityProvider": "AAD" } }, "region": "amer" } },

As you see above, the "organizerInfo" component only contains information (ID) about the person who organized/created the meeting. The "chatInfo" component contains threadId, which is also shared across all chat messages produced from the same meeting. If I base64 decode the middle part of the threadId value (M2RjN2RjMGQtZTNmMC00ZWJmLWFjNWUtM2U5YzBjODk4ZDA5), I get 3dc7dc0d-e3f0-4ebf-ac5e-3e9c0c898d09, which must be a UUID representing some resource. However, I have not been able to determine exactly what type of resource this value represents.

My goal is to be able to find/retrieve some essential information about the meeting from which this call originated, specifically, the meeting subject/title and the meeting description, at the least. So, the question is how do I achieve that? What information from the above payload (or other data available to the bot) can I use to retrieve the meeting details, and what API/SDK to use to achieve it?

ssulzer commented 3 years ago

@zhengni-msft @jsandoval-msft @yizhenww

zhengni-msft commented 3 years ago

@jong64 , it's not supported to get meeting info from a active call a bot is invited in. Instead, a bot can join a meeting. can you describe your scenario so we might be able to provide solution for you? Using policy-based recording sample seems not a right solution for you as it should NOT be used for any other purpose other than policy-based recording.

jong64 commented 3 years ago

Hi @zhengni-msft Thanks for the reply.

Basically, our requirement is that when policy-controlled users start or join any meeting, we need to capture not only the audio/video/screen sharing streams, but also enough metadata about the call/meeting so that when our application presents the collected data for policy evaluation at a later point, the reviewer should be able to re-construct the original context in which the communication was carried out. For our purpose, the meeting subject/description is important pieces of metadata.

I hope this clarifies the scenario. If not, please let me know.

jong64 commented 3 years ago

@jong64 , it's not supported to get meeting info from a active call a bot is invited in. Instead, a bot can join a meeting.

@zhengni-msft, Does this mean that one way the policy-based compliance recording bot could fulfill this need is for it to turn around and (perhaps in another thread?) join the meeting once again using the tokenMeetingInfo.token to retrieve the details about the meeting? Please advice.

zhengni-msft commented 3 years ago

@jong64, we don't support retrieving meeting details so far. And the conversation which the related user is in might not be a meeting either. rejoin the meeting doesn't resolve that.

JamyDev commented 3 years ago

@jong64 We just published documentation of our GetMeetingDetails API which should be able to give you some more context about this meeting. botframework is working on adding these to their SDK's, but you can always call them manually with threadId that you have in the above payload. Please let me know if you have any more questions.

Docs: https://docs.microsoft.com/en-us/microsoftteams/platform/apps-in-teams-meetings/create-apps-for-teams-meetings?tabs=json#meeting-details-api Dotnet: https://github.com/microsoft/botbuilder-dotnet/pull/5655 Overall tracking item: https://github.com/microsoft/botframework-sdk/issues/6304

jong64 commented 3 years ago

@JamyDev, Thanks for the information.

I'm not sure if I follow though. When I invoke the API with the threadId like the following, I get 400 error.

https://graph.microsoft.com/v1.0/meetings/19:meeting_NDk0MGQxNWYtODdjYi00NWU0LWE2NWUtM2RlZjRmOGY4YjA0@thread.v2

So, looks like you didn't mean the normal Graph API endpoints when talking about adding new capability. Also, I'm not sure how I can use threadId in a place expecting meetingId? Could you elaborate a bit more?

By the way, I was able to retrieve some of the meeting information (although not in real-time) by utilizing the call chain id made available to the bot. With it, I fetch callRecord object, from which I use joinWebUrl to further fetch corresponding onlineMeeting object, which gives me the meeting subject and the attendee list at the very least.

How does the GetMeetingDetails API different from the work around I used? Does it make more information accessible (e.g. meeting description, notes, etc.)? Or is it different in that the meeting information can be accessed in real time from inside bot while the meeting/call is in progress? The work around I used is no use while call/meeting is in progress, as the callRecord object won't be made available until sometime after the call is complete.