Citrix Web Interface: Error occurred while making the requested connection

I recently ran into a bizarre issue with users not being able to launch applications from a very old Citrix Presentation Server 4.0 farm when trying to launch from Citrix Web Interface 5.4. They were getting the eminently unhelpful, “An error occurred while making the requested connection.”

The Diagnosis

In the web interface application logs, I noticed this:

An error of type IMA with an error ID of 0x80000003 was reported from the Citrix XML Service at address (servername)

And this:

The farm MyFarm has been configured to use launch references, but a launch reference was not received from the Citrix XML Service. Check that the farm supports launch references or disable launch reference requests.

The Solution

To resolve this, I modified C:\inetpub\wwwroot\Citrix\XenApp\conf\WebInterface.conf on the Web Interface servers and changed the RequireLaunchReference directive as follows:
(It was set to On)

And it worked. Supposedly, that directive must be set to Off when using Web Interface 5.4 with PS 4.0. But, I’ve been running for years with it set to On and it worked fine until recently. Another Citrix mystery.

Want more Citrix tips and tricks? Watch my Citrix NetScaler course!

7 Ways To Speed Up Citrix XenApp Logons

1. Disable unused Group Policy sections

In each of the GPOs that are applied to your servers and users, both User and Computer processing is enabled by default. Disabling unused parts of a GPO can shave some time off both logons and server booting. You can do this in the GPO properties. Just bring up the GPO in Group Policy Management Editor, right-click the policy name, and click Properties. Continue reading

Should You Use The HP Universal Print Driver or Other Third-Party Print Drivers In XenApp 6?

One of the problems that has plagued Citrix admins and engineers has been third party print drivers. All it takes is for one bad print driver to misbehave, crash the print spooler, and generate dozens of support calls from users who suddenly cannot print.

This common problem led to Citrix including the Citrix Universal Print Driver (Citrix UPD) which is compatible with many popular printers, and is much easier on the Windows print spooler. In cases where the Citrix Universal Print Driver does not play well with an application or a particular printer, the Citrix Universal Printer can be mapped into a user’s session as a virtual printer that offloads the print job to the user’s client machine, using the native or third-party print driver installed on the client machine.

Between these two wonderful gifts from Citrix, why even consider using a third-party print driver like the HP Universal Print Driver?

Despite the stability and compatibility of the Citrix Universal Print Driver, I have found that even it sometimes causes the Windows print spooler to crash. I’m not saying that the driver itself is at fault. There could be a problem with the data an application is sending to the print subsystem and the Citrix UPD. Regardless, the print spooler sometimes crashes and has to be restarted to restore printing on the affected XenApp server.

There are three approaches to resolving the problem of the Citrix UPD crashing the spooler-
1. Eliminate the driver itself as the cause (blame an application, an OS patch, or something else)
2. Do not map client printers into a user’s session, and instead allow them to only use the Citrix Universal Printer
3. Allow use of native or third-party print drivers

Option 1 is the most time-consuming and possibly the least rewarding because you may find that the problem actually is the driver, or an application that cannot be rewritten for whatever reason, or an OS patch that is absolutely necessary.

Option 2, forcing users to use the Citrix Universal Printer, can potentially work marvelously for small print jobs provided the user understands how to use the Universal Printer options.

Option 3, using native or third-party print drivers, makes many of us cringe. In Windows Server 2008 R2, some native HP drivers simply cannot be used. The native drivers HP gave to Microsoft to include in Windows included a bug which prevented the drivers from being used. This problem leaves the HP Universal Print Driver as the only native option for HP printers in Windows Server 2008 R2. If you have other printer brands in your environment, native drivers included with Windows will probably work. But remember that there is no guarantee that the native drivers will not crash the print spooler.

So which option is best? As usual, it depends on your environment. Despite the issues, I propose that option 3 can be a good option for XenApp 6 environments where printing is not heavy. Allowing native and third-party print drivers in addition to the Citrix Universal Printer and the Citrix UPD offers the most flexibility. The biggest problem I have seen with using the HP Universal Print driver is that it can consume the entire CPU and render the server almost useless. If users in your XenApp environment are doing a lot of printing, don’t use the HP Universal Print driver. Don’t even install it. Otherwise, test it out and see how it holds up under your workload.

If you decide to try third-party printer drivers, you don’t have to worry about these drivers crashing the print spooler thanks to the inclusion of a new feature in Windows Server 2008 R2 that allows print drivers to be isolated from the spooler. Print driver isolation works by creating a separate process, PrintIsolationHost.exe, for each session. Instead of a faulty driver crashing the spooler, it will only crash the PrintIsolationHost process, impacting only the user whose print job triggered the crash. Recovery is as simple as having the user log out and back in.

Enabling print driver isolation is easy and is done on a per-driver basis. In Windows, just launch Print Management under Administrative Tools. Right-click the driver you wish to isolate, and select “Isolated”

The change takes effect immediately and no restart of the spooler is required. While print driver isolation is a valuable and much-needed feature, it is not compatible with all print drivers. And it is absolutely not compatible with the Citrix Universal Print driver! If there were a way to isolate it without breaking printing, it would save almost everyone from having to use native or third-party print drivers.

Of course, isolating native and third-party drivers is only part of the solution. For maximum flexibility and compatibility, we need to automatically map the Citrix Univeral Printer into all user sessions, and set policies regarding the use of the Citrix UPD.

Mapping the Citrix Universal Printer to all user sessions is done through Citrix user printing policies. When it comes to how the Citrix UPD is used, we have two options. We can either disallow the use of native and third-party print drivers, and allow only the use of Citrix UPD-

Or we can allow the use of native or third-party print drivers, if present, and fallback to the Citrix UPD if native drivers are unavailable.

The beauty of this configuration is that we can use Citrix policies to control when, if, and which print drivers are allowed without having to make any modifications to the XenApp server itself. Native and third-party print drivers are installed and isolated, but we can choose to disallow them by simply modifying the Citrix user policies. If the Citrix UPD causes problems with the print spooler, we can switch over to native and third-party drivers by simply changing the policies. And as if that weren’t enough, the Citrix policies can be filtered on a per-user basis. This means one group of users can be forced to use Citrix UPD, while another group can be permitted to use native drivers! Now you can see why I chose this configuration to provide the most control and flexibility without sacrificing stability of the XenApp environment.

Earlier I mentioned that the Citrix Universal Printer is useful for small print jobs when the user understands how to use it. Rendering larger print jobs through the Universal Printer is extremely slow, and if users are trained in its use they can end up unintentionally printing to the wrong printer. Also, the Citrix Universal Printer requires the appropriate print drivers be installed on the user’s client machine, making its universal use a potential administrative nightmare. In the future I hope to see some intelligence built into XenApp and the ICA client that automatically detects and selects the best method of printing based on the user’s unique configuration.

Citrix printing has improved tremendously over the years. One size still does not fit all, but we are getting there. Hopefully the Citrix Universal Print Server (Project Phaser) will be the silver bullet that solves printing in Citrix forever.

Use PowerShell to Find Citrix ICA Client Versions In Use On a XenApp 6 Farm

In many Citrix environments it’s common to have a large variety of ICA client versions. One thing that sometimes surprises users and IT folks alike is how much of a performance increase can be seen after upgrading an old ICA client. But how do you know which clients need upgrading?

One of the biggest challenges has been deciphering what ICA client version the cryptic “client build number” in a user’s session information translates to. Well thanks to the XenApp 6 PowerShell SDK and Get-XASession, we can easily find Citrix ICA client version information in a snap with the following script (download the script here):

# XenApp 6 Client Version Retrieval Script
# Created by Ben Piper
function convertToVersion($build) {
		6685 {"13.0"; break}30 {"12.1"; break}6 {"12.0.3"; break}6410 {"12.0"; break}142{"Java"; break}317{"3.0"; break}324{"3.0"; break}330{"3.0"; break}349{"3.0"; break}304{"MAC 6.3"; break}314{"MAC 6.3"; break}323{"MAC 6.3"; break}326{"MAC 6.3"; break}400{"MAC 7.0"; break}402{"MAC 7.0"; break}405{"MAC 7.0"; break}406{"MAC 7.0"; break}407{"MAC 7.0"; break}402{"MAC 7.0"; break}411{"MAC 7.0"; break}500{"MAC 7.1"; break}600{"MAC 10.0"; break}601{"MAC 10.0"; break}581{"4.0"; break}606{"4.0"; break}609{"4.0"; break}614{"4.0"; break}686{"4.0"; break}715{"4.2"; break}727{"4.2"; break}741{"4.2"; break}779{"4.21"; break}730{"wyse1200le"; break}910{"6.0"; break}931{"6.0"; break}961{"6.01"; break}963{"6.01"; break}964{"6.01"; break}967{"6.01"; break}985{"6.2"; break}986{"6.2"; break}1041{"7.0"; break}1050{"6.3"; break}1051{"6.31"; break}1414{"Java 7.0"; break}1679{"Java 8.1"; break}1868{"Java 9.4"; break}1876{"Java 9.5"; break}2600{"RDP 5.01"; break}2650{"10.2"; break}3790{"RDP 5.2"; break}6000{"RDP 6.0"; break}2650{"10.2"; break}5284{"11.0"; break}5323{"11.0"; break}5357{"11.0"; break}6001{"RDP 6.0"; break}8292{"10.25"; break}10359{"10.13"; break}128b1{"MAC 10.0"; break}12221{"Linux 10.x"; break}13126{"Solaris 7.0"; break}17106{"7.0"; break}17534{"7.0"; break}20497{"7.01"; break}21825{"7.10"; break}21845{"7.1"; break}22650{"7.1"; break}24737{"8.0"; break}26449{"8.0"; break}26862{"8.01"; break}28519{"8.05"; break}29670{"8.1"; break}30817{"8.26"; break}31327{"9.0"; break}31560{"11.2"; break}32649{"9.0"; break}32891{"9.0"; break}34290{"8.4"; break}35078{"9.0"; break}36280{"9.1"; break}36824{"9.02 WinCE"; break}37358{"9.04"; break}39151{"9.15"; break}44236{"9.15 WinCE"; break}44367{"9.2"; break}44376{"9.2"; break}44467{"Linux 10.0"; break}45418{"10.0"; break}46192{"9.18 WinCE"; break}49686{"10.0"; break}50123{"Linux 10.6"; break}50211{"9.230"; break}52110{"10.0"; break}52504{"9.2"; break}53063{"9.237"; break}55362{"10.08"; break}55836{"10.1"; break}58643{"10.15"; break}				
		default {$build; break}
$clientUsage = @()
foreach($session in Get-XASession -full | where {$_.state -eq "Active" -and $_.protocol -eq "Ica"}) {
	$clientUsage += new-object psobject -Property @{
		User = $session.accountname
		Workstation = $session.clientname
		Client = convertToVersion($session.clientbuildnumber)
$clientUsage | sort-object -Property Workstation | get-unique -asstring

The script makes use of build-to-version information gleaned from Nick Holmquist’s ICA Client Build List and the Citrix Client Build List thread on Citrix Forums (Thanks!). The convertToVersion function uses the PowerShell switch command to identify and then return the ICA client version based on the build number. If the key-value pair is not in the list, the build number is returned. All ICA client versions in the list have at least one decimal place to make it easy to distinguish build numbers from client versions.

How To Fix Citrix Receiver Error 2320

Recently I have seen a couple of cases where the Citrix Receiver 3 client produces the following error when trying to launch a published application:

Error number 2320
Citrix online plug-in Configuration Manager: No value could be found for (ClientHostedApps) that satisfies all lockdown requirements. The lockdown requirements in force may be conflicting.

The most salient part of the error message is in between the parenthesis. In the error message above, ClientHostedApps is a registry value that resides in two locations: HKLM\SOFTWARE\Wow6432Node\Citrix\ICA Client\Engine\Lockdown Profiles\All Regions\Lockdown\Virtual Channels\Control (on 64-bit systems: HKLM\SOFTWARE\Wow6432Node\Citrix\ICA Client\Engine\Lockdown Profiles\All Regions\Lockdown\Virtual Channels\Control) and HKCU\SOFTWARE\Citrix\ICA Client\Engine\Lockdown Profiles\All Regions\Lockdown\Virtual Channels\Control

The fix couldn’t be simpler. Just delete the value for ClientHostedApps in these locations, refresh your applications in Receiver, and you should be able to launch published applications.

Want more Citrix tips and tricks? Watch my Citrix NetScaler course!

Instantly Publishing Citrix Apps to Individual Servers Using PowerShell

Sometimes there is a need to publish an application to individual XenApp servers for baselining or troubleshooting purposes. But if you have a lot of published applications in your XenApp 6 farm, this can be a huge hassle. Thankfully PowerShell allows us to quickly and easily take our existing published applications and automatically create individually published apps for each server. We can use Worker Groups to control which servers get an individually published application. Not only that, we can organize the applications neatly by creating separate console and Client folders for each server. I wrote this script to accomplish all of the above using XenApp 6 PowerShell SDK’s powerful features:

$appFolder = "Applications"
$testfolderpath =  "Applications/Test/Single Server Test"
$sourceAppPath = "Applications/Test"	#apps in the root of this path will not be copied
$publishTo = "DOMAIN\GroupWithAccessToIndividualServers"
$targetWorkerGroup = "Main Farm Servers"
$clientFolder = "Test\Single Server Test"
$WhatIfPreference = $false		# Simulate script but do not execute any changes (will yield errors)
# Main Program
$servers = Get-XAServer -workergroupname $targetWorkerGroup
$sourceFolders = Get-XAFolder -folderpath $appFolder -recurse | where {$_ -notmatch $testfolderpath -and $_ -match $sourceAppPath -and $_ -ne $sourceAppPath}
# Create folder for each server
foreach ($server in $servers) {						
	#generate folder name for each server
	$createfolder = $testfolderpath+"/"+$server.servername
	#create folder for each server
	new-xafolder -folderpath $createfolder
	foreach ($folder in $sourceFolders) {
		#get list of apps to copy in each folder
		$appstocopy = Get-XAApplication -folderpath $folder			
		foreach ($app in $appstocopy) {
			## generate name for new app
			$newname = $app.displayname+" "+$server.servername
			$newclientfolder = $clientfolder+"\"+$server.servername
			## get existing accounts to remove			
			$accountsToRemove = ($app | Get-XAApplicationReport).accounts
			## copy application to server's folder		
			$newapp = $app | Copy-XAApplication -folderpath $createfolder
			## publish application to lone server		
			$newapp | set-xaapplication -servernames $server.servername -clientFolder $newclientFolder
			## remove existing accounts
			foreach ($account in $accountsToRemove) {
				$newapp | remove-xaapplicationaccount -Accounts $account
			## publish application to AD group
			$newapp | add-xaapplicationaccount -Accounts $publishTo
			## rename new application
			$newapp | rename-xaapplication -newdisplayname $newname						

Download the script from GitHub.

Just set the variables with what is appropriate for your environment and run the script.
The $appFolder variable is the root path of your applications (default is “Applications”)
$testfolderpath is the full path of the folder where the applications published to individual servers will be published (no trailing slash)
Set $sourceAppPath one level higher than the path of the folder containing the applications you wish to copy. The script will recurse down into child folders from this path, but will not copy applications that reside within this path.
$publishTo is a string containing the AD users or groups the newly published applications should be published to
$targetWorkerGroup is the name of the worker group containing the servers the applications will be published to
$clientFolder is the root Program Neighborhood/Client folder that the individual server folders will be created under

The once-daunting and time-consuming task of copying and modifying applications for each server can now be done automatically in a matter of minutes!

Update: It’s even easier to undo the changes made by the above script if you decide you want to scrap the newly published apps and folders and start over. Just use the following script:

$testfolderpath =  "Applications/Test/Single Server Test"
$WhatIfPreference = $false
# Main Program
(get-xaapplication -folderpath (Get-XAFolder -folderpath $testfolderpath)) | remove-xaapplication
(get-xafolder -folderpath $testfolderpath) | remove-xafolder

Deploying Citrix Access Gateway VPX with Web Interface 5.4 – CAG Setup with RADIUS

Deploying CAG with Web Interface 5.4 is actually very easy, there are just some “gotchas” that you have to be ready for. This is a guide to help you avoid those snags and pitfalls that commonly occur with a CAG VPX and Web Interface integration.

I recommend getting the Citrix Access Gateway VPX Getting Started Guide and HDX Remote Access Guide with Citrix Access Gateway VPX Express if you don’t already have them. The former document contains some inaccuracies but is has some useful reference info as well. The latter takes you through the fundamental setup of the CAG VPX and gets you to the web administration console, where most of the meaty configuration will take place.

There are some assumptions I’m making with this guide since it is based on my own requirements. They are:

  • The CAG VPX has two virtual NICs, external to service external users, and internal for management and communication with the XenApp servers
  • Two logon points will be configured: One that allows user authentication to take place at the web interface, and another that uses RADIUS
  • The CAG VPX will not reside in a DMZ. If your situation requires it to reside in a DMZ, setting it up is trivial once you’ve gotten everything else working.
  • You’ve already got the CAG VPX appliance imported and running, but not configured
  • You have your web interface server setup, with no websites configured.
  • You have installed the CAG VPX license on a Citrix license server

Also, a word of warning: Configuring CAG VPX with Web Interface is like playing chess. Every move you make will affect all of your successive moves. In areas where I suspect your setup might require you to deviate from this guide, I’ll offer some pointers to help you make the right move.

Let’s get started! First, follow the Getting Started guide to configure the management interface for the CAG via the VM console. If you are unsure about a setting, just take the default by hitting Enter.

Once you have your management IP assigned, you’ll need to access the web administration console by browsing to https://[IP address]/lp/adminlogonpoint . Login with the default username and password “admin”. You’ll see a nice dashboard with two dials and some nasty looking red X’s. Click on the Management tab. This will take you to the Networking portion of the System Administration menu group.

Here, enter the CAG’s hostname as an FQDN. You’ll see a list of your network interfaces (eth0, eth1, etc.) with one of them having the management IP address you assigned. To the right, there are four checkboxes labelled Internal, External, Appliance Failover, and Management.

Moving from left to right, the interface that will be used to connect to your XenApp servers should have the Internal checkbox checked.
The interface for management should already have the Management checkbox checked.
The interface that will be receiving external requests from end users should have the External checkbox checked.

If need be, your Internal and External interfaces can be the same. Make sure your DNS servers have an entry for your Internal IP!

Under the Default Gateway section, select the interface the CAG should use to route traffic for subnets to which it is not directly connected. This will probably be your External interface. Remember, the CAG has a direct connection to the subnet your XenApp servers are on, so it doesn’t need a gateway to get to those. But it does need a gateway to get back to your external users who are connecting from the Internet!

Click Save and restart the appliance using the big Restart button on the top right.

Log back into the web administration console and browse to Management > Name Server Providers. Enter your DNS servers and DNS suffixes.

Now go to Static Routes in the System Administration menu. Do you need a static route? If you plan on putting the CAG VPX into a DMZ later, go ahead and enter your static routes. Gateways you specify for static routes will take precedence over the default gateway you specified earlier. Remember, it does not hurt to add them now.

Now Browse down a few rows to Licensing and click Configure. Select the Licensing type and Remote Server for the licensing server. Enter the FQDN or IP of your Citrix licensing server, and click Save. The CAG will attempt to grab its licenses and upon a successful retrieval, it will display them as shown:

NB: If the CAG is unable to retrieve the licenses, I recommend stopping and troubleshooting until it is able to successfully pick up the licenses. You can continue your configuration, but you will not be able to test it until the license issue is resolved.

Moving right along, click on Authentication Profiles under the Access Control menu group. It’s time to add a RADIUS authentication profile! But before you do that, you have to set up a RADIUS server. I recommend reading How to Configure Radius Authentication/Authorization on Windows 2008 for Use on Citrix Access Gateway Standard Edition. (One caveat, however: don’t perform steps 13-17 in the KB article because they’re unnecessary and will cause problems.) Click Add and enter a name for the Authentication Profile. Click New and add your RADIUS server(s) and shared secret. Leave everything under Group Authorization as-is. You’re relying on the RADIUS server to check group authorization.

Now go to XenApp or XenDesktop under Applications and Desktops and enter the IP ranges of clients that can access XenApp servers via ICA and CGP. I really don’t know why there isn’t a checkbox that allows you the equivalent of a “permit ip all”, but there isn’t.

Next, click Secure Ticket Authority. These settings are arguably the most common cause of application launch issues. Select your STA servers carefully, and make sure all your XenApp servers have unique STA ID’s! If you are running Provisioning Services and streaming XenApp, read before proceeding. Once you are sure your STA IDs are unique, click New and enter the FQDN of each XenApp server that will be providing STA services. By default, the connection type is Secure, but I’m guessing your XenApp servers are not using SSL for STA traffic, so select Unsecure. Leave everything else as-is and click Add. Note the servers you selected here, because you will need them later.

At this point you can go ahead and restart the CAG VPX appliance, because it’s now time to do some work on the Web Interface (WI) side. Log into your WI server, launch the Citrix Web Interface Management console, and create a new site.

Should we do the easy one or the hard one first? Trick question. They’re both easy! We’ll set up a site to be used with RADIUS authentication. Click Create Site under the Actions pane on the right, name the website however you wish and click Next. Select “At Access Gateway” as the point of authentication and click Next. Here you’ll be greeted with an intimidating looking Authentication Service URL field. But as I said, this is easy! Just enter https://[cag-FQDN]/CitrixAuthService/AuthService.asmx and click Next, Next. After a few moments, your site will be created.

Right-click the site in the XenApp Web Sites list and select Server Farms. Configure your XenApp servers like you normally would in WI. There is nothing here unique to CAG.

Now right-click the site again and select Secure Access. Select the only item in the list and click Edit. Change Access method to Gateway direct and click Next. Next you’ll be asked for the address of the CAG. Enter the FQDN of the CAG, and optionally enable or disable session reliability. If enabled, you can request tickets from two STAs (A word on this option: When you setup a site for Citrix Receiver, this checkbox must be unchecked. This site you are creating now cannot be used for Receiver, so don’t worry about it here if you plan to use Receiver.) Click Next.

Remember I said to note the XenApp servers you entered into the CAG VPX as your STA servers? Web Interface wants to know about these servers too. Click Add and enter the URL of the first XenApp server you entered into the CAG in the following format:

I still do not know why it doesn’t just ask for the FQDN and assume the rest like the CAG does, but that’s how it is. Do this for all STA servers you entered into the CAG, and in the same order. Check, double check, and triple check the URLs! Also optionally change the “Bypass failed servers for” option to 1 minute. Click Finish.

Are we done? Almost. The CAG should be back up now, so log back into it. Click Logon Points under Access Control and click New. Now don’t be intimidated by all the settings. We only care about four things here. Enter the name of the logon point. Select this name carefully because it is what users will have to type in to connect to the CAG. If you enter “cag-logonpoint1” then users will have to go to which just looks ugly! Under Type select Basic. In the Web Interface field, enter the URL of the web interface site you created (no trailing slash). Under Authentication Profiles, select the RADIUS authentication profile you created earlier. Finally, check the “Single sign-on to web interface” check box and click Save.

Now, we are almost ready to test. But to save ourselves from a disappointing moment of temporary CAG dysfunction, click on Secure Ticket Authority again. Do you see unique STA IDs populated next to each of your XenApp servers? If not, troubleshoot until you do. If so, it’s time to test!

Browse to the logonpoint you just created. If you named your logonpoint “test1” and your CAG’s FQDN is, browse to

Do you get an SSL certificate error? Probably so. I intentionally did not cover installing a certificate because it introduces another level of complexity into the configuration. SSL Certificates are dependent on the hostname, and the hostname you use to connect to the CAG to enumerate and launch apps has to match up with the hostname on the SSL certificate. The certificate also must be signed by a trusted certificate authority. Unless you have your own certificate authority, getting a signed certificate can be a pain. Unfortunately, connecting to CAGs using untrusted SSL certs causes a lot of problems. You may encounter some of these problems or you may not. Test anyway. If you do run into problems, the good news is that the heavy lifting of configuring the CAG is done.

Now, it’s time for a moment of truth. Once you’ve gotten a login prompt, log in with an AD account that has appropriate authorization. You may need to specify the user in UPN or down-level domain format. It depends on your AD environment, but one of those should work. If you have trouble authenticating, first check the logs on the RADIUS server to make sure the denial is not occurring there. If you continue to have issues, it’s time to get acquainted with what will become your new best friend: the CAG debug log. The CAG debug log is at your service at . Watch it for any FLEXnet or STA errors.

Once you get logged in, try launching a published app. If all goes well, you should see something like…

How To Get a Unique STA ID for each of your PVS Provisioned XenApp Servers

Citrix Provisioning Services is very nice, but it does come with a slightly annoying quirk: All of your provisioned XenApp servers end up with the same STA ID! This will cause all sorts of problems for Citrix Access Gateway, Citrix Receiver, and anything else that may depend on having unique STA IDs. The good news is that fixing this little problem is easier than you might think.

To resolve the duplicate STA ID issue, we’ll do the following:
1. Create personality strings in Provisioning Services for each XenApp server
2. Put a PowerShell script on our golden image
3. Create a startup task to execute the PowerShell script

Let’s begin:

The format of the STA ID is simple. It is “STA” followed by the MAC address of the XenApp server’s NIC. The STA ID can really be anything beginning with “STA”, so you could get creative and have “STABLEFLY”, “STANK”, “STALE”, “STARTBUTTON”, “STACKOVERFLOW”.. and the list goes on. But I recommend sticking with the MAC address because it’s unique (usually), and is easy to match up.

1. In Provisioning Services, create a personality string for each server with the Name “UID” and the String “STA001122DDEEFF”, substituting the MAC address of the server for the hex I just threw in there.
Define Personality Strings

2. Copy this PowerShell script to your scripts location on your golden image: (Note: Download the file from the above link and do not copy and paste the text below, otherwise PS will complain.)

# STA Replacement Script for Citrix Provisioned Servers
# Created 7-25-11 by Ben Piper (email:, web: )
# Get UID string
# Replace STA ID
# Restart CTXHTTP service

$stastr = get-content C:\Personality.ini | Select-String -Pattern “UID=STA”
$CtxStaConfig = Get-Content ‘C:\Program Files (x86)\Citrix\system32\CtxSta.config’ | ForEach-Object {$_ -replace ‘^UID=.+$’, $stastr}
$CtxStaConfig | Set-Content ‘C:\Program Files (x86)\Citrix\system32\CtxSta.config’
Stop-Service CtxHTTP
Start-Service CtxHTTP

3. Create a scheduled task to execute the PowerShell script at startup. Make sure the account that will be executing the script has appropriate permissions.

If you are not already running PowerShell scripts, you’ll need to set the ExecutionPolicy on your gold image to Unrestricted by issuing the cmdlet ” Set-ExecutionPolicy Unrestricted” at a PS prompt.

I recommend testing the script first on your Master Target server before deploying it farm-wide. The script will still work as long as you have a personality string defined for your Master Target server, even if the vDisk is in Private mode.

How To Create XenApp Published Applications for Test In Just Seconds Using PowerShell

Prerequisite: XenApp6 PowerShell SDK

Let’s say you want to copy all currently published applications into a folder named “Test” in the console tree, while simultaneously modifying the new published apps with different permissions and client folder settings. Here’s how:

First, create the “Test” folder by hand (you can use New-XAFolder -FolderPath Applications\Test if you are so inclined), then use the following command to copy the applications into it:

get-XAApplication | Copy-XAApplication  -folderpath Applications\Test

Second, modify the published application properties to set the client folder (what folder the applications show up under in Program Neighborhood or Web Interface), and the permissions in one fell swoop. We’ll call the client folder “Test” and publish to the groups “domain1\citrix admins” and “domain2\Test Users”:

Get-XAApplication -folderpath Applications\Test | set-xaapplication -clientfolder Test -accounts "domain1\citrix admins","domain2\Test Users"

That’s it! Now doesn’t that beat right-click -> “Duplicate Application”?

Citrix XenApp6 0x80060016 Error In PowerShell

I ran into a little snag when executing some XenApp PowerShell commands. Certain commands like Get-XAFarm and Get-XAAdministrator would always give an “0x80060016” error. Here is an example and the fix:

PS C:\Windows\system32> Get-XAFarm
Get-XAFarm : Error reading the current administrator data (0x80060016)
At line:1 char:11
+ Get-XAFarm <<<<
+ CategoryInfo : InvalidResult: (:) [Get-XAFarm], CitrixException
+ FullyQualifiedErrorId : GetCitrixAdminType,Citrix.XenApp.Commands.GetFarmCmdlet

Typically this error code in Citrix indicates a problem with IMA. But in this case it was even simpler than that: IMA couldn’t resolve the hostname of the database server hosting the data store. Make sure that the correct DNS suffixes are being applied so IMA can find the server, and if that fails, just add it to the hosts file and try again.