Skip to main content

Overview

With this integration, Ocean can view and release Microsoft quarantined emails directly, streamlining the process and reducing the manual effort required to handle user release requests.

Prerequisites

  • Consent permissions have been granted, including the “Manage Exchange As Application” permission.
  • Ensure you have Exchange Online PowerShell installed and can connect (See Microsoft’s guide for setup details)
  • Have Ocean’s App ID:
    App ID
    xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxx
    
    Ocean provides this App ID. It is not something you generate yourself — reach out to your Ocean representative to obtain the App ID for your tenant before starting this setup.
NoteGranting Exchange.ManageAsApp unlocks the app-only authenticiation pathway to Exchange Online, but you still need to assign roles for what the app can do.

Process

1

Set up

PowerShell
Install-Module ExchangeOnlineManagement -Force -Scope CurrentUser
Install-Module Microsoft.Graph -Scope CurrentUser -Repository PSGallery
Import-Module ExchangeOnlineManagement
Import-Module Microsoft.Graph
Connect-ExchangeOnline
2

Create an Exchange service principal

PowerShell
$sp = Get-MgServicePrincipal -Filter "appId eq 'xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxx'"

# Create Exchange's pointer object and capture integrate
New-ServicePrincipal -AppId $sp.AppId -ObjectId $sp.ObjectId -DisplayName "Ocean Quarantine App"
$oceanExchangeSP = Get-ServicePrincipal -Identity "Ocean Security"
3

Create a custom role that includes only quarantine cmdlets

  • We create a custom role by duplicating the built-in Transport Hygeine role and removing all unnecessary cmdlets - keeping only those required to view and export quarantine data.
  • This ensure the Ocean app has the minimum access necessary and cannot perform any unrelated actions, such as modifying mailboxes, chaning rules, or impersonating users.
PowerShell
$role = "Ocean-Quarantine-Automation-Role"
New-ManagementRole -Parent "Transport Hygiene" -Name $role

# Keep only the quarantine (read) cmdlets
$keep = @("Get-QuarantineMessage", "Preview-QuarantineMessage", "Export-QuarantineMessage", "Get-QuarantineMessageHeader")

Get-ManagementRoleEntry "$role\*" | Where-Object { $_.Name -notin $keep } | ForEach-Object { Remove-ManagementRoleEntry -Identity "$role\$($_.Name)" -Confirm:$false }
4

Creating a scope

You can scope the role to a subset of mailboxes or a distribution group to enforce least-privilege boundaries.
PowerShell
# If scoping by a user list
$mailboxes = @("bob@acme.org","alice@acme.org")
$filter = ($mailboxes | ForEach-Object { "PrimarySmtpAddress -eq '$_'" }) -join " -or "

# If scoping with a distribution list
$group = Get-DistributionGroup -Identity "<GroupName>"
$filter = "MemberOfGroup -eq '$($group.DistinguishedName)'"

# Create the scope using one of the filters
New-ManagementScope -Name "Ocean-Quarantine-Scope" -RecipientRestrictionFilter $filter
5

Bind the role to the app

Using New-ManagementRoleAssignment, we attach the new custom role to the app’s service principal.
PowerShell
# Assign the app to the role using our scope
New-ManagementRoleAssignment -Name "Ocean-Quarantine-App-Assignment" -Role $role -App $oceanExchangeSP.Id -CustomResourceScope "Ocean-Quarantine-Scope"
6

Verifying the app has permissions

You can test the app has permissions on one of your users that’s inside the scope.
PowerShell
Test-ServicePrincipalAuthorization -Identity $oceanExchangeSp.Id -Resource bob@acme.org