SendKeyについて

解決


年寄りの冷や水  2004-05-28 21:54:22  No: 83631  IP: [192.*.*.*]

いつも拝見させていただいております。
当方VB6/XPホームエディションSP1です。
インターネットコントロールを利用して自動的に目的ページ
へたどり着きたいと思って、テスト的に次のような記述でう
まく動作しました。

Private Sub Command1_Click()
  Me.WebBrowser1.Navigate "http://www.google.co.jp/"
  Do Until Me.WebBrowser1.Busy = False
        DoEvents
  Loop
  SendKeys "ヤフー", True
  SendKeys "{ENTER}", True
End Sub

ところが、本来の目的のページはアクセスするのに認証(ログイン
IDとパスワードを要求する認証ウィンド)がポップアップであら
われます。
このウィンドに対しては、上記のSendKeysがまったく機能しません。
本来的に無理なのでしょうか。
認証を求める機能なので根本的に無理ならあきらめようと思います
が方法があるのであれば、ヒントだけでも御教示いただければ、幸
いです。
当方50歳会社員でVBはまったくの初心者・自己流です。
若かりしころCPU 6800 のマシンコードでプログラムを書いていた
経験がかろうじてありますが、VBはとっても便利なようで奥深く
久々にわくわくしながら取り組んでいる今日この頃です。
何とぞよろしくお願い申しあげます。

編集 削除
のん  2004-05-28 22:20:06  No: 83632  IP: [192.*.*.*]

SendKeysが機能していないのではなく、認証ダイアログがモーダルダイアログ
で表示されているので、そのあとのSendKeysの処理が動いていないだけだと思います。
VBにはデバッグでステップ実行というものがありますのでどこで処理が止まって
いるか確認してみてください。

編集 削除
年寄りの冷や水  2004-05-28 23:38:24  No: 83633  IP: [192.*.*.*]

のん様
早速のご指導ありがとうございます。
ご指導の通り試して見ました。
Do Until Me.WebBrowser1.Busy = False
            DoEvents  ←停止
    Loop

Me.WebBrowser1.Navigate "http://xxxxxxx/
を指定しているので当然といえば当然ですね。

SendKeysの信頼性が落ちるの覚悟の上で適当な
時間待ちの処理を入れてSendKeysを実行する処
理に変えてみてテストしたいと思います。
(=Do Until Me.WebBrowser1.Busy = Falseの
処理を削除してみます)

結果はまた明日ご報告させていただきます。
ほんとうにありがとうございました。

編集 削除
年寄りの冷や水  2004-05-29 00:02:21  No: 83634  IP: [192.*.*.*]

>結果はまた明日ご報告させていただきます。
などといっておりましたが、寝るに寝られず試して見ました。

Private Sub Command1_Click()
Me.WebBrowser1.Navigate "http://xxxxxxxxxxxxxxx/"
DoEvents
MsgBox "十分待ちましたか?"

'======================================================
DoEvents

SendKeys "LOGIN_ID", True      'ログインID
SendKeys "{TAB}", True      '次のフィールドへ
SendKeys "PASSWORD", True      'パスワード
SendKeys "{ENTER}", True
End Sub

nexbe

編集 削除
年寄りの冷や水  2004-05-29 00:19:07  No: 83635  IP: [192.*.*.*]

のん様
途中で送信してしまったようです。お見苦しい
発言で申し訳ありません。

Private Sub Command1_Click()
Me.WebBrowser1.Navigate "http://xxxxxxxxxxxxxxx/"
DoEvents
MsgBox "十分待ちましたか?"

'======================================================
DoEvents

SendKeys "LOGIN_ID", True      'ログインID
SendKeys "{TAB}", True      '次のフィールドへ
SendKeys "PASSWORD", True      'パスワード
SendKeys "{ENTER}", True
End Sub

をステップインで実行してみましたが、今度はどこで止まって
いるのかさっぱりわかりませんでした。

ソース上で行の色が変化している場所がありません。
デバッグ機能の使い方もかなりわかっておりませんが・・・。

認証ポップアップウインドウの裏に隠れていた

MsgBox "十分待ちましたか?"

をアクティブにしてOKをクリックしましたが状況は変化しません。
(認証ウィンドが表示されたまま)

プログラムは一時停止しません。

重ね重ねご迷惑おかけしますが、御指導・御教示よろしくお願い
いたします。

編集 削除
Say  2004-05-29 01:51:54  No: 83636  IP: [192.*.*.*]

>MsgBox "十分待ちましたか?"
>をアクティブにしてOKをクリックしましたが状況は変化しません。
>(認証ウィンドが表示されたまま)

まあ、MsgBoxをアクティブにした時点で
フォーカス失っているでしょうから・・・。

「ポップアップウインドウ」が何者なのか不明ですので
なんともいえませんが、
DocumentCompleteでSendKeysしたらどうなります?
(確実を期すなら、DocumentCompleteで「ポップアップウインドウ」の
存在チェックし(WindowならFindWindowやEnumWindowsなどで)、
見つかったらActiveにし、Focusをあて、
SendKeysするべきですが・・・ってここまでやるなら
SendKeysよりSendMessageしたほうがいいかも。)

もし制御が戻ってこないというなら、
別スレッド化別プロセス立てて監視することになるかも。
(それやるぐらいならWebBrowserでなく、
IEリモートオブジェクトをイベント付きで生成して、
objIE_DocumentCompleteとかでひっかけたほうがいいかも。)

編集 削除
のん  2004-05-29 09:23:58  No: 83637  IP: [192.*.*.*]

>をステップインで実行してみましたが、今度はどこで止まって
>いるのかさっぱりわかりませんでした。

やはり認証ダイアログがモーダルダイアログで表示されているので
処理がコントロール内から戻ってきていないのだと思います。

とりあえず、手動で認証ダイアログの表示を閉じてみてください。
制御が戻ってくるはずです。

そうであれば、Sayさんも仰っているように別スレッドで
その表示されている認証ダイアログに対して
SendMessageまたはPostMessageを行う必要がありそうですね。

編集 削除
年寄りの冷や水  2004-05-29 11:04:22  No: 83638  IP: [192.*.*.*]

のん様、Say様  ご親切なご指導ありがとうございました。
お二人のおっしゃる通り、SendKeys にこだわりすぎだったかも
しれません。

URL     => "zzzzzzzzzz"
user_id => "xxxxx"
pasword => "yyyyy" であった場合
いきなり
Me.WebBrowser1.Navigate "http://xxxxx:yyyyy@zzzzzzzzzz/"

で目的のサイトへのアクセスに成功しました。
たまたま目的のサイトの認証のみに有効なのかもわかりません。
もう少し皆様のご意見・方法など拝聴したく、しばらく解決
とせず、このままとさせていただきたいと思います。
ほんとうにありがとうございました。

編集 削除
魔界の仮面弁士  2004-05-29 15:31:10  No: 83639  IP: [192.*.*.*]

タイトルがSendKey「s」になっていないのはさておき。

> Me.WebBrowser1.Navigate "http://xxxxx:yyyyy@zzzzzzzzzz/"
URL の最初の "username:password@" を持つクリアテキスト認証機能は、
環境によっては使えないようにされている可能性があります。

理由は、セキュリティ情報 MS04-004 (サポート技術情報 832894) や、
下記のページを参照してみてください。
http://pcweb.mycom.co.jp/column/winxp/108/
http://support.microsoft.com/default.aspx?scid=kb;JA;837104

これを避けるためには、URLに直接パスワードを打ち込むのではなく、
下記のように、ヘッダにて認証を行う必要があります。

strAccount = UserName & ":" & Password
strAuthorization = (strAccountをBASE64で変換した文字列)
WebBrowser1.Navigate2 URL, Headers:="Authorization: Basic " & strAuthorization

編集 削除
年寄りの冷や水  2004-05-29 17:40:04  No: 83640  IP: [192.*.*.*]

魔界の仮面弁士様ありがとうございました。
予想していた通りオールマイティではなかったんですね。
ご指導いただいた方法の中で
>strAuthorization = (strAccountをBASE64で変換した文字列)
がわかりません。
BASE64 をこの掲示板で調べましたが、ありませんでした。
あつかましいとは思いますがもう少しお教えいただけませんで
しょうか?

編集 削除
魔界の仮面弁士  2004-05-30 00:17:33  No: 83641  IP: [192.*.*.*]

> BASE64 をこの掲示板で調べましたが、ありませんでした。
この掲示板だけではなく、www.google.co.jp などを使って、
もっと広範囲に調べて見てください。
BASE64に関する、詳しい資料が見つかるはずですよ。


詳細は、こちらを参照してください。
http://www.csl.sony.co.jp/cgi-bin/hyperrfc?rfc2045.txt

日本語訳は、こちら。
http://www.asahi-net.or.jp/~bd9y-ktu/dtd_f/rfc_f/rfc2045j.html


で。
上記だけだとわかりにくいかと思うので、少し説明しますと、BASE64とは、
「3バイト分のデータを、4文字のテキストに変換するためのエンコード」です。

データ中の3バイト(24bit)を、6bit×4 に分解し、その6bit分を、
ある規則で英数字に変換するという物です。

# BASE64の64には、「6ビットの文字、4の倍数」の意味があります。

分解された6bitの64個(64=2^6)のデータを、0〜63の数値に置き換えて、
  0〜25なら、A〜Z
  26〜51なら、a〜z
  52〜61なら、0〜9
  62なら、+
  63なら、/
という変換法則にて、英数字にすれば、BASE64エンコードとなります。


なお、元データが24bitの倍数になっていない時は、変換結果の最後に
余白文字として「=」を1個か2個追加して、結果を4文字の倍数の文字に
揃える事になります。

編集 削除
魔界の仮面弁士  2004-05-30 00:20:13  No: 83642  IP: [192.*.*.*]

例を挙げて説明して見ます。

たとえば、
    『VB6』
という文字列をBASE64変換すると、結果は
    『VkI2』
という文字列になります。


まず、元データを2進数に変換します。
    V → Asc("V") → 86 → 2進数で 01010110
    B → Asc("B") → 66 → 2進数で 01000010
    6 → Asc("6") → 54 → 2進数で 00110110
つまり、2進数で
    01010110  01000010  00110110
というデータですね。


これを6bit単位に区切ります。
    010101  100100  001000  110110

そして、先の変換法則で置き換えると、
    2進数 010101 (10進数で21) → V
    2進数 000100 (10進数で 4) → k
    2進数 001000 (10進数で 8) → I
    2進数 110110 (10進数で54) → 2
という事になるわけです。


もし、元データが『VB』だけなら、
    010101  100100  0010??  ??????
となりますので、
    「V」、「k」、「I〜Lのいずれか」、余白の「=」
となり、結果は『VkI=』となります。

元データが『V』だけなら、
    010110  10????  ??????  ??????
となり、
    「V」、「g〜vのいずれか」、余白の「=」、余白の「=」
となり、結果は『Vg==』です。

『VB6.0』なら、『VkI2LjA=』です。



なお、BASE64変換するための変換関数を自作するもの一興かと思いますが、
それが面倒なら、フリーの変換用DLL(BASP21など)を利用されるもの手かと。

編集 削除
年寄りの冷や水  2004-05-30 00:54:00  No: 83643  IP: [192.*.*.*]

魔界の仮面弁士様。ご丁寧な説明本当にありがとうございました。
0と1のご説明、完璧に理解できました。

BASP21はメールの送受信で結構使いこなしていたつもりだったんですが
BASE64のエンコード機能まで持っているとは、知らなかったです。

0と1が出てきたんで若かりしころマシンコードでプログラムを製作し
ていた頃を思い出し、久々にファイトが沸いてきました。
自作の関数にチャレンジしてみようと思います。
まさに「年寄りの冷や水」ですね。・・・・。

本当にご丁寧な説明ありがとうございました。
「解決」とさせていただきます。

編集 削除
年寄りの冷や水  2004-05-30 00:55:46  No: 83644  IP: [192.*.*.*]

解決チェック

編集 削除