September 5th, 2019
Using Systems Manager to Resize EBS Volumes
By Alexandra Shumway

A few weeks ago, a client requested help with automating the resizing of EBS volumes associated with their Windows EC2 instances. Diligent searching only returned results of the manual steps using Windows GUIs and guides riddled with screenshots of setup wizards.

After digging a bit deeper, I discovered that resizing an EBS volume was possible with PowerShell using the AWS Tools for PowerShell. These tools come installed by default on all Windows Amazon Machine Images (AMIs). I was ecstatic to find out that it could be done via tools already available on my EC2 instances and turned to AWS Systems Manager for the next step: automation.

While you have the option to RDP into your Windows EC2 instances at any time and run a PowerShell script on the remote machine, this becomes time consuming and impractical at scale. Thus, there is a need for automating this process. If you find yourself often needing to resize EBS volumes, consider updating the EBS volume size earlier in your pipeline, such as in your CloudFormation Template. If your use case aligns with mine, which is to resize a batch of volumes attached to various EC2 instances as a maintenance task, this guide may help you.

If you are completely unfamiliar with AWS Systems Manager, I’d recommend reading up a bit on the service before utilizing this solution, but I will cover some of the basics here as well.

Create and attach an IAM role to your target instance(s)

For Systems Manager to have access to an EC2 instance, you must create and attach an IAM role. For this scenario, you will need the AWS Managed Policy named AmazonEC2RoleforSSM attached. For more detailed instructions on creating this IAM role, see here.

Once your role is created, attach it to the desired EC2 instance(s). Instructions on how to attach a role to an EC2 instance can be found here.

Once your role is attached, you should see your EC2 instance(s) in AWS Systems Manager under Shared Resources > Managed Instances.

Create a Systems Manager Document (Previously called SSM Document)

A Document defines a set of actions that can be run on your managed instances. Visit AWS Systems Manager in your AWS Console, and under Shared Resources select Documents. In the top right of the screen there will be an orange button labeled Create document.

One thing worth noting about Documents is the concept of “default versions.” Each document is assigned version 1 as its default upon creation, and this will remain the default version until the user specifies otherwise. This was misleading to me as I made changes to my documents, and when I opened the content later, it appeared as though my changes had not been saved. They had, in fact, been saved; I was unaware of how versioning worked and was being shown the default version (version 1) again and again.

Here is the document I created, which you can use to get started:


---
schemaVersion: "2.2"
description: "Resizes the specified EBS volume to the target size"
parameters:
VolumeId:
type: "String"
description: "(Required) EBS volume ID"
Size:
type: "String"
description: "(Required) Target size for the selected volume in GB"
mainSteps:
- action: "aws:runPowerShellScript"
name: "ModifyVolumeSize"
inputs:
runCommand:
- "Edit-EC2Volume -VolumeId {{VolumeId}} -Size {{Size}}"
- "$VolumeReady = $false"
- "Write-Host 'Waiting for resize to be complete'"
- "Write-Verbose 'Checking whether Volume is ready for partition extension.'"
- "while ($VolumeReady -ne $true){ $VolumeStatus = (Get-EC2VolumeModification -VolumeId {{VolumeId}}).ModificationState.Value; if($VolumeStatus -eq 'completed'){ Write-Host 'Volume is now updated' ; $VolumeReady = $true} else{ Write-Host 'Volume is not ready... will try again in 10 seconds'; Start-Sleep -Seconds 10}}"
- "$SerialNo = '{{VolumeId}}' -Replace '-',''"
- "$Disk = Get-Disk | where-object SerialNumber -eq $SerialNo"
- "Write-Host $Disk"
- "$PartitionNumber = (Get-Partition -DiskNumber $Disk.Number | Where-Object -FilterScript {$_.Type -ne 'Reserved'}).PartitionNumber[0]"
- "$Size = (Get-PartitionSupportedSize -DiskNumber $Disk.Number -PartitionNumber $PartitionNumber).SizeMax"
- "Write-Host 'Maximum volume size in bytes:'"
- "$Size"
- "Resize-Partition -DiskNumber $Disk.Number -PartitionNumber $PartitionNumber $Size"
- "Get-Disk"
- "Write-Host 'Resize and extension complete.'"

I included a number of Write-Host statements for debugging purposes, but those could easily be removed without affecting the functionality of this document. The meat of this document is essentially the following steps:

  1. Resize the EBS volumes using the Edit-EC2Volume command
  2. Check to see if the volume has finished resizing before proceeding, using a While statement
  3. Ensure that the correct volume is selected; I did this using the SerialNumber property found using Get-Disk. You may do this using the volume’s name, number, or another parameter
  4. Resize the partition using Resize-Partition to realize the updated size capacity

You may have standardized names for the volumes attached to your fleet of EC2 instances and could modify this document to run it on multiple instances at once. Hopefully at the very least, this example will save you some time and headache next time you want to resize an EBS volume attached to a Windows EC2 instance.

Run the Command

You can run the Document on your configured instance(s) using either the AWS Command Line Interface or the AWS console. In the console, select Run Command (found beneath Instances and Nodes) then select the button labeled Run Command. Search for the name you specified for your new document, then select the circle next to it (be careful not to select the hyperlink of the document’s name, as this will take to you the Documents portal).

Make sure the most up-to-date version of the document is selected to be run, enter the parameters, and select the EC2 instance from the list of available instances. If your instance does not appear here, see this guide on attaching an IAM role to an EC2 instance.

You have options to write output to either CloudWatch or S3, as well as SNS notifications. Conveniently, the console also generates the CLI command for you if you are on Linux/Unix/OS X!

Either paste the CLI command into your configured terminal or click Run in the bottom right. It shouldn’t take more than a few minutes to complete the operation, and you’ll need to refresh the page to see whether or not it completed.

This solution saved me a great deal of time, as it is a repeatable process. Once the three steps above are completed, you can just skip straight to step 3 for future iterations. Rather than the 15-20 minutes it would take to manually RDP into your Windows EC2 instance, resize the volume, and extend the partition, you can now complete this task in 2-3 minutes, and even modify this document to run on multiple machines concurrently.

If you have questions about AWS Systems Manager, EC2, or any other AWS service, let us know! Schedule a consultation with our AWS Experts, or reach out to us at info@1strategy.com. We’d love to chat with you about how 1Strategy can help your business with your journey into the AWS cloud.