Powershell 2 copy-item, which creates a folder if it does not exist

$from = "\\something\1 XLS\2010_04_22\*" $to = "c:\out\1 XLS\2010_04_22\" copy-item $from $to -Recurse 

This works if c:\out\1 XLS\2010_04_22\ exists. Is it possible to create c:\out\1 XLS\2010_04_22\ with one command if it does not exist?

+56
powershell copy
Apr 23 '10 at 0:50
source share
8 answers

Yes, add the -Force .

 copy-item $from $to -Recurse -Force 
+72
Apr 23 '10 at 7:36
source share

In PowerShell 2.0, it’s still not possible to get the Copy-Item cmdlet to create a destination folder, you will need the following code:

 $destinationFolder = "C:\My Stuff\Subdir" if (!(Test-Path -path $destinationFolder)) {New-Item $destinationFolder -Type Directory} Copy-Item "\\server1\Upgrade.exe" -Destination $destinationFolder 

If you use -Recurse in the Copy-Item, it will create all the subfolders of the source structure in the recipient, but it will not create the actual destination folder even with the -Force option.

+95
Jan 13 '12 at 12:45
source share

In PowerShell 3 and above, I use Copy-Item with New-Item.

 copy-item -Path $file -Destination (new-item -type directory -force ("C:\Folder\sub\sub\" + $newSub)) -force -ea 0 

I have not tried this in version 2.

+10
Feb 17 '16 at 16:09
source share
  $filelist | % { $file = $_ mkdir -force (Split-Path $dest) | Out-Null cp $file $dest } 
+3
Jul 01 '16 at 11:48
source share
 function Copy-File ([System.String] $sourceFile, [System.String] $destinationFile, [Switch] $overWrite) { if ($sourceFile -notlike "filesystem::*") { $sourceFile = "filesystem::$sourceFile" } if ($destinationFile -notlike "filesystem::*") { $destinationFile = "filesystem::$destinationFile" } $destinationFolder = $destinationFile.Replace($destinationFile.Split("\")[-1],"") if (!(Test-Path -path $destinationFolder)) { New-Item $destinationFolder -Type Directory } try { Copy-Item -Path $sourceFile -Destination $destinationFile -Recurse -Force Return $true } catch [System.IO.IOException] { # If overwrite enabled, then delete the item from the destination, and try again: if ($overWrite) { try { Remove-Item -Path $destinationFile -Recurse -Force Copy-Item -Path $sourceFile -Destination $destinationFile -Recurse -Force Return $true } catch { Write-Error -Message "[Copy-File] Overwrite error occurred!`n$_" -ErrorAction SilentlyContinue #$PSCmdlet.WriteError($Global:Error[0]) Return $false } } else { Write-Error -Message "[Copy-File] File already exists!" -ErrorAction SilentlyContinue #$PSCmdlet.WriteError($Global:Error[0]) Return $false } } catch { Write-Error -Message "[Copy-File] File move failed!`n$_" -ErrorAction SilentlyContinue #$PSCmdlet.WriteError($Global:Error[0]) Return $false } } 
+3
Jun 01 '17 at 18:17
source share

My favorite is to use the .Net class [IO.DirectoryInfo], which takes care of some logic. I really use this for many similar scripting tasks. It has a .Create () method, which creates directories that do not exist, without errors, if they do.

Since this is still a two-step problem, I use the foreach alias to make it simple. For individual files:

 [IO.DirectoryInfo]$to |% {$_.create(); cp $from $_} 

As for your file with multiple files / directories, I would use RoboCopy over xcopy. Remove the "*" from yours and just use:

 RoboCopy.exe $from $to * 

You can still add / r (Recurse), / e (Recurse, including Empty), as well as 50 other useful switches.

Edit: Looking back at this, it's concise, but not very readable unless you often use code. I usually broke it into two parts, for example:

 ([IO.DirectoryInfo]$to).Create() cp $from $to 

In addition, DirectoryInfo is a type of the parent property of FileInfo, so if your $ to is a file, you can use them together:

 ([IO.FileInfo]$to).Parent.Create() cp $from $to 
+2
Sep 09 '16 at 14:27
source share

Here is an example that worked for me. I had a list of 500 specific files in a text file containing about 100 different folders, which I had to copy to a backup in case these files were needed later. The text file contained the full path and file name, one per line. In my case, I wanted to remove the drive letter and the name of the first subfolder from each file name. I wanted to copy all of these files to a similar folder structure in another destination root folder that I specified. I hope other users find this helpful.

 # Copy list of files (full path + file name) in a txt file to a new destination, creating folder structure for each file before copy $rootDestFolder = "F:\DestinationFolderName" $sourceFiles = Get-Content C:\temp\filelist.txt foreach($sourceFile in $sourceFiles){ $filesplit = $sourceFile.split("\") $splitcount = $filesplit.count # This example strips the drive letter & first folder ( ex: E:\Subfolder\ ) but appends the rest of the path to the rootDestFolder $destFile = $rootDestFolder + "\" + $($($sourceFile.split("\")[2..$splitcount]) -join "\") # Output List of source and dest Write-Host "" Write-Host "===$sourceFile===" -ForegroundColor Green Write-Host "+++$destFile+++" # Create path and file, if they do not already exist $destPath = Split-Path $destFile If(!(Test-Path $destPath)) { New-Item $destPath -Type Directory } If(!(Test-Path $destFile)) { Copy-Item $sourceFile $destFile } } 
+2
Mar 09 '19 at 1:40
source share

I came across this twice, and this last time was a unique situation, and even if I use copy-item , I wanted to post the solution I used.

It has a list of only files with a full path, and in most cases the files do not have extensions. the -Recurse -Force parameter will not work for me, so I dropped the copy-item function and returned to something like below using xcopy, since I still wanted to keep it with one liner. I was originally associated with Robocopy, but it seems to be looking for a file extension, and since many of mine did not have the extension, he considered it a directory.

 $filelist = @("C:\Somepath\test\location\here\file","C:\Somepath\test\location\here2\file2") $filelist | % { echo f | xcopy $_ $($_.Replace("somepath", "somepath_NEW")) } 

Hope this helps someone.

+1
Mar 25 '16 at 10:15
source share



All Articles