13 years of blogging and 2 000 000 views

Today, January 26th 2023, I hit a huge milestone. 2 000 000 views since I started blogging in 2009. msunified.net has been the home for me to share technical nuggets about Exchange, OCS, Lync, Skype for Business, Teams and Microsoft 365 for over 13 years. I have even shared productivity tips which has culminated in to my Digital Wellbeing thinking. I want to reflect and share my 10 all time most visited blogposts, my 5 favorited blogposts, some external articles I have written and share what I am working on these days.

If you have found any of my articles useful at some point, give this article or the social media post you found this through a like 👍 :)

10 all time most viewed blogposts

My 5 favorite blogposts which I often use today

External articles I have written for other sites and Tech Community

Office 365 for IT Pros

For four years, between 2018 and 2022, I contributed to the calling and meetings chapter for Office 365 for IT Pros. I strongly believe in that format, because it gets updated monthly😱 Tony Redmond heads up that book and the author team does a fantastic job of keeping you up do date on best practices and technical facts in Office 365. Blogposts are seldom kept up to date and that is why you have seen less blogposts here these years, since they get outdated faster than you can type :) I recommend you go and buy a subscribtion to Office 365 for IT Pros right now👍

msunified.net moving forward and what I am currently working on

Do I think blogposts are still worth it today? yes and no. No for “how to” blogposts because learn.microsoft.com is so much better than Microsoft documentation has ever been. Maybe you would rather suggest a change to the learn article if you find information missing. Yes when you want to share a routine, script, your understanding and design principles. I would say no to opinion pieces on a personal blog, maybe you want to share those on LinkedIn or a third party blogsite

These days I work mainly in two areas

  • Digital Wellbeing and working smart with Microsoft 365 combined with Microsoft Viva
    • I published 8 hours of deep dive training for free on YouTube which are indexed here
    • I recently rebranded as a Digital Wellbeing coach delivering inspiration talks, keynotes, leadership training and organizational training based on my Digital Wellbeing thinking :)
    • I run workshops, proof of concepts and talk at conferences about Microsoft Viva
    • I am part of the #VivaExplorers an enthusiastic gang of over 60 MVPs who bring their own angle in to the broad world of Microsoft Viva thought leadership and understanding.
  • Complex hybrid deployment for Exchange/Skype for Business/Teams
    • I see larger more complex and risk averse companies stretching or migrating to Microsoft 365
    • In those more locked down environments we need to be more precise in knowing what works and how
    • These past years i have spent a lot of time as advisor and hands-on with hybrid Exchange solving problems like free/busy, Autodiscover, oauth, hybrid modern auth, Outlook Mobile and making sure nothing is more open than it should be, some of it resulted in this blogpost and I might blog more about troubleshooting these scenarios
    • Same for hybrid Skype for Business, but that is easier than hybrid Exchange, if you have gone down the route and set up a proper Edge server topology :)
  • Make sure you check out my YouTube channel to get my latest videos and talks I do that other channels shares

Thanks to everyone who visits my blog on a daily basis and I think I struck a nerve when blogging about Set the custom Focusing status in Microsoft Teams from PowerShell using Power Automate which is daily the most visited blogpost on my site :)

No media connectivity with Lync Server 2010 collocated mediation server and external users

At a customer site there was a Lync Server 2010 that had been running for about a year. This solution was now going to be expanded with a collocated mediation server over a dedicated PSTN network card. The mediation server deployed fine and I added routes and tested connection with the SIP trunk provider over telnet, TCP 5060 and it seemed fine. Continue reading

Gartner Magic Quadrant for Unified Communications 2012

Is that time of the year again when Gartner releases their yearly analysis of the Unified Communications vendors and their offerings called Magic Quadrant for Unified Communications. The vendors evaluated must meet certain criteria which is a product portfolio that supports

  • voice and telephony
  • conferencing
  • messaging
  • presence and IM
  • support for different client platforms
  • support communications-enabled Applications

It is a tradition to comment on the Gartner UC MQ’s here at the msunified.net, and I have done so since 2009. See the previous articles here:

Lync Server 2010 Monitoring reports and why you always should deploy them

There is actually a lot of good documentation on Lync Server Monitoring and Monitoring reports. If you got the time you could really drill down in to understanding and getting the most out the reports from the different sources. I want this post to highlight some of the main features with the monitoring reports and give a quick introduction and a overveiw of what to expect. Continue reading

Lync Features and how to configure them moving to TechNet Wiki

The Lync Community has produced a lot of great articles about Lync Server 2010 features and how to configure them. Since the Lync Server went RTM I have noted down good blog posts that explains the Lync technology or tell us how to configure it in this post: https://msunified.net/2010/11/22/lync-server-2010-features-and-how-to-configure-them/ Continue reading

What is CSContactImporter and how can it be used

CSContactImporter was released 12.04.2012 and can be downloaded here: http://www.microsoft.com/download/en/details.aspx?id=29558

At first i thought it was a PowerShell script to add contacts to a users contact list since the name starts with CS. After downloading and installing it I found out it was a program that enables you to do this from a GUI.

What does it do?

  • It lets you import contacts into Lync\OCS from
    • AOL Instant Messenger (blt export, version 2)
    • Windows Live (csv export)
      • Cannot import groups
      • Because some WLM contacts may not have msn domain the contacts may be imported wrong and not working
      • Example: sh@msunified.net needs to be in the format sh(msunified.net)@msn.com in Lync, when its not imported like this it will fail so beware
    • YAHOO Messenger (Yahoo csv export)
      • Cannot import groups
    • Plain Text
      • One line per contact, optionally add comma and group name
      • Example: sh@msunified.net,Sales
      • For distribution groups, enter the group email and then _dg_ as the group name
      • Example: accounting@contoso.com,_dg_
  • The contacts can be imported to a single user or a group of users using the batch option
  • You need to use dbimpexp.exe to export all contacts or indivdual contacts from the Lync SQL contact store
    • The tool is a Lync native tool found under C:\Program Files\Common Files\Microsoft Lync Server 2010\Support
  • After you have exported your users you can use the CSContactImporter to append the contacts to the users list
  • Then you need to use dbimpexp.exe to import the users contacts to the Lync SQL contact store again

What does it look like?

Using it in a scenario

To me the batch import is the most interesting scenario. Being able to prepopulate a Lync users contact list with its closest peers in the office or his og her virtual coworkers. The ability to add a default group to all contact lists with telepresence rooms or IT support seems like a usable scenario. Espcially when its the first time users start using Lync, I bet the new users spends their first time in Lync trying to find their coworkers.

To populate a few users with their closest coworkers in a group

  • You need to export all users contact list from the Lync contact database, even though the contact lists is empty
    • For Standard Edition run the command: dbimpexp.exe /hrxmlfile:”c:\TempCSCI\users.xml”
    • For Enterprise Edition run the command: dbimpexp.exe /hrxmlfile:”c:\TempCSCI\users.xml” /sqldatabase:”sql server hostname”\”instance name”
    • It is not possbile to export groups of users using this tool, only one or all
  • Create the contacts you want imported into the users contact lists in a txt
    • sh@msunified.net,Sales
    • vf@msunified.net,Sales
    • me@msunified.net,Sales
    • Where sales is the group name, if a group exists from before it will update this group if you check “Carry over groups”
  • If you just want to add a distribution group instead use the following syntax
    • sales@msunified.net,_dg_
    • Personally I don’t like using distribution groups because sometimes the group expansion is not always that snappy and not all clients support them
  • You need to create one file per user with the content above and the filename must match the SIP address of the user they will be imported into
    • sh@msunified.net.txt
  • Make sure all the files are stored in the same folder
  • Populate CSContactImporter as shown below and hit Generate
    • The importer will only alter the users specified in the txt files and no other users

  • A log file will be written to the same folder and you can open it to see if any users failed to import
  • Now you need to use dbimpexp.exe to import the new contact lists
    • For Standard Edition run the command: dbimpexp.exe /import /hrxmlfile:”c:\TempCSCI\users_merged.xml” /restype:all
    • For Enterprise Edition run the command: dbimpexp.exe /import /hrxmlfile:”c:\TempCSCI\users_merged.xml” /sqldatabase:”sql server hostname”\”instance name” /restype:all
  • After the import is finished, the users need to log out of Lync and then in again to see the new groups and contacts
    • Remember that all changes users have done to their contact lists between you export and import will be lost, make sure to do this in low traffic periods


The tool works and it is now possible to import contacts form other IM solutions or predefening contacts based on AD groups or office location before users log on using this tool. If you have lots of users a lot of these steps may be automated using PowerShell, like finding the users you want to have in your group, creating the txt files and dbimpexp export\import. The only manual thing here is the tool itself. I am sure a cool script to handle this will be written as the community will get more hands-on.

You may also want to try out LyncAddContacts.vbs – VBS Script to add Groups to multiple contacts created by MVP Jeff Guillet. The main difference between CSImportContact and LyncAddContacts:

  • CSImportContacts can new users and groups based on text files or import from another IM program and is a GUI
  • LyncAddContacts needs to have a defined dummy user with only the groups or users you want to import and is a VBS script

Todays Lesson Learned – Lync and Exchange UM integration when the UM server is in another subdomain

This is a follow-up post in a series called Todays Lesson Learned started by fellow Lync MVP Tommy Clarke with this post: Todays lesson learned–Exchange 2010 upgrade with Active Sync and MobileIron and my follow up post on: Todays Lesson Learned – Lync Server 2010 and ST node for OpsMgr 2007 R2 It is a blog series noting down “learn from my mistakes” and “gotchas that can stop an entire project” type of problems with learning by doing and learning the hard way.

I was doing an Exchange UM integration with Lync. Everything worked fine and I was following fellow MVP blog article by Jeff Schertz: http://blog.schertz.name/2010/11/lync-and-exchange-um-integration/

The Problem

  • When I got to the point where I was going to run the Exchange script exchucutil.ps1 on the Exchange UM server I got the following error

Using Global Catalog: GC://”Different subdomain”

The UM server wasn’t able to read the Communications Server pool objects. Verify that Communications Server is deployed in this Active Directory forest and you’re a member of the RTCUniversalServerReadOnlyGroup group or have sufficient rights to read this Active Directory container object.Additional information:Group RTCUniversalServerAdmins couldn’t be found.

Probable Cause

  • The cause of this was that Exchange Schema extension was done in another subdomain.
  • When the Get-Ucpools.ps1 script triggered it could not find the Lync security groups to access the Lync pool configuration.

The Solution

  • As the blog depicts the solution was to edit the Get-Ucpools.ps1 script that is used by the ExchUcUtil.ps1 script
    • Make a copy of the original script before editing
    • Remember to open NotePad “as administrator”, else you can not save the script
  • Comment out the original global catalog discovery line
    • #$entry.psbase.Path = “GC://” + $globalCatalog
    • $entry.psbase.Path = “GC://MYGCin.Domain.com”
  • Add a local domain controller that is also a global catalog
  • Save the script
  • Rerun ExchUcUtil.ps1

Featured on NextHop blog Series: Interview with a Lync Pro

I had the honour of being interviewed by Justin Morris who writes the blog series Interview with a Lync Pro hosted at the Lync NextHop blog. It is really cool be featured in such a way and recognized as a Lync Pro by the community together with the people I myself turn to for expert knowledge. Head over to NextHop to read the entire interview and also make sure to read the interview of the other Lync Pro’s as well: http://blogs.technet.com/b/nexthop/archive/2012/03/23/interview-with-a-lync-pro-st-229-le-hansen.aspx

NextHop is the Microsoft Lync Server team’s customer response channel—a new medium to rapidly make the information you need available to you, when you need it. NextHop provides pertinent, short-format, technical articles between major releases of the product and associated product documentation (technical library content, Resource Kit book, whitepapers, and tools).
NextHop highlights the knowledge of experts in the Lync Server community, bringing you information from internal and external experts, such as the Lync Server engineering team and our Most Valuable Professional (MVP) community. In addition to publishing great content by contributing authors, NextHop keeps a pulse on the community. The Lync Server Blog Roll and @DrRez Twitter feed highlight the activities of other sites and blogs focused on Communications Server. NextHop provides pointers to a wealth of information about Lync Server. Our plan is to support, encourage, and evangelize all the great content that is being written about Lync Server.

Todays Lesson Learned – Lync Server 2010 and ST node for OpsMgr 2007 R2

This is a follow-up post in a series called Todays Lesson Learned started by fellow Lync MVP Tommy Clarke with this post: Todays lesson learned–Exchange 2010 upgrade with Active Sync and MobileIron It is a blog series noting down “learn from my mistakes” and “gotchas that can stop an entire project” type of problems with learning by doing and learning the hard way.

Lately I have been working with Lync Server 2010 and using System Center Operations Manager 2007 R2 (OpsMgr) for the best possible monitoring and troubleshooting environment for a customer. Everything got set up correct and the integration seemed to look ok. Except that Synthetic Transactions did not work.


Synthetic Transactions can be run from PowerShell in any Lync deployment. They are “test-cs” cmdlets and enables you to test features serverside with actual users. If you run (get-command “test-cs*”).count from Lync Server Management Shell you will see that there are 36 test cmdlets ranging from testing the ability to log on (Test-CsRegistration) to testing Audio Video conferencing (Test-CsAvConference).

OpsMgr continuously run Synthetic Transactions (ST) against the Lync environment to make sure everything is working. In a best practice environment you should deploy a dedicated server to run the ST’s from. This is because they may generate heavy load on you production servers. OpsMgr runs a PowerShell script that access the node remotely and runs the test cmdlets

For more information on how to deploy Lync Server 2010 Management Pack for System Center Operations Manager 2007 R2, download and read the documentation here: http://www.microsoft.com/download/en/details.aspx?id=12375


After OpsMgr was deployed we noticed the following symptoms

  • Some of the ST’s did not work failing with a “This operation has timed out” message
  • The ones that did not work was
    • AV conferencing
    • Instant Messaging Conferencing
    • Instant Messaging P2P
    • Presence
    • P2P AV
  • The rest of them seemed to work
  • Logging on the ST Node we ran the test cmdlets manually and all of them worked
  • So the problem was that it worked locally, but not remotely from OpsMgr and no other indications or errors where thrown


I figured it had to be a configuration problem somewhere and went through all of the configuration on the Node from start to end using this blog post: http://www.vnext.be/2011/03/06/scom-opsmgr-lync-2010-management-pack-deploying-synthetic-transactions-sts/ It hit me when I saw the cmdlet for configuring CsTrustedApplication that we defined a port this application would access.

New-CsTrustedApplication -ApplicationId -TrustedApplicationPoolFqdn -Port <PortNumber> -Verbose

Checking the local Windows Firewall on the server I found that an exception for that port had not been created, and it dawned on me that they need to be created manually. Adding the exception for the port on the server and recalculating the ST health on OpsMgr solved to problem this time, saving the day and made me able to roll out Lync to that customer.


Always remember when creating Trusted Applications you need to manually create a firewall rule allowing inbound traffic to that specific port.

Lync Server and PowerShell – My favourite features, oneliners and scripts

I was preparing to speak at Microsoft Technology User Group (MTUG) here in Norway at the PowerShell Script Club. My session for the night was going to be Lync Server Management Shell. First I thought I was not going to prepare anything and wing the whole session. The more I thought about it, winging any session that I am going to give in front of an audience is seldom a good idea. So I thought, ok make a blog post instead. I will here add my favourite features, oneliners and scripts that I have found working with Lync Server. I will update this blogpost as I remember and find new features, oneliners and scripts. Please let me know of your best PowerShell tricks in Lync.

Last updated 17.01.2012


In addition to log on the Lync Server and open Lync Server Management Shell you can also access and work with Lync through remote PowerShell which came available in V2. Here is what you need to connect. The url could be your external webservices url as well

$session = New-PSSession -ConnectionUri https://lync-admin.contoso.local/OcsPowershell -Credential (Get-Credential)
Import-PSSession -Session $session

Finding cmdlets

There are several ways to find cmdlets in Lync. If you like the graphical representation like a mind map there is some good ones created by MVP Tom Arbuthnot

In PowerShell there is some cmdlets available as well when finding what is available

#Get all cmdlets for Lync that contains -Cs
Get-Command *-Cs* -CommandType cmdlet -Module Lync
#Get all cmdlets that contains user
Get-Command *user* -CommandType cmdlet -Module Lync

#When you find the cmdlet you want to use find the syntax on how to use it
Get-Help Get-CsUser -Examples
#Use -Online to open the TechNet website for that cmdlet
Get-Help Get-CsUser -Online

#Looking for a specific setting to set and don't know which cmdlet that can modify it use the below code
$params = Get-Command -CommandType Cmdlet *-Cs* | % { $n = $_.Name ; $_.Parameters.Values | % { Add-Member -in $_ noteproperty CmdletName $n; $_ } }
$params | where { $_.Name -like "*meeting*" } | select Name,CmdletName
#This is cool, found the trick over at http://blogs.technet.com/b/csps/archive/2010/06/14/howtofindsetting.aspx


There are some cmdlets I use more than others and find useful. Let me know what is your most used cmdlets.

#List a lot of the topology information, here you can sort to find URLs, ports and servernames configured

#List all pools in your topology, useful for finding Front End pool name, when you forget it

#The only policy that is not available in Lync Control Panel, lot of nice features can be configured here

#Update the AddressBook files

#List the CMS replication status for each Lync Server


The most used oneliners that I use

#Find what Lync Services are running
Get-CsWindowsService -ExcludeActivityLevel | ft Name, Status
#Start any stopped services
Get-CsWindowsService -ExcludeActivityLevel | where {$_.Status -like "Stopped"} | Start-CsWindowsService

#Find all users that are enabled for Lync and have a LineUri, sort them by LineUri, display displayname and LineUri
Get-CsUser -Filter {LineURI -ne $Null} | sort -Property LineURI | ft DisplayName,LineURI

#Quickly find and open the share folder for the Lync pool
Invoke-Item(Get-CsService -FileStore | Select-Object -ExpandProperty UncPath)


There are a lot of scripts that is created and expand on Lync Server PowerShell functionality and and some that simplifies working with Lync as well as monitors the solution. Below are some of my favourite scripts. Please let me know of other epic scripts out there.


A script to install prerequisites on Server 2008 R2 before you start install Lync Server on the OS.  You can download the resource kit tools, Silverlitght and other tools easily. You even have som post deployment options in the script as well. This script is highly recommended and I use it in every deployment.


A scripts that read unassigned numbers and depends on you having put you entire number serie there. It will find all numbers assigned to users, devices and features in Lync and find what numbers are available in any given unassigned numbers series. This is a script that saves you the pain of managing available numbers in an excel sheet.


This script is for demo or initial deployments only. It is created for norwegian rules and genereates an easy way to dial out through one gateway and has the usual normalization rules for Norway. To edit the script and find the nomralization rules for your country see the Dialing Rule Optimizer.


This script is used in an OCS to Lync migration scenario. It will reset all policies to $Null so that they use Global or Pool level policies for External access, Voice Policy and so on. The reason for this is that all users should use what you define for Lync and not what you inherit from OCS.


This script lists user connections, client versions and the distribution of users in a load balanced scenario

Monitoring OCS and Lync Peak Call Capacity

Script to monitor how many concurrent calls a particular OCS or Lync Mediation Server is handling. The script grabs the counters for inboud and outbound calls, parses their values, adds them together, and dumps the output into a CSV file. A good tool to find how many concurrent calls you have on your deployment


A script that enables you to import AD photos from file and store it in the thumbnailPhoto attribute. It is a central feature in Lync to show a photo of users


A script to enable users to search for external contacts and Video Conferencing endpoints from Lync. It creates a contact in AD and adds the SIP address to the msRTCSIP-PrimaryUserAddress so it will be synced to the addressbook in Lync.

Scripting Tips

There is a lot of techniques used for scripting. The best script tips I know of I will list here.

Use Write-Debug

Lets you easilly define debug lines that can test variables and logic in you script that is good to use when developing the script but that not need to be there when it is used in production. When you want to debug the script you change the $DebugPreference from ‘SilentlyContinue’ to ‘Continue’. Then all Write-Debug lines will be displayed.

$DebugPreference = 'Continue'

$var = Read-Host "Enter a computer name"
Write-Debug “’$var’ contains $var“

$DebugPreference = 'SilentlyContinue'

Use Functions

Functions are scripts in scripts. If it is certain things you need to do more than once in you script, make it a function with an input and output. I have also seen functions being used to organize your script in a better way to make it easier and more ordered to view.

Function Do-Something ($computername,$domainname) {
	# function code goes here


The Official Lync PowerShell Blog: http://blogs.technet.com/b/csps/p/categories.aspx
The Official Lync PowerShell Blog Cmdlet Descriptions: http://blogs.technet.com/b/csps/archive/2010/07/16/refallcmdlets.aspx
MVP Pat Richard’s Blog: http://www.ehloworld.com/category/powershell