Copying File Attachments from one SR to another?
Best Answer
-
Aaron_Smith Customer IT Monkey ✭After doing some cleanup on another script that was written. I was able to get this to work for the archive piece:
#
#Author: Patrik Sundqvist, www.litware.se
#Description: Can be used to archive attached files
#
Import-Module smlets$SRclass = Get-SCSMClass -Name System.WorkItem.ServiceRequest$SRObject = Get-SCSMObject -Class $SRclass -Filter "ID -eq SR68848"$Archive = "D:\Archive"
$Id = $SRObject
$ArchiveRootPath = $Archive
$ComputerName = "prd-scsm01.defendersecurity.com"
$WIhasAttachMent = "aa8c26dc-3a12-5f88-d9c7-753e5a8a55b4"
$CIhasAttachMent = "095ebf2a-ee83-b956-7176-ab09eded6784"
#Adjust path
$ArchiveRootPath = $ArchiveRootPath.TrimEnd("\")
#Make sure path exists
if(!(Test-Path $ArchiveRootPath))
{
Write-Error "Provided archive path $ArchiveRootPath doesn't exists" -ErrorAction Stop
}
#Making sure smlets is loaded
if(!(get-module smlets))
{
import-module smlets -Force -ErrorAction Stop
}
#Get Emo
$Emo = Get-SCSMObject -Class $SRclass -filter "ID -eq $Id" -ComputerName $ComputerName
#Check if this is a work item or config item
$WIhasAttachMentClass = Get-SCSMRelationshipClass -Id $WIhasAttachMent -ComputerName $ComputerName
$WIClass = Get-SCSMClass -Name System.WorkItem -ComputerName $ComputerName
#Figure out if this is a work item or a config item to make sure we use the correct relationship
if($Emo.IsInstanceOf($WIClass))
{
$files = Get-SCSMRelatedObject -SMObject $Emo -Relationship $WIhasAttachMentClass -ComputerName $ComputerName
}
else
{
$CIhasAttachMentClass = Get-SCSMRelationshipClass -Id $CIhasAttachMent -ComputerName $ComputerName
$CIClass = Get-SCSMClass System.ConfigItem$ -ComputerName $ComputerName
if($Emo.IsInstanceOf($CIClass))
{
$files = Get-SCSMRelatedObject -SMObject $Emo -Relationship $CIhasAttachMentClass -ComputerName $ComputerName
}
else
{
Write-Error "Instance isn't of supported type" -ErrorAction Stop
}
}
#For each file, archive to entity folder
if($files -ne $Null)
{
#Create archive folder
$nArchivePath = $ArchiveRootPath + "\" + $Emo.Id
New-Item -Path ($nArchivePath) -ItemType "directory" -Force|Out-Null
$files|%{
Try
{
$_.DisplayName
$fs = [IO.File]::OpenWrite(($nArchivePath + "\" + $_.DisplayName))
$memoryStream = New-Object IO.MemoryStream
$buffer = New-Object byte[] 8192
[int]$bytesRead|Out-Null
while (($bytesRead = $_.Content.Read($buffer, 0, $buffer.Length)) -gt 0)
{
$memoryStream.Write($buffer, 0, $bytesRead)
}
$memoryStream.WriteTo($fs)
}
Finally
{
$fs.Close()
$memoryStream.Close()
}
}
}6
Answers
I've managed it indirectly in PowerShell. Copying file attachments out to a folder somewhere and then reimporting them into a new work item. I found the solution in two half's searching online. It wasn't super simple but see how you get on.
Geoff
Import-Module ‘D:\Program Files\Microsoft System Center 2012 R2\Service Manager\Powershell\System.Center.Service.Manager.psd1’
$SMServer = ”<servername>”
$SR = Get-SCClassInstance -ComputerName $SMServer | where {$_.Id -eq "SR68848"}
$targetclass = Get-SCSMRelationship -ComputerName $SMServer -DisplayName “Has File Attachment” | where {$_.Source -eq (get-scsmclass -ComputerName $SMServer -Name System.WorkItem.ServiceRequest$)}
$files = $SR.GetRelatedObjectsWhereSource($targetclass)
$ArchiveRootPath = ”D:\Attachments”
#For each file, archive to entity folder
$filelist = @()
if($files -ne $Null)
{
#Create archive folder
$nArchivePath = $ArchiveRootPath + “” + $SR.Id
New-Item -Path ($nArchivePath) -ItemType “directory” -Force|Out-Null
$files|%{
Try
{
$filelist += ”$nArchivePath$_”
$fileId = $_.EnterpriseManagementObject.Id
$fileobject = get-scsmclassinstance -ComputerName $SMServer -Id $fileId
$fs = [IO.File]::OpenWrite(($nArchivePath + “” + $_.EnterpriseManagementObject.DisplayName))
$memoryStream = New-Object IO.MemoryStream
$buffer = New-Object byte[] 8192
[int]$bytesRead|Out-Null
while (($bytesRead = $fileobject.Content.Read($buffer, 0, $buffer.Length)) -gt 0)
{
$memoryStream.Write($buffer, 0, $bytesRead)
}
$memoryStream.WriteTo($fs)
}
Finally
{
$fs.Close()
$memoryStream.Close()
}
}
}
$file1=$filelist[0]
#$file2=$filelist[1]
#$file3=$filelist[2]
#
#Author: Patrik Sundqvist, www.litware.se
#Description: Can be used to archive attached files
#
Import-Module smlets
$Id = $SRObject
$ArchiveRootPath = $Archive
$ComputerName = "prd-scsm01.defendersecurity.com"
$WIhasAttachMent = "aa8c26dc-3a12-5f88-d9c7-753e5a8a55b4"
$CIhasAttachMent = "095ebf2a-ee83-b956-7176-ab09eded6784"
#Adjust path
$ArchiveRootPath = $ArchiveRootPath.TrimEnd("\")
#Make sure path exists
if(!(Test-Path $ArchiveRootPath))
{
Write-Error "Provided archive path $ArchiveRootPath doesn't exists" -ErrorAction Stop
}
#Making sure smlets is loaded
if(!(get-module smlets))
{
import-module smlets -Force -ErrorAction Stop
}
#Get Emo
$Emo = Get-SCSMObject -Class $SRclass -filter "ID -eq $Id" -ComputerName $ComputerName
#Check if this is a work item or config item
$WIhasAttachMentClass = Get-SCSMRelationshipClass -Id $WIhasAttachMent -ComputerName $ComputerName
$WIClass = Get-SCSMClass -Name System.WorkItem -ComputerName $ComputerName
#Figure out if this is a work item or a config item to make sure we use the correct relationship
if($Emo.IsInstanceOf($WIClass))
{
$files = Get-SCSMRelatedObject -SMObject $Emo -Relationship $WIhasAttachMentClass -ComputerName $ComputerName
}
else
{
$CIhasAttachMentClass = Get-SCSMRelationshipClass -Id $CIhasAttachMent -ComputerName $ComputerName
$CIClass = Get-SCSMClass System.ConfigItem$ -ComputerName $ComputerName
if($Emo.IsInstanceOf($CIClass))
{
$files = Get-SCSMRelatedObject -SMObject $Emo -Relationship $CIhasAttachMentClass -ComputerName $ComputerName
}
else
{
Write-Error "Instance isn't of supported type" -ErrorAction Stop
}
}
#For each file, archive to entity folder
if($files -ne $Null)
{
#Create archive folder
$nArchivePath = $ArchiveRootPath + "\" + $Emo.Id
New-Item -Path ($nArchivePath) -ItemType "directory" -Force|Out-Null
$files|%{
Try
{
$_.DisplayName
$fs = [IO.File]::OpenWrite(($nArchivePath + "\" + $_.DisplayName))
$memoryStream = New-Object IO.MemoryStream
$buffer = New-Object byte[] 8192
[int]$bytesRead|Out-Null
while (($bytesRead = $_.Content.Read($buffer, 0, $buffer.Length)) -gt 0)
{
$memoryStream.Write($buffer, 0, $bytesRead)
}
$memoryStream.WriteTo($fs)
}
Finally
{
$fs.Close()
$memoryStream.Close()
}
}
}