メモ:プロキシ自動構成PACファイルから使用するProxyを取得する

 以前から「どうやるんだろ? JScript.DLLキックつーのもなぁ…」と思っていたのだが、WinHTTPでサービス用APIが提供されていたのは知らんかった。
MSの解説はこちら
WinHttpGetProxyForUrlを使えばよい、とのこと。

 テスト用にDelphi6で書いてみる。残念ながらD6にはWinHTTPのヘッダファイルは付いていないので、とりあえず必要な定数と型(WINHTTP_AUTOPROXY_OPTIONS、WINHTTP_PROXY_INFO)WinHttpOpen、WinHttpGetProxyForUrl だけMSDN見ながらポーティング。抜粋しとくとこんな感じ。


PWINHTTP_AUTOPROXY_OPTIONS
= ^WINHTTP_AUTOPROXY_OPTIONS;
WINHTTP_AUTOPROXY_OPTIONS = record
dwFlags: DWORD;
dwAutoDetectFlags: DWORD;
lpszAutoConfigUrl: LPCWSTR;
lpvReserved: Pointer;
dwReserved: DWORD;
fAutoLogonIfChallenged: BOOL;
{$EXTERNALSYM WINHTTP_AUTOPROXY_OPTIONS}
TWINHTTP_AUTOPROXY_OPTIONS
= WINHTTP_AUTOPROXY_OPTIONS;
LPWINHTTP_AUTOPROXY_OPTIONS
= PWINHTTP_AUTOPROXY_OPTIONS;
{$EXTERNALSYM LPWINHTTP_AUTOPROXY_OPTIONS}

PWINHTTP_PROXY_INFO
= ^WINHTTP_PROXY_INFO;
WINHTTP_PROXY_INFO = record
dwAccessType: DWORD;
lpszProxy: LPWSTR;
lpszProxyBypass: LPWSTR;
{$EXTERNALSYM WINHTTP_PROXY_INFO}
TWINHTTP_PROXY_INFO = WINHTTP_PROXY_INFO;
LPWINHTTP_PROXY_INFO = PWINHTTP_PROXY_INFO;
{$EXTERNALSYM LPWINHTTP_PROXY_INFO}

function WinHttpOpen(
pwszUserAgent: PWideChar;
dwAccessType: DWORD;
pwszProxyName, pwszProxyBypass: PWideChar;
dwFlags: DWORD
): HINTERNET; stdcall;

function WinHttpGetProxyForUrl(
hSession: HINTERNET;
lpcwszUrl: LPCWSTR;
lpAutoProxyOptions:
PWINHTTP_AUTOPROXY_OPTIONS;
pProxyInfo: PWINHTTP_PROXY_INFO
): BOOL; stdcall;

implementation
const
winhttpdll = 'winhttp.dll';

function WinHttpOpen;
external winhttpdll name 'WinHttpOpen';
function WinHttpGetProxyForUrl;
external winhttpdll name 'WinHttpGetProxyForUrl';

で、呼び出してみる。要するに、評価対象にしたいURLをWinHttpGetProxyForUrlに食わせてみると、PACを取ってきてキャッシュし、中の FindProxyForURL(url, host) で評価して結果を返してくれる。

var
hHttpSession: HINTERNET ;
AutoProxyOptions: WINHTTP_AUTOPROXY_OPTIONS;
ProxyInfo : WINHTTP_PROXY_INFO;

begin
 // セッションを作る
hHttpSession := WinHttpOpen('TEST',
WINHTTP_ACCESS_TYPE_NO_PROXY,
WINHTTP_NO_PROXY_NAME,
WINHTTP_NO_PROXY_BYPASS,
0 );

AutoProxyOptions.dwFlags
:= WINHTTP_AUTOPROXY_CONFIG_URL;
AutoProxyOptions.lpszAutoConfigUrl
:= 'http://my.pac.server/Proxy.Pac';
AutoProxyOptions.fAutoLogonIfChallenged
:= FALSE;

 // PAC評価
if (WinHttpGetProxyForUrl(
hHttpSession,
'http://www.dest.com/', // 評価したいURL
@AutoProxyOptions,
@ProxyInfo
)) then …


 結果はProxyInfo(WINHTTP_PROXY_INFO)に返ってくる。

 ProxyInfo.dwAccessType:
  WINHTTP_ACCESS_TYPE_DEFAULT_PROXY (0) 設定時のみ
  WINHTTP_ACCESS_TYPE_NO_PROXY (1) 直接接続
  WINHTTP_ACCESS_TYPE_NAMED_PROXY (3) Proxy経由

 ProxyInfo.lpszProxy: Proxyのリスト
 Proxyinfo.lpszProxyBypass:プロクシのバイパスのリスト
[PR]
by SIGNAL-9 | 2006-12-27 14:14 | TIPSとかKludgeとか
<< iTextSharpでPDFの... あの映画はなんだったのか? >>