Schlagwort-Archive: outlook

PowerShell Outlook Scripting

This small PowerShell example opens my Outlook and searches for a inbox folder called „Planungen“.
It’s going through all mail and processes them if they have special keywords in them like Planung and KAR. If there are keywords like NB or Nachberechnung it’s not processed. Then it saves the attachment to a temporary Directory and uses pscp to copy it over to a linux machine. It uses my Windows kerberos key to authenticate via GSSAPI so I don’t need a RSA Key or password. It’s executed each day as a scheduled job. Neat, isn’t it?


$pscp_path="C:\Users\someuser\Downloads\pscp.exe"
$linux_path="somehost.de:/tmp"
$linux_user="someuser"
$filepath = "C:\temp\"
$date = get-date -format d
$time = get-date -format h-mm
$log = "C:\Temp\Logs\parameterpflege_" + $date + "_" + $time + ".log"

$olFolderInbox = 6 
$outlook = new-object -com outlook.application; 
$ns = $outlook.GetNameSpace("MAPI");
$inbox = $ns.GetDefaultFolder($olFolderInbox)
$planungsordner=$inbox.Folders | where-object { $_.name -eq "Planungen" }
$messages = $planungsordner.items 

foreach($message in $messages){
  If ($message.subject -match ".*Planung.*" -And $message.subject -match ".*KAR.*" -And $message.UnRead -eq "$true" -And (!($message.subject -match ".*NB.*" -Or $message.subject -match ".*Nachberechnung.*"))) {
    Start-Transcript -Force -Path $log
    $subject=$message.subject
    write-host "bearbeite Mail ""$subject"""
    # save attachment
    $message.attachments|foreach {
      $attachmentname = $_.filename
      If ($attachmentname.Contains("doc")) {
        Write-Host "save $attachmentname to $filepath"
        $_.saveasfile((Join-Path $filepath $attachmentname)) 
      } 
    }
    # mark as read so it's not gonna processed again
    $message.UnRead = $false
    $docfile = "$filepath" + $attachmentname
    Write-Host "kopiere $docfile nach $linux_user@$linux_path"
    &$pscp_path $docfile $linux_user@$linux_path
    Stop-Transcript
  }
}

geöffnete Outlook PST Dateien sichern | how to backup open PST files

Es ist nicht ganz trivial PST Dateien zu sichern, die gerade bei Outlook geöffnet sind. Windows lässt das natürlich nicht zu, was auch Sinn macht in Bezug auf Datenkonsistenz und so weiter.
Nur was ist wenn auf Laptops immer Outlook geöffnet ist und allerhöchstens am Abend in den Standy Modus versetzt wird um dann am morgen weiter betrieben zu werden und niemals Outlook geschlossen wird? Also fallen Hilfswerkzeuge wie pfbackup weg. Dieses ermöglicht es bei schließen von Outlook die Sicherung der Dateien. Auch muss bei dem Tool die PST Dateien ausgewählt werden die gesichert werden sollen.

Das vorgestellte Skript sucht auf dem ganzen Laufwerk(en) nach PST Dateien und speichert diese in einen vorgegebenen Backup Ordner auf der eigenen Festplatte. In unserer Umgebung ist dies ein Truecrypt Container der immer als S: gemountet wird.
Um ein Backup von einer geöffneten Datei anzulegen ist es nötig eine Shadow Copy von der Festplatte anzulegen. Dies führt dazu, dass der aktuelle Stand gespeichert wird und ein kopieren möglich wird da die Datei dann nicht mehr mit einem lock versehen ist.
Als Hilfswerkzeug kommt vscsc und dosdev (in einem Microsoft Toolset enthalten) zum Einsatz.

In meinem Fall sind alle Dateien in C:\vscsc.
Diese wären:

  • dosdev.exe
  • vscsc.exe
  • findPST.vbs
  • script_c.bat
  • script_s.bat

dosdev.exe erlaubt einen so seltsame Windows Laufwerksnamen wie \\?\GLOBALROOT\Device\HarddiskVolumeShadowCopy15 auf ein Laufwerksbuchstaben zu mounten. Damit kann man dann auch in Skripten auf das Laufwerk zugreifen.

vscsc.exe erstellt die temporäre Shadow Copy vom Laufwerk. Ist das Skript durch verfällt die Shadow Copy.

findPST.vbs sucht alle PST Dateien auf dem Laufwerk das gerade als Shadow Copy existiert (Laufwerk B:) und kopiert diese ans Backupziel.

script_c.bat nimmt als Argument den Laufwerksnamen der Shadow Copy an und mountet es als Laufwerk B. Es ruft dann die findPST.vbs auf mit dem Laufwerksbuchstaben der Festplatte, die gerade also Shadow Copy vorliegt.
Man kann dem Skript leider keine Argumente übergeben, deswegen ein Skript für jedes Laufwerk.

Hier die Inhalte der Dateien. Denke diese sind selbsterklärend.

script_c.bat:

@echo off
DOSDEV B: %1
rem At this point B: is an immutable snapshot of C:, and you can copy from it.
rem You just need to write some stuff that actually copies data from B:
rem My favourite is rdiff-backup, but only robocopy can operate in backup mode
rem as a member of the Backup Operators group (/B switch), therefore bypassing
rem file permissions and security. This might be required sometimes.
rem .ost files are forbidden to appear in a snapshot
rem see HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\BackupRestore\FilesNotToSnapshot
wscript findPST.vbs C:
DOSDEV /D B:

script_s.bat:

@echo off
DOSDEV B: %1
wscript findPST.vbs S:
DOSDEV /D B:

findPST.vbs:


<pre>
laufwerksbuchstaben = WScript.Arguments.Item(0)
backupFolder = "S:\Secure Daten\Backup Outlook\"
backupFolderPart = "S:\Secure Daten"
strComputer = "."
Const OverwriteExisting = True
Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objWMIService = GetObject("winmgmts:\\" & strComputer & "\root\cimv2")
QueryString = "Select * from CIM_DataFile Where Extension = 'pst' AND Drive = '" & laufwerksbuchstaben & "'"
'Wscript.Echo QueryString
Set re = New RegExp
Set re2 = New RegExp
With re
  .Pattern = ".*recycle.bin.*"
  .Global = True
  .IgnoreCase = True
End With 
With re2
  .Pattern = ".*S:\Secure Daten\Backup Outlook.*"
  .Global = True
  .IgnoreCase = True
End With 

Set colFiles = objWMIService.ExecQuery (QueryString)
  
' if there are no pst files found just exit the script
If colFiles.Count = 0 Then
    Wscript.Quit
End If
' if our secure drive is not mounted exit the script
If Not (objFSO.DriveExists("S:")) Then
  Wscript.Quit
End If

For Each objFile in colFiles
  filePathAndName = "B:" & objFile.Path & objFile.FileName & "." & objFile.Extension
  'filePathAndName = objFile.Drive & objFile.Path & objFile.FileName & "." & objFile.Extension
  'Wscript.Echo filePathAndName
  If Not re.Test(filePathAndName) And Not re2.Test(filePathAndName) Then ' check if pst is in recycle.bin or in backup folder
    ' create folders if they dont exist
    If Not (objFSO.FolderExists(backupFolderPart)) Then objFSO.CreateFolder(backupFolderPart)
    If Not (objFSO.FolderExists(backupFolder)) Then objFSO.CreateFolder(backupFolder)
    'Wscript.Echo "copy " & filePathAndName & " to " & backupFolder
    objFSO.CopyFile filePathAndName , backupFolder, OverwriteExisting
  End If
'Wscript.Echo objFile.FileSize
Next
</pre>

Um alle PST Dateien auf C: zu sichern wird der folgender Befehl ausgeführt:
vscsc.exe -exec=script_c.bat C:

Für Laufwerk S:
vscsc.exe -exec=script_s.bat S:

Nachtrag:
Ich wollte auch für das Laufwerk S: eine Shadow Copy anlegen. Es handelt sich dabei aber um ein Truecrypt Container und das ist von TrueCrypt nicht unterstützt. Ich zitiere aus der TrueCrypt „Known Issues & Limitations“:

The Windows Volume Shadow Copy Service is currently supported only for partitions within the key scope of active system encryption (e.g. a system partition encrypted by TrueCrypt, or a non-system partition located on a system drive encrypted by TrueCrypt, mounted when the encrypted operating system is running). Note: For other types of volumes, the Volume Shadow Copy Service is not supported because the documentation for the necessary API is not available.