目次
はじめに
PowerQueryでAWS Price List API (AKA the Bulk API) からオファーファイルの一覧を取得する #AWS - Qiita
以前、QiitaブログにPowerQueryでAWS Price List APIを取得する方法を投稿しました。
AWSで利用料を確認する際には、各サービスページの料金ページを参照する事が多いのですが。
直接オファーファイルを確認したくなることも、たまにあります。
そのような場合にExcelでURIの一覧を取得できるようにPowerQueryで取得する方法のブログ記事を書きましたが、今回はこの一覧をPowerShellで作成するスクリプトを書いたので紹介します。
なおそもそもAWS Price List API (AKA the Bulk API) が何かについては、上述のQiitaブログに記載しているため本記事では割愛します。
動作確認している環境
- Windows PowerShell 5.1.26100.2161
- PowerShell 7.4.6
今回作成しているスクリプトについて
- 最新のリージョン別のオファーファイルのURLのみ取得するGet-CurrentAWSOfferFileURLByRegion.ps1
- 過去バージョンのリジョン別のオファーファイルのURLを取得するGet-HistoryAWSOfferFileURLByRegion.ps1
の2種類のスクリプトを作成しています。
最新のリージョン別オファーファイルのURLを取得(Get-CurrentAWSOfferFileURLByRegion.ps1)
#!/usr/bin/env pwsh
<#
.SYNOPSIS
AWSサービスでインデックスファイルから最新のオファーファイル(リージョン別)のURL一覧を取得
.DESCRIPTION
AWS Price List API (AKA the Bulk API)から最新のオファーファイルURLを取得する
.EXAMPLE
# 最新のオファーファイルURLを全取得
PS > ./Get-CurrentAWSOfferFileURLByRegion.ps1
# AmazonEC2 かつ ap-northeast-1 となるオファーファイルURLを取得
PS > ./Get-CurrentAWSOfferFileURLByRegion.ps1 -offerCode AmazonEC2 -regionCode ap-northeast-1
結果をtxtファイルに出力する場合(省略されないようにWidth 1000 指定)
PS > ./Get-CurrentAWSOfferFileURLByRegion.ps1 | Format-Table * | Out-File ./CurrentAWSOfferFileURLByRegion.txt -Width 1000
結果をcsvファイルに出力する場合
PS > ./Get-CurrentAWSOfferFileURLByRegion.ps1 | Export-Csv ./CurrentAWSOfferFileURLByRegion.csv
.INPUTS
None
.OUTPUTS
pscustomobject serviceName, regionCode, offerFileUrl
#>
[CmdletBinding()]
param (
[Parameter(Mandatory = $false)]
[string]$offerCode = "*",
[Parameter(Mandatory = $false)]
[string]$regionCode = "*"
)
PROCESS {
Set-StrictMode -Version Latest
$ErrorActionPreference = "stop"
# AmazonPriceListAPIのベースUri
$baseUri = "https://pricing.us-east-1.amazonaws.com"
# AWSのサービス一覧を取得
$serviceList = ((Invoke-RestMethod "$baseUri/offers/v1.0/aws/index.json").offers.psobject.Properties.value)
# 引数のofferCodeでフィルタ
$targetServiceList = $serviceList | Where-Object offerCode -Like $offerCode
foreach ($serviceRow in $targetServiceList) {
# 最新のリージョン別のインデックスファイルURL生成
$currentRegionIndexUrl = ($baseUri + $serviceRow.currentRegionIndexUrl)
# 最新のリージョン別のサービスインデックスファイル取得
$currentRegionIndex = (Invoke-RestMethod -Uri $currentRegionIndexUrl).regions.psobject.Properties.value
# 引数のregionCodeでフィルタ
$targetCurrentRegionIndex = $currentRegionIndex | Where-Object regionCode -Like $regionCode
# リージョンごとのインデックスファイルからオファーファイルのURLを生成
foreach ($regionRow in $targetCurrentRegionIndex) {
$outputLine = [pscustomobject]@{
serviceName = $serviceRow.offerCode
regionCode = $regionRow.regionCode
offerFileUrl = ($baseUri + $regionRow.currentVersionUrl)
}
Write-Output $outputLine
}
}
}
上記、PowerShellスクリプトを引数を付けずに実行すると最新のサービス別リージョン別のオファーファイルのURLが表示されます。
EXSAMPLEに記載していますが、ファイルに保存する場合はOut-FileやExport-CSVにするなど適宜調整してください。
やってる事は単純で、
- https://pricing.us-east-1.amazonaws.com/offers/v1.0/aws/index.json からサービス別のインデックスファイルを取得
- インデックスファイルにはサービスごとにcurrentRegionIndexUrlにリージョンごとのインデックスファイルの識別子があるので、URLにしてリージョンごとのインデックスファイルを取得
- リージョンごとのインデックスファイルの中にはオファーファイルの識別子があるので、これをURLにして出力
バージョン別にリージョン別オファーファイルのURLを取得(Get-HistoryAWSOfferFileURLByRegion.ps1)
#!/usr/bin/env pwsh
<#
.SYNOPSIS
AWSサービスでインデックスファイルから取得できるすべてのオファーファイル(リージョン別)のURL一覧を取得
.DESCRIPTION
AWS Price List API (AKA the Bulk API)から最新のオファーファイルURLを取得する
.EXAMPLE
# リージョン別オファーファイルURLをHistoryを含めて全取得
PS > ./Get-HistoryAWSOfferFileURLByRegion.ps1
# AmazonEC2 かつ ap-northeast-1 となるオファーファイルURLをHistoryを含めて全取得
PS > ./Get-HistoryAWSOfferFileURLByRegion.ps1 -offerCode AmazonEC2 -regionCode ap-northeast-1
結果をtxtファイルに出力する場合(省略されないようにWidth 1000 指定)
PS > ./Get-HistoryAWSOfferFileURLByRegion.ps1 | Format-Table * | Out-File ./HistoryAWSOfferFileURLByRegion.txt -Width 1000
結果をcsvファイルに出力する場合
PS > ./Get-HistoryAWSOfferFileURLByRegion.ps1 | Export-Csv ./HistoryAWSOfferFileURLByRegion.csv
.INPUTS
None
.OUTPUTS
pscustomobject serviceName, versionEffectiveBeginDate, versionEffectiveEndDate, regionCode, offerFileUrl
#>
[CmdletBinding()]
param (
[Parameter(Mandatory = $false)]
[string]$offerCode = "*",
[Parameter(Mandatory = $false)]
[string]$regionCode = "*"
)
PROCESS {
Set-StrictMode -Version Latest
$ErrorActionPreference = "stop"
# AmazonPriceListAPIのベースUri
$baseUri = "https://pricing.us-east-1.amazonaws.com"
# AWSのサービス一覧を取得
$serviceList = ((Invoke-RestMethod "$baseUri/offers/v1.0/aws/index.json").offers.psobject.Properties.value)
# 引数のofferCodeでフィルタ
$targetServiceList = $serviceList | Where-Object offerCode -Like $offerCode
foreach ($serviceRow in $targetServiceList) {
# versionIndexUrl URL生成
$versionIndexUrl = ($baseUri + $serviceRow.versionIndexUrl)
# リージョン別のサービスインデックスデータ取得
$versionIndex = (Invoke-RestMethod -Uri $versionIndexUrl).versions.psobject.Properties.value | Sort-Object versionEffectiveBeginDate
# 該当サービスの提供リージョン一覧を表示
foreach ($versionRow in $VersionIndex) {
# offerVersionUrlのindex.jsonをregion_index.jsonに書き換えてリージョンごとのインデックスファイルURLを生成
$regionIndexUrl = ($baseUri + $versionRow.offerVersionUrl -replace "index.json", "region_index.json")
# リージョンごとのインデックスファイル取得
$regionIndex = (Invoke-RestMethod -Uri $regionIndexUrl).regions.psobject.Properties.value
# 引数のregionCodeでフィルタ
$targetRegionIndex = $regionIndex | Where-Object regionCode -Like $regionCode | Sort-Object regionCode
# リージョンごとのインデックスファイルからオファーファイルのURLを生成
foreach ($regionRow in $targetRegionIndex ) {
$outputLine = [pscustomobject]@{
serviceName = $serviceRow.offerCode
versionEffectiveBeginDate = $versionRow.versionEffectiveBeginDate
versionEffectiveEndDate = $versionRow.versionEffectiveEndDate
regionCode = $regionRow.regionCode
offerFileUrl = ($baseUri + $regionRow.currentVersionUrl)
}
Write-Output $outputLine
}
}
}
}
こちらもやっている事は単純ですが、サービス別のインデックスファイルには最新のファイル用のリージョン事のインデックスファイルの識別子としてcurrentRegionIndexUrlが用意されていますが。
バージョンごとの方についてはリージョン事のインデックスファイルの識別子は用意されていません。
versionRegionIndexUrlといた項目があれば、それを使えばよいのですがないのでindex.jsonをregin_index.jsonに読み替えてリージョン毎のインデックスファイルを取得します。
あとは最新の情報を取得するときと一緒でリージョン毎のインデックスファイルを取得して、その中にオファーファイルの識別子があるのでこれをURLにして出力。
総評
以前、PowerQueryでオファーファイルのURLを取得する仕組みを作成してみましたが、今回はちょっとPowerShellのコマンドベースでオファーファイルのURLを取得する仕組みが欲しくなったので作成してみました。
方式としてサービス別のインデックスファイルを取得 ー> サービスごとにリージョン別のインデックスファイルを取得 といった流れとなるため、インデックスファイル分の1回+対象とするサービスの個数回のInvoke-RestMethodが発生するので、引数で条件指定せずに全サービス取得しようとするとだいぶ時間はかかります。
- カテゴリー
- タグ