【2021/5/12訂正】【PowerShell】複数サーバへのPingとTCPポートの疎通確認を一括で実行する

スポンサーリンク
powershell
スポンサーリンク

一度に複数のサーバに対してPingとTCPポートの疎通確認をしたい

仕事で、監視サーバへの疎通が可能であるかどうかを10台分くらい調べることになった。最初はPingなどのコマンドを各サーバで手動実行しようと思ったけど、監視サーバも8台分あるので、一々やるのは結構面倒・・・時間もかかる・・・・。
というわけで、さくっとPingとTCPの疎通確認を複数サーバに対して一括で実行できるスクリプトを作ることにした。

搭載機能

  • 指定したリスト(CSV)に存在するIPアドレスに対してPowershellの「Test-NetConnection 宛先IPアドレス -port XXX」を行う。※対象ポートが空いていても空いていなくても、同コマンドでPingの成功はPingSucceededで確認が可能
  • サーバリストはフォーマット固定にする。第一カラムをIPaddressとする。
  • 取得する情報は、Test-Netconnectionで取得できる以下値とする。
     PingSucceeded
     TcpTestSucceeded ※ポートXXX向け
     全情報 ※情報不足が後で判明すると面倒なので、全てのプロパティの出力結果を残しておく
  • 結果はCSVファイルで出力する。ファイル名に実行年月日時分秒をつける。
  • 対象数が多いと時間がかかるので、進捗状況が表示されるようにする。
  • IPアドレスリストはテキストボックスで指定できるようにする。
  • 後からエラーなどを終えるように実行ログを別ファイルとして吐き出す。

コード

絶対改善余地があるけどこんな感じ。


# 疎通確認対象IPアドレス情報の初期化
$IPaddressList = $null

# CSVテーブルの用意
$CSVdatas = @()

# 日付の取得
$date = Get-Date -Format "yyyyMMdd";

# 時間の取得
$time = Get-Date -Format "HHmmss";

# ホスト名の取得
$hostname = hostname

# 調査結果を出力するフォルダ
$scriptPath = $MyInvocation.MyCommand.Path
$scriptPath_split = Split-Path -Parent $scriptPath
$ResultFolder = ($scriptPath_split+"\"+$hostname+"_結果")

# 調査結果出力結果フォルダがなかったら作成
if( -not (Test-Path $ResultFolder) ) {
    New-Item $ResultFolder -Type Directory
}

# 実行結果出力ファイル名
$ExecuteLogFile = ( "\"+$hostname+"_ExecuteLog_"+$date+"_"+$time+".log" )

#実行結果出力フォルダとファイル名のマージ
$ExecuteLog = Join-Path $ResultFolder $ExecuteLogFile

# アセンブリ読み込み
Add-Type -AssemblyName System.Windows.Forms
Add-Type -AssemblyName System.Drawing

# フォーム作成
$Form = New-Object System.Windows.Forms.Form
$Form.Size = New-Object System.Drawing.Size(400,130)
$Form.Text = "Ping&TCPポート疎通確認ツール"

# ラベル作成
$LabelFilePath = New-Object System.Windows.Forms.Label
$LabelFilePath.Location = New-Object System.Drawing.Point(20,10)
$LabelFilePath.Size = New-Object System.Drawing.Size(300,20)
$LabelFilePath.Text = "IPアドレスリストのファイル(CSVのみ)を入力してください"
$Form.Controls.Add($LabelFilePath)

# 入力用テキストボックス
$TextBoxFilePath = New-Object System.Windows.Forms.TextBox
$TextBoxFilePath.Location = New-Object System.Drawing.Point(20,30)
$TextBoxFilePath.Size = New-Object System.Drawing.Size(300,20)
$Form.Controls.Add($TextBoxFilePath)

# 参照ボタン
$ButtonFilePath = New-Object System.Windows.Forms.Button
$ButtonFilePath.Location = New-Object System.Drawing.Point(320,30)
$ButtonFilePath.Size = New-Object System.Drawing.Size(40,20)
$ButtonFilePath.Text = "参照"
$Form.Controls.Add($ButtonFilePath)

# OKボタン
$ButtonOK = New-Object System.Windows.Forms.Button
$ButtonOK.Location =  New-Object System.Drawing.Point(230,60)
$ButtonOK.Size = New-Object System.Drawing.Size(60,20)
$ButtonOK.Text = "OK"
$Form.Controls.Add($ButtonOK)

# Cancelボタン
$ButtonCancel = New-Object System.Windows.Forms.Button
$ButtonCancel.Location =  New-Object System.Drawing.Point(300,60)
$ButtonCancel.Size = New-Object System.Drawing.Size(60,20)
$ButtonCancel.Text = "キャンセル"
$ButtonCancel.DialogResult = "Cancel"
$Form.Controls.Add($ButtonCancel)

# フォームを最前面に表示
$form.Topmost = $True

# 参照ボタンをクリック時の動作
$ButtonFilePath.add_click{

    #ダイアログを表示しファイルを選択する
    $Dialog = New-Object System.Windows.Forms.OpenFileDialog
    $Dialog.Filter = "CSVファイル(*.csv) | *.csv"
    if($Dialog.ShowDialog() -eq "OK"){
        $TextBoxFilePath.Text = $Dialog.FileName
    }
}

# OKボタンをクリック時の動作
$ButtonOK.add_click{

    #ファイルパスが入力されていないときは背景を黄色にする
    if($TextBoxFilePath.text -eq ""){
        $TextBoxFilePath.BackColor = "yellow"
    }else{
        $Form.DialogResult = "OK"
    }
}


Start-Transcript $ExecuteLog

# フォームを表示し処理が完了したら結果を返す
$FormResult = $Form.ShowDialog()
if($FormResult -eq "OK"){

$IPaddressList = $TextBoxFilePath.Text

# 調査結果出力ファイル名
$ResultFile = ( "\"+$hostname+"_Ping&TCP_"+$date+"_"+$time+".csv" )

# 調査結果出力フォルダとファイル名のマージ
$Result = Join-Path $ResultFolder $ResultFile

echo $IPaddressList"のPing&TCP疎通確認を開始します。この処理は数分ほどかかる場合があります。調査中にPowershellのウィンドウのサイズ変更をしないでください。"

###進捗表示用###
echo "IPアドレス数取得中"
$GetIPList = Import-CSV $IPaddressList
$IPCount = $GetIPList.Length
$counter   = 0
echo ("IP数="+$IPCount)
echo "調査開始"
echo ""
$denominator = "/"+[string]$IPCount

ForEach($a in $GetIPList){
    $counter ++;
    Write-Progress -activity "進捗状況" -status $counter$denominator -percentComplete ($counter / $IPCount * 100)
   if( $a.IPaddress -eq ""){
    } else {
            $CSVdata = New-Object PSObject | Select-Object IPaddress,Ping,TCPResult,ALL
        
            $TCPItem =  Test-NetConnection $a.IPaddress -port XXX 
                        
            $CSVdata.IPaddress = $a.IPaddress
            $CSVdata.Ping =  $TCPItem.PingSucceeded
            $CSVdata.TCPResult =  $TCPItem.TcpTestSucceeded
            $CSVdata.ALL = $TCPItem | select-object -Property * | Out-String
            $CSVdatas += $CSVdata

           }
   }

$CSVdatas | Export-CSV $Result -Encoding Default -NoTypeInformation

Invoke-item $Result

} else {

        echo "操作はキャンセルされました"
        }

Stop-Transcript

実行イメージ

2021/5/12追記
事例ではSNMP161,162ポートを対象にしているが、よく考えたらUDPポートなのでTest-NetConnectionコマンドではFALSEに決まっている・・・・。TCPポートのみが対象なのでご注意ください。

IPaddressリストの選択
実行中画面。
出力結果CSV

注意点と補足

  • PowerShellが実行可能な環境である必要があります。
  • 本ツールで疎通確認できるのはTCPポートだけです。

改版履歴

2021/05/12 
SNMPポート161、162を対象としていたが、UDPは疎通確認できないのでその旨全体的に修正した。

2021/05/06 
初版公開

コメント

タイトルとURLをコピーしました