【チュートリアル】VBAでIE自動化ツールを作る(その15) 書籍検索ツール開発(実装・エラー制御と処理の高速化)

こんにちは、自動化エンジニアをしています。kozuです。

エクセルVBAによりWebページの要素(テキストボックス、ボタンなど)を操作したり、表示されている情報を取得する自動化ツールの開発方法を紹介します。実際のWebサイトを自動操作し情報を取得するマクロの開発を通して、自動化ツールの開発について学ぶことができます。

本連載では、チュートリアルということでVBAの開発手順から始め、IEの操作についてどのようなページでも共通で使用できるコード(共通部品)を作成します。最初に共通部品を作成しておくことで、自分でIEの自動化ツールを作成する際に少量の実装で効率よく開発できるようになります。

この章では、これまでに実装した共通部品を使用したIEの自動化ツールの開発を行っていきます。出版社(秀和システム)のWebサイトから指定した条件で新しい本を検索するツールを開発します。前回までにツールとしての機能は完成しました。今回はエラー制御と処理の高速化について、どのようなツールを作成する場合にも当てはまる事項を対応します。

1.対象者

ブラウザで定期的に手作業で行っているデータ入力やデータ収集等の作業から開放されたい、楽したいと考えている方を対象に、エクセルVBAで自動化するツールの開発ができるようになることを目指しています。プログラミングの経験がない方でも、コードをコピーすれば開発できるようになっています。

2.開発環境

以下の環境を使用します。
バージョンは異なっていても問題ないと思います。
・OS:Windows10
・エクセル:Microsoft Excel2007
・ブラウザ:InternetExploer11

3.0件の制御

実行時に検索結果が0件の場合、以下の画像のようにVBAの処理でエラーになります。検索結果に本の要素がなく、次のページをクリックしようとしたときにリンクを取得できず空のオブジェクトに対しclickを実行していることが原因です。

今まで要素が存在することを前提に実装していましたが、場合によって要素が存在しないことも考慮する必要があります。要素を取得するたびに全てチェックしてもよいですが、今回は検索結果が0件の場合の制御を追加します。

0件

「SearchBooks」の「GetBookInfos」プロシージャを以下のように編集してください。「elementsCount」でページ内に表示されている本の数を取得しているので、この数が0の場合に終了するように最後の「If」文のチェックを追加しています。

'書籍情報取得
Public Function GetBookInfos(ByVal url As String, ByRef info As SearchInfo, ByVal getCount As Integer) As BookInfo()
   '省略
   
   '本の詳細情報取得
   Do While True
       'ページ内に表示されている本の数を取得
       Dim objIEBookList As Object
       Dim elementsCount As Integer
       Set objIEBookList = IEControl.GetHtmlObjByQuerySelectorAll(objIE, SELECTOR_RESULT_DETAIL)
       elementsCount = objIEBookList.Length
       
       'ページに本が存在するか確認
       If elementsCount = 0 Then
           '0件の場合は終了
           Exit Do
       End If

次に、「Sheet1(インプット)」の「書籍検索」プロシージャを以下の通りに編集してください。「IsExistsInfo」プロシージャは新しく追加しています。書籍情報取得後に配列に情報が存在することを確認し、存在すれば結果を出力し、存在しない場合は0件である旨のメッセージを表示します。これでエラーにならずに最後まで処理することができます。

Public Sub 書籍検索()
   '省略
   
   '書籍情報取得
   Dim bookInfos() As SearchBooks.BookInfo
   bookInfos = SearchBooks.GetBookInfos(url, info, getMaxCount)

   If IsExistsInfo(bookInfos) Then
       '取得結果出力
       Call OutputSearchResult(bookInfos)
       MsgBox ("書籍検索が完了しました。")
   Else
       MsgBox ("検索結果が0件です。検索条件を変更してください。")
   End If
   
End Sub


'書籍情報存在確認
Public Function IsExistsInfo(ByRef varArray() As SearchBooks.BookInfo) As Boolean
On Error GoTo Catch

   If UBound(varArray) > 0 Then
       IsExistsInfo = True
   End If

   Exit Function

Catch:
   IsExistsInfo = False
End Function

インプットやアウトプットについて、想定外の場合にエラーになる場合があるので、ある程度の対応を入れるとツールとしてより使いやすくなります。あらゆることを想定して対応するのは費用対効果が低くなるため、何かがない場合や0件の場合等は特に意識するようにしましょう。

4.処理の高速化

書籍情報の取得後にシートに出力する際に1行ずつ出力しています。セルに値を設定しながらエクセルの表示を行っています。出力する件数が少ない場合は問題ありませんが、件数が多くなるとセルの更新と表示を繰り返し行い、処理に時間がかかってしまいます。どこに時間がかかっているのかというと、更新したセルの表示を描画する際に時間がかかっています。対策としてはセルの更新を1回にする、または、描画を停止する方法が考えられます。今回は、簡単に対応可能な後者の描画を停止する方法を選択します。

「Sheet1(インプット)」の「書籍検索」プロシージャを以下のように編集してください。処理の最初と最後に「Application.ScreenUpdating」の設定を変更しています。最初に「False」に設定し最後に「True」とすることで、処理の途中の描画を停止し最後に1回描画が行われ、処理速度の高速化を図れます。

Public Sub 書籍検索()
   '描画を停止する
   Application.ScreenUpdating = False

   '省略
   
   '描画を再開する
   Application.ScreenUpdating = True
End Sub


ここまでで本連載を完結とします。VBAでIEを自動操作するツールを作ることができました。ここまでの開発を活かしてプライベートや仕事で応用し、作業を効率化するツールを作成するきっかけになれば幸いです。

この記事が気に入ったらサポートをしてみませんか?