Tuesday, September 8, 2015

Move Sharepoint folders and files in list/Libraries through powershell



I had this folder movement structure of
1)Adjacency
    2)Group
          3)Subgroup

Below is the Powershell code through which I achieved it.It can be used to move files and folders in the same library or to different library.You could also pick only the subfolders to be moved or the whole main folder to be moved



$snapin = Get-PSSnapin | Where-Object {$_.Name -eq 'Microsoft.SharePoint.Powershell'}
if ($snapin -eq $null) {
Write-Host "Loading SharePoint Powershell Snapin"
Add-PSSnapin "Microsoft.SharePoint.Powershell"
}


$logFile = "LogFile_MoveFiles.txt"

function create-fileitems()
    {
     [CmdletBinding()]
     param(
[Parameter(position=1, mandatory=$true, parametersetname="Default")] [Microsoft.SharePoint.SPDocumentLibrary]$SourceList,
[Parameter(position=2, mandatory=$true, parametersetname="Default")] [Microsoft.SharePoint.SPDocumentLibrary]$DestinationList,
     [Parameter(position=3, mandatory=$true, parametersetname="Default")] [string] $SourceAdjacencyToMove,
     [Parameter(position=4, mandatory=$true, parametersetname="Default")] [string] $ConfirmAdjToMove,
     [Parameter(position=5, mandatory=$true, parametersetname="Default")] [string] $SourceGroupToMove,
     [Parameter(position=6, mandatory=$true, parametersetname="Default")] [string] $DestinationAdjToMove,
     [Parameter(position=7, mandatory=$true, parametersetname="Default")] [Microsoft.SharePoint.SPWeb]$sourceweb
     )
        $src = $SourceList
        $tgt = $DestinationList
        $SourceAdjacency = $SourceAdjacency
        $AllFolders = $src.Folders
        $srcRootFolder = $src.RootFolder
        $allfiles = $src.items
        $RootItems = $srcRootFolder.files
        $destRootFolder = $tgt.RootFolder
        $arrListFolderURLToDelete = New-Object System.Collections.ArrayList
        Try
         {
          foreach($Folder in $src.RootFolder.SubFolders)
           {
         if($Folder.Name -eq $SourceAdjacencyToMove)
           {
            $srcFolderURL = $folder.url
            $destFolderURL = $srcFolderURL          
            $destFolderURL = $destFolderURL -replace $SourceAdjacencyToMove, $DestinationAdjToMove
            $srcItems = $Folder.folder.files
            if(!($tgt.Folders | ? {$_.URL -eq $destFolderURL}))
            {
             
                $parentFolderURL = $Folder.ParentFolder.ServerRelativeUrl
                $newFolder = $src.Additem($parentFolderURL,[Microsoft.SharePoint.SPFileSystemObjectType]::Folder,$DestinationAdjToMove)
                $newFolder.Update()
                write-host -ForegroundColor Green "Folder Creation:"$destFolderURL" - Complete"
                Add-Content $logFile "Folder Creation: $destFolderURL - Complete"
            }          
               foreach($subFolder in $Folder.SubFolders)
               {
                   if($ConfirmAdjToMove -eq "N" -or $ConfirmAdjToMove -eq "n")
                     {
                        if($subFolder.Name -eq $SourceGroupToMove)
                        {
                            MoveGroup $Folder $subFolder $srcRootFolder $destRootFolder $tgt $AllFiles
                            $arrListFolderURLToDelete.Add($subFolder.URL) | Out-Null
                        }
                     }
                   else
                     {
                       MoveGroup $Folder $subFolder $srcRootFolder $destRootFolder $tgt $AllFiles
                       $arrListFolderURLToDelete.Add($subFolder.URL) | Out-Null
                     }
                   
               }
             if($ConfirmAdjToMove -eq "Y" -or $ConfirmAdjToMove -eq "y")
               {
                 $arrListFolderURLToDelete.Add($Folder.URL) | Out-Null
               }  
                     
           }

        }
          Foreach($folderURLToDelete in $arrListFolderURLToDelete)
           {

                $folderToDelete = $sourceweb.GetFolder($folderURLToDelete)
                $folderToDelete.Delete()

             }
         }
        catch
         {
            Write-Host  $_.Exception.Message
            Add-Content $logFile    "***Error description Starts****`n"
            Add-Content $logFile    $_.Exception.Message      
            Add-Content $logFile    "***Error description ends****`n"
         }

      }

 function MoveGroup($Folder,$subFolder , $srcRootFolder ,$destRootFolder,$tgt,$AllFiles)
    {
        $srcSubFolderURL = $subFolder.url
        $destSubFolderURL = $srcSubFolderURL                  
        $destSubFolderURL = $destSubFolderURL -replace $SourceAdjacencyToMove, $DestinationAdjToMove
        $srcSubItems = $subFolder.folder.files
          if(!($tgt.Folders | ? {$_.URL -eq $destSubFolderURL}))
              {
                        $parentFolderURL = $Folder.serverrelativeurl
                        $parentFolderURL = $parentFolderURL -replace $SourceAdjacencyToMove, $DestinationAdjToMove                                              
                        $newFolder = $src.Additem($parentFolderURL,[Microsoft.SharePoint.SPFileSystemObjectType]::Folder,$subFolder.name)
                        $newFolder.Update()
                        write-host -ForegroundColor Green "Folder Creation:"$destSubFolderURL" - Complete"
                        Add-Content $logFile "Folder Creation: $destSubFolderURL - Complete"
                      }
                   
                foreach($sub2Folder in $subFolder.SubFolders)
                      {
                            $srcSub2FolderURL = $sub2Folder.url
                            $destSub2FolderURL = $srcSub2FolderURL                          
                            $destSub2FolderURL = $destSub2FolderURL -replace $SourceAdjacencyToMove, $DestinationAdjToMove
                            $srcSub2Items = $sub2Folder.folder.files
                            if(!($tgt.Folders | ? {$_.URL -eq $destSub2FolderURL}))
                              {
                                $parentFolderURL = $subFolder.serverrelativeurl              
                                $parentFolderDestination = $destRootFolder                              
                                $parentFolderURL = $parentFolderURL -replace $SourceAdjacencyToMove, $DestinationAdjToMove                                                      
                                $newFolder = $src.Additem($parentFolderURL,[Microsoft.SharePoint.SPFileSystemObjectType]::Folder,$sub2Folder.name)
                                $newFolder.Update()
                                write-host -ForegroundColor Green "Folder Creation:"$destSub2FolderURL" - Complete"
                                Add-Content $logFile "Folder Creation: $destSub2FolderURL - Complete"
                              }
                     
                       $destFolder = $src.Folders | ? {$_.url -eq $destSub2FolderURL}
                             if($sub2Folder.Files.count -gt 0)
                              {
                                $srcItems = $sub2Folder.Files
                                    foreach ($item in $srcItems)
                                    {
                                        $sourceListItem = $item.Item
                                        [Microsoft.Office.RecordsManagement.RecordsRepository.Records]::UndeclareItemAsRecord($sourceListItem)
                                        $Relative = $Item.URL
                                        $TargetItem = $AllFiles | ? {$_.URL -eq $Relative}
                                        $sBytes = $TargetItem.File.OpenBinary()
                                        $dFile = $destFolder.Folder.Files.Add($TargetItem.Name, $sBytes, $true)
                                        $ditem = $dfile.Item
                                        $ditem["Modified"] = $Item.TimeLastModified.ToLocalTime()
                                        $ditem["Created"] = $Item.TimeCreated.ToLocalTime()
                                        $ditem["Author"] = $Item.Author
                                        $ditem["Editor"] = $Item.ModifiedBy                                                                              
                                        $ditem.SystemUpdate($true)
                                        $dFile.CheckIn("Check in by Administrator")
                                        $dFile.Update()
                                        write-host -ForegroundColor Green "File Creation:" $dfile.name" - Complete"
                                        Add-Content $logFile "File Creation: $dfile.name - Complete"
                                    }
                               }
                       }
   }
 


$siteURL = Read-Host "Enter the Site collection URL - Eg:http://Yourwebapplication:1234/ "
$site = Get-SPSite -Identity  $siteURL
$sourceweb = $site.Openweb()
$sourcelist = $sourceweb.lists["LibraryA"]
$destinationlist = $sourceweb.lists["LibraryB"]

$SourceAdjacencyToMove = Read-Host "Enter the name of source Adjacency to be moved"
$DestinationAdjToMove = Read-Host "Enter the name of Destination Adjacency where the files has to be moved to :"
$ConfirmAdjToMove = Read-Host "Press (Y) to move all files ,Press (N) to select Group"


if($ConfirmAdjToMove -eq "N" -or $ConfirmAdjToMove -eq "n")
    {
        $SourceGroupToMove =Read-Host "Enter the Name of Group to be moved"
        create-fileitems -sourcelist $sourcelist -destinationlist $destinationlist -SourceAdjacencyToMove $SourceAdjacencyToMove  -ConfirmAdjToMove  $ConfirmAdjToMove -SourceGroupToMove $SourceGroupToMove -DestinationAdjToMove $DestinationAdjToMove -sourceweb $sourceweb
    }
elseif($ConfirmAdjToMove -eq "Y" -or $ConfirmAdjToMove -eq "y")
    {
        $SourceGroupToMove = " "
        create-fileitems -sourcelist $sourcelist -destinationlist $destinationlist -SourceAdjacencyToMove $SourceAdjacencyToMove  -ConfirmAdjToMove  $ConfirmAdjToMove -SourceGroupToMove $SourceGroupToMove -DestinationAdjToMove $DestinationAdjToMove  -sourceweb $sourceweb
    }




Note: I am using the "[Microsoft.Office.RecordsManagement.RecordsRepository.Records]" because I am working on the Record center and my files are marked as records .Without un-declaring as record ,you cannot perform any action on the document even through powershell or through C# codes.