Desktop and Application Streaming

How to use SSM Run to perform programmatic actions on AppStream 2.0 image builders

Amazon AppStream 2.0 is a fully managed application streaming service that allows you to centrally manage your desktop applications and deliver them to any computer. AppStream 2.0 streaming instances are created based off an AppStream 2.0 image that you build by installing and configuring your desktop applications. AppStream 2.0 recently released the Image Assistant command line interface (CLI) operations that enable you to programmatically specify what applications your users can launch, what files should be optimized to accelerate application launch, and other details necessary for the image. These CLI operations are made available via an executable on the image builder.

In a previous blog post, we showcased how you can create an image programmatically with the AppStream 2.0 Image Assistant CLI operations using remote commands with PowerShell executed from a Microsoft Windows EC2 administrative server. In this blog, I will show you how to use AWS Systems Managers Run Command to execute remote commands on an AppStream 2.0 image builder through your EC2 administrative server. This enables you to execute remote commands on your image builders using the AWS API/SDK.

Prerequisites

Once you have completed configuring the prerequisites, you can get started using the SSM Run command to make the EC2 administrative server execute remote PowerShell commands against the target AppStream 2.0 image builder. At a high level, this is the workflow for executing commands against your AppStream 2.0 image builder:

Figure 1. Workflow for executing commands against your AppStream 2.0 image builder

  1. Administrator with sufficient permissions invokes SSM Run using the AWS-RunPowerShellScript SSM document with a script for the EC2 administrative server to execute
  2. The EC2 administrative server executes the PowerShell script which contains remote PowerShell commands
  3. The AppStream 2.0 image builder executes the PowerShell Script that the EC2 administrative server sent to it
  4. SSM Run captures the console output logs from the EC2 administrative server (and image builder if configured), and stores them in the specified S3 Bucket

In the following examples, I will walk through how to use SSM Run command to execute the Image Assistant List-Applications CLI operation to find what applications have been specified on the image builder.

Using SSM’s Management Console to execute commands against your image builder

SSM’s Management Console provides a simple graphical user interface-based approach to creating and executing commands that your administrative server will execute on the image builder.

To execute a command on the EC2 administrative server using the SSM Management Console:

  1. Navigate to the SSM Management Console in the same AWS Region as your administrative server.
  2. From the left navigation menu, select Run Command.
  3. Choose Run Command.
  4. Search for and choose the AWS-RunPowerShellScript command document.
  5. Modify the following PowerShell script, then enter it into the Commands text box. You can find the IP address of the image builder by using the AppStream 2.0 DescribeImageBuilders API action, EC2 DescribeNetworkInterfaces API action (filtering on description), or the image builder itself.
    $strAccountPassword = ConvertTo-SecureString "<Password for the image builder administrator account>" -AsPlainText -Force
    
    $objAccountCredentials = New-Object System.Management.Automation.PSCredential ("<Username for the image builder administrator account>",$strAccountPassword)
    
    Invoke-Command -ComputerName <IP address of the target image builder> -ScriptBlock { image-assistant.exe list-applications } -credential $objAccountCredentials

    Note: You can use the EC2 administrative server to perform AWS API actions such as finding the IP address of the image builder. Ensure that the IAM Role the EC2 administrative server is asserting has sufficient permissions to execute AWS API actions.

  6. In the Targets section, select Choose instances manually, then choose the EC2 administrative server.
  7. (Optional) In the Output options section, choose to write the command output to an Amazon S3 bucket. By default, SSM will only display the last 2500 characters of output in the console, while the log in the S3 bucket will have the complete output.
  8. Choose the Run command.
  9. After a few minutes choose the Refresh icon. Repeat until the overall status moves to success.
  10. Once the overall status moves to success, choose the EC2 administrative server in the Targets and outputs section, then choose View output.
  11. Expand the Step 1 – Output section. You will see the JSON output from the Image Assistant List-Applications CLI operation.

Using the AWS Tools for Windows PowerShell to execute commands against your image builder

The following script uses the AWS Tools for Windows PowerShell to execute the Image Assistant List-Applications CLI operation on the image builder with the EC2 administrative server. You will have to update the parameters in the script to ensure it works for your environment.

 

############
## Parameters to modify
############
$strEc2AdminServer = '<Instance ID of the EC2 administrative server>'
$strIbName = '<Name of the target image builder>'
$strIbUsername = '<Username of the Windows user with administrator rights on the image builder'
$strIbPassword = '<Password of the Windows user with administrator rights on the image builder'
$strAWSRegion = '<AWS Region the EC2 administrative server is in>'
$strS3BucketName = '<Name of the S3 Bucket to write the SSM Run output to>'
$strS3KeyPrefix = '<Folder structure for the S3 Bucket>'

$strIbIp = (Get-APSImageBuilderList -Name $strIbName).NetworkAccessConfiguration.EniPrivateIpAddress #Find the IP address of the target image builder using its name and the AppStream 2.0 API

############
## PowerShell commands to execute on EC2 administrative server that execute on target image builder
############
$strArrCommands = @() #Initialize the commands array
$strArrCommands += '$strAccountPassword = ConvertTo-SecureString "'+$strIbPassword+'" -AsPlainText -Force'
$strArrCommands += '$objAccountCredentials = New-Object System.Management.Automation.PSCredential ("'+$strIbUsername+'",$strAccountPassword)'
$strArrCommands += 'Invoke-Command -ComputerName "'+$strIbIp+'" -ScriptBlock { image-assistant.exe list-applications } -credential $objAccountCredentials'

############
## Call SSM Run command, then wait for output.
############
$objRunPSCommand = Send-SSMCommand -InstanceId $strEc2AdminServer -DocumentName AWS-RunPowerShellScript -Parameter @{'commands'=$strArrCommands} -OutputS3BucketName $strS3BucketName -OutputS3KeyPrefix $strS3KeyPrefix -Region $strAWSRegion
do {
    Start-Sleep -Seconds 5 #Waiting for command execution to complete.
    $objPSCommandDetails = Get-SSMCommandInvocation -CommandId $objRunPSCommand.CommandId -Details $true -InstanceId $strEc2AdminServer -Region $strAWSRegion
} while ($objPSCommandDetails.Status -eq "InProgress")

$objPSCommandDetails | select -ExpandProperty CommandPlugins 

Here is an example output:

Name                   : aws:runPowerShellScript
Output                 : {
                           "status": 0,
                           "message": "Success",
                           "applications": [
                             {
                               "Name": "firefox",
                               "AbsoluteAppPath": "C:\\Program Files (x86)\\Mozilla Firefox\\firefox.exe",
                               "DisplayName": "Mozilla FireFox",
                               "AbsoluteIconPath": "C:\\ProgramData\\Amazon\\Photon\\AppCatalogHelper\\AppIcons\\43eeb6c5-ede1-49c0-9dcc-1302e99bf4d4.png"
                             }
                           ]
                         }
                         
OutputS3BucketName     : <redacted S3 bucket name>
OutputS3KeyPrefix      : 79119fd7-c077-4755-9e98-bff16a607acc/<EC2 administrative server instance ID>/awsrunPowerShellScript
OutputS3Region         : us-east-1
ResponseCode           : 0
ResponseFinishDateTime : 10/13/2019 11:55:58 PM
ResponseStartDateTime  : 10/13/2019 11:55:54 PM
StandardErrorUrl       : https://s3.amazonaws.com/<Output S3 bucket name>/79119fd7-c077-4755-9e98-bff16a607acc/<EC2 administrative server instance ID>/awsrunPowerShellScript/0.awsrunPowerShellScript/stderr
StandardOutputUrl      : https://s3.amazonaws.com/<Output S3 bucket name>/79119fd7-c077-4755-9e98-bff16a607acc/<EC2 administrative server instance ID>/awsrunPowerShellScript/0.awsrunPowerShellScript/stdout
Status                 : Success
StatusDetails          : Success 

Clean up

In this blog post, you used a Windows EC2 instance to remotely execute commands on a running AppStream 2.0 image builder. If you chose to do so, the output from the SSM Run command was stored within an S3 bucket. Once you have completed using the resources, be sure to terminate the EC2 instance and its EBS volume, stop the AppStream 2.0 image builder, and delete the created objects in the S3 bucket to not continue incurring charges.

Conclusion

You can use the SSM Run command/API action with a Windows EC2 instance to enable installing software on your image builders, specify applications that users can launch, then create the image without having to use the graphical user interface. You can even use this capability in combination with image builders assuming IAM Roles in your AWS account for further extensibility!