PACファイル(プロキシ自動設定ファイル)の記述方法完全版
はじめに
- PACファイルとは、Proxy Auto-Configurationの略で、ブラウザのプロキシ設定を自動的に管理するためのファイルです。
- PACファイルには、JavaScriptの関数が記述されており、ブラウザがアクセスするURLやホスト名に応じて、使用するプロキシを決定します。
- 本記事では、PACファイルの記述方法について、基本概念から応用例まで詳しく解説します。
ファイル名
PACファイルは拡張子「.pac」でなければなりません。
サーバーの設定
- PACファイルをダウンロードできるように、MIMEタイプに「.pac」拡張子を下記のように設定する必要があります。
application/x-ns-proxy-autoconfig
IISの場合は、IISマネージャでMIMEの種類を開き、追加で、ファイル名の拡張子に
.pac
、MIMEの種類にapplication/x-ns-proxy-autoconfig
を設定します。
PACファイルの基本構造
- PACファイルは、次のようなJavaScriptの関数を必ず含める必要があります。
function FindProxyForURL(url, host) { // プロキシ設定を返すコード }
- この関数は、引数としてURLとホスト名を受け取り、プロキシ設定を表す文字列を返します。
- プロキシ設定の文字列は、次のような書式に従います。
- DIRECT:プロキシを使用せずに直接接続する
- PROXY host:port:指定されたプロキシを使用する
- SOCKS host:port:指定されたSOCKSサーバーを使用する
- HTTP host:port:指定されたHTTPプロキシを使用する(Firefoxのみ)
- HTTPS host:port:指定されたHTTPSプロキシを使用する(Firefoxのみ)
- SOCKS4 host:port, SOCKS5 host:port:指定されたSOCKSサーバーを(指定されたSOCKSバージョンで)使用する(Firefoxのみ)
- プロキシ設定の文字列は、セミコロンで区切って複数指定することができます。その場合、最も左にある有効な設定が優先されます。
- PACファイルで使用できる関数と変数
- PACファイルでは、JavaScriptの標準的な関数や変数に加えて、次のような特殊な関数や変数が使用できます。
- ホスト名に基づく条件
- isPlainHostName(host):ホスト名にドットが含まれない場合にtrueを返す
- dnsDomainIs(host, domain):ホスト名が指定されたドメインと一致する場合にtrueを返す
- localHostOrDomainIs(host, hostdom):ホスト名が指定されたホスト名またはドメインと一致する場合にtrueを返す
- isResolvable(host):ホスト名がDNSで解決できる場合にtrueを返す
- isInNet(host, pattern, mask):ホスト名が指定されたパターンとマスクに一致するIPアドレスを持つ場合にtrueを返す
- 関連するユーティリティ関数
- dnsResolve(host):ホスト名からIPアドレスを取得する
- convert_addr(ipaddr):IPアドレスから整数値に変換する
- myIpAddress():自分自身のIPアドレスを取得する
- dnsDomainLevels(host):ホスト名に含まれるドットの数を取得する
- URL/ホスト名に基づく条件
- shExpMatch(str, shexp):文字列が指定されたシェル式に一致する場合にtrueを返す
- 時刻に基づく条件
- weekdayRange(wd1, wd2, gmt):現在の曜日が指定された範囲内にある場合にtrueを返す
- dateRange(day1, month1, year1, day2, month2, year2, gmt):現在の日付が指定された範囲内にある場合にtrueを返す
- timeRange(hour1, min1, sec1, hour2, min2, sec2, gmt):現在の時刻が指定された範囲内にある場合にtrueを返す
- ログ用ユーティリティ
- alert(message):メッセージをログに出力する
- 定義済みの連想配列(非推奨)
- ProxyConfig.bindings:プロキシ設定の値をキーとして持つオブジェクト
- ホスト名に基づく条件
- PACファイルでは、JavaScriptの標準的な関数や変数に加えて、次のような特殊な関数や変数が使用できます。
PACファイルの記述例
ここでは、PACファイルの記述方法をいくつかの例で紹介します。
- 例1:特定のドメインにはプロキシを使用せず、それ以外はプロキシを使用する。
function FindProxyForURL(url, host) { if (dnsDomainIs(host, ".example.com")) { return "DIRECT"; } else { return "PROXY 192.168.100.20:8080"; } }
説明:もしURLが”.example.com”ドメインの場合はプロキシを使用しないで直接接続する。それ以外は、プロキシ192.168.100.20:8080を使用する。
- 例2:特定のIPアドレス範囲にはプロキシを使用せず、それ以外はプロキシを使用する。
function FindProxyForURL(url, host) { if ( isInNet(host, "10.0.0.0", "255.0.0.0") || isInNet(host, "172.16.0.0", "255.240.0.0") || isInNet(host, "192.168.0.0", "255.255.0.0") ) { return "DIRECT"; } else { return "PROXY 192.168.100.20:8080"; } }
説明:もしIPアドレスが、10.0.0.0/8、172.16.0.0/12、192.168.0.0/16の範囲に含まれる場合はプロキシを使用しないで直接接続する。それ以外はプロキシ192.168.100.20:8080を使用する。
- 例3:特定のURLパターンにはSOCKSサーバーを使用し、それ以外はプロキシを使用する。
function FindProxyForURL(url, host) { if (shExpMatch(url, "://.example.com/*")) { return "SOCKS socks.example.com:1080"; } else { return "PROXY 192.168.100.20:8080"; } }
説明:もしURLが”.example.com”ドメインの場合はSOCKSサーバーsocks.example.com:1080を使用し、それ以外はプロキシ192.168.100.20:8080を使用する。
- 例4:特定の曜日や時刻にはプロキシを使用せず、それ以外はプロキシを使用する。
function FindProxyForURL(url, host) { if (weekdayRange("SAT", "SUN") || timeRange(18, 0, 0, 9, 0, 0)) { return "DIRECT"; } else { return "PROXY 192.168.100.20:8080"; } }
説明:土曜日と日曜日の場合または、18:00~09:00まではプロキシを使用しないで直接接続する。それ以外はプロキシ192.168.100.20:8080を使用する。
- 例5:社内で運用しているWebサーバなどにある、ホスト名がNetBIOS名の場合(”.”を含まない)はプロキシを使用せず、それ以外はプロキシを使用する。
function FindProxyForURL(url, host) { if (isPlainHostName(host)){ return "DIRECT"; } else { return "PROXY 192.168.100.20:8080"; } }
説明:アクセスするURLが”http://example/”、”https://intrasite/”などホスト名が”.”を含まない場合はプロキシを使用しないで直接接続する。それ以外はプロキシ192.168.100.20:8080を使用する。
- 例6:ホスト名がNetBIOS名の場合(”.”を含まない)または社内のローカルドメインの場合はプロキシを使用せず、それ以外はプロキシを使用する。
function FindProxyForURL(url, host) { if ( isPlainHostName(host) || shExpMatch(host, "*.intra1.local") || shExpMatch(host, "*.intra2.local") || shExpMatch(host, "*.intra3.local") ){ return "DIRECT"; } else { return "PROXY 192.168.100.20:8080"; } }
説明:アクセスするURLが”http://example/”、”https://intrasite/”などホスト名が”.”を含まない場合、またはホスト名が”*.intra1.local”、”*.intra1.local”、”*.intra1.local”のパターンに一致する場合はプロキシを使用しないで直接接続する。
それ以外はプロキシ192.168.100.20:8080を使用する。 - urlパラメータ
アクセスするURLです。
例:http://www.example.com/ - hostパラメータ
URLから抽出したホスト名です。
例:www.example.com - urlパラメータに渡される値のHTTPプロトコルとHTTPSプロトコルでの違い
FindProxyForURL(url, host)
関数では、url
パラメータにはアクセスするURLが渡されます。ただし、HTTPとHTTPSでこのurl
パラメータの内容に違いがあります。- HTTPの場合:
url
パラメータには完全なURL(パスとクエリを含む)が渡されます。 - HTTPSの場合:
url
パラメータには、パスとクエリの部分が削除されたURLが渡されます。
例:アクセスするURL urlに渡される値 hostに渡される値 HTTPの場合 http://www.example.com/site/sample/index.html http://www.example.com/site/sample/index.html www.example.com HTTPSの場合 https://www.example.com/site/sample/index.html https://www.example.com/ www.example.com
- HTTPの場合:
これは、HTTPS通信の内容が暗号化されており、PACファイル(特にJavaScriptコード)がHTTPSリクエストの詳細(パスやクエリパラメータなど)を見ることができないためです。
ただし、この挙動はブラウザによります。例えば、現在のEdgeやChromeではこの設定を無効にすることはできませんが、Firefoxでは、この設定はnetwork.proxy.autoconfig_url.include_path
で制御できます。
したがって、PACファイルを使用する際は、これらの違いを理解し、必要に応じて適切に対応することが重要です。
まとめ
- PACファイルでは、JavaScriptの関数と変数を使って、プロキシ設定のロジックを記述します。
- PACファイルは、ブラウザのプロキシ設定を自動的に管理するためのファイルです。
- PACファイルの記述方法は、様々な条件や目的に応じてカスタマイズできます。
コメント
You completed a few good points there. I did a search on the topic and found a good number of people will go along with with your blog.
Thank you. There were few articles about PAC files, so I compiled them myself.