AWSWindows

Powershellを用いて、aws ec2-instance-connect open tunnelをバックグラウンドで実行

はじめに

先日、EC2 Instance Connect Endpointを用いて、パブリックIPがないWindows Serverへ接続!という記事を書きました。
その中で、AWS CLIコマンドを用いてプライベートトンネルを確立するところがあります。
具体的には、タイトルにあるコマンド「aws ec2-instance-connect open tunnel」を実行します。
Powershellで実行すると、下記のように実行中状態になるため複数同時実行に困ります。 (新しくPowershellプロセスを開けばいい、、、)

そのため、複数実行するためにバックグラウンド実行しようと思いました。
さらに、手動で毎回実行するのは手間がかかるためスクリプト化しました!

コード

インスタンスが起動していない場合、強制終了するようにしています。
インスタンスが起動していて、やっとジョブによってバックグラウンド実行されます!
Start-Jobのコマンドの際にAWS CLIコマンドを指定していますが、インスタンスIDパラメータで変数を指定するとジョブが完了します。
そのため、インスタンスIDを直書きしています。(何故だろう、、、)

# awsのプロファイル定義
$env:AWS_PROFILE="kano-test"

# server1のインスタンスID
$server1 = "i-0a52120b80a762b5c"

# server2のインスタンスID
$server2 = "i-0f6b1765365ca59dc"

# インスタンスの起動有無確認
$instanceStatus1 = aws ec2 describe-instances --instance-ids $server1 --query "Reservations[].Instances[].State.Name" --output text
$instanceStatus2 = aws ec2 describe-instances --instance-ids $server2 --query "Reservations[].Instances[].State.Name" --output text

if ($instanceStatus1 -eq "stopped" -or $instanceStatus2 -eq "stopped") {
    # エラー文言
    $errorString = "強制終了ため、「Enter」押してください"

    # 両方のインスタンスが停止している場合    
    if ($instanceStatus1 -eq "stopped" -and $instanceStatus2 -eq "stopped") {
        Write-Host "両方のインスタンスが停止しています:$server1 , $server2"
        Read-Host $errorString
        exit
    }
    # server1のみ停止している場合
    elseif ($instanceStatus1 -eq "stopped" -and $instanceStatus2 -ne "stopped") {
        Write-Host "片方のインスタンスが停止しています:$server1"
        Read-Host $errorString
        exit
    }
    # server2のみ停止している場合
    else {
        Write-Host "片方のインスタンスが停止しています:$server2"
        Read-Host $errorString
        exit
    }
}

# (インスタンスIDを変数で入れた場合、ジョブ状態がRunningにならないため直打ち)
# WIN2022-DC01のプライベートトンネルジョブ
$job1 = Start-Job { aws ec2-instance-connect open-tunnel --instance-id i-0a52120b80a762b5c --remote-port 3389 --local-port 65000 }
# WIN2022-FS01のプライベートトンネルジョブ
$job2 = Start-Job { aws ec2-instance-connect open-tunnel --instance-id i-0f6b1765365ca59dc --remote-port 3389 --local-port 65001 }


# ジョブ情報取得 or ジョブの削除
$isValidJob = $false

while (-not $isValidJob) {
    $chooseAction = Read-Host "ジョブ情報取得[G] or ジョブ削除[D]を選択してください"

    # Gの場合、ジョブ情報取得
    if ($chooseAction -eq "G" -or $chooseAction -eq "g") {
        Get-Job
        Write-Host "ジョブ一覧を取得しました。"
    } 
    # Dの場合、プライベートトンネルのジョブ削除
    elseif ($chooseAction -eq "D" -or $chooseAction -eq "d") {
        $isValidJob = $true
        Remove-Job -Id $job1.Id,$job2.Id -Force
        Write-Host "ジョブを削除しました。"
    }
    else {
        Write-Host "無効な入力です。[G] か [D] で再入力してください。"
    }
}

使用イメージ

両方のインスタンスが停止している場合

片方のインスタンスが停止している場合

両方のインスタンスが起動している場合 (ジョブ一覧取得かジョブ削除)

もちろん接続できます!

課題

現状のコードが2インスタンスを想定して書いてるが、
3インスタンス以上の複数インスタンスを想定していないこと。
(いつかコードより良くしたいです!)

まとめ

コードをテンプレート化していません。基本変更が必要なところは下記のとおりです。
・awsのプロファイル定義
・server1, 2変数のインスタンスID
・job1, 2変数のインスタンスIDとローカルポート (空きポート)

目的のバックグラウンド実行を果たすことができました!少しはWindows Serverの勉強が捗りそうです。
本記事が誰かの一助になれば嬉しいかぎりです!

参照

PowerShellで処理をバックグラウンドで実行する

Kano

社会人5年目のKanoです。tech系を筆頭に投稿します。 資格:AWS13冠、TOEIC 795

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です