Public/Start-MDSADSyncSyncCycle.ps1
Function Start-MDSADSyncSyncCycle { <# .SYNOPSIS Start an Azure AD Connect sync cycle remotely. .DESCRIPTION Start an Azure AD Connect sync cycle remotely. The default servername can be set with Set-MDSConfiguration or a servername can be specified with the -ServerName parameter. Credentials can be passed with MDSCredential or Credential. The -StartSync swtich parameter is required to start a sync. .EXAMPLE Start-MDSADSyncSyncCycle -MDSCredential MyCred1 -StartSync Start a sync cycle using a stored MDSCredential. Uses the MDSConfiguration file's ADConnectServer value for the target server. .EXAMPLE Start-MDSADSyncSyncCycle -Credential MyUserName -StartSync Start a sync cycle with a password prompt for the username MyUserName. Uses the MDSConfiguration file's ADConnectServer value for the target server. .EXAMPLE Start-MDSADSyncSyncCycle -MDSCredential MyCred1 -ServerName MyServer -StartSync Start a sync cycle using a stored MDSCredential against the specified server MyServer .NOTES #> [CmdletBinding(DefaultParameterSetName="MDSCredential")] Param ( [parameter(Position=0,ParameterSetName="MDSCredential")] [ValidateNotNullOrEmpty()] [String]$MDSCredential, [parameter(Position=0,ParameterSetName="Credential")] [ValidateNotNullOrEmpty()] [System.Management.Automation.CredentialAttribute()] $Credential, [parameter(Position=1, ParameterSetName="MDSCredential", Mandatory=$False)] [parameter(Position=1, ParameterSetName="Credential", Mandatory=$False)] [string]$ServerName, [parameter(Position=2, ParameterSetName="MDSCredential", Mandatory=$True)] [parameter(Position=2, ParameterSetName="Credential", Mandatory=$True)] [switch]$StartSync ) Begin {} Process { # Capture MDS Credentials. If no credentials were specified the current credentials are used. If ($PsCmdlet.ParameterSetName -eq "MDSCredential" -and -not [string]::IsNullOrEmpty($MDSCredential)) { Try { $Credential = Get-MDSCredential -Name $MDSCredential } Catch { $PsCmdlet.ThrowTerminatingError($PSItem) } } # Use the configuration file if a servername was not specified If (-not $ServerName) { Try {$ServerName = Get-MDSConfiguration -Setting ADConnectServer} Catch { Throw "A server name was not specified. Use the -ServerName parameter or configure the ADConnectServer setting with Set-MDSConfiguration." } } $Parameters = @{ 'ComputerName' = $ServerName 'ErrorAction' = "Stop" } If ($Credential) {[void]$Parameters.Add('Credential',$Credential)} If (Invoke-Command @Parameters -ScriptBlock {Get-ADSyncConnectorRunStatus}) { Write-Warning "A sync cycle is already in progress." } Else { Try { # Load the module and start the sync on the AD Connect Server Write-Verbose "Initializing Azure AD Delta Sync..." Invoke-Command @Parameters -ScriptBlock {Import-Module ADSync;Start-ADSyncSyncCycle -PolicyType Delta} # Wait 10 seconds for the sync connector to wake up. Start-Sleep -Seconds 10 # Progress Bar Variables $StartTime = Get-Date # Initial status check $ADSyncConnectorRunStatus = Invoke-Command @Parameters -ScriptBlock {Get-ADSyncConnectorRunStatus} # Monitor the status If ($ADSyncConnectorRunStatus.RunState) { Write-Verbose "Sync has started..." # Monitor the runstate and record the progress with a progress bar While($null -ne $ADSyncConnectorRunStatus.RunState) { $ADSyncConnectorRunStatus = Invoke-Command @Parameters -ScriptBlock {Get-ADSyncConnectorRunStatus} # Progress Bar Processing $Date = Get-Date $CurrTime = $Date - $StartTime $WrPrgParam = @{ Activity = ( "Last Refresh: $($Date.ToLongTimeString())", "Elapsed Time: $($CurrTime -replace '\..*')", "Run State: $($ADSyncConnectorRunStatus.RunState)", "Syncing: $($ADSyncConnectorRunStatus.ConnectorName)" ) -join '|' Status = "Refreshes every 10 seconds until the sync completes. Ctrl + C to stop monitoring." } Write-Progress @WrPrgParam Start-Sleep -Seconds 9 } Write-Verbose "Sync completed at $($Date.ToLongTimeString())" } # The connector status only returns a value if it's running. If it wasn't found running notify the user Else { $Message = "Get-ADSyncConnectorRunStatus could not confirm the sync started after 10 seconds." Throw (New-Object -TypeName System.Exception -ArgumentList $Message) } } Catch {$PsCmdlet.ThrowTerminatingError($PSItem)} } } End {} } |