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.