# -*- coding: utf-8 -*-
from setuphelpers import *
import time
r"""
Usable WAPT package functions: install(), uninstall(), session_setup(), audit(), update_package()
Citrix Receiver 4.12 reached End-of-life in December 2019 -
https://www.citrix.com/support/product-lifecycle/workspace-app.html
CitrixReceiver.exe /?
Paramètres pris en charge :
/help - Affiche ces informations d'utilisation
/uninstall - Supprime une installation existante
/silent - Supprime toutes les interfaces utilisateur graphiques
/noreboot - Supprime tous les redémarrages et invites de redémarrage
/preview - Affiche un aperçu des modifications sans modifier la machine
/extract <dossier> - Extrait un pack auto-extractible sur un dossier existant
/includeSSON - Installe le composant Single Sign-On pour l'ouverture de session unique au domaine
/EnableCEIP - Active (true) ou désactive (false) le Programme Citrix d'amélioration de la satisfaction client (CEIP)
/AutoUpdateCheck - Active la mise à jour automatique (auto), active la mise à jour manuelle (manual), interdit la mise à jour automatique (disabled)
/AutoUpdateStream - Spécifie le cycle de mise à jour automatique : Long Term Service Release (LTSR) ou Short Term Service Releases (Current)
/DeferUpdateCount - Spécifie le nombre de fois qu'il est possible de différer la mise à jour automatique
Les valeurs de propriété MSI sont prises en charge et doivent être séparées par des espaces, par ex. :
PROPERTY="Valeur" PROPERTY2="Valeur2"
Exemple de ligne de commande silencieuse utilisant toutes les valeurs par défaut :
CitrixReceiver.exe /silent
Exemple de ligne de commande spécifiant de multiples options :
CitrixReceiver.exe /silent ADDLOCAL="ReceiverInside,ICA_Client,USB,DesktopViewer,Flash,Vd3d,WebHelper" INSTALLDIR="C:\mondossier" ENABLE_DYNAMIC_CLIENT_NAME="No" CLIENT_NAME="mon_nom_remplacé" DEFAULT_NDSCONTEXT="Contexte1,Contexte2"
Exemple de ligne de commande pour activer l'authentification unique au domaine :
CitrixReceiver.exe /silent /includeSSON ADDLOCAL="ReceiverInside,ICA_Client,SSON,USB,DesktopViewer,Flash,Vd3d,WebHelper" INSTALLDIR="C:\mondossier" ENABLE_DYNAMIC_CLIENT_NAME="No" CLIENT_NAME="mon_nom_remplacé" DEFAULT_NDSCONTEXT="Contexte1,Contexte2"
Exemple de ligne de commande pour installer le serveur Single Sign-On mais pour désactiver la capture des informations d'identification d'ouverture de session :
CitrixReceiver.exe /includesson LOGON_CREDENTIAL_CAPTURE_ENABLE=No [valeur par défaut Yes]
Exemple de ligne de commande pour installer Receiver en mode non autonome
CitrixReceiver.exe SELFSERVICEMODE = false [la valeur par défaut est true]
Exemple de ligne de commande destinée à prendre en charge la mise à niveau de versions non prises en charge vers la dernière version
CitrixReceiver.exe /RCU
Exemple de ligne de commande pour désactiver le programme CEIP :
CitrixReceiver.exe /EnableCEIP=false [la valeur par défaut est true]
Exemple de ligne de commande pour activer la mise à jour manuelle :
CitrixReceiver.exe /AutoUpdateCheck=manual [valeur par défaut = auto]
Exemple de ligne de commande pour désactiver la mise à jour automatique :
CitrixReceiver.exe /AutoUpdateCheck=disabled
Exemple de ligne de commande pour choisir un cycle Long Term Service Release :
CitrixReceiver.exe /AutoUpdateStream=LTSR
Exemple de ligne de commande pour différer la mise à jour automatique à 2 reprises :
CitrixReceiver.exe /DeferUpdateCount=2
[Appuyez sur Entrée pour fermer cette fenêtre.]
"""
# Declaring global variables - Warnings: 1) WAPT context is only available in package functions; 2) Global variables are not persistent between calls
bin_name = "CitrixReceiver.exe"
silentflags = "/AutoUpdateCheck=disabled /EnableCEIP=false /silent /noreboot"
app_uninstallkey = "CitrixOnlinePluginPackWeb"
# app_dir = makepath(programfiles32, 'Citrix', 'ICA Client')
app_name = "Citrix Reveiver"
installer_process_list = ["TrolleyExpress", "CitrixReceiver"]
def install():
# Initializing variables
package_version = control.version.split("-", 1)[0]
# Uninstalling older versions of the software
for to_uninstall in installed_softwares(uninstallkey=app_uninstallkey):
if Version(to_uninstall["version"]) < Version(package_version) or force:
print("Removing: %s (%s)" % (to_uninstall["name"], to_uninstall["version"]))
killalltasks(installer_process_list)
killalltasks(control.impacted_process.split(","))
# run(uninstall_cmd(to_uninstall["key"]))
run_notfatal('"%s" %s' % (bin_name, "/uninstall /silent /noreboot"))
wait_uninstallkey_absent(to_uninstall["key"])
# Installing the package
print("Installing: %s (%s)" % (bin_name, package_version))
install_exe_if_needed(
bin_name,
silentflags=silentflags,
key=app_uninstallkey,
min_version=package_version,
)
# Avoiding the usage by WAPT of the app built-in Uninstallstring
uninstallkey.remove(app_uninstallkey)
# Disable Telemetry (procedure: https://docs.citrix.com/en-us/hdx-optimization/2-4-ltsr/overview.html)
if iswin64():
registry_set(HKEY_LOCAL_MACHINE, r"SOFTWARE\WOW6432Node\Citrix\ICA Client\CEIP", "Enable_CEIP", 0)
else:
registry_set(HKEY_LOCAL_MACHINE, r"SOFTWARE\Citrix\ICA Client\CEIP", "Enable_CEIP", 0)
def audit():
# Declaring local variables
package_version = control.version.split("-", 1)[0]
# Getting installed software version
if installed_softwares(uninstallkey=app_uninstallkey):
installed_version = installed_softwares(uninstallkey=app_uninstallkey)[0]["version"]
else:
installed_version = None
# Auditing software
print("Auditing: %s" % control.package)
if installed_version is None:
print("%s is not installed" % (app_name, installed_version))
return "ERROR"
elif Version(installed_version) != Version(package_version):
print("%s is installed in version (%s) instead of (%s)" % (app_name, installed_version, package_version))
return "WARNING"
else:
print("%s is installed in correct version (%s)" % (app_name, installed_version))
return "OK"
def uninstall():
# Uninstalling the software
for to_uninstall in installed_softwares(uninstallkey=app_uninstallkey):
print("Removing: %s (%s)" % (to_uninstall["name"], to_uninstall["version"]))
killalltasks(control.impacted_process.split(","))
run(uninstall_cmd(to_uninstall["key"]) + ["/silent"])
wait_uninstallkey_absent(to_uninstall["key"])
def update_package():
# Declaring local variables
result = False
# Checking version from file
version = get_version_from_binary(bin_name, property_name="FileVersion")
# Changing version of the package
if Version(version) > Version(control.get_software_version()):
print("Software version updated (from: %s to: %s)" % (control.get_software_version(), Version(version)))
result = True
else:
print("Software version up-to-date (%s)" % Version(version))
control.version = "%s-%s" % (Version(version), control.version.split("-", 1)[-1])
# control.set_software_version(version)
control.save_control_to_wapt()
# Validating update-package-sources
return result
def get_version_from_binary(filename, property_name="ProductVersion"):
r"""Get installer version from file informations, for now, only exe and msi files are compatibles
Args:
filename (str): path to the file
property_name (str): selected property
Returns:
str: version number
"""
if filename.endswith(".msi"):
return get_msi_properties(filename)[property_name]
else:
return get_file_properties(filename)[property_name]
def wait_uninstallkey_absent(key=None, max_loop=120, keywords=None, name=None, raise_on_timeout=False):
if len([f for f in [key, keywords, name] if f]) > 1:
error("Arguments conflict key: %s keywords: %s name: %s" % (key, keywords, name))
if key:
searchparam = "key: %s" % str(key)
elif name:
searchparam = "name: %s" % str(name)
else:
searchparam = "keywords: %s" % str(keywords)
print("Waiting for the removal of %s from Windows registry" % searchparam)
loop = 0
while uninstall_key_exists(key, keywords=keywords, name=name):
loop += 1
if loop > max_loop:
if raise_on_timeout:
error("timeout after %s seconds" % max_loop)
else:
return "timeout after %s seconds" % max_loop
time.sleep(1)