App-V: Adding Additional Languages to Office 2010 Packages (. . . and pre-setting the Outlook Default Language)
Here is the scenario: You have gone through the trouble of sequencing Office 2010 with either 4.6 or 5.0 and you have it working like a champ. You then get a call. “We need this also deployed for our users in <FILL_IN_THE_BLANK_NATION_THAT_REQUIRES A DOUBLE BYTE CHARACTER SET>. Did I mention we need it by the end of the week [It is Thursday, by the way.]
Don’t panic. Adding an additional language pack is a pretty straight forward process as long as the sequencing workstation is set up properly in advance. You will also have to do some additional tweaking to get yourself out of a “chicken/egg” scenario if you want the “Outlook Startup” to now be in a different localized language. Since we cannot open up Outlook to change the default input and display languages, this will need to be applied through registry imports.
Enabling OS Language Support on the Sequencer
First Add the OS Language Support on the Sequencer. This can be done easily using the “Region and Language” Control Panel in Windows 7
For more specific information on how to change/add languages in Windows 7, please refer to this link: http://windows.microsoft.com/en-US/windows7/Add-or-change-an-input-language
With Windows 8 this is done in the “Language Control Panel.”
For more information on how to change/add languages in Windows 8, please refer here: http://support.microsoft.com/kb/2607607
Office 2010 Language Files
Now you will need the supporting language files for Office 2010. This will require you have the files at the ready on or attached to the sequencer as well as the locale XML configuration file. You will then re-run setup with the /config switch pointing to the locale configuration file. For example, if you were applying the Japanese language support files to the existing office package you would only need the *.ja-jp directories and the ja-jp.xml file.
Custom Registrations
Outlook Display Language, Help Language, and Editing Language changes can either occur after the user has run Outlook in the default English (and makes the modifications post deployment) or before the fact. In this particular scenario, you already have a virtualized office package that was English-only. If you desire that the automatic startup language for existing and new Outlook profiles be already configured to default to another language for the display, help, and editing language, you will need to include some custom registrations in order to change the language. You will first need to know the decimal and hex equivalents of the LCID structure. You can look those up using the following reference:
http://msdn.microsoft.com/en-us/library/cc233968.aspx
For example, English is 0x409 in hex (1033 in decimal.) if you were wanting use Japanese instead, it would be 0x411 (or 1041 in decimal.) You will then need to ensure that the following registry keys are set to that specific LCID during sequencing:
- Key: HKEY_CURRENT_USERSoftwareMicrosoftOffice14.0Outlook
Value: LastUILanguage
Data Type: REG_DWORD
Data (hex): <LCID Code in Hex> - Key: HKEY_CURRENT_USERSoftwareMicrosoftOffice14.0OutlookOptionsGeneral
Value: LastUILang
Data Type: REG_DWORD
Data (hex): <LCID Code in Hex> - Key: HKEY_CURRENT_USERSoftwareMicrosoftOffice14.0CommonLanguageResources
Value: UILanguage
Data Type: REG_DWORD
Data (hex): <LCID Code in Hex> - Key: HKEY_CURRENT_USERSoftwareMicrosoftOffice14.0CommonLanguageResources
HelpLanguage
Data Type: REG_DWORD
Data (hex): <LCID Code in Hex> - Key: HKEY_CURRENT_USERSoftwareMicrosoftOffice14.0CommonLanguageResources
InstallLanguage
Data Type: REG_DWORD
Data (hex): <LCID Code in Hex> - Key: HKEY_CURRENT_USERSoftwareMicrosoftOffice14.0CommonLanguageResources
OutlookChangeInstallLanguage
Data Type: REG_SZ
Data: Yes - Key: HKEY_CURRENT_USERSoftwareMicrosoftOffice14.0CommonLanguageResources
Value: FollowSystemUI
Data Type: REG_SZ
Data: Off
Procedure for Modifying Sequence
Whether you are using App-V 4.6 or 5.0, the process is the same. You will need to open the existing application virtualization package using the procedure to “Add new application.”
This will invoke the monitoring phase. During monitoring, you will need to first run the command to add in the language files. For example, if you were to add support for the Japanese language files, you would type the following command:
setup.exe” /config ja-jp.xml
This would then install the native Japanese language files for office 2010.
Following that, you would need to add in the registrations. What I usually do is put all of them into a REG file and import them from the command prompt during sequencing. For example, if I were to import defaults for the Japanese language interface, I would import the reg file below:
Windows Registry Editor Version 5.00
[HKEY_CURRENT_USERSoftwareMicrosoftOffice14.0Outlook]
“LastUILanguage”=dword:00000411
[HKEY_CURRENT_USERSoftwareMicrosoftOffice14.0OutlookOptionsGeneral]
“LastUILang”=dword:00000411
[HKEY_CURRENT_USERSoftwareMicrosoftOffice14.0CommonLanguageResources]
“UISnapshot”=hex(7):31,00,30,00,33,00,33,00,3b,00,31,00,30,00,34,00,31,00,00,
00
“UIFallback”=hex(7):31,00,30,00,34,00,31,00,3b,00,30,00,3b,00,31,00,30,00,33,
00,33,00,00,00
“HelpFallback”=hex(7):31,00,30,00,34,00,31,00,3b,00,30,00,3b,00,31,00,30,00,33,
00,33,00,00,00
“UILanguage”=dword:00000411
“HelpLanguage”=dword:00000411
“InstallLanguage”=dword:00000411
“OutlookChangeInstallLanguage”=”YES”
“FollowSystemUI”=”Off”
Upon completion of these two procedures, I would then save the package and proceed to test.
Come See Me at TechEd 2013 North America!
TechEd 2013 North America is 6/2 through 6/6 in New Orleans!
http://northamerica.msteched.com/?mtag=TENAC9TEPage
I’ll be there and I hope to see you there too! Alfred Ojukwu, Henry Schulman, and myself will be there from MCS presenting two sessions on App-V 5.0:
Sequencing Applications Using the New Microsoft Application Virtualization 5.0 Sequencer
https://channel9.msdn.com/Events/TechEd/NorthAmerica/2013/WCA-B205#fbid=UNR8sVE6CJM
June 5, 2013 from 3:15PM to 4:30PM
Integrating the New Microsoft Application Virtualization 5.0 with other Virtualization Solutions
https://channel9.msdn.com/Events/TechEd/NorthAmerica/2013/WCA-B324#fbid=UNR8sVE6CJM
June 6, 2013 from 8:30AM to 9:45AM
In addition, I’ll be manning the MDOP and Desktop Virtualization booths periodically through the week so feel free to stop by!
MED-V: To Cache Credentials or to not Cache Credentials (Ramifications of Disabling “DisablePasswordSaving” vs. Enabling it)
How’s that for a double negative? Disabling the disabling of password saving. In essence, allowing users to cache/save passwords for SSO (single-sign-on) when authenticating to MED-V workspaces. In MED-V, if the credentials do not match, or you do not check the box to have your credentials
remembered, you are presented with the standard RDP prompt for access to the virtual machine.
This is not to be confused with the initial MED-V prompt for authentication (first appearing during first-time-setup) which looks like this:
Both RDP and MED-V can allow for the caching of credentials, however, while MED-V only temporarily caches credentials in memory, RDP will cache using the Credential Manager. The MED-V authentication mirrors that of RDP in that the Windows 7 host is connecting via RDP to the Windows XP virtual
machine. Depending on how you have configured MED-V settings for authentication, the end user is typically prompted at some point to enter their password, either the first time MED-V is started or the first time that they try to open a published application. If LogonStartEnabled has been configured,
it will happen when MED-V starts in the user session. Otherwise, it will occur when you first launch a published MED-V application. Caching credentials seems like it would make sense as it does improve the user experience, but there are trade-offs.
Unintended Inconvenience
- If the user accidentally mistypes their credentials in the logon dialog and specifies to cache them, the incorrect credentials are saved and the user will be prompted to re-enter their credentials each time the VM is started or resumed. This state will persist until the user credentials are manually cleared.
- If the user selects to cache their password and later the password expires or credentials domain name has been renamed, the user will be prompted to re-enter their credentials each time the VM is started or resumed until the cached password is cleared.
MED-V has a special credential manager that helps to avoid the above inconvenience. It allows you to control aspects of credential caching including:
- Whether the credentials the end user enters are stored in Credential Manager.
- In what manner the end user is presented with the option of entering and saving their password. For example, if MED-V is configured to start when the end user logs on to the host but Authentication is disabled, the end user is only prompted one time during logon. In this case, credentials are valid until the end user logs off from the host. If it is necessary, you can use Credential Manager to remove any stored end-user credentials. By default, credential storing is disabled, but you can change this setting either before or after workspace deployment.
Pre MED-V Workspace Deployment
While you are creating the MED-V workspace package, you can modify the PowerShell (though the New-MedvConfiguration cmdlet) by setting the UxCredentialCachingEnabled to either 1 or 0. This simply tells MED-V whether or not the “Remember My Credentials” will be in place for MED-V FTS and RDP
authentication prompts.
After MED-V Workspace Deployment
The MED-V Credential component cannot override the Group policy Remote Desktop Connection Client “Do not allow passwords to be saved” value. This is represented in the registry by the DisablePasswordSaving value. One way you can set this post-deployment is by modifying this policy. This policy controls whether the password saving check box appears on the RDP client dialog window and whether the MED-V credential prompt is displayed.
My favorite way of disengaging credential caching altogether is by changing the UxCredentialCacheEnabled in WMI to FALSE.
The WMIC command easily can do this:
WMIC /namespace:\rootMicrosoftMedv PATH setting set uxCredentialCacheEnabled=FALSE
After that, the option to save the password will no longer be available:
If you also want to manually leverage the RDP policy to DisablePasswordSaving, you can do so by going to the following registry key:
HKEY_LOCAL_MACHINESOFTWAREMicrosoftVirtual MachinePoliciesDisablePasswordSaving
Play it Safe
While users prefer caching the credentials to avoid retyping in the credentials, there are risks associated with doing so. When credential caching is enabled, the end user’s password is stored in a reversible format through CredMan (the Windows Credential Manager.) This opens up the user to potential issues should a
malicious program somehow get on to that system and is able to run as SYSTEM. The credentials could then be retrieved. The only way to reduce this exposed surface area is by setting DisablePasswordSaving to Enabled and modifying the UxCredentialCacheEnabled property.
App-V and CM 2012: GRRRRRRRR! Where did “Remove this virtual application when it is no longer advertised” go!?!?!?
With Configuration Manager 2007 Integration in App-V 4.6, there was a very popular feature that allowed for what we refer to as “implicit uninstall.” This means that when a user is no longer part of collection, the virtual applications advertised to them would then be removed. This was very easy to configure by selecting “Remove this virtual application when it is no longer advertised” when importing the virtual application. This meant the client would uninstall the virtual application if they are removed from the target collection.
This exact feature is not implemented this exact same way with Configuration Manager 2012. The APP-V 5/Configuration Manager 2012 Integration whitepaper has been updated to include a methodology for achieving this same effect through custom collections – both through the console or through WQL.
Page 30 of the updated Configuration Manager White Paper discusses this:
App-V: Process Exit Codes and why they matter when troubleshooting virtual applications
In a previous blog post (http://blogs.technet.com/b/gladiatormsft/archive/2013/04/27/on-the-art-of-troubleshooting-app-v-applications.aspx) I discussed the “art” of troubleshooting virtual applications and mentioned the fact that there are a lot of custom recipe’s out on the Internet (many courtesy of our own MVP’s.) People ask me how they figure these out. My answer is usually along the lines of “they troubleshot/revered engineered/mangled though until they came up with something that worked.” We know the next question: How do you learn to do that? To keep my promise in helping people to *LEARN* to troubleshoot virtual applications, I have been working on scenarios using real-world applications. I figured a good place to start was using an application that fails and leaves NO error message whatsoever. This is a good way to demonstrate the use of Process Monitor to track process exit codes in order to resolve issues.
The application we will be looking at is Google Chrome 15 sequenced with App-V 5. I chose this one because it is really easy to create a bad sequence (using the Google Enterprise Installer.) All you do is during monitoring – is accept all defaults (click – next – next – next etc.) Now if you ever have had to sequence Google Chrome and did your research on the Internets, you have found many complicated recipes for Google Chrome. My favorite is Aaron Parker’s (an APP-V MVP) 4.6 recipe: http://stealthpuppy.com/virtualisation/sequencing-google-chrome-15/ (Yes, I am a fan of the stealth puppy.) It is one of the many examples of one of our solid MVP’s sharing quality APP-V packaging information to prevent others from having to reinvent the wheel.
If you would like to follow along and try this at home, download the Google Chrome 15 Enterprise Installer (http://www.google.com/chrome/eula.html?msi=true) – sequence it accepting all defaults on a clean sequencer template (default exclusions) and enjoy the troubleshooting!
Symptom: I double-clicked on the virtual application – AND NOTHING HAPPENS!
So this is the issue. You have virtualized an application(Google Chrome 15) with App-V 5 and it adds/publishes successfully. However, when you go to launch the application, nothing happens. You may notice the process starts in Task Manager but then disappears. A not so nice silent exit with NO error message whatsoever. Now is a good time to break out Process Monitor and capture a simple reproduction of the launch and subsequent silent exit.
Process Exit Codes
So whenever you get strange exits or “lack of launch” with no error – your best recourse is to try to find out why those key processes exited. This time we are going to take advantage of the fact that Process Monitor tracks exit codes.
First, inventory the EXE’s with Chrome. You can do it with a local install or view the shortcut to the EXE to get the main executable. (In 4.6, you would look in the OSD file.) The key EXE’s I find with Google Chrome are CHROME.EXE and GOOGLEUPDATE.EXE.
Now, capture the issue with Process Monitor. Once you have captured the session, you will want to apply a display filter for the following operations:
– Process Start
– Process Exit
Apply the filter and start from the beginning. Well look! Not a lot of events! This is much easier to walk through.
The WMIPRVSE.exe is noise (WMI background process) but notice that in addition to the CHROME.EXE process, there is a “GOOGLEUPDATE.EXE” process. What is interesting is that the shortcut I clicked on was supposed to load the CHROME.EXE process. This will cause me to want to look at Parent PIDs to see what spawned what because for some strange reason, the GOOGLEUPDATE.EXE process started before the CHROME.EXE process. The chrome.exe process was spawned by Parent PID 832 – which turns out to be EXPLORER.EXE. GOOGLEUPATE.EXE appears to have been spawned by PID 1620 which is the AppVClient.exe process.
Looking at the command details for GoogleUpdate.exe, it begins to make sense – GoogleUpdate is a service process (GoogleUpdate.exe/svc) so it was captured as a virtual service therefore it must start before the application does. One of the many reasons why the App-V virtualization engine hooks CreateProcess.
You can add the “Create Process” operation to your filter and you can see Process Create events which is an easier way of looking at who spawned who.
In the detail we see Exit Status codes from both processes when they exit. If the exit status is 0, the process exited normally. If the exit status is a simple number, you can often look these up with the NET HELPMSG command.
I usually work these from the bottom up. Chrome.EXE exited with a status code of 6.
That is an invalid handle. The GoogleUpdate.exe process exited with a numerical representation of an HREF (which is better to understand once converted to hex.)
Convert -2147024894 to hex and you get 0x80070002. That’s a well-known HREF
HINT – download this conversion tool – http://www.microsoft.com/en-us/download/details.aspx?id=985
It says Exchange but it will resolve standard Windows API HREF codes as well. The above resolves to ERROR_FILE_NOT_FOUND. At this point, it is time to reset the filter and create a new filter where we include the process name GOOGLEUPDATE.exe and exclude success. Then exclude NAME_NOT_FOUND
(noise.) Look for PATH_NOT_FOUND. Well what do you know? There it is!
And now we have to reset the filter to make sure there were no additional success events (due to path searching and alternate location searches.)
Looking at the last one registering a PATH_NOT_FOUND, unlike the previous ones where additional searches found the intended file, the attempt to create several files beneath the update folder did not. Verifying this in the package directory, we see the file is not there. By default, on a local install, the file is not there. However upon first launch when the Google Update service runs the files are downloaded successfully.
What are your Options Now?
At this point, there are a few paths we can take:
Add in those missing files? Adding in those missing files will generate the same results because there is a check from the application to download the most up-to-date binaries for the update engine. Process Monitor revealed the same ERROR_FILE_NOT_FOUND exit code.
Disable Virtual Services? You can disable virtual services altogether in either the deployment_config.xml file (for the application) or you can disable the virtual services in the registry (quick way is [reg add HKLMSoftwareMicrosoftAppVSubsystemDisable /v “Virtual Services /t REG_DWORD /d 1 ) client-wide.
NOTE:Upon disabling virtual services – the ISSUE STILL REMAINED. Again since the symptom is the same – I go back to the exit codes with process Monitor. This time, the GOOGLEUPDATE.EXE process did not start as desired.
Yet this time chrome still failed because of the bad handle issue. So simply taking the update component out of the sequence is not good enough. You need to be able to configure the application not to auto-update (if possible.) This goes back to the “knowing of your application” principle.
Application Disabling/Sequencing Exclusion of the Particular Service
If disabling the service through the App-V subsystem is not successful, you can still virtualize the application with App-V if there is a mechanism within the application to disengage the service altogether. To be honest, this is the best way, otherwise, the application will treat the service as a dependency for functionality. In the case of Google Chrome, you can disable this through the following registry key:
Path: HKEY_LOCAL_MACHINESOFTWAREPoliciesGoogleUpdate
Value: AutoUpdateCheckPeriodMinutes
Data Type: REG_SZ
Data: 0
In addition you will want to add in a directoryVFS exclusion for the [{ProgramFiles}]GoogleUpdate directory.
So I hope this was able to shed some light on how you get from a default-installation-based failed sequence to a working one through the use of a good reverse engineering tool. Of course, don’t forget to share your success stories in the form of recipes. You can do this on the App-V Sequencing Recipe forum here: http://social.technet.microsoft.com/Forums/en-US/prescriptiveguidance/threads
MCS is Hiring: Especially in Virtualization!
Microsoft Consulting Services is sponsoring a career webinar on Tuesday 5/21 from 5:00pm – 6:00pm Central time. This event is free of charge and is targeted towards potential delivery candidates. We are focusing on Identity Management, Desktop Delivery and Virtualization
however all strong delivery candidates will be considered and welcome to attend (Engagement Managers, Sales, Program Mangers and Delivery Consultants with profiles others than what was previously mentioned). The call is in partnership with our staffing team and will feature three of our delivery consultants sharing their “Day In The Life” stories. Guess What! I am one of them.
Register Here: http://bit.ly/17pNdYp
App-V 5: MSI Wrapper Caveats (Oh, and App-V WMI classes are different in 5.0)
For those enterprises using 3rd-party ESD (Electronic Software Distribution) products to deploy and manage software, use of the MSI-wrapper makes it easy to incorporate these types of applications into their environments. In App-V, when you “install” a virtual application using the MSI wrapper, all that is being done are custom actions that add and publish the package globally to all users on that machine. In addition, it will place an entry in the “Program and Features” list (formerly Add/Remove Programs.) This entry in the programs list is pretty much the difference between using the MSI to publish the application instead of manually using the PowerShell AppV cmdlets. Because of this entry, it is also advised to always use the programs list (or the msiexec /uninstall command) to remove the application instead of the manual PowerShell commands in order to prevent an orphaned entry from remaining.
It is also important to note that the MSI checks are more resilient in v5, where if you try to uninstall an application that is currently in use, it will echo a 0200000508 error:
Following the warning, the uninstallation stops, the package will remain and the entry will remain in the programs list. This is different from 4.6 where the entry would get removed while the virtual application would remain published and you would have to manually remove the application using SFTMIME cleanup commands. The specific error in 4.6 would be:
The Application Virtualization Client could not complete the operation.
The operation failed to complete because the package is still in use. Report the following error code to your System Administrator
Error code: xxxxxx-xxxxxx04-00001808
In 4.6, once you got the 1808 error, at this point you had to remove the application using the manual SFTMIME command (SFTMIME DELETE PACKAGE) http://technet.microsoft.com/en-us/library/cc843829.aspx
If you are using a 3rd-party ESD (Electronic Software Distribution) product to manage applications, you can query the WMI namespace for App-V to determine if a package is still in use in order to prevent this from happening.
If the package is indeed in use, you can then use the Stop-AppVClientPackage and/or Stop-AppVClientConnectionGroup cmdlet although the standard caveats apply with regards to open documents and unsaved information.
Speaking of WMI
In V5, the WMI classes are now located in a different namespace (rootappv) and the classes have been expanded to align with PowerShell objects. The classes are:
- AppVClientPackage
- AppVClientApplication
- AppVClientConnectionGroup
You can use PowerShell, VBScript, WMIC, or native/managed code to query WMI to get information about virtual applications, packages, and connection groups. For example, you can inventory packages using these PowerShell commands:
$VPackages = Get-WmiObject -Class AppvClientPackage -Namespace rootappv
$VPackages | Format-List -Property Name, InUse, PercentLoaded
What is really great about App-V 5.0’s WMI is the inclusion of Connection groups which allows extensibility for management of not only applications, but super-bubbles (especially with Configuration Manager 2012 SP1 – which actually refers to them as virtual environments.)
App-V 5 Scripting: Change
It is almost easier to pretend you know nothing about App-V 4.x scripting when looking at scripting in 5.0. That is often my first response to many rumblings about difficulty getting scripting set up in 5.0. These rumblings come mostly from users of App-V 4.x. Change is hard, I know, but we have a better set of options and frankly, in my opinion, it’s much better this way in the long run. It is just a paradigm shift that does require somewhat of a translation process for bringing older scripts from 4.x over to 5.0.
No More SCRIPTBODY (Embed in the Package, not the XML)
First of all, there are no more <SCRIPTBODY> elements. Instead of embedding the script inside the XML, the intent is to have the script embedded inside the package in the .Scripts folder. This is the ideal place for it as it will be one of the default search paths when calling a script. If you have already sequenced a package (or converted a package) and want to add a SCRIPT element into the dynamic configuration, you will need to specify the path to the script interpreter and script file. So in essence you have as the command and argument the script interpreter as the command and the script (and options) as the argument.
Not Enabled by Default
Before you even begin to start testing scripts, you will have to make sure the client is set up to allow for package scripts. The quickest way to do this is through PowerShell using the following
Set-AppvClientConfiguration -EnablePackageScripts $true
You can also do it by GPO or manually in the registry. Always verify this before testing scripts.
Security Context
Some scripts will run in the SYSTEM context or the currently logged on user depending on the scripts package event. Later I’ll discuss workflows that will also help you determine the context (Machine or User) for running the script (which is another new concept in 5.0.) The following table outlines how the security context relates to the package event.
Event |
Runs As |
When the package is added |
Local System |
When the package is published globally |
Local System |
When the package is published to a user |
Current User |
After a Virtual Environment (Package) is built |
Current User |
After a virtual application is started |
Current User |
After a process exits |
Current User |
When the VE shuts down |
Current User |
Right before a package is unpublished to a user |
Current User |
Right before a package is unpublished globally |
Local System |
Right before a package is removed |
Local System |
Package Events?*
You need to forget the concept of PRE and POST events. Scripts can be called based on specific events in the lifecycle of the package. You will need to know at what point you want the script to be triggered. If your script needs to run in a specific context, this will help determine your event. If you decide your script needs to be triggered during application initialization (at the start of the virtual environment, the start of the process, when a process exits) you will need to also specify the specific application, rollback options, and whether you want to run it inside or outside the virtual environment.
*I so want to call this “event trigger” but it would be confusing.
To explain how the PRE and POST Options of before evolved into Package Event Elements – but not directly – look at the table below:
Package Event |
4.6 |
5.0 |
When the package is added |
N/A |
AddPackage |
When the package is published globally |
N/A |
PublishPackage |
When the package is published to a user |
N/A |
PublishPackage |
Before a Package is Streamed |
PRE STREAM |
N/A |
After a Package is Streamed |
POST STREAM |
N/A |
After a Virtual Environment (Package) is built |
N/A |
StartVirtualEnvironment |
When a virtual application is started |
PRE LAUNCH |
N/A – but same effect can be achieved with StartVirtualEnvironment |
After a virtual application is started |
POST LAUNCH |
StartProcess WAIT=TRUE |
After a process exits |
POST SHUTDOWN |
ExitProcess |
When the VE shuts down |
N/A |
TerminateVirtualEnvironment |
Right before a package is unpublished to a user |
N/A |
UnPublishPackage |
Right before a package is unpublished globally |
N/A |
UnPublishPackage |
Right before a package is removed |
N/A |
RemovePackage |
The key is to know what package/app event you want to trigger execution: (AddPackage, PublishPackage, StartVirtualEnvironment, StartProcess, ExitProcess, TerminateVirtualEnvironment, UnPublishPackage, RemovePackage)
Wait Options
In addition to the command <Path> and <Arguments> you have your “Wait” options (Wait, RollbackOnError, Timeout.) If you have a <Wait> element with nothing else, it will default to RollbackOnFailure=”True” and Timeout=0.
Element Flow
When we put it all together, you will see the element flow follows this basic process:
[MACHINE OR USER CONTEXT?]
[EVENT TO TRIGGER EXECUTION?] [IF VE or Process Event – Also the option of running inside the VE]
[MY Command Path]
[MY Command’s arguments]
[My Wait Options]
[Optional AppID EXE w/ tokenized path if this is a Process event]
Where an example of a machine targeted script looks like this:
<MachineScripts>
<PublishPackage>
<Path>PowerShell.exe</Path>
<Arguments>-f file.ps1 </Arguments>
<Wait RollbackOnError=”true” Timeout=”30″/>
</PublishPackage>
As another example, if a script was targeted for a user, set for PRE LAUNCH/ABORTRESULT=1/PROTECTED=TRUE in 4.x, and was only needed for one app, you could call it this way in 5.0
<UserScripts>
<StartProcess RunInVirtualEnvironment=”true”>
<Path>cscript</Path>
<Arguments>myscript.vbs</Arguments>
<Wait RollbackOnError=”true”/>
<ApplicationId>[{AppVPackageRoot}]DirectorySubdirectoryApp.EXE</ApplicationId>
</StartProcess>
Deployment Configuration and Dynamic User Configuration
Many of the problems with testing scripts come with proper placement in deployment and dynamic configuration files and how they are targeting. Scripts that need to be called during package add and global publishing events should be part of the DeploymentConfig.XML file. These scripts will also run in the context of the local system account so scripts that map drives, for example, should not go here. Those need to be called as a <UserScript> element. I use the following visual workflow to help me determine targeting and publishing.
In the case of global publishing, the deployment configuration also has a UserConfiguration element in addition to MachineConfiguration which means that scripts appearing during these events will apply to all users when the package is published globally. This would be the appropriate place to have scripts which map network drives.