IEのサポート終了とWebBrowserに代わるブラウザコントロール

タグの編集
投稿者 ママネコ  (社会人) 投稿日時 2021/5/20 17:34:14
IEのサポート終了をYahoo!ニュースで見ました。
ついに来たかという感じです。
以前、WebBrowserコントロールを使用したアプリを作りましたが、
今後、WebBrowserコントロールはどうなっていくのでしょうか?
代替コントロールはあるのでしょうか?
投稿者 魔界の仮面弁士  (社会人) 投稿日時 2021/5/20 18:56:28
代わりに Chromium Embedded Framework はどうでしょうか。
https://support.google.com/webdesigner/answer/10043691?hl=ja

VB からだと CefSharp というライブラリが有名です。
https://www.youtube.com/watch?v=cpaCHIC6Dbo
投稿者 魔界の仮面弁士  (社会人) 投稿日時 2021/5/20 19:19:48
どうやら WebBrowser や WinINet についてはまだ生き残るそうです。
(サポート終了時期は未定)
https://twitter.com/ms_yuhara/status/1395054154716913665

新規作成する分については、WebBrowser から
ChromiumWebBrowser (CefSharp) に切り替えるのも手ですが、
WebBrowser とは使い方が異なってくるので、単純な置き換えとはならないですね。

CreateObject("InternetExplorer.Application") などによるオートメーションについては続報待ち。
投稿者 ママネコ  (社会人) 投稿日時 2021/5/26 10:09:40
魔界の仮面弁士さま、書き込みありがとうございます。
なるほど、今後のことを考えると、新しいライブラリに移行した方がよいようですね。
ただ、単純な置き換えにはならないとのこと、大変そうですね。

WebBrowserの使用では、WebBrowserのドキュメント(System.Windows.Forms.HtmlDocument)より
GetElementByIdで特定タグ(System.Windows.Forms.HtmlElement)を得たり、
GetElementsByTagNameでタグ要素のコレクションを得て、
指定タグの属性値を読み書きしたり、指定タグのInvokeMember("click")等を行ったことがあり、
これらはIE用のクラスを.net用にカプセル化したものなのだと思いますが、
他のライブラリでも同様のことができるのでしょうか?

投稿者 魔界の仮面弁士  (社会人) 投稿日時 2021/5/26 14:22:43
> なるほど、今後のことを考えると、新しいライブラリに移行した方がよいようですね。
そうですね。サイト側が IE 対応をいつまで続けるか…という問題もありますので、
IE に拘りがなければ、別の選択肢を模索しておくべきでしょう。

Web ページを画面に表示させるのではなく、別プロセスのブラウザーそのものを
操作する目的であれば、クロスプラットフォームな WebDriver (Selenium) が
ずいぶん前から業界標準となっています。
https://codezine.jp/article/detail/10225
https://www.w3.org/TR/2018/REC-webdriver1-20180605/

ただし近年はセキュリティ上の理由により、外部から操作中のブラウザーは、
リモート制御中であることがポップアップ表示されるようになっています。

もしもデータ収集が目的で、画面表示は必ずしも必要ではないのであれば、
curl.exe コマンドや、PowerShell Core の Invoke-WebRequest コマンドレットという手もあります。
https://qiita.com/uezo/items/66e20b064ffd5f239b9a

あくまでも画面表示が目的(かつブラウザーを制御したいわけでは無い)なら、
WebBrowser については生き残るので、現状維持という見方もでくなくはないですが、
やはり IE 終焉後に向け、先に紹介したような Chromium 系の WebBrowser コントロールを
使ってみては如何でしょう。同様に Gecko 系(FireFox) のコントロールもあります。


> 他のライブラリでも同様のことができるのでしょうか?
今までと同様、テキストを読み書きしたり、ボタンを押したりすることができますよ。
それを呼び出すための手順は、以前とほぼ同じになることもあれば、まったく異なる場合もあります。

ライブラリ固有のメソッドについては個別に調べる必要があり、単純移植とは
いかないかもしれませんが、DOM に由来したメソッドやプロパティは
他のライブラリでも活かしやすいので、今までの知識が生かせる場面は多いかと思います。


> これらはIE用のクラスを.net用にカプセル化したものなのだと思いますが、
ざっくり言えばそんな感じですが、もう少し掘り下げてみると。

document オブジェクトは、1997 年頃に Dynamic HTML のために用意された機構です。

御存知かも知れませんが、ここから操作できるオブジェクト群を総称して「DOM」と呼ぶことがあります。
(HtmlDocument クラスの DomDocument プロパティで得られるアンマネージオブジェクトなど)
DOM 操作の習得は、他のライブラリを使う場合にも重要な基礎技術となりますね。


ブラウザの外部制御技術は IE3 当時からありましたが(WebBrowser_V1)、外部からの
ドキュメント操作技術が進んだのは、DHTML が発展した IE4 以降だったと思います。

document 操作技術は W3C によって標準化され、1998年10月に
Document Object Model(DOM) Level 1 として勧告されました。
IE 以外のブラウザ(Netscape)でも同様の API セットが実装されています。
W3C 標準以前からあったブラウザ固有の機能は、DOM Level 0 とも呼ばれます。
https://ja.wikipedia.org/wiki/Document_Object_Model

今お使いの WebBrowser の場合、エンジンそのものは IE (Trident)であることから、
その Document から得られる DOM は IE 向けの API セットである MSHTML 系の実装です。

DOM で決まっているのはインターフェイスだけであり、そのインターフェイスを
どのように実装するかは各社まちまちですが、IE の場合は、ActiveX/COM  として
実装していることから、JScript / VBScript / VBA / Delphi / C++ / VB / C# といった
多数の ActiveX 対応言語から扱えるようになっています。

しかし COM オブジェクトのままだと .NET からは若干扱いにくいため、
ActiveX 版 MSHTML を .NET から利用しやすくカプセル化したもののひとつが
System.Windows.Forms.HtmlDocument となります。
(MSHTML の .NET 向けカプセル化には、他にも NetOffice などがあります)


> GetElementByIdで特定タグ(System.Windows.Forms.HtmlElement)を得たり、
getElementById メソッドは当時、DOM Level 1 として定義されていました。
getElementsByName メソッドは当時、DOM Level 2 ですね。
https://developer.mozilla.org/ja/docs/Web/API/Document/getElementById
https://developer.mozilla.org/ja/docs/Web/API/Document/getElementsByName

大文字小文字の違いには注意が必要ですし、ブラウザ固有の差異も多少ありますが、
標準化されたものなので、OS や言語やブラウザーが異なる他のライブラリでも
そのまま応用できる場面は多いでしょう。

> GetElementsByTagNameでタグ要素のコレクションを得て、
getElementsByTagName も標準化されています。ただし名前空間付きのタグを
指定する場合は、ライブラリによって手続きが異なる場合があります。
https://developer.mozilla.org/ja/docs/Web/API/Element/getElementsByTagName

> 指定タグのInvokeMember("click")等を行ったことがあり、
その呼び出しは、古い IE だと DOM Level 2 の click メソッドに相当します。
https://developer.mozilla.org/en-US/docs/Web/API/HTMLElement/click

InvokeMember そのものは、標準 DOM の機能ではないため、他のライブラリだと、
click 処理を発火させるために別の呼び方が必要になる可能性があります。
たとえば dispatchEvent メソッドなど。
http://yuuxxxx.hatenablog.com/entry/2013/09/20/224801
https://developer.mozilla.org/ja/docs/Web/API/EventTarget/dispatchEvent


MSHTML の機能は多岐にわたるため、DOM 機能のすべてを
.NET のマネージオブジェクトとして再実装するのではなく、
プロパティもメソッドもごちゃまぜにして、メンバー名指定による実行時バインドで
InvokeMember メソッドとして呼び出せるようにしてあります。

DOM の機能は今後も拡張されていく可能性があったため、
名前指定で呼び出せるような簡易設計にしたのでしょうね。

HtmlElment.InvokeMember では呼び出しきれない機能については、
HtmlElement.DomElement からアンマネージ版の DOM を取得して
MSHTML で提供される本来のメソッドを呼ぶことになります。