I'm use Microsoft Graph API for retrieve attachments in mails.
I use this endpoint for retrieve attachments https://graph.microsoft.com/v1.0/users/{mailbox.mail}/messages/{message.id}/attachments/
$callAPI = @{
Headers = @{
Authorization = "Bearer $token"
}
Uri = "https://graph.microsoft.com/v1.0/users/{mailbox.mail}/messages/{message.id}/attachments/"
Method = "GET"
}
$attachments = (Invoke-RestMethod @callAPI).value;
After I use foreach for retrieve attachment content with this endpoint : https://graph.microsoft.com/v1.0/users/{mailbox.mail}/messages/{message.id}/attachments/{attachment.id}/$value
$callAPI = @{
Headers = @{
Authorization = "Bearer $token"
}
Uri = "https://graph.microsoft.com/v1.0/users/{mailbox.mail}/messages/{message.id}/attachments/{attachment.id}/$value"
Method = "GET"
}
$content = Invoke-RestMethod @callAPI;
And I use this command line for save file :
Set-Content -Path "$($attachmentsTempDestination)\$($attachment.name)" -Value $content
But my file is bad and not recognized by Excel.
I try the endpoint for attachment content in PostMan and I save response ( Picture : PostMan save response). The saved file is correct.
Probably, it's my last PowerShell command for save content isn't good, but I don't know how do for fix this issue.
Please help me !
With @glen-scales answer, I find a good PowerShell code for my usecase :
$callAPI = @{
Headers = @{
Authorization = "Bearer $token"
}
Uri = "https://graph.microsoft.com/v1.0/users/{mailbox.mail}/messages/{message.id}/attachments/"
Method = "GET"
}
$attachments = (Invoke-RestMethod @callAPI).value;
foreach ($attachment in $attachments) {
[System.IO.File]::WriteAllBytes("$($attachmentsTempDestination)\$($attachment.name)",[System.Convert]::FromBase64String($attachment.contentBytes))
}
CodePudding user response:
The attachment content is a base64 encoded string so the way your using set-content will just be writing that base64 content to the file which would not be valid.
You need to first convert it to a byte array and then you should be able to do something like
Set-Content -Path "$($attachmentsTempDestination)\$($attachment.name)" -Value [System.Convert]::FromBase64String($content) -Encoding Byte
otherwise you could also use (which maybe faster as set-content)
[System.IO.File]::WriteAllBytes("$($attachmentsTempDestination)\$($attachment.name)",[System.Convert]::FromBase64String($content))