I need to copy the files from one folder to many. Here's an example of my directory structure:
\\files\CA1\Files\Files
CA = state code
1 = office in that state
I want to copy all files from a source folder into the last files folder. The last files folder in that directory structure above is the destination. The script just needs to cycle through all of the directories with that state code and copy the new files into \\files\CA*\files\FILES\ folder. For instance, I want to copy all files from c:\documents into all folders that are for CA, regardless of the office number. Here's what I have so far:
$source = 'C:\Documents'
$destination = (Get-ChildItem -Path \\files\CA*\Files\Files -Recurse -Directory)
foreach ($dir in $destination){
Get-ChildItem $dir.Fullname | ForEach-Object {
$_.FullName
#Copy-Item -Path $Source -Destination $_ -Force -Recurse -WhatIf
}}
Related
Here is a section of code from a larger script. The goal is to recurse through a source directory, then copy all the files it finds into a destination directory, sorted into subdirectories by file extension. It works great the first time I run it. If I run it again, instead of overwriting existing files, it fails with this error on each file that already exists in the destination:
Copy-Item : Cannot overwrite the item with itself
I try, whenever possible, to write scripts that are idempotent but I havn't been able to figure this one out. I would prefer not to add a timestamp to the destination file's name; I'd hate to end up with thirty versions of the exact same file. Is there a way to do this without extra logic to check for a file's existance and delete it if it's already there?
## Parameters for source and destination directories.
$Source = "C:\Temp"
$Destination = "C:\Temp\Sorted"
# Build list of files to sort.
$Files = Get-ChildItem -Path $Source -Recurse | Where-Object { !$_.PSIsContainer }
# Copy the files in the list to destination folder, sorted in subfolders by extension.
foreach ($File in $Files) {
$Extension = $File.Extension.Replace(".","")
$ExtDestDir = "$Destination\$Extension"
# Check to see if the folder exists, if not create it
$Exists = Test-Path $ExtDestDir
if (!$Exists) {
# Create the directory because it doesn't exist
New-Item -Path $ExtDestDir -ItemType "Directory" | Out-Null
}
# Copy the file
Write-Host "Copying $File to $ExtDestDir"
Copy-Item -Path $File.FullName -Destination $ExtDestDir -Force
}
$Source = "C:\Temp"
$Destination = "C:\Temp\Sorted"
You are trying to copy files from a source directory to a sub directory of that source directory. The first time it works because that directory is empty. The second time it doesn't because you are enumerating files of that sub directory too and thus attempt to copy files over themselves.
If you really need to copy the files into a sub directory of the source directory, you have to exclude the destination directory from enumeration like this:
$Files = Get-ChildItem -Path $Source -Directory |
Where-Object { $_.FullName -ne $Destination } |
Get-ChildItem -File -Recurse
Using a second Get-ChildItem call at the beginning, which only enumerates first-level directories, is much faster than filtering the output of the Get-ChildItem -Recurse call, which would needlessly process each file of the destination directory.
I have a complex folder structure to move
I have a folder containing 2000 files that must be moved in new file structure, I do some simple task with powershell but not so complex so I'm completely lost... Didn't found any solution on other questions...
all folders containing 23 files (some .dds some .xml and so ones) folder must be moved completely
here is the actual situation:
files\128891\
files\128986\
files\129362\
files...\
that must be moved to:
files\128891\aaa\bbb\ccc\ddd\eee\real\128891\
files\128986\aaa\bbb\ccc\ddd\eee\real\128986\
files\129362\aaa\bbb\ccc\ddd\eee\real\129362\
files...\aaa\bbb\ccc\ddd\eee\real...\
have around 2000 folders in files that must be moved with their files in
Thanks a lot for helping
You can modify my code (not better way but works)
$foldernames=Get-ChildItem -Recurse "D:\testdir" | ?{ $_.PSIsContainer } #get all folder in start folder, for you must be "...files\"
foreach($foldername in $foldernames){
$files=Get-ChildItem -Path $foldername.FullName|Where-Object {! $_.PSIsContainer} #get all files in current folder, no recurse,no subfolders.
$files|Move-Item -Destination (New-Item -ItemType Directory -Path (Join-Path -path $foldername.FullName -ChildPath ("aaa\bbb\ccc\ddd\eee\real\"+$foldername.Name)) -Force)
#move all files and create directories
}
Additional:
If you have in folder , subfolders you must fix code like that
$foldernames=Get-ChildItem "D:\testdir" | ?{ $_.PSIsContainer }
foreach($foldername in $foldernames){
$files=Get-ChildItem -Path $foldername.FullName
$files|Move-Item -Destination (New-Item -ItemType Directory -Path (Join-Path -path $foldername.FullName -ChildPath ("aaa\bbb\ccc\ddd\eee\real\"+$foldername.Name)) -Force)
}
It's move all from folder 128891(an exapmle) including subfolders
If you have in folder subfolders but you want move only files from it you must filetring like this:
$files=Get-ChildItem -Path $foldername.FullName -recurse|Where-Object {! $_.PSIsContainer}
But remember in this case errors may occur due to duplicate file names
I am trying to copy a whole bunch of files using Powershell, from one directory to another on my computer.
I used Get-ChildItem C:\Users\Tom\Google Drive\My Files\*\Assessment 1\* to identify that this was the path that I wanted to copy too, and I know about Copy-Item, but I want to maintain parts of the path name when copied.
Example:
If I copy from C:\Users\Tom\Google Drive\My Files\Cool Stuff\Assessment 1\*
I want the files to go to a folder that is created called C:\Users\Tom\Archive\Cool Stuff\Assessment 1
Whereas if I copy from C:\Users\Tom\Google Drive\My Files\New Stuff\Assessment 1\*
I want the files to go to a folder that is created called C:\Users\Tom\Archive\New Stuff\Assessment 1
You could use the Get-ChildItem cmdlet to recursively find all Assessment 1 folders within your base directory and then remove the base path using -replace to finally copy the items using the Copy-Item cmdlet:
$baseDir = 'C:\Users\Tom\Google Drive\My Files\'
$destination = 'C:\Users\Tom\Archive\'
Get-ChildItem $baseDir -directory -Filter 'Assessment 1' -Recurse | ForEach-Object {
$newPath = Join-Path $destination ($_.FullName -replace [regex]::Escape($baseDir))
Copy-Item $_.FullName $newPath -Force -Recurse
}
I have a folder "C:\program", which has two sub-directories "C:\program\Excel" and "C:\program\scripts" and several other files.
When I run the following, all the files copy successfully apart from the files in the Excel directory, which seem to copy to the root of $Destination instead of a directory being created in $Destination called Excel
$Path = 'C:\program\*'
$Destination = 'C:\program\Previous Version\'
$Files = Get-ChildItem $Path
foreach ($File in $Files){
Copy-Item $File.FullName $Destination -Recurse -Container
}
How do I get Copy-Item to copy the contents of the Excel folder to a new Excel folder in the root of $Destination?
Any help would be much appreciated.
Dear Powershell Gurus,
I have a few thousands of files in a folder called C:\Downloads\Signs.
The files are named with their dimensions such as 13X20 abcdjd.psf, 8X20 jdscnjfc.psf, 14X24 dje.psf etc.
What I want to do is to move these files to destination folders created within the C:\Downloads\Signs and the folder names are the dimensions of the file names. Example the folder names will be 13X20, 8X20, 14X24 etc and it depends upon as many unique file names with their dimensions.
So, instead of moving them manually looking at how many files are there in the C:\Downloads\Signs folder and then moving them individually, how can we do it in Powershell?
Thanks,
Sanders.
This script will pick up all psf from the root of the C:\Downloads\Signs folder and will move the files to the destination folders (folders will create if they do not exist):
Get-ChildItem C:\Downloads\Signs -Filter *.psf | Where-Object {!$_.PSIsContainer} | Foreach-Object{
$dest = Join-Path $_.DirectoryName $_.BaseName.Split()[0]
if(!(Test-Path -Path $dest -PathType Container))
{
$null = md $dest
}
$_ | Move-Item -Destination $dest -Force
}