Investigating Backup and Disaster Recovery in Lync 2010

June 26, 2012

Understanding how to properly backup and maintain your Lync environment is absolutely key to success in the event of a DR scenario.  Often times not enough time is spent verifying and testing your DR plan.  So this document is an attempt to document the backup procedure and recovery needed for the purposes of DR.  There are a few good documents out there in terms of backup.  First is the TechNet article on backing up Lync and second is a great and very complete script for backup written by Traci Herr.  I’ll be offering the script I use below as well.

Lync Backup Instructions – Traci Herr

What to Backup

In order to complete your DR testing and real-life event, it’s important that you have some critical items.

  • Backup of CS Configuration (export-csconfiguration)
  • Backup of LIS Configuration (export-cslisconfiguration)
  • Backup of user contacts (dbimpexp.exe)
  • Backup of meeting content

Other items that are handy to have are:

  • Backup of Response Group setup/information.
  • Exchange UM/AA/SA Object setup

One note here – the backup of LIS Configuration is critical!  The other items above can be gotten from other servers or you could live without contacts, but without a backup of the LIS Database, there is NO WAY to move your CMS database.  Without being able to move it, you are literally going back to the drawing board.

So what might a script look like:

# Export Script for Backup
# Created By Richard Brynteson
# Avtex 2012
# Import Lync Module
Import-Module “C:Program FilesCommon FilesMicrosoft Lync Server 2010ModulesLyncLync.psd1”
###Variables To Set
$folderPath = “D:LyncBackupBackups”
#Delete Older Than 30 Days – Production Side
get-childitem “D:LyncBackupBackups” -recurse | where {$_.lastwritetime -lt (get-date).adddays(-30) -and -not $_.psiscontainer} |% {remove-item $_.fullname -force }
#Delete Empty Folders – Production Side
$a = Get-ChildItem “D:LyncBackupBackups” -recurse | Where-Object {$_.PSIsContainer -eq $True}
$a | Where-Object {$_.GetFiles().Count -eq 0} | Remove-Item
#Delete Older Than 30 Days – DR Side
get-childitem “\drserverProdbackup$” -recurse | where {$_.lastwritetime -lt (get-date).adddays(-30) -and -not $_.psiscontainer} |% {remove-item $_.fullname -force }
#Delete Empty Folders – DR Side
$a = Get-ChildItem “\drserverProdbackup$” -recurse | Where-Object {$_.PSIsContainer -eq $True}
$a | Where-Object {$_.GetFiles().Count -eq 0} | Remove-Item
#Message Out
Write-Host -ForegroundColor Green “Backup to server in progress”
#Get Date and Create Folder
$currDate = get-date -uformat “%a-%m-%d-%Y-%H-%M”
New-Item $folderPath$currDate -Type Directory
#Export CMS/XDS and LIS
Export-CsConfiguration -FileName $folderPath$
Export-CsLisConfiguration -FileName $folderPath$
#Export RGS Config
Import-Module D:LyncBackupRgsImportExport.ps1
Export-CsRgsConfiguration -FileName $folderPath$ -Source
#Export User Information
D:LyncToolsLyncBackupdbimpexp.exe /hrxmlfile:”$folderPath$currDateUserData.xml” /
#Export Exchange Contact Information
Get-CsExUmContact | Select “AutoAttendant”,”IsSubscriberAccess”,”Description”,”DisplayNumber”,”LineURI”, “DisplayName”,”ProxyAddresses”,”HomeServer”,”EnabledForFederation”,”EnabledForInternetAccess”, “PublicNetworkEnabled”,”EnterpriseVoiceEnabled”,”EnabledForRichPresence”,”SipAddress”,”Enabled”,
“RegistrarPool”,”DialPlan”,”LocationPolicy”,”ClientPolicy”,”ClientVersionPolicy”,”ArchivingPolicy”,”PinPolicy”, “ExternalAccessPolicy”,”HostedVoicemailPolicy”,”HostingProvider”,”Name”,”DistinguishedName” | Export-Csv -Path $folderPath$currDateExUMContacts.csv
Write-Host -ForegroundColor Green “XDS, LIS, User and Exchange UM Contacts backup to server is completed.  Files are located at $folderPath$currDate”
Write-Host -ForegroundColor Green “Please make sure to export Voice Configuration”
#Copy Files to DR Server
robocopy “d:lyncbackupBackups” “\drserverProdbackup$” /COPYALL /S

So for this script to work, in your folder along with this script you would need a copy of dbimpexp.exe (found on the server in the common files directory) and a copy of the RgsImportExport (which can be found here).  I have tried to comment along the way in what it does, but at a high level, it creates a director for each backup, only holds onto the last thirty days, exports the needed information and copies it to the DR server.

I don’t claim to be a PowerShell expert so feel free to modify/update as you see fit.

The DR Experience

So now that we have a backup of everything, we need to actually test and validate the process.  This part is important, test your DR Plan.  I mean, really test it.  Turn off your servers in the primary site, force move your CMS database and force move some users.  If you don’t do this, you will never learn the process, you will never know what items are going to come up when you really need it.  And trust me, if you are a large organization that says Lync is a Tier III application with something crazy like 3 week recovery, don’t believe them.

So how do we recover.  First, I’m assuming we have another pool (Enterprise or Standard) sitting in a DR location for this exercise.  It can be in the same central site.  You should also configure your pool for automatic failover.

So to complete your testing you should make sure your script has run and you have a backup of everything on your DR server.  Go to your production servers and turn them off.  Be nice about it, no need to pull the power or anything crazy like that.

              1. Go to your DR Standard Edition server and login as a member of RTCUniversalServerAdmins group (or domain admin).
              2. Install a clean copy of the CMS Databases (xds and lis) to your DR SQL Server.
                Install-CSDatabase -CentralManagementDatabase -SqlServerFqdn 
        –CleanYou need to have sysadmin rights to the SQL Server as it will drop any existing xds and lis databases.  Also make sure that you are picking the right server here.
              3. Move your CMS Database.  This task can take a little bit depending on your network size.
                Move-CsManagementServer -ConfigurationFileName “” -LisConfigurationFileName “” –Force -Verbose
              4. Verify that replication occurred successfully.  This can be done with two commands.  The first will show you who is the active Master FQDN.  The second shows the replication status.
                Get-CsManagementStoreReplicationStatus –CentralManagementStoreStatus
                Get-CsManagementStoreReplicationStatus | ft ReplicaFqdn, UpToDate
              5. Force move your conference directories.  This is important.  If you are doing testing, don’t do this step.  You are going to have to trust it works.  The command would be this:
                Get-CsConferenceDirectory | where {$_.ServiceID -match “UserServer:
      ” }| Move-CsConferenceDirectory -TargetPool -ForceYou will also need to restore your conference directory information as well
              6. Next, we need to force move all of the users from the pool to the DR pool.  Again, if you are testing, I would suggest just picking 10 users for the purpose of the test.
                Get-CsUser | where {$_.registrarpool –match “
      ”} | Move-CsUser –target “” –Force
              7. Next, you should move all of your external DNS records.  These would include items like your meet and dialin simple URLs.
              8. Now we are going to import in contact/conferencing inforomation for users.  Again, in a real DR scenario you would want to run the first command but given we are testing, you should choose the import on an individual basis.Import All – dbimpexp.exe /import /hrxmlfile:”c:BackupUser.xml” / /restype:all
                Import Individual Records –
                dbimpexp.exe /import /hrxmlfile: “c:BackupUser.xml” /user:<sip URL> / /restype:user

At this point in time, users should now have their contacts back and would be running on the DR Server.  As you go through this process, you should make sure you have someone taking notes with you.  Additionally, all of this information should be typed up and I would recommend storing a copy of the document on both the production servers and DR servers.  Don’t store these directions in e-mail or some other electronic form if that far side is down.


Written by Richard Richard is an Office Apps &amp; Services MVP (Teams / Skype) who lives in Minneapolis, MN. Microsoft Certified Solutions Master (MCSM) and MCSM Instructor - when those were a thing long ago. When not writing code, breaking teams - debate coach and avid golfer.
Follow on Twitter

Built using Gatsby and Material-UI

Copyright © TheArgyleMVP 2022.