Public/FlyExchangeApi.ps1
<#
.SYNOPSIS Add mappings into the specified Exchange project. .DESCRIPTION Add mappings into the specified Exchange project. .PARAMETER Project Specify the name of the project to import mappings. .PARAMETER Path Specify the csv file path of the project mappings to import. .OUTPUTS None #> function Import-FlyExchangeMappings { [CmdletBinding()] Param ( [Parameter(Mandatory = $true)] [String] ${Project}, [Parameter(Mandatory = $true)] [String] ${Path} ) Process { 'Calling method: Import-FlyExchangeMappings' | Write-Debug $PSBoundParameters | Out-DebugParameter | Write-Debug Try { $targetProject = Get-FlyProjectByName -ProjectName $Project $mappings = New-Object System.Collections.ArrayList; $importedMappings = Get-FlyMappingsFromCsv -Path $Path #Construct the project mapping list to import foreach ($mapping in $importedMappings) { $item = [PSCustomObject]@{ "sourceIdentity" = $mapping.Source "sourceType" = Get-FlyDataType $mapping.'Source type' "destinationIdentity" = $mapping.Destination "destinationType" = Get-FlyDataType $mapping.'Destination type' } [void]$mappings.Add($item); } #Import project mapping list to the project [System.Net.HttpWebRequest]::DefaultMaximumErrorResponseLength = -1 $result = Add-FlyExchangeMappings -ProjectId $targetProject.Id -ExchangeMappingCreationModel $mappings.ToArray() if ($result) { Write-Host 'Successfully added the mappings to the project.' -ForegroundColor Green } } Catch { Write-Host 'Failed to add the mappings to the project.' -ForegroundColor Red if ($_.ErrorDetails.Message) { $errorModel = ConvertFrom-Json $_.ErrorDetails.Message if ($errorModel.ErrorCode -eq 'ProjectMappingDuplicated') { Write-Host 'ErrorDetail : ProjectMappingDuplicated' -ForegroundColor Red $errorDetails = ConvertFrom-Json $errorModel.ErrorMessage $errorDetails | Select-Object SourceIdentity, DestinationIdentity, ProjectName | Format-Table } else { Write-Host $_.ErrorDetails.Message -ForegroundColor Red } } Write-Error $_.Exception throw } } } <# .SYNOPSIS Export the Exchange migration mapping status to a csv file. .DESCRIPTION Export the Exchange migration mapping status to a csv file. .PARAMETER Project Specify the name of the project to export mappings. .PARAMETER OutFile Specify the csv file path of the project mappings to export. .PARAMETER Filter Specify the csv file to filter specific project mappings to export, export all mappings of the project if not specified. .OUTPUTS None #> function Export-FlyExchangeMappingStatus { [CmdletBinding()] Param ( [Parameter(Mandatory = $true)] [String] ${Project}, [Parameter(Mandatory = $true)] [String] ${OutFile}, [Parameter(Mandatory = $false)] [String] ${Mappings} ) Process { 'Calling method: Export-FlyExchangeMappingStatus' | Write-Debug $PSBoundParameters | Out-DebugParameter | Write-Debug Try { $targetProject = Get-FlyProjectByName -ProjectName $Project -PlatformType 'Exchange' $result = New-Object System.Collections.ArrayList; #Retrieve the project mappings from the specified project $allMappings = Get-FlyAllProjectMappings -ProjectId $targetProject.Id #Match the project mapping list between csv file and specified project if ($Mappings) { $targetMappings = Get-FlyMappingsFromCsv -Path $Mappings foreach ($target in $targetMappings) { foreach ($mapping in $allMappings) { $sourceIdentity = [System.Web.HttpUtility]::UrlDecode($target.'Source') $destinationIdentity = [System.Web.HttpUtility]::UrlDecode($target.'Destination') if ($mapping.SourceIdentity -eq $sourceIdentity -and $mapping.DestinationIdentity -eq $destinationIdentity) { [void]$result.Add($mapping); break; } } } } else { $result = @($allMappings) } if ($result.Count -gt 0) { $folderPath = [System.IO.Path]::GetDirectoryName($OutFile) If (-not (Test-Path $folderPath)) { # Folder does not exist, create it [void](New-Item -Path $folderPath -ItemType Directory) } #Output the matched project mappings to specified file path in csv format $result | ForEach-Object { Convert-FlyMappingStatus -Mapping $_ } | Export-Csv -Path $OutFile -NoTypeInformation Write-Host 'Successfully retrieved the migration mappings. File path:' $OutFile -ForegroundColor Green } else { throw 'No mapping in the CSV file matches the existing migration mappings in this project.' } } Catch { Write-Host 'Failed to retrieve the migration mappings.' -ForegroundColor Red ErrorDetail -Error $_ throw } } } <# .SYNOPSIS Generate migration report for the specified project mappings. .DESCRIPTION Generate migration report for the specified project mappings. .PARAMETER Project Specify the name of the project to generate their migration report. .PARAMETER OutFolder Specify the folder path of migration report file to download. .PARAMETER FileType Specify the format of the generated report file, CSV or Excel, optional for CSV type. .PARAMETER Mappings Specify the csv file to filter specific project mappings to generate report, for all mappings of the project if not specified. .PARAMETER TimeZoneOffset Specify the UTC time offset of current browser. This value will be used to adjust time values when generating the report file, optional for UTC timezone. .PARAMETER Include Specify a list of objects to be included in the migration report, use Tab for available values, optional if you do not export object details. .OUTPUTS None #> function Export-FlyExchangeMigrationReport { [CmdletBinding()] Param ( [Parameter(Mandatory = $true)] [String] ${Project}, [Parameter(Mandatory = $true)] [String] ${OutFolder}, [Parameter(Mandatory = $false)] [String] ${Mappings}, [Parameter(Mandatory = $false)] [ValidateSet('CSV', 'Excel')] [String] ${FileType} = [ReportFileType]::CSV, [Parameter(Mandatory = $false)] [Int32] ${TimeZoneOffset}, [Parameter(Mandatory = $false)] [ValidateSet('ErrorObjects', 'WarningObjects', 'SuccessfulObjects', 'SkippedObjects', 'FilterOutObjects', 'NotFoundObjects', 'ErrorIgnoredObjects', 'UnsupportedObjects')] [String[]] ${Include} ) Process { 'Calling method: Export-FlyExchangeMigrationReport' | Write-Debug $PSBoundParameters | Out-DebugParameter | Write-Debug Try { $targetProject = Get-FlyProjectByName -ProjectName $Project -PlatformType 'Exchange' $targetMappings = Get-FlyExchangeMappings -ProjectId $targetProject.Id -Mappings $Mappings #Construct the settings of report job $reportSetting = [PSCustomObject]@{ "includeMappingSummary" = $true "includeDetails" = $false "reportItemStatus" = @() "reportFileType" = $FileType "isSelectAll" = $true "mappingIds" = @() "timeZone" = $TimeZoneOffset } if ($Include -and $Include.Count -gt 0) { $reportSetting.includeDetails = $true $reportSetting.reportItemStatus = $Include -replace "ErrorObjects", "FailedObjects" } if ($targetMappings -and @($targetMappings).Count -gt 0) { $mappingIds = $targetMappings | Select-Object -Property Id | ForEach-Object { "$($_.Id)" } $reportSetting.mappingIds = @($mappingIds) $reportSetting.isSelectAll = $false } #Trigger the migration report job and get the job id $jobId = Start-FlyExchangeReportJob -ProjectId $targetProject.Id -GenerateReportSettingsModel $reportSetting #Monitor the job status and download the report file when job is finished while ($true) { Write-Host 'The report generation job is running.' -ForegroundColor Green Start-Sleep -Seconds 60 $job = Get-FlyReportJobs -RequestBody @($jobId) $jobStatus = $job.data[0].Status if ($jobStatus -eq [MappingJobStatus]::Finished -or $jobStatus -eq [MappingJobStatus]::FinishedWithException) { Write-Host 'The report generation job is finished.' -ForegroundColor Green $result = Get-FlyReportUrl -JobId $jobId if ($null -ne $result.ReportUrl) { $fileName = Split-Path $([uri]$result.ReportUrl).AbsolutePath -Leaf $filePath = Join-Path -Path $OutFolder -ChildPath $fileName If (-not (Test-Path $OutFolder)) { # Folder does not exist, create it [void](New-Item -Path $OutFolder -ItemType Directory) } Invoke-WebRequest -URI $result.ReportUrl -OutFile $filePath -UseBasicParsing Write-Host 'Successfully downloaded the job report. Report path:' $filePath -ForegroundColor Green } break; } elseif ($jobStatus -eq [MappingJobStatus]::Failed -or $jobStatus -eq [MappingJobStatus]::Stopped) { throw ('The report generation job is {0} with id {1}' -f [MappingJobStatus].GetEnumName($jobStatus), $job.data[0].JobName) } } } Catch { Write-Host 'Failed to generate the migration report.' -ForegroundColor Red ErrorDetail -Error $_ throw } } } <# .SYNOPSIS Start a pre-scan job against the selected project mappings. .DESCRIPTION Start a pre-scan job against the selected project mappings. .PARAMETER Project Specify the name of the project to run job. .PARAMETER Mappings Specify the csv file to filter specific project mappings to run job, for all mappings of the project if not specified. .OUTPUTS A Boolean value indicates whether the work has started successfully #> function Start-FlyExchangePreScan { [CmdletBinding()] Param ( [Parameter(Mandatory = $true)] [String] ${Project}, [Parameter(Mandatory = $false)] [String] ${Mappings} ) Process { 'Calling method: Start-FlyExchangePreScan' | Write-Debug $PSBoundParameters | Out-DebugParameter | Write-Debug Try { $targetProject = Get-FlyProjectByName -ProjectName $Project $targetMappings = Get-FlyExchangeMappings -ProjectId $targetProject.Id -Mappings $Mappings #Construct the settings of the migration job $jobSettings = [PSCustomObject]@{ "type" = [MappingJobType]::Assessment "isSelectAll" = $true "mappingIds" = @() } if ($targetMappings -and @($targetMappings).Count -gt 0) { $mappingIds = $targetMappings | Select-Object -Property Id | ForEach-Object { "$($_.Id)" } $jobSettings.mappingIds = @($mappingIds) $jobSettings.isSelectAll = $false } $result = Start-FlyExchangePreScanJob -ProjectId $targetProject.Id -ProjectMappingOperationModel $jobSettings if ($result) { Write-Host 'The job has started.' -ForegroundColor Green } } Catch { Write-Host 'Failed to start the job.' -ForegroundColor Red ErrorDetail -Error $_ throw } } } <# .SYNOPSIS Start a verify job against the selected project mappings. .DESCRIPTION Start a verify job against the selected project mappings. .PARAMETER Project Specify the name of the project to run job. .PARAMETER Mappings Specify the csv file to filter specific project mappings to run job, for all mappings of the project if not specified. .OUTPUTS A Boolean value indicates whether the job has started successfully #> function Start-FlyExchangeVerification { [CmdletBinding()] Param ( [Parameter(Mandatory = $true)] [String] ${Project}, [Parameter(Mandatory = $false)] [String] ${Mappings} ) Process { 'Calling method: Start-FlyExchangeVerification' | Write-Debug $PSBoundParameters | Out-DebugParameter | Write-Debug Try { $targetProject = Get-FlyProjectByName -ProjectName $Project $targetMappings = Get-FlyExchangeMappings -ProjectId $targetProject.Id -Mappings $Mappings #Construct the settings of the migration job $jobSettings = [PSCustomObject]@{ "type" = [MappingJobType]::Validation "isSelectAll" = $true "mappingIds" = @() } if ($targetMappings -and @($targetMappings).Count -gt 0) { $mappingIds = $targetMappings | Select-Object -Property Id | ForEach-Object { "$($_.Id)" } $jobSettings.mappingIds = @($mappingIds) $jobSettings.isSelectAll = $false } $result = Start-FlyExchangeVerificationJob -ProjectId $targetProject.Id -ProjectMappingOperationModel $jobSettings if ($result) { Write-Host 'The job has started.' -ForegroundColor Green } } Catch { Write-Host 'Failed to start the job.' -ForegroundColor Red ErrorDetail -Error $_ throw } } } <# .SYNOPSIS Start a migration job against the selected project mappings. .DESCRIPTION Start a migration job against the selected project mappings. .PARAMETER Project Specify the name of the project to run job. .PARAMETER Mode Specify the mode of the migration job, use Tab for available values. .PARAMETER Mappings Specify the csv file to filter specific project mappings to run job, for all mappings of the project if not specified. .PARAMETER ScheduleTime Specify the time when you want the job to be scheduled. By default the job will be executed as soon as possible, optional for no schedule. .OUTPUTS A Boolean value indicates whether the job has started successfully #> function Start-FlyExchangeMigration { [CmdletBinding()] Param ( [Parameter(Mandatory = $true)] [String] ${Project}, [Parameter(Mandatory = $true)] [ValidateSet('FullMigration', 'IncrementalMigration', 'ErrorOnly', 'PermissionOnly')] [String] ${Mode}, [Parameter(Mandatory = $false)] [String] ${Mappings}, [Parameter(Mandatory = $false)] [Datetime] ${ScheduleTime} ) Process { 'Calling method: Start-FlyExchangeMigration' | Write-Debug $PSBoundParameters | Out-DebugParameter | Write-Debug Try { $targetProject = Get-FlyProjectByName -ProjectName $Project $targetMappings = Get-FlyExchangeMappings -ProjectId $targetProject.Id -Mappings $Mappings #Construct the settings of the migration job $jobSettings = [PSCustomObject]@{ "type" = $Mode "scheduledTime" = 0 "isSelectAll" = $true "mappingIds" = @() } if ($targetMappings -and @($targetMappings).Count -gt 0) { $mappingIds = $targetMappings | Select-Object -Property Id | ForEach-Object { "$($_.Id)" } $jobSettings.mappingIds = @($mappingIds) $jobSettings.isSelectAll = $false } if ($ScheduleTime) { $jobSettings.scheduledTime = $ScheduleTime.Ticks } $result = Start-FlyExchangeMigrationJob -ProjectId $targetProject.Id -MigrationJobSettingsModel $jobSettings if ($result) { Write-Host 'The job has started.' -ForegroundColor Green } } Catch { Write-Host 'Failed to start the job.' -ForegroundColor Red ErrorDetail -Error $_ throw } } } |