InternetExplorer11で変更されたUserAgent書式に対応する

今まで問題なく稼動していたとあるシステムにて、InternetExplorer11(以下IE11)のブラウザにて不具合が発生する旨の報告を受けて調べたところ、IE11ではユーザーエージェントの書式が変更になっていて、ブラウザ判定処理が「不明なブラウザ」として処理されていたことがわかった。
今までユーザーエージェントのブラウザバージョントークン(UAの”MSIE 9.0″とか書いてある部分)でIEブラウザの判定とIEバージョンを取得していたのだが、IE11からはこのブラウザバージョントークンがなくなってしまい、新たに”rv”というリビジョントークンが設けられてました(※IE11標準ブラウザモード)。
今後IE11を含めてユニークにIEを判定するには、ブラウザエンジンであるトライデントトークン(UAの”Trident/7.0″とか書いてある部分)の存在確認もOR条件で判定しないといけなくなった。

IE11のUserAgent

  • Mozilla/5.0 (Windows NT 6.3; WOW64; Trident/7.0; Touch; rv:11.0) like Gecko
  • Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.3; Trident/7.0)

問題なのが、IEの互換表示モードだ。IEの互換表示モードはIE9から導入された機能だが、このモードにすると現状の全てのIEにおいてUAのブラウザバージョントークンがIE7となってしまう。互換表示の際についても正確にIE11と判定させるには、まずトライデントトークンを先に判定して、トライデントのバージョンが7.0以上だったらIE11として判定しリビジョントークンからブラウザバージョンを取得し、それ以外はブラウザバージョントークンからバージョンを取得するという処理にする必要がある。さらにIE11より下位の互換表示モードをもつIE9とIE10用の処理も必要だ。
また、IE7以下はトライデントトークンを持っていないので、IE7用の判定処理も別途必要となる…(いやはや、まるで嫌がらせのような仕様だな…)。

試しにこのDEVLABで利用している独自のクライアントデバイス判定処理(PHP)で、IE11にも対応した判定処理に修正してみた。

まずは、今までのIE判定処理内容。
[php]
$ua = $_SERVER[‘HTTP_USER_AGENT’];
$results[‘browser’] = ”;
$results[‘version’] = ”;
if (preg_match(‘/(MSIE \d{1,}?(.\d{1,}?){1,}?;)/’, $ua, $mtcs)) {
$results[‘browser’] = ‘msie’;
list(, $vstr) = explode(‘ ‘, str_replace(‘;’, ”, $mtcs[0]));
$results[‘version’] = $vstr;
}
[/php]

ここを、下記のように変更しました。
バージョン番号抽出部の処理もちょっとダサかったので、修正しました。

[php]
$ua = $_SERVER[‘HTTP_USER_AGENT’];
$results[‘browser’] = ”;
$results[‘version’] = ”;
if (preg_match(‘/Trident\/(\d{1,}(.\d{1,}){1,}?)/i’, $ua, $mtcs)) {
$results[‘browser’] = ‘msie’;
if ((float)$mtcs[1] >= 7) {
if (preg_match(‘/rv:(\d{1,}(.\d{1,}){1,}?)/i’, $ua, $mtcs)) {
$results[‘version’] = (float)$mtcs[1];
} else {
$results[‘version’] = 11.0;
}
} elseif ((float)$mtcs[1] >= 6) {
$results[‘version’] = 10.0;
} elseif ((float)$mtcs[1] >= 5) {
$results[‘version’] = 9.0;
} elseif ((float)$mtcs[1] >= 4) {
$results[‘version’] = 8.0;
}
}
if (empty($results[‘browser’])) {
if (preg_match(‘/MSIE\s(\d{1,}(.\d{1,}){1,}?);/i’, $ua, $mtcs)) {
$results[‘browser’] = ‘msie’;
$results[‘version’] = (float)$mtcs[1];
}
}
[/php]

IEを判定するだけでこれだけのステップがいるというのがかなり嫌な感じだ…。

本音を言えば、ブラウザエンジンが変更されたとか、大幅な根本仕様の変更以外のアップグレードでUserAgentのフォーマットを変更するのはやめてもらいたいものだ…。

おすすめ記事