---
title: How to connect M365 and Entra without granting Global Reader
description: "Note: The only method from Microsoft to grant “View only recipient&quot; as described below, is via Powershell. Note:  This section is only necessary if you don't already have an app created for M365 or En"
---

[Skip to content](https://support.preludesecurity.com/how-to-connect-m365-and-entra-without-global-reader#main-content)

English

Show submenu for translations

[Contact support](https://support.preludesecurity.com/kb-tickets/new?hsLang=en)

![Prelude\_Wordmark\_Black\_Transparent.png\]](https://support.preludesecurity.com/hs-fs/hubfs/Prelude_Wordmark_Black_Transparent.png?height=50&name=Prelude_Wordmark_Black_Transparent.png)

Open main navigation

Close main navigation

- English
  
  Show submenu for translations
- [Contact support](https://support.preludesecurity.com/kb-tickets/new)
- [Visit the website](https://www.preludesecurity.com/)

[Visit the website](https://www.preludesecurity.com/)

 Find what you're looking for

- There are no suggestions because the search field is empty.

1. [Knowledge Base](https://support.preludesecurity.com/?hsLang=en)
2. [Monitor](https://support.preludesecurity.com/monitor?hsLang=en)
3. [Identity Management Integrations](https://support.preludesecurity.com/monitor?hsLang=en#identity-management-integrations)

# How to connect M365 and Entra without granting Global Reader

Note: The only method from Microsoft to grant “View only recipient" as described below, is via Powershell.

### Create an App Registration

Note:  This section is only necessary if you don't already have an app created for [M365](https://support.preludesecurity.com/docs/microsoft-m365-integration?hsLang=en) or [Entra ID](https://support.preludesecurity.com/docs/entra-id?hs_preview=elHNFsqz-185029109845&hsLang=en)

 Navigate to the [App registrations section](https://portal.azure.com/#view/Microsoft_AAD_RegisteredApps/ApplicationsListBlade) in the Azure Portal.  
Select “+ New registration” toward the top of the page.

- Enter a name for your application 
    - Choose Single tenant as the supported account type (Accounts in this organizational directory only). Click Register.
    - Leave Redirect URI (optional) as it is.  
      After registration:
- Note down the Application (client) ID and Directory (tenant) ID from the app’s Overview page.
- In the left menu, expand the Manage section and select Certificates & secrets and create a new Client Secret:
- Click New client secret, enter a description, and set an expiration period.  
  Note down the generated Client Secret Value (you won’t be able to view it later).

we now have:

APP ID (Application (client) ID) from step 6  
TENANT ID (Directory (tenant) ID) from step 6  
APP SECRET (Client Secret Value) from step 7

### Granting API Permissions

- Grant the above app the API permissions for Entra, M365 or both:
- [Microsoft Entra ID API Permissions](https://support.preludesecurity.com/docs/entra-id?hsLang=en)
- [Microsoft M365 API Permissions](https://support.preludesecurity.com/docs/microsoft-m365-integration?hsLang=en)

### Assigning roles to your App

- Save the following powershell script as a .ps1 file
- Add your app name from the "Create An App Registration" step above in the # CONFIGURATION line, replacing "app\_name" with your app name
- Run the script

```
<#.SYNOPSISAssigns Exchange Online roles to a Microsoft Entra ID (Azure AD) app (service principal)..DESCRIPTION- Connects to Microsoft Graph and Exchange Online.- Finds the Azure AD App by display name.- Ensures it is registered as a service principal in Exchange Online.- Assigns one or more management roles to the service principal.#># CONFIGURATION$AppName    = "app_name"$RoleNames  = @("View-Only Recipients", "Security Reader")$SPName     = "SP for App $AppName"$ProgressPreference = 'SilentlyContinue'function Ensure-Module {    param ([string]$Name)    if (-not (Get-Module -ListAvailable -Name $Name)) {        Write-Host "Installing module '$Name'..." -ForegroundColor Cyan        Install-Module -Name $Name -Scope CurrentUser -Force -AllowClobber    }}# Ensure required modulesEnsure-Module "ExchangeOnlineManagement"Ensure-Module "Microsoft.Graph.Applications"Import-Module ExchangeOnlineManagement -ErrorAction StopImport-Module Microsoft.Graph.Applications -ErrorAction Stop# Connect to Graph and Exchange Onlinetry {    Connect-MgGraph -Scopes "Application.Read.All", "Directory.Read.All"    Connect-ExchangeOnline -ErrorAction Stop} catch {    Write-Error ("Connection failed: {0}" -f $_.Exception.Message)    exit 1}# Find Azure AD App's Service Principal$AzureADApp = Get-MgServicePrincipal -Filter "DisplayName eq '$AppName'"if (-not $AzureADApp) {    Write-Warning "Azure AD App '$AppName' not found in Microsoft Graph. Exiting."    exit 1}Write-Host "Found Azure AD App in Graph: $($AzureADApp.AppId)" -ForegroundColor Green# Create Service Principal in Exchange Online (if needed)try {    $existingSP = Get-ServicePrincipal | Where-Object { $_.AppId -eq $AzureADApp.AppId }    if (-not $existingSP) {        Write-Host "Creating service principal in Exchange Online..." -ForegroundColor Cyan        $null = New-ServicePrincipal -AppId $AzureADApp.AppId -ObjectId $AzureADApp.Id -DisplayName $SPName -ErrorAction Stop        Start-Sleep -Seconds 10    } else {        Write-Host "Service Principal already exists in Exchange Online." -ForegroundColor Green    }} catch {    Write-Warning ("Could not create service principal (might already exist): {0}" -f $_.Exception.Message)}# Retrieve SP from Exchange Online$SP = Get-ServicePrincipal | Where-Object { $_.AppId -eq $AzureADApp.AppId }if (-not $SP) {    Write-Error "Failed to find Service Principal in Exchange Online after creation."    exit 1}# Assign roles to the service principalforeach ($RoleName in $RoleNames) {    $existingAssignment = Get-ManagementRoleAssignment -Role $RoleName -GetEffectiveUsers |        Where-Object { $_.RoleAssigneeType -eq "ServicePrincipal" -and $_.App -eq $SP.ObjectId }    if ($existingAssignment) {        Write-Host "Service Principal is already assigned to role '$RoleName'. Skipping." -ForegroundColor Yellow    } else {        try {            New-ManagementRoleAssignment -Role $RoleName -App $SP.ObjectId -ErrorAction Stop            Write-Host "Role '$RoleName' assigned to Service Principal '$($SP.DisplayName)'" -ForegroundColor Green        } catch {            Write-Error ("Failed to assign role '{0}': {1}" -f $RoleName, $_.Exception.Message)        }    }}
```

​

​

- [Monitor](https://support.preludesecurity.com/monitor?hsLang=en#main-content)

    - [Introduction to Control Monitor](https://support.preludesecurity.com/monitor?hsLang=en#introduction-to-control-monitor)
    - [Configuration](https://support.preludesecurity.com/monitor?hsLang=en#configuration)
    - [Client Hardware Security Integrations](https://support.preludesecurity.com/monitor?hsLang=en#client-hardware-security-integrations)
    - [Device Discovery Integrations](https://support.preludesecurity.com/monitor?hsLang=en#device-discovery-integrations)
    - [EDR Integrations](https://support.preludesecurity.com/monitor?hsLang=en#edr-integrations)
    - [Email Integrations](https://support.preludesecurity.com/monitor?hsLang=en#email-integrations)
    - [Identity Management Integrations](https://support.preludesecurity.com/monitor?hsLang=en#identity-management-integrations)
    - [Endpoint Management Integrations](https://support.preludesecurity.com/monitor?hsLang=en#endpoint-management-integrations)
    - [Vulnerability Management Integrations](https://support.preludesecurity.com/monitor?hsLang=en#vulnerability-management-integrations)
    - [Reporting](https://support.preludesecurity.com/monitor?hsLang=en#reporting)
    - [Troubleshooting](https://support.preludesecurity.com/monitor?hsLang=en#troubleshooting)
- [Detect](https://support.preludesecurity.com/detect?hsLang=en#main-content)

    - [Basics](https://support.preludesecurity.com/detect?hsLang=en#basics)
    - [Integrations](https://support.preludesecurity.com/detect?hsLang=en#integrations)
    - [Probe deployment](https://support.preludesecurity.com/detect?hsLang=en#probe-deployment)
    - [Security tests](https://support.preludesecurity.com/detect?hsLang=en#security-tests)
    - [Alert suppression](https://support.preludesecurity.com/detect?hsLang=en#alert-suppression)
    - [Assurance](https://support.preludesecurity.com/detect?hsLang=en#assurance)
- [Integrations](https://support.preludesecurity.com/integrations?hsLang=en#main-content)

    - [SASE](https://support.preludesecurity.com/integrations?hsLang=en#sase)
- [Account](https://support.preludesecurity.com/account?hsLang=en#main-content)

    - [SSO](https://support.preludesecurity.com/account?hsLang=en#sso)
- [CLI](https://support.preludesecurity.com/cli?hsLang=en)
- [Release Notes](https://support.preludesecurity.com/release-notes?hsLang=en)

[![Origin Technology Logo](https://support.preludesecurity.com/hs-fs/hubfs/origin_logo_inverse_000000.png?width=5000&height=5000&name=origin_logo_inverse_000000.png "Origin Technology Logo")](http://originhq.com)

Prelude Security Knowledge Base

Copyright © 2026, Origin Technology