We utilize Teams during incidents and create channels for each. We would like to be able to export conversation history.
Problem Statements
- Right now the only option we have is to go through Security & Compliance.
- Teams usage is growing in every organization and it would soon become unreasonably to only have Administrators be the ones doing exports of channels for all the Teams.
Solution
This script uses Microsoft 365 CLI to export the conversations from Microsoft Teams Channels.
Prerequisites
- CLI for Microsoft 365
- Microsoft Teams Channel with Coversations
Notes
- Commands m365 teams message list and reply list are based on an API that is currently in preview and is subject to change once the API reached general availability.
- You can only retrieve a message from a Microsoft Teams team if you are a member of that team.
PowerShell Script
function Get-Teams {
$teams = m365 teams team list -o json | ConvertFrom-Json -AsHashtable
return $teams
}
function Get-Channels {
param (
[Parameter(Mandatory = $true)] [string] $teamId
)
$channels = m365 teams channel list --teamId $teamId -o json | ConvertFrom-Json -AsHashtable
return $channels
}
function Get-Messages {
param (
[Parameter(Mandatory = $true)] [string] $teamId,
[Parameter(Mandatory = $true)] [string] $channelId
)
$messages = m365 teams message list --teamId $teamId --channelId $channelId -o json | ConvertFrom-Json -AsHashtable
return $messages
}
function Get-MessageReplies {
param (
[Parameter(Mandatory = $true)] [string] $teamId,
[Parameter(Mandatory = $true)] [string] $channelId,
[Parameter(Mandatory = $true)] [string] $messageId
)
$messageReplies = m365 teams message reply list --teamId $teamId --channelId $channelId --messageId $messageId -o json | ConvertFrom-Json -AsHashtable
return $messageReplies
}
Try {
$teamsCollection = [System.Collections.ArrayList]@()
$teams = Get-Teams
$progressCountTeam = 1;
foreach ($team in $teams) {
Write-Progress -Id 0 -Activity "Processing channels in Team : $($team.displayName)" -Status "Team $progressCountTeam of $($teams.length)" -PercentComplete (($progressCountTeam / $teams.length) * 100)
$channelsCollection = [System.Collections.ArrayList]@()
$channels = Get-Channels $team.id
$progressCountChannel = 1;
foreach ($channel in $channels) {
Write-Progress -Id 1 -ParentId 0 -Activity "Processing messages in channel : $($channel.displayName)" -Status "Channel $progressCountChannel of $($channels.length)" -PercentComplete (($progressCountChannel / $channels.length) * 100)
$messages = Get-Messages $team.id $channel.id
$messagesCollection = [System.Collections.ArrayList]@()
foreach ($message in $messages) {
$messageReplies = Get-MessageReplies $team.id $channel.id $message.id
$messageDetails = $message
[void]$messageDetails.Add("replies", $messageReplies)
[void]$messagesCollection.Add($messageDetails)
}
$channelDetails = $channel
[void]$channelDetails.Add("messages", $messagesCollection)
[void]$channelsCollection.Add($channelDetails)
$progressCountChannel++
}
$teamDetails = $team
[void]$teamDetails.Add("channels", $channelsCollection)
[void]$teamsCollection.Add($teamDetails)
$progressCountTeam++
}
Write-Progress -Id 0 -Activity " " -Status " " -Completed
Write-Progress -Id 1 -Activity " " -Status " " -Completed
$output = @{}
[void]$output.Add("teams", $teamsCollection)
$executionDir = $PSScriptRoot
$outputFilePath = "$executionDir/$(get-date -f yyyyMMdd-HHmmss).json"
# ConvertTo-Json cuts off data when exporting to JSON if it nests too deep. The default value of Depth parameter is 2. Set your -Depth parameter whatever depth you need to preserve your data.
$output | ConvertTo-Json -Depth 10 | Out-File $outputFilePath
Write-Host "Open $outputFilePath file to review your output" -F Green
}
Catch {
$ErrorMessage = $_.Exception.Message
Write-Error $ErrorMessage
}
I hope this script has been helpful, and don’t forget to check out this article written by Anupam Shrivastava on exporting Microsoft teams chat messages.