Monthly Archives: May 2025

External domain takeover and Microsoft Graph

When attempting to prove ownership of a domain administrators sometimes encounter a scenario where the domain is associated with another tenant. It is possible that the domain is associated with an unmanaged (viral) tenant within Microsoft 365.

We provide documentation to administrators on how to convert the unmanaged tenant to managed and then remove the domain. https://learn.microsoft.com/en-us/entra/identity/users/domains-admin-takeover

The external takeover method relies on Microsoft Graph to complete the process. Unfortunately, the instructions currently contained in our published guidance no longer work. In this post I want to provide updated guidance on how to utilize graph to perform the external takeover method.

In order to preform an external takeover the account or graph application that you are using must have the appropriate rights for domain management. Information on domain verify can the permissions supported may be found here: https://learn.microsoft.com/en-us/graph/api/domain-verify?view=graph-rest-1.0&tabs=http. In this instance Domain.ReadWrite.All are the only permissions supported. Please note that consent may be required in order to add these permissions.

Prior to performing the external admin takeover, the domain will need to be added to the tenant and the appropriate DNS records for validation in place.

To perform the process of the external takeover we will:

  • Connect to Microsoft Graph and specify the minimum permissions required.
  • Create a URL to call domain verify.
  • Create body parameters to include with the domain verify post that force takeover is specified.
  • Invoke the graph method and capture the results.

The code is as follows:

Connect-MGGraph -scopes "Domain.ReadWrite.All"

$domainID = "domainToTakeOver.com"

$uri = "https://graph.microsoft.com/v1.0/domains/$domainID/verify"

$body = @ { forceTakeover = $true } | ConverTo-JSON

$response = Invoke-MGGraphRequest -Method POST -uri $uri -Body $body

$response | ConvertTo-JSON

$response

The response should contain a success or failure message.

Microsoft 365 GCC High Tenants and Missing Domains

Microsoft 365 provides a Government Community Cloud High offering for the U.S Government, contractors, and other organizations that qualify. As with our commercial or worldwide tenants many customers elect to add a vanity or custom domain to their M365 GCC-H tenant.

In a typical commercial tenant the vanity domains are managed through the domains tab of the Microsoft 365 Administration Center. Here is a sample instructions for commercial customers – https://learn.microsoft.com/en-us/microsoft-365/admin/setup/add-domain?view=o365-worldwide.

In the M365 Admin Center for GCC-H tenants the domains tab is missing. This is currently by design. When adding, verifying, or removing domains in a GCC-H tenant Microsoft Graph must be utilized. In this post I want to outline the manual steps for adding and verifying a domain in a GCC-H tenant.

Graph commands often span multiple PowerShell modules in order to achieve their work. Prior to running any graph commands, I recommend that all associated graph PowerShell modules be updated. This ensures that you do not have a mismatch, for example, between the authentication module and the identity module. Note: This process can take a long time depending on the number of graph modules you have installed.

Get-InstalledModule Microsoft.Graph.* | Update-InstalledModule -force -confirm:$FALSE

If you are new to graph or to ensure that you have the module necessary to perform domain work, the Microsoft.Graph.Identity.DirectoryManagement module must be installed.

Install-Module Microsoft.Graph.Identity.DirectoryManagement

When adding and verifying the domain there are three graph commands that will be utilized.

In order to run the following commands, the graph permission Domain.ReadWrite.All must either be consented to on the individual account or for the entire organization. Note: If you do not have global administrator privileges you will not be able to provide consent for graph scopes. It may be necessary for another administrator to perform the consent on your behalf.

The process to add a domain via graph:

$tenantID = "Entra Tenant ID for the GCC H" organization" #User Supplied
$scopes = "Domain.ReadWrite.All"
$environment = "USGov"

Connect-MgGraph -Environment $environment -TenantId $tenantID -Scopes $scopes
$domainID = "contoso.com"

$params = @{
	id = $domainID
}

new-MGDomain -bodyParameter $params

If the new-MGDomain command is successful the following return is expected.

Id          AuthenticationType AvailabilityStatus IsAdminManaged IsDefault IsInitial IsRoot IsVerified Manufacturer Mod
                                                                                                                    el
--          ------------------ ------------------ -------------- --------- --------- ------ ---------- ------------ ---
contoso.com Managed                               True           False     False     False  False

Once the domain has been added with new-MGDomain the DNS verification records are obtained. In the below example for the record type TXT you would use the value MS=ms41165256 or for the record type MX you would use ms41165256.msv1.invalid with preference 32767.

$dnsRecords = get-MGDomainVerificationDNSRecord -domainID $domainID
$dnsRecords | fl

Id                   : aceff52c-06a5-447f-ac5f-256ad243cc5c
IsOptional           : False
Label                : contoso.com
RecordType           : Txt
SupportedService     : Email
Ttl                  : 3600
AdditionalProperties : {[@odata.type, #microsoft.graph.domainDnsTxtRecord], [text, MS=ms41165256]}

Id                   : 5fbde38c-0865-497f-82b1-126f596bcee9
IsOptional           : False
Label                : contoso.com
RecordType           : Mx
SupportedService     : Email
Ttl                  : 3600
AdditionalProperties : {[@odata.type, #microsoft.graph.domainDnsMxRecord], [mailExchange, ms41165256.msv1.invalid],
                       [preference, 32767]}

These records are inserted into your commercial DNS provider for the domain you are adding. Please note that it can take several minutes for your new public DNS records to be accessible. You may consider using a third party tool or nslookup to validate that the DNS records are available prior to proceeding with the next step.

confirm-MGDomain -domainID $domainID

If the confirm is successful, the domain will be validated and available in the M365 GCC-H tenant.

To complete the integration of custom domains with Microsoft 365 services you have to publish additional DNS records. For GCC-H tenants these DNS records must be calculated manually. You can find resources for calculating these DNS records at https://learn.microsoft.com/en-us/microsoft-365/enterprise/dns-records-for-office-365-gcc-high?view=o365-worldwide.