How To - Deploy StoreFront For Citrix Virtual Apps And Desktops - HTML5 using PowerShell API

Scope

This Knowledge Base article provides you with the PowerShell commands and steps to fully deploy StoreFront for Citrix Virtual Apps And Desktops using RADIUS authentication, including configuration for HTML5 WebSocket. 

 

Note: Downloading of the ICA file is not supported when HTML5 WebSocket connections are required. The client's browser must detect the Citrix Workspace/Receiver application. If you do not require HTML5 WebSockets, use the script in the following Knowledge Base article:

How To - Deploy StoreFront For Citrix Virtual Apps And Desktops using PowerShell API

 

Requirements for Variables 

  •  Credentials for the LoadMaster bal account or another admin account
  •  Text file called storefront.txt containing your StoreFront servers. PowerShell points to this file. 
  •  Text file called servers.txt containing your VDI servers. PowerShell points to this file. 
  •  Domain name such as kemp.ax
  •  RADIUS servers
  •  RADIUS Shared Secret
  •  Citrix Store Name
  •  Citrix External FQDN
  •  Certificate Name which is found under Certificates & Security > SSL Certificates > Identifier
  •  Virtual Service IP address

 

PowerShell Documentation

For further information on the PowerShell API, refer to the PowerShell Interface Description.

You can download the wrapper from this page: LoadMaster PowerShell API Wrapper.

 

Run Script

Update variables where it says UPDATE using comments and copy all contents into a Citrix.ps1 file. The name of the file is not important. 

 


##########################
# Set LoadMaster Variables
##########################
$LoadmasterIP = "10.1.1.10" ## UPDATE - LoadMaster API IP Address (shared address if using High Availability (HA))
$KempAdmin = "bal" ## UPDATE - LoadMaster Admin Account
$KempPassword = "2fourall" ## UPDATE - LoadMaster Admin Account Password

########################################################
# Set Virtual Service Client Side SSO Variables (RADIUS)
########################################################
$RadiusServers = "10.1.1.11" ## UPDATE - RADIUS Servers IP Addresses (space-separated)
$SharedSecret = "su5PavUc" ## UPDATE - RADIUS Shared Secret
$Domain ="kemptest.com" ## UPDATE - SSO Name and SSO Domain


#################################
# Set Citrix Gateway Virtual Service Variables
#################################
$StorePath = "/Citrix/kempWeb" ## UPDATE - Citrix Store Name URL
$FQDN = "citrix.kemp.ax" ## UPDATE - External Citrix FQDN
$CertName = "kemptest" ## UPDATE - Cert Name

# CertName is located on the LoadMaster under Certificates & Security > SSL Certificates > Identifier

###########################
# Virtual Service Variables
###########################

$VirtualServiceIp = "10.1.1.12" ## UPDATE - Virtual Service IP
$VirtualServiceName = "Citrix StoreFront Gateway" ## No change required but must be unique
$VirtualServicePort = "443" ## No change required
$RealServerPort = "443" ## No change required

  

###################################################################
# Sets StoreFront Server IP Addresses
# Matrix is loaded from file "storefront.txt"
# "storefront.txt" file will contain VDI Server IP Addresses or FQDNs, one per line. 
####################################################################

$StoreFrontIp = Get-Content .\storefront.txt ##List of StoreFront Servers taken from file

###################################################################
# Sets VDI Server IP Addresses or FQDN (as per ICA file)
# Matrix is loaded from file .\servers.txt
# File lists IP addresses or FQDN for VDI servers
####################################################################

$servers = Get-Content .\servers.txt ##List of New VDI Servers taken from file

Write-Host ""
Write-Host "List of StoreFront servers:"
$StoreFrontIp
write-host ""
write-host "List of VDI serves:"
$servers
write-host ""
start-sleep -Seconds 2

 

 

##############VARIABLES CONFIGURED###############

 

##############
# Create Login
##############

$SecureString = ConvertTo-SecureString -String $KempPassword -AsPlainText -Force
$cred = New-Object -TypeName System.Management.Automation.PSCredential -ArgumentList $KempAdmin, $SecureString
$Login = Initialize-LmConnectionParameters -Address $LoadmasterIP -LBPort 443 -Credential $cred


#################################
#Creates Radius MFA Configuration
#################################
New-SSODomain -Domain $Domain
Set-SSODomain -Domain $Domain -logon_domain $Domain -auth_type RADIUS -Server $RadiusServers -radius_shared_secret $SharedSecret -logon_fmt Principalname -sess_tout_idle_pub 1800 -sess_tout_idle_priv 1800
start-sleep -Seconds 1

###############################
# Create Content Matching Rules
###############################
New-AdcContentRule -RuleName "Citrix_Auth" -MatchType regex -NoCase $true -Pattern "/^\/Citrix\/.*Auth\/.*|^\/Citrix\/.*\/CitrixAuth\/Login.*|\/Citrix\/.*\/ExplicitAuth\/AllowSelfServiceAccountManagement.*|\/Citrix\/.*\/Resources\/List.*/"
New-AdcContentRule -RuleName "Citrix_Auth_Cookie" -MatchType regex -Header Cookie -Pattern "CtxsAuthId" -NoCase $true -OnlyOnFlag 2
New-AdcContentRule -RuleName "Citrix_LMDATA_Cookie" -MatchType regex -Header Cookie -Pattern "lmdata" -NoCase $true -SetFlagOnMatch 2
New-AdcContentRule -RuleName "Citrix_LM_Auth_Proxy"-MatchType regex -NoCase $true -Pattern "/^\/lm_auth_proxy.*/"
New-AdcContentRule -RuleName "Citrix_Logout" -MatchType regex -Pattern "/^\/Citrix\/.*\/Authentication\/Logoff.*/" -NoCase $true -SetFlagOnMatch 3
New-AdcContentRule -RuleName "Citrix_Receiver_Useragent" -MatchType regex -Header User-Agent -Pattern "/^CitrixReceiver.*|CitrixWorkspace.*/"-NoCase $true
New-AdcContentRule -RuleName "Citrix_Useragent_Desktop_Receiver" -MatchType regex -Header User-Agent -Pattern "/^CitrixReceiver.*SelfService.*/"-NoCase $true -Negate $true -SetFlagOnMatch 2
start-sleep -Seconds 1


##################################
# Create Header Modification Rules
##################################
New-AdcContentRule -RuleName Citrix_AcceptEncoding -Type 2 -Pattern Accept-Encoding
New-AdcContentRule -RuleName Citrix_Browser_URL -Type 4 -Pattern /^\/$/ -Replacement $StorePath
New-AdcContentRule -RuleName Citrix_Delete_CtxAithID -Type 1 -Header Set-Cookie -Replacement "CtxsAuthId=*; expires=Thu, 14-Jun-1990 16:53:03 GMT; path=$StorePath/; secure" -OnlyOnFlag 3
New-AdcContentRule -RuleName Citrix_HTTPS -Type 1 -Header X-Citrix-IsUsingHTTPS -Replacement Yes
New-AdcContentRule -RuleName Citrix_HTTP_200_To_302 -Type 4 -Pattern "200 OK" -Replacement "301 Moved Permanently"
New-AdcContentRule -RuleName Citrix_Redirect -Type 1 -Header Location -Replacement "https://$FQDN$StorePath/"
start-sleep -Seconds 1

################################
# Create Body Modification Rules
################################
New-AdcContentRule -RuleName Citrix_GatewayAddress -Type 5 -Pattern "GatewayAddress" -Replacement "Address" -OnlyOnFlag 2 -NoCase $true
New-AdcContentRule -RuleName Citrix_SSL_On -Type 5 -Pattern "SSLEnable=Off" -Replacement "SSLEnable=On" -NoCase $true
start-sleep -Seconds 1

write-host "rules created"
write-host ""
start-sleep -seconds 2


######################################
#Create VS - Citrix StoreFront Gateway
######################################
New-AdcVirtualService -VirtualService $VirtualServiceIp -nickname $VirtualServiceName -VSPort $VirtualServicePort -VSProtocol tcp -VSType http -SSLAcceleration $true -SSLReencrypt $true -CertFile $CertName

 

##########################################
#Create VS - Citrix StoreFront Gateway - HTTP redirect
#Redirection from port 80
##########################################
New-AdcVirtualService -VirtualService $VirtualServiceIp -nickname "Citrix StoreFront Gateway - HTTP redirect" -VSPort 80 -VSProtocol tcp -VSType http
Set-AdcVirtualService -VirtualService $VirtualServiceIp -VSPort 80 -VSProtocol tcp -ErrorCode 302 -ErrorUrl https://%h%s
start-sleep -Seconds 1


############################################
#Add Rules to VS - Citrix StoreFront Gateway
############################################
New-AdcVirtualServiceRule -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp -RuleType request -RuleName Citrix_Browser_URL
New-AdcVirtualServiceRule -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp -RuleType response -RuleName Citrix_Delete_CtxAithID
New-AdcVirtualServiceRule -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp -RuleType pre -RuleName Citrix_Logout
New-AdcVirtualServiceRule -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp -RuleType pre -RuleName Citrix_LMDATA_Cookie

start-sleep -Seconds 2


#############################
# Create SubVSs
#############################

 

###################################
#SubVS-1 StoreFront Browser Auth ESP

$StoreFrontBrowserAuthESP = New-AdcSubVirtualService -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp
$StoreFrontBrowserAuthESPIndex = ($StoreFrontBrowserAuthESP.Data.VS.SubVS[-1]).VSIndex
$StoreFrontBrowserAuthESPIndex
$StoreFrontBrowserAuthESPIndexRS = $StoreFrontBrowserAuthESP.Data.VS.SubVS.RSIndex

Set-AdcSubVirtualService -SubVSIndex $StoreFrontBrowserAuthESPIndex -Persist Super -PersistTimeout 3600 -CheckPort $RealServerPort -CheckType https -CheckUrl $StorePath -CheckUse1_1 1 -Nickname "StoreFront Browser Auth ESP" -VSType http -Weight 1000
New-AdcVirtualServiceRule -VSIndex $StoreFrontBrowserAuthESPIndex -RuleType request -RuleName Citrix_HTTPS
New-AdcVirtualServiceRule -VSIndex $StoreFrontBrowserAuthESPIndex -RuleType request -RuleName Citrix_AcceptEncoding
New-AdcVirtualServiceRule -VSIndex $StoreFrontBrowserAuthESPIndex -RuleType response -RuleName Citrix_Redirect
New-AdcVirtualServiceRule -VSIndex $StoreFrontBrowserAuthESPIndex -RuleType response -RuleName Citrix_HTTP_200_To_302
start-sleep -Seconds 1

############
# Enable ESP
Set-AdcSubVirtualService -SubVSIndex $StoreFrontBrowserAuthESPIndex -ESPEnabled $true -InputAuthMode 2 -AllowedHosts $FQDN -AllowedDirectories "/*" -OutputAuthMode 2
Set-AdcSubVirtualService -SubVSIndex $StoreFrontBrowserAuthESPIndex -Domain $Domain -ServerFbaPath "$StorePath/PostCredentialsAuth/Login" -Logoff $StorePath/Authentication/Logoff

 


#################################
# Add a Real Server to the SubVS1
#################################
foreach ($SFIP in $StoreFrontIP) {
New-AdcRealServer -RealServer $SFIP -RealServerPort $RealServerPort -Enable $true -Forward nat -VSIndex $StoreFrontBrowserAuthESPIndex -Weight 1000 -Non_Local $true
}


################################
# Add Content Rule to the SubVS1
New-AdcRealServerRule -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp -RSIndex $StoreFrontBrowserAuthESPIndexRS -RuleName Citrix_LM_Auth_Proxy
New-AdcRealServerRule -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp -RSIndex $StoreFrontBrowserAuthESPIndexRS -RuleName Citrix_Logout
New-AdcRealServerRule -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp -RSIndex $StoreFrontBrowserAuthESPIndexRS -RuleName default

start-sleep -seconds 2


############################################
#SubVS-2 StoreFront Browser Launch HTML5 App
$StoreFrontBrowserLaunchHTML5App = New-AdcSubVirtualService -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp
$Index = Get-AdcVirtualService -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp
$StoreFrontBrowserLaunchHTML5AppIndex = ($Index.Data.VS.SubVS[-1]).VSIndex
$StoreFrontBrowserLaunchHTML5AppIndex
$StoreFrontBrowserLaunchHTML5AppIndexRS = ($Index.Data.VS.SubVS[-1]).RSIndex
$StoreFrontBrowserLaunchHTML5AppIndexRS

Set-AdcSubVirtualService -SubVSIndex $StoreFrontBrowserLaunchHTML5AppIndex -Persist Super -PersistTimeout 3600 -CheckPort $RealServerPort -CheckType https -CheckUrl $StorePath -CheckUse1_1 1 -Nickname "StoreFront Browser Launch HTML5 App" -VSType http -Weight 1000
New-AdcVirtualServiceRule -VSIndex $StoreFrontBrowserLaunchHTML5AppIndex -RuleType request -RuleName Citrix_AcceptEncoding
start-sleep -Seconds 1



###################################
### Add a Real Server to the SubVS2
foreach ($SFIP in $StoreFrontIP) {
New-AdcRealServer -RealServer $SFIP -RealServerPort $RealServerPort -Enable $true -Forward nat -VSIndex $StoreFrontBrowserLaunchHTML5AppIndex -Weight 1000 -Non_Local $true
}



#################################
## Add content Rule to the SubVS2
New-AdcRealServerRule -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp -RSIndex $StoreFrontBrowserLaunchHTML5AppIndexRS -RuleName Citrix_Auth_Cookie

start-sleep -seconds 2

 

##################################################
#SubVS-3 StoreFront Workspace-Receiver Add Account
$StoreFrontWorkspaceReceiverAddAccount = New-AdcSubVirtualService -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp
$Index = Get-AdcVirtualService -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp
$StoreFrontWorkspaceReceiverAddAccountIndex = ($Index.Data.VS.SubVS[-1]).VSIndex
$StoreFrontWorkspaceReceiverAddAccountIndex
$StoreFrontWorkspaceReceiverAddAccountIndexRS = ($Index.Data.VS.SubVS[-1]).RSIndex
$StoreFrontWorkspaceReceiverAddAccountIndexRS

Set-AdcSubVirtualService -SubVSIndex $StoreFrontWorkspaceReceiverAddAccountIndex -Persist Super -PersistTimeout 3600 -CheckPort $RealServerPort -CheckType https -CheckUrl $StorePath -CheckUse1_1 1 -Nickname "StoreFront Workspace-Receiver Add Account" -VSType http -Weight 1000
start-sleep -Seconds 1

###################################
### Add a Real Server to the SubVS3
foreach ($SFIP in $StoreFrontIP) {
New-AdcRealServer -RealServer $SFIP -RealServerPort $RealServerPort -Enable $true -Forward nat -VSIndex $StoreFrontWorkspaceReceiverAddAccountIndex -Weight 1000 -Non_Local $true
}


#################################
## Add content Rule to the SubVS3
New-AdcRealServerRule -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp -RSIndex $StoreFrontWorkspaceReceiverAddAccountIndexRS -RuleName Citrix_Auth


start-sleep -seconds 2

 


#################################################
#SubVS-4 StoreFront Workspace-Receiver Launch App
$StoreFrontWorkspaceReceiverLaunchApp = New-AdcSubVirtualService -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp
$Index = Get-AdcVirtualService -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp
$StoreFrontWorkspaceReceiverLaunchAppIndex = ($Index.Data.VS.SubVS[-1]).VSIndex
$StoreFrontWorkspaceReceiverLaunchAppIndex
$StoreFrontWorkspaceReceiverLaunchAppRS = ($Index.Data.VS.SubVS[-1]).RSIndex
$StoreFrontWorkspaceReceiverLaunchAppRS

Set-AdcSubVirtualService -SubVSIndex $StoreFrontWorkspaceReceiverLaunchAppIndex -Persist Super -PersistTimeout 3600 -CheckPort $RealServerPort -CheckType https -CheckUrl $StorePath -CheckUse1_1 1 -Nickname "StoreFront Workspace-Receiver Launch App" -VSType http -Weight 1000
New-AdcVirtualServiceRule -VSIndex $StoreFrontWorkspaceReceiverLaunchAppIndex -RuleType pre -RuleName Citrix_Useragent_Desktop_Receiver
New-AdcVirtualServiceRule -VSIndex $StoreFrontWorkspaceReceiverLaunchAppIndex -RuleType request -RuleName Citrix_AcceptEncoding
start-sleep -Seconds 1

##################################
### Add a Real Server to the SubVS4
foreach ($SFIP in $StoreFrontIP) {
New-AdcRealServer -RealServer $SFIP -RealServerPort $RealServerPort -Enable $true -Forward nat -VSIndex $StoreFrontWorkspaceReceiverLaunchAppIndex -Weight 1000 -Non_Local $true
}


#################################
## Add content Rule to the SubVS4
New-AdcRealServerRule -VirtualService $VirtualServiceIp -VSPort $VirtualServicePort -VSProtocol tcp -RSIndex $StoreFrontWorkspaceReceiverLaunchAppRS -RuleName Citrix_Receiver_Useragent


write-host ""
write-host "Sub Virtaul Services and rules created"
start-sleep -seconds 2

 

##################################
# Create VDI 2598 Secure Listeners
##################################
$citrix_starting_index = 1
$citrix_vs_starting_port = 4431
$citrix_vs_name ="Citrix_Workspace_VDI_"
$RealServerPort ="2598"

$VSIndex = Get-AdcVirtualService -VirtualService $VirtualServiceIp -VSPort 443 -VSProtocol tcp
$SubVSIndex = ($VSIndex.Data.VS.SubVS[-1]).VSIndex

 


for ($i=0; $i -lt $servers.Count; $i++)
{

$RuleName = $citrix_vs_name + ($citrix_starting_index + $i)
$Port = $citrix_vs_starting_port + $i
$Pattern = "Address=" + $servers[$i] + ":1494"
$Replacement = "SSLProxyHost=" + $FQDN + ":" + $Port

echo $RuleName
echo $Port

### Create new Virtual Service Secure Listeners
New-AdcVirtualService -VirtualService $VirtualServiceIp -nickname $RuleName -VSPort $Port -VSProtocol tcp -VSType http -SSLAcceleration $true -SSLReencrypt $false -CertFile $CertName -CheckType none

### Add Real Server to VS
New-AdcRealServer -RealServer $servers[$i] -RealServerPort $RealServerPort -Non_Local 1 -Enable $true -Forward nat -Weight 1000 -VirtualService $VirtualServiceIp -VSPort $Port -VSProtocol tcp

### Create new ICA Rewrite Rules
New-AdcContentRule -RuleName $RuleName -Type 5 -Pattern $Pattern -Replacement $Replacement -NoCase 1

### Add new ICA Rules to SubVS
New-AdcVirtualServiceResponseBodyRule -VSIndex $SubVSIndex -RuleName $RuleName
}

 

### New rules need to be promoted. To do so, Remove and re-add the below two rules.
Remove-AdcVirtualServiceResponseBodyRule -VSIndex $SubVSIndex -RuleName Citrix_GatewayAddress -Confirm:$false
Remove-AdcVirtualServiceResponseBodyRule -VSIndex $SubVSIndex -RuleName Citrix_SSL_On -Confirm:$false

New-AdcVirtualServiceResponseBodyRule -VSIndex $SubVSIndex -RuleName Citrix_GatewayAddress
New-AdcVirtualServiceResponseBodyRule -VSIndex $SubVSIndex -RuleName Citrix_SSL_On


write-host ""
write-host "VDI Listeners created and rules assigned"
start-sleep -seconds 4

 


########################################
# Create VDI HTML5 8008 Secure Listeners
########################################

$citrix_vs_starting_port = $Port + 1
$citrix_vs_name ="Citrix_HTML5_VDI_"
$RealServerPort ="8008"
$servers = Get-Content .\servers.txt ##List of VDI Servers taken from file
$VSIndex = Get-AdcVirtualService -VirtualService $VirtualServiceIp -VSPort 443 -VSProtocol tcp
$SubVSIndex = ($VSIndex.Data.VS.SubVS[-3]).VSIndex

 


for ($i=0; $i -lt $servers.Count; $i++)
{

$RuleName = $citrix_vs_name + ($citrix_starting_index + $i)
$Port = $citrix_vs_starting_port + $i
$Pattern = "Address=" + $servers[$i] + ":1494"
$Replacement = "SSLProxyHost=" + $FQDN + ":" + $Port
echo $RuleName
echo $Port

### Create new Virtual Service Secure Listeners
New-AdcVirtualService -VirtualService $VirtualServiceIp -nickname $RuleName -VSPort $Port -VSProtocol tcp -VSType http -SSLAcceleration $true -SSLReencrypt $false -CertFile $CertName -CheckType none

### Add Real Server to VS
New-AdcRealServer -RealServer $servers[$i] -RealServerPort $RealServerPort -Non_Local 1 -Enable $true -Forward nat -Weight 1000 -VirtualService $VirtualServiceIp -VSPort $Port -VSProtocol tcp

### Create new ICA Rewrite Rules
New-AdcContentRule -RuleName $RuleName -Type 5 -Pattern $Pattern -Replacement $Replacement -NoCase 1

### Add new ICA Rules to Sub VS
New-AdcVirtualServiceResponseBodyRule -VSIndex $SubVSIndex -RuleName $RuleName
}

 

### Create new Virtual Service Secure Listeners
New-AdcVirtualService -VirtualService $VirtualServiceIp -nickname $RuleName -VSPort $Port -VSProtocol tcp -VSType http -SSLAcceleration $true -SSLReencrypt $false -CertFile $CertName -CheckType none

### Add Real Server to Virtual Service
New-AdcRealServer -RealServer $servers[$i] -RealServerPort $RealServerPort -Non_Local 1 -Enable $true -Forward nat -Weight 1000 -VirtualService $VirtualServiceIp -VSPort $Port -VSProtocol tcp

### Create new ICA Rewrite Rules
New-AdcContentRule -RuleName $RuleName -Type 5 -Pattern $Pattern -Replacement $Replacement -NoCase 1

### Add new ICA Rules to SubVS
New-AdcVirtualServiceResponseBodyRule -VSIndex $SubVSIndex -RuleName $RuleName
}

### New rules need to be promoted. To do so, Remove and re-add the below two rules.
Remove-AdcVirtualServiceResponseBodyRule -VSIndex $SubVSIndex -RuleName Citrix_GatewayAddress -Confirm:$false
Remove-AdcVirtualServiceResponseBodyRule -VSIndex $SubVSIndex -RuleName Citrix_SSL_On -Confirm:$false

New-AdcVirtualServiceResponseBodyRule -VSIndex $SubVSIndex -RuleName Citrix_GatewayAddress
New-AdcVirtualServiceResponseBodyRule -VSIndex $SubVSIndex -RuleName Citrix_SSL_On

write-host ""
write-host "HTML5 Listeners created and rules assigned"

write-host ""
write-host "Script completed"

Was this article helpful?

0 out of 0 found this helpful

Comments