Created
April 12, 2025 14:07
-
-
Save nanoDBA/cdc5b8f209ae703670c197b60214ae68 to your computer and use it in GitHub Desktop.
Modifies AWS EBS volumes with enhanced validation and confirmation π
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
function Edit-EBSVolumes { | |
<# | |
.SYNOPSIS | |
Modifies AWS EBS volumes with enhanced validation and confirmation π§π | |
.DESCRIPTION | |
This function lets you change multiple AWS EBS volumes in one go! | |
It supports modifications to volume type, size, IOPS, and throughput | |
with safety confirmations and detailed feedback. | |
Itβs essentially a wrapper around AWS's Edit-EC2Volume command with extra spice for validation. | |
.PARAMETER VolumeIds | |
Array of AWS EBS Volume IDs to modify. | |
.PARAMETER TargetSize | |
New volume size in GB. | |
.PARAMETER TargetEbsType | |
New volume type (gp2, gp3, io1, io2, sc1, st1). | |
.PARAMETER TargetIops | |
New IOPS value (required for io1/io2; optional for gp3). | |
.PARAMETER TargetThroughput | |
New throughput value in MB/s (applicable only for gp3). | |
.PARAMETER Region | |
AWS region of the volumes. Default: 'us-east-1'. | |
.PARAMETER Force | |
Bypasses confirmation and applies changes immediately. | |
.EXAMPLE | |
Edit-EBSVolumes -VolumeIds 'vol-0a1b2c3d4e5f6a7b','vol-0a1b2c3d4e5f6a7c' -TargetSize 2701 | |
# Resizes specified volumes to 2701 GB in the default region. | |
.EXAMPLE | |
Edit-EBSVolumes -VolumeIds 'vol-0a1b2c3d4e5f6a7b' -TargetEbsType 'io2' -TargetIops 16000 -Region 'us-west-2' | |
# Changes the volume to io2 with 16000 IOPS in us-west-2. | |
.EXAMPLE | |
Edit-EBSVolumes -VolumeIds 'vol-0a1b2c3d4e5f6a7b' -TargetEbsType 'gp3' -TargetIops 5000 -TargetThroughput 600 | |
# Changes volume to gp3 with 5000 IOPS and 600 MB/s throughput. | |
.NOTES | |
Author: Enhanced from original script by Lars, then refined by Lars and Claude. | |
Date: April 10, 2025 | |
Prerequisites: AWS PowerShell module and proper AWS credentials. | |
β οΈ Note: Modifications follow AWS limits and constraints. | |
#> | |
[CmdletBinding(SupportsShouldProcess = $true, ConfirmImpact = 'High')] | |
param ( | |
[Parameter(Mandatory = $true, ValueFromPipeline = $true, Position = 0)] | |
[string[]]$VolumeIds, | |
[Parameter(Mandatory = $false)] | |
[ValidateRange(1, 16384)] | |
[int]$TargetSize, | |
[Parameter(Mandatory = $false)] | |
[ValidateSet('gp2', 'gp3', 'io1', 'io2', 'sc1', 'st1')] | |
[string]$TargetEbsType, | |
[Parameter(Mandatory = $false)] | |
[ValidateRange(100, 64000)] | |
[int]$TargetIops, | |
[Parameter(Mandatory = $false)] | |
[ValidateRange(125, 1000)] | |
[int]$TargetThroughput, | |
[Parameter(Mandatory = $false)] | |
[string]$Region = 'us-east-1', | |
[Parameter(Mandatory = $false)] | |
[switch]$Force | |
) | |
begin { | |
# Check for AWS PowerShell modules | |
if (-not (Get-Module -ListAvailable -Name AWSPowerShell, AWS.Tools.EC2)) { | |
Write-Error "A required AWS PowerShell module is missing. Please install either 'AWS.Tools.EC2' (recommended) or 'AWSPowerShell' using: Install-Module -Name AWS.Tools.EC2 -Force" | |
return | |
} | |
# Validate parameter logic for EBS types | |
if ($TargetEbsType) { | |
if ($TargetEbsType -in @('io1', 'io2') -and -not $TargetIops) { | |
Write-Error "TargetIops is required for io1 or io2 volume types." | |
return | |
} | |
if ($TargetEbsType -ne 'gp3' -and $TargetThroughput) { | |
Write-Warning "TargetThroughput applies only to gp3 volumes and will be ignored." | |
} | |
} | |
# Console header output π | |
$separator = '=' * 50 | |
Write-Host $separator -ForegroundColor Yellow | |
Write-Host " EBS VOLUME MODIFICATION UTILITY " -ForegroundColor Cyan | |
Write-Host " Region: $Region " -ForegroundColor Cyan | |
Write-Host $separator -ForegroundColor Yellow | |
} | |
process { | |
foreach ($volId in $VolumeIds) { | |
try { | |
Write-Host "`nRetrieving details for volume $volId..." -ForegroundColor Gray | |
$currentVolume = Get-EC2Volume -VolumeId $volId -Region $Region -ErrorAction Stop | |
if (-not $currentVolume) { | |
Write-Error "Volume $volId not found in region $Region" | |
continue | |
} | |
# Build parameters for the volume modification π | |
$paramHash = @{ | |
VolumeId = $volId | |
Region = $Region | |
} | |
if ($TargetSize) { $paramHash.Size = $TargetSize } | |
if ($TargetEbsType) { $paramHash.VolumeType = $TargetEbsType } | |
if ($TargetIops) { $paramHash.Iops = $TargetIops } | |
if ($TargetThroughput -and ($TargetEbsType -eq 'gp3' -or $currentVolume.VolumeType -eq 'gp3')) { | |
$paramHash.Throughput = $TargetThroughput | |
} | |
# Check if any actual changes were specified | |
$changeRequested = $false | |
foreach ($key in $paramHash.Keys) { | |
if ($key -notin @('VolumeId', 'Region')) { | |
$changeRequested = $true | |
break | |
} | |
} | |
if (-not $changeRequested) { | |
Write-Warning "No changes specified for volume $volId. Skipping." | |
continue | |
} | |
# Display the volume modification details π― | |
Write-Host "`n======== VOLUME MODIFICATION DETAILS ========" -ForegroundColor Yellow | |
Write-Host "Volume ID: $volId" -ForegroundColor Cyan | |
Write-Host "State: $($currentVolume.State)" -ForegroundColor Cyan | |
Write-Host "Attached to: $(if ($currentVolume.Attachments) { $currentVolume.Attachments[0].InstanceId } else { 'Not attached' })" -ForegroundColor Cyan | |
Write-Host "Availability Zone: $($currentVolume.AvailabilityZone)" -ForegroundColor Cyan | |
Write-Host "" | |
Write-Host "CURRENT SETTINGS:" -ForegroundColor Green | |
Write-Host " Type: $($currentVolume.VolumeType)" | |
Write-Host " Size: $($currentVolume.Size) GB" | |
Write-Host " IOPS: $(if ($currentVolume.Iops) { $currentVolume.Iops } else { 'N/A' })" | |
Write-Host " Throughput: $(if ($currentVolume.Throughput) { $currentVolume.Throughput } else { 'N/A' }) MB/s" | |
Write-Host "" | |
Write-Host "CHANGES TO BE APPLIED:" -ForegroundColor Red | |
$changesDisplayed = $false | |
foreach ($key in $paramHash.Keys) { | |
if ($key -notin @('VolumeId', 'Region')) { | |
$currentValue = switch ($key) { | |
'Size' { $currentVolume.Size } | |
'Iops' { $currentVolume.Iops } | |
'VolumeType' { $currentVolume.VolumeType } | |
'Throughput' { $currentVolume.Throughput } | |
default { 'N/A' } | |
} | |
Write-Host " $key`: $($paramHash[$key]) (Current: $currentValue)" | |
$changesDisplayed = $true | |
} | |
} | |
if (-not $changesDisplayed) { | |
Write-Host " No changes specified for this volume" -ForegroundColor Yellow | |
continue | |
} | |
Write-Host "" | |
<# | |
Breakdown: | |
# PowerShell ShouldProcess Pattern Explained | |
## 1. Using $PSCmdlet.ShouldProcess: | |
- Returns false when -WhatIf is used. | |
- Prompts confirmation when -Confirm is specified. | |
- Defaults to true if neither parameter is used. | |
## 2. Building the confirmation string: | |
- Converts the parameter hashtable to a readable list of changes. | |
- Uses GetEnumerator() to iterate through key-value pairs. | |
- Filters out non-change parameters (VolumeId and Region). | |
- Joins the changes with commas for clear output. | |
## 3. Executing after confirmation: | |
- Displays a status message. | |
- Uses splatting (@paramHash) to call the AWS command. | |
- Enforces error handling with -ErrorAction Stop in a try/catch block. | |
This pattern is a PowerShell best practice for functions that make potentially destructive changes. | |
#> | |
# Proceed with modification based on Force or user confirmation | |
$shouldProceed = $Force | |
if (-not $Force) { | |
$confirmation = Read-Host "Are you sure you want to proceed with these changes? (yes/no)" | |
$shouldProceed = $confirmation -eq 'yes' | |
} | |
if ($shouldProceed) { | |
if ($PSCmdlet.ShouldProcess( | |
$volId, | |
"Modify EBS volume with parameters: $( | |
($paramHash.GetEnumerator() | | |
Where-Object { $_.Key -notin @('VolumeId', 'Region') } | | |
ForEach-Object { "$($_.Key)=$($_.Value)" } | |
) -join ', ' | |
)" | |
)) { | |
Write-Host "Proceeding with volume modification..." -ForegroundColor Yellow | |
$result = Edit-EC2Volume @paramHash -ErrorAction Stop | |
Write-Host "Modification initiated successfully." -ForegroundColor Green | |
Write-Host "New state: $($result.ModificationState)" -ForegroundColor Green | |
Write-Host "Progress: $($result.Progress)%" -ForegroundColor Green | |
} | |
} | |
else { | |
Write-Host "Volume modification canceled for $volId" -ForegroundColor Red | |
} | |
Write-Host "=========================================" -ForegroundColor Yellow | |
} | |
catch { | |
Write-Error "Error processing volume $volId`: $_" | |
Write-Host "=========================================" -ForegroundColor Yellow | |
} | |
} | |
} | |
end { | |
Write-Host "EBS volume modification process complete. π" -ForegroundColor Green | |
Write-Host "Run 'Get-EC2Volume -VolumeId <id> -Region $Region' to check status." -ForegroundColor Cyan | |
Write-Host $separator -ForegroundColor Yellow | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment