move multiple user folders

lee roberts 186 Reputation points
2021-04-08T14:53:18.117+00:00

Hi,

I have to copy the contents of multiple user folders to new folders on a different drive. The issue is the folder names will be different. E.G Adam.smith will now be SmithA.

I have a CVS file with the old folder names (Adam.Smith) and also the new folder names (SmithA).

Example would be c:\temp\Adam.smith that will need the contents copied to g:\users\SmithA.

Is this possible using powershell?

Windows Server PowerShell
Windows Server PowerShell
Windows Server: A family of Microsoft server operating systems that support enterprise-level management, data storage, applications, and communications.PowerShell: A family of Microsoft task automation and configuration management frameworks consisting of a command-line shell and associated scripting language.
5,355 questions
0 comments No comments
{count} votes

Accepted answer
  1. Ian Xue (Shanghai Wicresoft Co., Ltd.) 29,486 Reputation points Microsoft Vendor
    2021-04-12T12:43:56.893+00:00

    Hi,

    Have you set the $sourcePath and the $targetPath? Please see if this works.

    $sourcepath = 'c:\temp'  
    $targetpath = 'g:\users'  
    $mapFile = 'C:\temp\UserNames.csv'  
    Import-Csv $mapFile -Header 'OriginalName', 'NewName' | ForEach-Object {  
        Copy-Item -Path (Join-Path $sourcePath $_.OriginalName) -Destination (Join-Path $targetPath $_.NewName) -Recurse }  
    

    In your csv file it should be like this

    "Adam.smith","SmithA"  
    

    Best Regards,
    Ian Xue

    ============================================

    If the Answer is helpful, please click "Accept Answer" and upvote it.
    Note: Please follow the steps in our documentation to enable e-mail notifications if you want to receive the related email notification for this thread.


2 additional answers

Sort by: Most helpful
  1. Michael Taylor 47,716 Reputation points
    2021-04-08T15:58:47.483+00:00

    Yes. Read the CSV file, I assume that field 1 is the old name and field 2 is the new name, and then enumerate the lines using Move-Item to move source to destination. Alternatively first test with -WhatIf or Copy-Item.

       Test 1, Test1  
       Test 2, Test2  
       Test 3, Test3  
    

    Note that I'm assuming you're running a new enough version of PS (at least 5.1+) such that Import-Csv is available to easily parse the CSV. If for some reason you cannot do that then use Get-Content to load the file contents and then manually split the line instead.

       # Import the CSV file, assuming no header in the file so create one manually  
       $mappings = Import-Csv $mapFile -Header 'OriginalName', 'NewName'  
         
       # Copy each source folder into the destination folder by combining the names with the source and target paths  
       $mappings | foreach-object { Copy-Item -Path ([System.IO.Path]::Combine($sourcePath, $_.OriginalName)) -Destination ([System.IO.Path]::Combine($targetPath, $_.NewName)) -Recurse }  
    

    Here I'm using the Copy-Item for several reasons.

    1. Move-Item is documented as not working if you are moving across drives. Given your post it sounds like this is true so Move-Item won't work.
    2. Move-Item does not allow rename while moving. You would therefore need to first move the items then use Rename-Item to rename each folder.
    3. For testing/recovery purposes if something goes wrong you can blow away the target structure and run your command again. Only after you've verified everything copied correctly (perhaps by counting files) should you then delete the source. Move-Item would not allow this. If something went wrong you'd have to move all the directories back and try again, potentially.
    0 comments No comments

  2. lee roberts 186 Reputation points
    2021-04-09T07:48:31.887+00:00

    HI Coodadtx,

    Thank you for getting back to me.

    When i run the above script i'm getting the below error

    Import-Csv : Cannot validate argument on parameter 'Delimiter'. The argument is null. Provide a valid value for the argument, and then try running the command again.
    At line:1 char:54

    • $mappings = Import-Csv -Path "C:\temp\UserNames.csv" $mapFile -Header ...
    • ~~~~~~~~
    • CategoryInfo : InvalidData: (:) [Import-Csv], ParameterBindingValidationException
    • FullyQualifiedErrorId : ParameterArgumentValidationError,Microsoft.PowerShell.Commands.ImportCsvCommand

    Copy-Item : An item with the specified name \FILE-03\Home\Lee already exists.
    At line:6 char:30

    • ... ch-object { Copy-Item -Path ([System.IO.Path]::Combine($sourcePath, $ ...
    • ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    • CategoryInfo : ResourceExists: (\FILE-03\Home\Lee:String) [Copy-Item], IOException
    • FullyQualifiedErrorId : DirectoryExist,Microsoft.PowerShell.Commands.CopyItemCommand

    Copy-Item : An item with the specified name \FILE-03\Home\Lee\User.1 already exists.
    At line:6 char:30

    • ... ch-object { Copy-Item -Path ([System.IO.Path]::Combine($sourcePath, $ ...
    • ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    • CategoryInfo : ResourceExists: (\FILE-03\Home\Lee\User.1:String) [Copy-Item], IOException
    • FullyQualifiedErrorId : DirectoryExist,Microsoft.PowerShell.Commands.CopyItemCommand