Public/Copy-Object.ps1
function Copy-Object { <# .SYNOPSIS Copy object(s) .DESCRIPTION Copy list of objects matching specifications (wrapper for Copy-Item with checks) .PARAMETER Path The path parameter corresponds to the location of the objects to copy. .PARAMETER Destination The destination parameter corresponds to the target copy location. /!\ This path must be a directory. .PARAMETER Filter The filter parameter corresponds to the filter to apply to the name of objects to copy. .PARAMETER Exclude The exclude parameter corresponds to the filter to apply to the name of objects *not* to copy. .PARAMETER Force The force parameter enable the overwrite of the target object. .NOTES File name: Copy-Object.ps1 Author: Florian Carrier Creation date: 2021-07-06 Last modified: 2022-08-02 #> [CmdletBinding ( SupportsShouldProcess = $true )] Param ( [Parameter ( Position = 1, Mandatory = $true, HelpMessage = "Path to the items" )] [ValidateNotNullOrEmpty ()] [System.String] $Path, [Parameter ( Position = 2, Mandatory = $true, HelpMessage = "Target location" )] [ValidateNotNullOrEmpty ()] [Alias ("Target")] [System.String] $Destination, [Parameter ( Position = 3, Mandatory = $false, HelpMessage = "Filter to apply" )] [ValidateNotNullOrEmpty ()] [System.String] $Filter = "*", [Parameter ( Position = 4, Mandatory = $false, HelpMessage = "Pattern to exclude" )] [ValidateNotNullOrEmpty ()] [System.String[]] $Exclude = $null, [Parameter ( HelpMessage = "Switch to force copy" )] [Switch] $Force ) Begin { # Get global preference vrariables Get-CallerPreference -Cmdlet $PSCmdlet -SessionState $ExecutionContext.SessionState # Check path if (Select-String -InputObject $Path -Pattern ".+\\\*") { Write-Log -Type "DEBUG" -Message $Path Write-Log -Type "ERROR" -Message "Please provide a path to a single directory or file" -ErrorCode 1 } } Process { if ($PSCmdlet.ShouldProcess($Path, "Copy")) { # Check target type $Target = Get-Object -Path $Path if ($Target -is [System.IO.DirectoryInfo]) { # If target is a directory $Destination = Join-Path -Path $Destination -ChildPath (Split-Path -Path $Path -Leaf) if (Test-Object -Path $Destination -NotFound) { # Ensure destination exists to prevent error "Copy-Item : Container cannot be copied onto existing leaf item." Write-Log -Type "DEBUG" -Message "Create destination directory ""$Destination""" New-Item -Path $Destination -ItemType "Directory" | Out-Null } else { if ($Force -eq $false) { Write-Log -Type "ERROR" -Message "Destination path already exists ""$Destination""" Write-Log -Type "WARN" -Message "Use the -Force switch to overwrite" Stop-Script -ExitCode 1 } } # Copy directory content Write-Log -Type "DEBUG" -Message "Copy directory and content ""$Path"" to ""$Destination""" Copy-Item -Path "$Path\*" -Destination $Destination -Filter $Filter -Exclude $Exclude -Recurse -Force:$Force } elseif ($Target -is [System.IO.FileInfo]) { # If target is a single file Write-Log -Type "DEBUG" -Message "Copy file ""$Path"" to ""$Destination""" # Check target destination type if (Test-Object -Path $Destination -NotFound) { # Ensure destination exists to prevent contents to be added to a dummy file Write-Log -Type "DEBUG" -Message "Create destination directory ""$Destination""" New-Item -Path $Destination -ItemType "Directory" | Out-Null } Copy-Item -Path $Path -Destination $Destination -Container -Force:$Force } } } } |