EWS-Office365-Contact-Sync icon indicating copy to clipboard operation
EWS-Office365-Contact-Sync copied to clipboard

ModernAuth Update

Open benj288 opened this issue 2 years ago • 16 comments

Hello,

i currently can't get the Contacts List and also can't execute the Contact Sync due to Basic auth deactivation. (Errors in particular: "Can't fetch Data" "Autodiscover failed") Is there a way, to update the Script, without making a Azure AD App? Thank you Kind regards

benj288 avatar Jul 11 '22 08:07 benj288

@benj288

Are you using the -ModernAuth flag?

grahamr975 avatar Jul 11 '22 11:07 grahamr975

Yes, i get this error however, when the script is trying to fetch the Contact info image

benj288 avatar Jul 11 '22 13:07 benj288

Hey, got the same error. Is there an easy way to fix this? Thanks :)

SeidelMahla avatar Jul 18 '22 12:07 SeidelMahla

I have so far resolved the issue regarding the fetching of the Contact info after implementing an Azure app and adapting the Get-GALContacts Module (Issue #46) However, I get following error when it is trying to Sync to the Mailbox.

VERBOSE: Loading module from path 'C:\Kontaktesynchronisierung\Skripts\SyncModul\EWSContacts\Module\bin\Microsoft.IdentityModel.Clients.ActiveDirectory.dll'. PS>TerminatingError(Connect-EXCExchange): "Exception calling "AutodiscoverUrl" with "2" argument(s): "The Autodiscover service couldn't be located.""

TerminatingError(Connect-EXCExchange): "Exception calling "AutodiscoverUrl" with "2" argument(s): "The Autodiscover service couldn't be located."" 2022.07.18 15:27:13 ERROR Kontakte Sync fehlgeschlagen fuer [email protected] Exception calling "AutodiscoverUrl" with "2" argument(s): "The Autodiscover service couldn't be located."

Is there a updated version of the Connect-EXCExchange Module and the Sync-ContactList module?

benj288 avatar Jul 18 '22 13:07 benj288

Which version of PowerShell you are using?

Can you try to run this command prior and then try again? I currently using PowerShell 4.0 on Server 2012 R2 and this helped me

[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12

christianneeb avatar Jul 25 '22 14:07 christianneeb

I fixed it by installing the new [Exchange Online Powershell V2 Module ]

(https://docs.microsoft.com/en-us/powershell/exchange/exchange-online-powershell-v2?view=exchange-ps)

and editing the "Get-GALContacts.ps1" script. (See below)

EDIT: I got the flag for "DIRECTORY" working. You need to modify the script "Get-Mailboxes.ps1" (See very bottom)

function Get-GALContacts {
	<#
	.SYNOPSIS
		Uses Office 365 services to generate a list of contacts. Only includes contacts with an email address.
	
	.PARAMETER ConnectionUri
		Used to connect to Office 365, by default this is https://outlook.office365.com/powershell-liveid/.
	
	.PARAMETER Credentials
		Office 365 Admin Credentials
	.PARAMETER ExcludeContactsWithoutPhoneNumber
		Switch; Only return contacts that have a phone or mobile number
	.PARAMETER ExcludeSharedMailboxContacts
		Switch; Excludes contacts that are a shared mailbox, or a mailbox without a liscense
	.PARAMETER IncludeNonUserContacts
		Switch; Also return contacts that aren't users/mailboxes in your directory. These contacts must still have an email address.
	
	.EXAMPLE
		PS C:\> Get-GALContacts -ConnectionUri 'https://outlook.office365.com/powershell-liveid/' -Credentials $Credentials
	#>
[CmdletBinding()]
param (
	[Parameter(Position = 0, Mandatory = $true)]
	[string]
	$ConnectionUri,

	[Parameter(Position = 1, Mandatory = $true)]
	[System.Management.Automation.PSCredential]
	$Credentials,

	[Parameter(Position = 2, Mandatory = $false)]
	[bool]
	$ExcludeContactsWithoutPhoneNumber,

	[Parameter(Position = 3, Mandatory = $false)]
	[bool]
	$ExcludeSharedMailboxContacts,

	[Parameter(Position = 4, Mandatory = $false)]
	[bool]
	$IncludeNonUserContacts
)
process {
	try {
		# Connect to Office 365 Exchange Server using a Remote Session
        Connect-ExchangeOnline -ConnectionUri $ConnectionUri -Credential $Credentials
   	
		# Import Global Address List into Powershell from Office 365 Exchange as an array
		$ContactList = Get-User -ResultSize unlimited 

		# If the ExcludeSharedMailboxContacts switch is enabled, exclude contacts that are a shared mailbox or mailbox with no liscense
		if ($ExcludeSharedMailboxContacts) {

            $DirectoryList = $(Get-EXOMailbox -ResultSize unlimited | Where-Object {$_.HiddenFromAddressListsEnabled -Match "False"})

			$EmailAddressList = $DirectoryList.PrimarySMTPAddress
			$ContactList = $ContactList | Select-Object DisplayName,FirstName,LastName,Title,Company,Department,WindowsEmailAddress,Phone,MobilePhone | Where-Object {$EmailAddressList.Contains($_.WindowsEmailAddress)}
		} else {
			$ContactList = $ContactList | Select-Object DisplayName,FirstName,LastName,Title,Company,Department,WindowsEmailAddress,Phone,MobilePhone
		}
		
		# If the IncludeNonUserContacts switch is enabled, also include contacts that aren't actual users in the directory
		if ($IncludeNonUserContacts) {
			$ContactList += Get-Contact -ResultSize unlimited | Select-Object DisplayName,FirstName,LastName,Title,Company,Department,WindowsEmailAddress,Phone,MobilePhone
		}

		# If the ExcludeContactsWithoutPhoneNumber switch is enabled, exclude contacts that don't have a phone or mobile number
		if ($ExcludeContactsWithoutPhoneNumber) {
			$ContactList = $ContactList | Where-Object {$_.Phone -or $_.MobilePhone}
		}
        Disconnect-ExchangeOnline -Confirm:$false

	# Only return contacts with email addresses
	return $ContactList | Where-Object {$null -ne $_.WindowsEmailAddress -and "" -ne $_.WindowsEmailAddress}
	} catch {
		Write-Log -Level "FATAL" -Message "Failed to fetch Global Address List Contacts from Office 365 Directory" -exception $_.Exception.Message
	}
}
}

This is the Get-Mailboxes.ps1 script

function Get-Mailboxes {
	<#
	.SYNOPSIS
		Uses Office 365 services to generate a list of contacts 
	
	.PARAMETER ConnectionUri
		Used to connect to Office 365, by default this is https://outlook.office365.com/powershell-liveid/.
	
	.PARAMETER Credentials
		Office 365 Admin Credentials
	
	.EXAMPLE
		PS C:\> Get-GALContacts -ConnectionUri 'https://outlook.office365.com/powershell-liveid/' -Credentials $Credentials
	#>
[CmdletBinding()]
param (
	[Parameter(Position = 0, Mandatory = $true)]
	[string]
	$ConnectionUri,

	[Parameter(Position = 1, Mandatory = $true)]
	[System.Management.Automation.PSCredential]
	$Credentials
)
process {
	try {
	# $Null = @() is a workaround for this function returning a random filename such as "tmp_z1ci55dv.kke" at the start of the output....
	$Null = @(
		# Connect to Office 365 Exchange Server using a Remote Session
     Connect-ExchangeOnline -ConnectionUri $ConnectionUri -Credential $Credentials 
    

			$DirectoryList = $(Get-Mailbox -ResultSize unlimited | Where-Object {$_.HiddenFromAddressListsEnabled -Match "False"}).PrimarySMTPAddress
    
    
        Disconnect-ExchangeOnline -Confirm:$false
      
		
	)

	} catch {
		Write-Log -Level "FATAL" -Message "Failed to fetch user mailbox list from Office 365 directory" -exception $_.Exception.Message
	}
	return $DirectoryList | Where-Object {$null -ne $_ -and "" -ne $_}
}
}

JimSnead avatar Jul 28 '22 18:07 JimSnead

Which version of PowerShell you are using?

Can you try to run this command prior and then try again? I currently using PowerShell 4.0 on Server 2012 R2 and this helped me

[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12

Where have you added this line?

benj288 avatar Aug 08 '22 10:08 benj288

Sorry for writing again - i have made our script finally work. However, in my Azure AD Sign-in logs, there is still an entry coming up from the script. Since basic auth will be disabled on October 1st, i need to adjust the script to this.

My only problem is the Sync-ContactList.ps1 Has anyone adjusted this script for an Azure APP? If so, could you please share this with me? I would be grateful.

Kind regards Ben

benj288 avatar Aug 08 '22 11:08 benj288

@benj288 Could you source the website where you found the basic authentication depreciation date? I thought it was next year, rather than October 1st. Thanks

grahamr975 avatar Aug 08 '22 15:08 grahamr975

@benj288 Could you source the website where you found the basic authentication depreciation date? I thought it was next year, rather than October 1st. Thanks

You will find the informations here: https://docs.microsoft.com/en-us/exchange/clients-and-mobile-in-exchange-online/deprecation-of-basic-authentication-exchange-online

christianneeb avatar Aug 08 '22 18:08 christianneeb

Yes they announced it last year Did anybody adjust their scripts?

benj288 avatar Aug 09 '22 11:08 benj288

@christianneeb Where have you added the [Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12 In your Scripts?

benj288 avatar Aug 09 '22 12:08 benj288

@benj288 Several users have had success with setting up an Azure app for ExchangeOnline in issue #46. I'm working on an update for the main script with a tutorial for setting this up.

As for the EWS portion of the script, I don't think this needs to be changed as it's already coded to generate an OAuth token from the user credentials when using the -ModernAuth flag.

grahamr975 avatar Aug 09 '22 18:08 grahamr975

I run the script via a scheduled Task and therefor created a small script that referenced to this script here. Script is running on a Windows Server 2012 R2 with PowerShell 4.0. If you have any newer version, you wont need to add this line.

grafik

christianneeb avatar Aug 10 '22 11:08 christianneeb

@benj288 Several users have had success with setting up an Azure app for ExchangeOnline in issue #46. I'm working on an update for the main script with a tutorial for setting this up.

As for the EWS portion of the script, I don't think this needs to be changed as it's already coded to generate an OAuth token from the user credentials when using the -ModernAuth flag.

Thank you for your info. Is there new version of the Main script working?

benj288 avatar Aug 25 '22 13:08 benj288

@benj288 I'm still working on the new version + a guide for setting up an Azure app cert. Once it's available, I'll publish it for everyone.

grahamr975 avatar Aug 29 '22 21:08 grahamr975

@benj288 and others,

I published the new OAuth script version & guide in commit 9fcfe1f06192848882564615dd9aa05e71d69970. All basic authentication has been upgraded to certificate based. If anyone has any questions, please reach out.

grahamr975 avatar Sep 13 '22 13:09 grahamr975