Exchange 2007 Unified Messaging & Lync Server 2013 – Key Mapping Issue

I recently deployed a Microsoft Lync Server 2013 infrastructure for a customer running Microsoft Exchange Server 2007 SP3, and while this version of Exchange Server is supported it should be noted there are a few additional amendments that need to made in order to make UM Auto Attendant key mappings to Lync extensions work correctly. Following the typical UM integration through the use of OCSUMUtil.exe and ExchUMUtil.ps1, all Unified Messaging functionality seemed to be working correctly, including dial by extension. It wasn’t until a key mapping was added to an Auto Attendant to transfer a call to a specific Lync extension, did I see an issue. When calling the attendant and pressing one for example, which was directed to extension 319, the Unified Messaging service would produce the following error and the attendant would tell the caller “The call could not be transferred”.

As you can see, there is not a specific amount of detail to go on and researching this particular Event ID suggested this was an error that could pertain to a number of issues. On researching further however, I noted the following from the TechNet article on integrating Lync Server 2013 with Exchange Unified Messaging:

If you are using a version of Exchange that is earlier than Microsoft Exchange Server 2010 SP1, you must enter the fully qualified domain name (FQDN) of the corresponding Exchange Unified Messaging (UM) SIP dial plan in the Lync Server 2013 dial plan Simple name field. If you are using Microsoft Exchange Server 2010 SP1 or latest service pack, this dial plan name matching is not necessary.

In order to resolve the key mapping issue the following was performed.

1. Connect to the Lync Server 2013 control panel and click Voice Routing and then select the Dial Plans tab.

2. Double click the “Global” dial plan to edit it and in the Simple Name dialog box, remove the word Global and replace it with the name of your Exchange Unified Messaging dial plan followed by your internal Active Directory domain name. For example, if my UM Dial Plan name was “DefaultUM” and my internal domain was “company.local”, I would enter DefaultUM.company.local into the Simple Name field.

3. Click OK and then commit the change, you will then need to wait a few moments for the change to take affect before trying the key mapping again. It should also be noted that in the Global dial plan you will need sufficient normalisation rules for the key mapping to work when transferring to an extension. In my case the dial plan now looked like the following:

That’s it, hopefully your Auto Attendant key mapping issues to Lync extensions will now be resolved.

Lync Server 2010/2013 Response Group Holiday Sets

I recently performed a Lync Server 2010 deployment for an organisation with a branch office in Aberdeen, Scotland. As their bank holidays vary slightly in comparison to England and Wales, I created a Response Group Holiday Set for Scotland. The original script layout credit goes to UnifiedMe, which you can find here.

1. Connect to your Microsoft Lync Server 2010/2013 front end server.

2. Open the Microsoft Lync Server Management Shell and paste the following contents in its entirety. Prior to doing so, enter the FQDN of your front end pool in the “ApplicationServer” section before running the command.

 $a = New-CsRgsHoliday -StartDate “06/05/2013 12:00 AM” -EndDate “07/05/2013 12:00 AM” -Name “2013 Early May”
$b = New-CsRgsHoliday -StartDate “27/05/2013 12:00 AM” -EndDate “28/05/2013 12:00 AM” -Name “2013 Spring”
$c = New-CsRgsHoliday -StartDate “05/08/2013 12:00 AM” -EndDate “06/08/2013 12:00 AM” -Name “2013 Summer”
$d = New-CsRgsHoliday -StartDate “02/12/2013 12:00 AM” -EndDate “03/12/2013 12:00 AM” -Name “2013 St Andrew’s Day”
$e = New-CsRgsHoliday -StartDate “26/12/2013 12:00 AM” -EndDate “27/12/2013 12:00 AM” -Name “2013 Boxing Day”
$f = New-CsRgsHoliday -StartDate “25/12/2013 12:00 AM” -EndDate “26/12/2013 12:00 AM” -Name “2013 Christmas Day”
$g = New-CsRgsHoliday -StartDate “01/01/2014 12:00 AM” -EndDate “02/01/2014 12:00 AM” -Name “2014 New Years Day”
$h = New-CsRgsHoliday -StartDate “02/01/2014 12:00 AM” -EndDate “03/01/2014 12:00 AM” -Name “2014 2nd January”
$i = New-CsRgsHoliday -StartDate “18/04/2014 12:00 AM” -EndDate “19/04/2014 12:00 AM” -Name “2014 Good Friday”
$j = New-CsRgsHoliday -StartDate “05/05/2014 12:00 AM” -EndDate “06/05/2014 12:00 AM” -Name “2014 Early May”
$k = New-CsRgsHoliday -StartDate “26/05/2014 12:00 AM” -EndDate “27/05/2014 12:00 AM” -Name “2014 Spring”
$l = New-CsRgsHoliday -StartDate “04/08/2014 12:00 AM” -EndDate “05/08/2014 12:00 AM” -Name “2014 Summer”
$m = New-CsRgsHoliday -StartDate “01/12/2014 12:00 AM” -EndDate “02/12/2014 12:00 AM” -Name “2014 St Andrew’s Day”
$n = New-CsRgsHoliday -StartDate “26/12/2014 12:00 AM” -EndDate “27/12/2014 12:00 AM” -Name “2014 Boxing Day”
$o = New-CsRgsHoliday -StartDate “25/12/2014 12:00 AM” -EndDate “26/12/2014 12:00 AM” -Name “2014 Christmas Day”
$p = New-CsRgsHoliday -StartDate “01/01/2015 12:00 AM” -EndDate “02/01/2015 12:00 AM” -Name “2015 New Years Day”
$q = New-CsRgsHoliday -StartDate “02/01/2015 12:00 AM” -EndDate “03/01/2015 12:00 AM” -Name “2015 2nd January”
$r = New-CsRgsHoliday -StartDate “03/04/2015 12:00 AM” -EndDate “04/04/2015 12:00 AM” -Name “2015 Good Friday”
$s = New-CsRgsHoliday -StartDate “04/05/2015 12:00 AM” -EndDate “05/05/2015 12:00 AM” -Name “2015 Early May”
$t = New-CsRgsHoliday -StartDate “25/05/2015 12:00 AM” -EndDate “26/05/2015 12:00 AM” -Name “2015 Spring”
$u = New-CsRgsHoliday -StartDate “03/08/2015 12:00 AM” -EndDate “04/08/2015 12:00 AM” -Name “2015 Summer”
$v = New-CsRgsHoliday -StartDate “30/11/2015 12:00 AM” -EndDate “01/12/2015 12:00 AM” -Name “2015 St Andrew’s Day”
$w = New-CsRgsHoliday -StartDate “28/12/2015 12:00 AM” -EndDate “29/12/2015 12:00 AM” -Name “2015 Boxing Day”
$x = New-CsRgsHoliday -StartDate “25/12/2015 12:00 AM” -EndDate “26/12/2015 12:00 AM” -Name “2015 Christmas Day”
New-CsRgsHolidaySet -Parent ApplicationServer:servername.domain.local -Name “Scotland Bank Holidays” -HolidayList ($a,$b,$c,$d,$e,$f,$g,$h,$i,$j,$k,$l,$m,$n,$o,$p,$q,$r,$s,$t,$u,$v,$w,$x)

3. In the Lync Control Panel click “Response Groups” and then click to create or edit a workflow. Once the web site loads select the hunt or interactive response group that you need to apply the holiday set to and click edit. In the workflow editior under the “Specify Your Holidays” section you should now see the Response Group Holiday Set name displayed. Click to check the holiday set and the configure your preferred call routing method for the days contained within the created set and click Save at the bottom of the workflow once you have finished.

That’s it, the holiday set will now be active.

Lync 2013 EWS With Forefront TMG 2010 Issues

I recently performed a Microsoft Lync Sever 2013 migration and following this process I noted that Lync 2013 clients connecting from external networks were continually prompted for Outlook authentication in order to retrieve data from Exchange Web Services (EWS). After investigating the issue, it appears this occurs when utilising forms based authentication for the /Autodiscover/* and /EWS/* virtual directories when utilising an SSL web listener in Forefront TMG 2010. In order to resolve the issue a separate global IP address was obtained and assigned to a web listener that does not perform any pre-authentication and simply passes the authentication request directly to Exchange Server 2010. The reason a separate global IP address and web listener was utilised, is that should you be using a single web listener for all Exchange services you will need to disable forms based authentication for OWA, Outlook Anywhere and Exchange ActiveSync, in most environment this would not be a desirable approach, however using a separate listener purely for autodiscover and EWS satisfies most security requirements. The following steps were performed in Forefront TMG 2010 to resolve the issue.

1. In Forefront TMG 2010 right click “Firewall Policy” -> “New” -> “Exchange Web Client Access Publishing Rule”.

2. When the wizard invokes enter a name for the publishing rule such as “Exchange Web Services” and click Next.

3. On the select services page click the drop down item and select the appropriate version of Exchange Server for your environment, and then check to select “Outlook Anywhere (RPC\HTTP(s))” and then also select “Publish additional folders on the Exchange Server for Outlook 2007 clients” and then click Next.

4. On the Publishing Type page ensure that “Publish a single website or load balancer” is checked and click Next, on the following Server Connection Security page select “Use SSL to connect to the published web server for server farm” and click Next.

5. On the Internal Publishing Details page in the Internal site name dialogue box enter the fully qualified domain name of your Exchange Client Access Server and then click Next.

6. On the Public Names page enter the the fully qualified domain name used for external autodiscover, for example autodiscover.domain.com and then click Next.

7. On the Select Web Listener page click “New” and then enter and appropriate name for the listener and click next, on the following page select “Require SSL secured connections with client” and then click Next.

8. On the Web Listener IP address page, click External and then “Select IP Addresses” and continue to select the new global IP address that is to be used for Exchange Web Services and then click Next.

9. On the Listener SSL Certificate page click “Select Certificate” and then choose your third party SSL certificate for Exchange Services, this certificate must include the subject alternative name of autodiscover.domain.com, once selected click Next.

10. On the Authentication Settings page click the drop down item and select “No Authentication” and thenclick next and then next again past the Single Sign On page and the click Finish.

11. Back in the main publishing rule wizard, ensure the newly created listener is selected and then click Next. On the Authentication Delegation page click the drop down item and select “No delegation but client may authenticate directly” and then click Next, on the following User Sets page click Next and then Finish to create the publishing rule.

12. Once the rule has been created right click it and select properties and select the paths tab and remove the /OAB/* and /rpc/* entries and click OK. Following this change click Apply on the Firewall Policy page and wait for the TMG configuration store to update accordingly.

13. The Exchange Web Services rule is now created, and should look like the following as detailed below, please click to enlarge.

14. If the publishing of the rule has applied correctly, when connecting with your Lync 2013 client externally you should now longer be continually prompted for Outlook credentials and additionally under the configuration information section of the client, which can be accessed by holding down the control (Ctrl) key and then left clicking the Lync 2013 task tray icon and selecting “Configuration Information”, the EWS status should now say “EWS Status OK”.

That’s it, hopefully your EWS external access now works as intended.                             

Veeam SureBackup – Virtual Lab Creation Failure

I was recently in the process of configuring a virtual lab for Veeam Backup & Replication 6.1 Patch 1 to find that should you select not to create a virtual machine folder or resource pool at the Host configuration stage, the lab creation will fail. A valid question would be why would you not want to create the folder or resource pool, however in my case this was a small deployment and the customer only had VMware Essentials Plus licensing which does not offer resource pools as a feature. The error being experienced was the following:

Registering proxy appliance Error: The object has already been deleted or has not been completely created

Failed to register VM, configFile ‘[Datastore Name]  Virtual Lab Name/drv_va.vmx’, name ‘Virtual Lab Name’, isTemplate ‘False’, poolRef ‘resgroup-8’, hostRef ‘host-9’, folderRef ‘ha-folder-vm’

In order to resolve this error, ensure that the creation of the virtual machine folder and resource pool is enabled in the virtual lab configuration. As a result, I have now logged this issue with Veeam as a product bug.

That’s it!

Update: Veeam have now confirmed this is a bug in version 6.1 Patch 1.

URL: http://forums.veeam.com/viewtopic.php?f=24&t=13501

VMware View – Adding & Removing Pool Entitlements Via Scheduled Tasks

I recently had a requirement for a customer to automatically add and remove user entitlements on VMware View 5.0 virtual desktop pools. While this can be achieved through View PowerCLI, the customer needed to query Active Directory to obtain a security group and then apply or remove this group from a pool. The issue with View PowerCLI in 5.0 is that the PowerShell aspect is a snap-in and not a module. Due this, a simple script calling both the Active Directory and View PowerCLI modules is not possible. To work around the limitation I have written the following scripts to add and remove pool entitlements using Active Directory groups.

Add Entitlement PowerShell Script: Download

Remove Entitlement PowerShell Script: Download

There are a two environment specific variables that need changing in each of the .PS1 files, these are the following:

 Get-ADGroup“Users” | Add-PoolEntitlement -pool_id “Test”

 Get-ADGroup“Users” | Remove-PoolEntitlement -pool_id “Test”

Where “Users” is the name of the Active Directory security group you wish to add or remove from a pool, and where “Test” is the name of the pool in which you want to apply or remove an entitlement. To run the scripts as scheduled tasks, place each script on one of your VMware View Connection Servers, in a directory such as C:\ViewScripts. Proceed and create a new basic task in the Windows Task Scheduler and specify the required bat file as available for download below.

Add Entitlement Bat File: Download

Remove Entitlement Bat File: Download

The created bat files essentially call powershell.exe and then execute the required .PS1 file. A specific “-File” parameter in the bat file needs amending for your environment, as detailed below.

C:\Windows\System32\WindowsPowerShell\v1.0\powershell.exe -file “C:\ViewScripts\AddEntitlement.ps1”

The process is now complete.

Lync Server 2010 & Mitel Direct SIP Connectivity

I recently performed a direct SIP trunk integration between a Mitel SX3300 PBX and Microsoft Lync Server 2010. Mitel have published a technical reference for direct SIP connectivity with Lync Server 2010, however this predominantly focuses on the configuration of the SIP trunk from the Mitel side as you would probably expect and the technical reference does not go into detail about what configuration is required in Lync Server 2010 in order to establish connectivity. The following information focuses on the Lync Server 2010 configuration for direct SIP connectivity and does not discuss the Mitel SIP or ASR rules required when placing calls through the 3300 gateways, this information focuses obtain the configuration of PSTN gateways in Lync Server 2010 for Mitel integration only.

1. Obtain Mitel technical reference SIPCoE 11-4940-00161 from the Mitel portal if you have an authorised account or from your PBX vendor. Alternatively you can view the configuration PDF file from here. Although this information is written specifically for MCD 4.2, the SIP trunk integration will work with lower software revisions, you will however notice some of the SIP configuration options detailed in the PDF will not be available in lower revisions.

2. Once the Mitel side of the SIP trunk has bee configured, connect to your Lync Server 2010 front end and open the topology builder. Once the topology builder has opened ensure that you have the mediation server role installed within your topology as this will be required when configuring Lync users for enterprise voice. If this feature is not installed, proceed and install the mediation server role before continuing onto step two.

3. Once the mediation server role is installed, navigate back to the topology builder and expand the “Mediation Pools” container. You should now see the FQDN of the server that holds the mediation role. Right click this object and select “Edit Properties” to invoke the properties window. Within the properties window check the “Enable TCP port” option and then continue to set the TCP listening port to 5060 as for the Mitel SIP trunk side the target TCP port for connectivity is 5060, so we need to ensure our mediation server is listening for requests on this port. An import thing to note here is that if you have any trusted applications, such as RCC integration or Cisco CUPS that already utilise port 5060 you will need to change the mediation server listening port and the destination TCP port of the Mitel SIP trunk to ensure the integration works correctly. If you are in this scenario I recommend setting the mediation server listening port to 5068 and also setting the target TCP port on the Mitel SIP trunk to 5068. The following screenshot illustrates the mediation server role configuration that is required.

Once the port has been set, continue and publish the topology to the CMS. Once the publishing has completed, either restart your front end server or restart the mediation server service. This is required so that the new mediation server port is enabled and listening for connections on the front end server. To confirm this, open a new command prompt window and type “netstat /an” and press return and you should now see the server listening for connections on port 5060 or port 5068 depending on your scenario.

4. Once the mediation server is now listening on the correct port, the required PSTN gateway can be added to the topology. In the topology builder right click the “PSTN Gateways” container and select “New IP/PSTN Gateway”. In the gateway dialog box enter the IP address or FQDN of the Mitel PBX you are establishing the SIP trunk to and then proceed to set the listening port to 5060 and the transport protocol to TCP. For reference the Mitel side of the SIP trunk will only accept inbound connections on TCP port 5060. Once this has been completed, click OK and return to the topology builder and then publish the topology. The following screenshot details the PSTN gateway configuration.

5. In the topology builder window expand the “Mediation Pools” container, right click the FQDN of your mediation server and select “Edit Properties” to invoke the properties window. You should now see the IP address or FQDN of your Mitel PBX as a PSTN gateway that can be associated with the mediation server. Highlight the created PSTN gateway in the unassociated gateways field and then click “Add” and click OK. Following this, continue and publish the topology before continuing to the next step.

6. Open the Lync Control Panel and navigate to Voice Routing -> Trunk Configuration and then click New -> Pool Trunk, when prompted select the PSTN gateway you have just created. For the direct SIP connectivity to work with Mitel systems we need to disable RCTP and refer support as Mitel does not support this functionality, you will note this is detailed in the Mitel technical reference on the final page of the document. Mitel do recommend enabling media bypass, however in Lync Server 2010 to achieve media bypass enablement with refer support and RCTP functionality disabled we need to perform some specific steps. Proceed and uncheck the “Enable refer support” and “Enable Media Bypass” boxes in the pool trunk window and then click OK. When back in the main trunk configuration window click “Commit” and then select to commit all changes. The following screenshot illustrates the aforementioned configuration.

7. Once the gateway has been added in the trunk configuration open the Lync Server Management Shell and run the following PowerShell commands to disable RCTP functionality. In the below example my PSTN gateway is called mitel.domain.local, please replace this FQDN with your own Mitel system when running the following commands.

Set-CsTrunkConfiguration -Identity PstnGateway:mitel.domain.local -RCTPActiveCalls $false -RTCPCallsonHold $false

Set-CsTrunkConfiguration -Identity PstnGateway:mitel.domain.local -EnableSessionTimer $true

8. Once the PowerShell commands have been executed return to the Lync Control Panel and navigate to Voice Routing -> Trunk Configuration. Select to edit your pool trunk PSTN gateway and in the configuration window check “Enable Media Bypass” and then click OK.  When back in the main trunk configuration window click “Commit” and then select to commit all changes.

The configuration of the SIP trunk is now complete, once a dial plan, voice policy, PSTN usage and route have been configured you should now be able to call between Mitel and Lync users and also pass calls to the PSTN once the Mitel ASR rules have been configured.

Lync Server 2010 – Client Recording Location

I recently had a requirement to store Lync 2010 recordings on a UNC path for a customer. Natively in Lync 2010, setting the recording location directly through the client to either a UNC path or a mapped drive is not supported, and there is a good reason as to why this is the case. When a Lync 2010 recording is invoked the data is streamed to the recording location and when the recording is stopped it is then processed and viewable in both the the Lync Recording Manager and as a WMV file if selected. If for example there was an interuption to network connectivity on the local client, this would impact the recording itself. If you do try and select a mapped drive as a recording location in the Lync 2010 client, the following error will be displayed.

If you have a particular requirement to place Lync recordings onto a mapped drive, the following work around can be performed. This work around utilises a HKEY_CURRENT_USER registry modification that is executed every time a user logs onto a workstation, the registry key itself sets the “RecordingRootDirectory1” value to be the mapped drive or UNC path that you require. In order achieve this, the following actions need to be performed.

1. Download the LyncRecordingLocation registry file from here.

2. Open the registry file in notepad and amend the “RecordingRootDirectory1″=”S:\\LyncRecordings\\” entry to read a mapped drive or UNC location of your choice and then save the file.

3. Connect to a domain controller in your infrastructure and then open the Group Policy Management Console. From here, create a new GPO named “Lync Recording Location” for example, and then right click the newly created object and select edit.

4. When the GPO Editor opens navigate to the following location, User Configuration -> Policies -> Windows Settings ->Scripts, as illustrated below.

5. In the Scripts action pane, double click Logon to configure the script. When the Logon dialog box opens click Add which will invoke the “Add a script” dialog box. In the “Script Name” field type the following without quotes, “Regedit.exe”. In the parameters field enter the following without quotes “/s LyncRecordingLocation.reg”. See below for an illustration of this and once both of these fields have been populated click OK.

6. To complete the creation of the script, click the “Show Files” button and in the policies folder that then displays copy and then paste the LyncRecordingLocation.reg file into this area and close the window. Click Apply and the OK on the Logon Properties dialog box and then exit the Group Policy Management Editor.

7. Back in the Group Policy Management Console, locate an Organisational Unit (OU) where your Lync 2010 users reside, right click the OU and then select “Link an existing GPO” and then select the Lync Recording Location GPO that you have created. This could also be filtered to a specific Active Directory group that requires recordings to be stored centrally, choose which ever option is suitable for your environment.

8. Have your Lync 2010 users log off their workstations and back on again. Open the Lync 2010 client, select Options -> File Saving, and ensure that the Lync Recordings Save To dialog box is now showing the mapped drive or UNC path you set in the registry file, as illustrated below.

That’s it, the process is now complete.

Lync Server 2010 – Deleting User Contacts Via SQL

I recently experienced an issue at a customer whereby they had used the very helpful LyncAddContacts VBS script from the EXPTA blog, however this process had gone slightly wrong for the customer and they wanted to delete all contacts that had been pushed out to users and start again. Unfortunately the handy dbimpexp.exe tool does not allow you to explicitly delete contacts from users in bulk or individually. To get around this issue I utilised the following Microsoft SQL query against the Lync RTC database in order to delete a users contacts in their entirety. Please use the following information with caution, the query listed below modifies tables in the RTC database and should be used at your own discretion.

1. Using the Microsoft SQL Management Studio tools connect LyncServerName\RTC using an account that has full CSAdministrator rights.

2. When connected, under databases right click “RTC” and select “New Query”.

3. In the new query entry fieldtype the following:

DECLARE @RC int
DECLARE @_Owner nvarchar(4000)
EXECUTE @RC = [rtc].[dbo].[ImpDeleteContactGroups2] “[email protected]
GO

4. Under the Execute command detailed above change the users SIP address to be the desired one. To run this for multiple people at once, add more Execute lines for each person and then click Execute in the tool bar to run the script
 
5. Once the query has run, log into the Lync 2010 client as the user(s) and ensure their contacts list is now blank.
 
That’s it, the process is complete.

Veeam Backup & Replication – Exchange 2010 DAG Issue

I recently experienced an issue with a Microsoft Exchange 2010 Database Availability Group (DAG) failing over during a Veeam Backup & Replication job. The issue was occurring due to the snapshot committal process in VMware, which causes a brief pause in virtual machine I/O. This pause was causing the DAG member to lose sight of the file share witness, which in this case was housed on the customer CAS server, and subsequently fail over.

The resolution to this issue was to increase the CrossSubnetThreshold and CrossSubnetDelay of the cluster. The CrossSubnetThreshold specifies how many heartbeats can be skipped before the cluster fails over and the CrossSubnetDelay specifies the heartbeat interval. The threshold you set for both of these properties can depend on many factors, for example the speed of your underlying storage array or the size of the virtual machine that be being snapshot. In my case I needed to set both values to their maximum. This can be performed by carrying out the following:

1. Navigate to Start -> Administrative Tools and launch Windows PowerShell Modules

2. When the Powershell Window opens please enter the following command:
 
$cluster = Get-Cluster; $cluster.CrossSubnetThreshold = 10; $cluster.CrossSubnetDelay = 4000
 
3. Once the command has completed please run the following and ensure that the CrossSubnetDelay and CrossSubnetThreshold are set to 4000 and 10.
 
Get-Cluster | fl *

4. Re-run your Veeam backup job and see if the cluster fails over. If the backup completes correctly you can they reduce the CrossSubnetDelay and CrossSubnetThreshold to find the optimum values.

That’s it, your done.