本連載ではここ数回、PowerShellスクリプトを使ってWebページを取得する方法を試している。前回は「curl.exe」を使ってWebページが取得できることを確認した。curlは双方向の通信にも利用できる便利なユーティリティなのだが、curlでは取得できないWebページも存在する。今回はそういった場合の対処方法を模索していく。
curlを使ったWebページ作成PowerShellスクリプト
前回作成したPowerShellスクリプト「netcat.ps1」は次の通りだ。
#!/usr/bin/env pwsh
#========================================================================
# URLで指定されたリソースを取得
#========================================================================
#========================================================================
# 引数を処理
# -URL url WebリソースのURL
#========================================================================
Param(
[Parameter(Mandatory=$true)][String]$URL = "",
[String]$Agent = "Mozilla/5.0 (Windows NT 10.0; Win64; x64)"
)
#========================================================================
# Webリソース取得に利用するアプリケーション
#========================================================================
$curl='C:\Windows\System32\curl.exe'
#========================================================================
# curl を使って取得する
#========================================================================
& $curl --location `
-A $Agent `
-get $URL
今のところ、ただの「curl.exe」へのラッパースクリプトにしかなっていないのだが、netcat.ps1をPowerShellスクリプトとして独立させているのには理由がある。curlは便利なコマンドではあるのだが、curlでは取得できないWebページが存在する。取得できない場合には別のソフトウエアで取得したいので、別スクリプトとして独立させている。netcat.ps1の中で使用するソフトウエアを切り分ければよく、ユーザーは何も気にせずnetcat.ps1を実行すればよいという状態にしたいわけだ。
curlでは取得できないWebページ
先述の通り、Webページは必ずしもcurlで取得できるとは限らない。Webサーバによってはアクセス元が人間であるかどうか判定しているものがあり、人間以外に対してはコンテンツの提供を行わないものがあるからだ。そういった意図がないページであっても、コンテンツを動的に表示するタイプのWebページだと、curlコマンドでは想定しているデータが得られないこともある。
例えば、次のWebページを見てみよう。このWebページはMicrosoftが月例の累積更新プログラムの影響を行う際にまとめサイト的に公開しているもので、「どのプロダクトにセキュリティ脆弱性が含まれているか」といった要約情報が掲載されている。
このWebページをMicrosoft Edgeで閲覧すると次のようになる。
当然だが、Webブラウザでは想定通りにコンテンツが表示されている。
では、このページを前回作成したnetcat.ps1で取得しようとするとどうなるか。次のようになる。
PS C:\Users\daichi> netcat.ps1 https://msrc.microsoft.com/update-guide/releaseNote/2022-Jun
<!doctype html><html lang="en" dir="ltr"><head><meta charset="utf-8"/><meta http-equiv="Pragma" content="no-cache"/><meta http-equiv="cache-control" content="no-cache, no-store, must-revalidate"/><link rel="icon" href="/update-guide/favicon/favicon.svg"/><meta name="viewport" content="width=device-width,initial-scale=1"/><meta name="theme-color" content="#0078d4"/><meta name="color-scheme" content="dark light"/><meta name="description"/><meta name="keywords"/><link rel="apple-touch-icon" href="/update-guide/favicon/logo192.png"/><link rel="manifest" href="/update-guide/manifest.json"/><title>Security Update Guide - Microsoft Security Response Center</title><style>@media (prefers-color-scheme:dark){html{color:#f5f5f5;background:#000}}</style><script defer="defer" src="/update-guide/static/js/main.9f990607.js"></script><link href="/update-guide/static/css/main.400450b5.css" rel="stylesheet"></head><body><noscript>You need to enable JavaScript to run this app.</noscript><div id="root"></div><script nomodule>S
ring.prototype.endsWith||(String.prototype.endsWith=function(t,n){return(void 0===n||n>this.length)&&(n=this.length),this.substring(n-t.length,n)===t})</script></body></html>
PS C:\Users\daichi>
Microsoft Edgeで先ほどのWebページのソースコードを閲覧すると次のようになる。
Webブラウザでもcurlでも、同じソースコード(HTML)を取得できていることがわかる。
セキュリティ脆弱性情報はユーザーが自分で回ってチェックするよりも、定期的に自動取得して自動解析を行い、必要があるときだけユーザーに通知が届くようにしておきたい。この方法なら、管理する対象のソフトウエアが増えたとしても、脆弱性をチェックする手間を低減することができる。逆に言えば、そうでもしないとやっていられない。
しかし、Microsoft Edgeで表示させたHTMLのソースコードからも、netcat.ps1で取得したHTMLソースコードからも、必要な情報を得ることができない。これでは処理の自動化もできず、結局人間が手動で定期的にチェックしなければいけないということになる。