デベロッパー

デベロッパー

定期実行する.NETコンソールアプリケーションの作成

John Peterson
2008年7月29日 / 10:00
 
 

はじめに

 私としてはよくあることなのですが、本稿のアイデアは私が最近携わったプロジェクトから生まれたものです。詳しい説明は省きますが、とあることを毎日実行する必要がある、というのが基本的な要件でした。

 この種の要件を実装するのは初めてではなかったのですが、以前のソリューションを引っ張り出してみると、確かに有効ではあるものの、非常に時代遅れであることが分かりました。そのソリューションは.vbsファイルに書かれていて、WSHから実行するように設計されていました。

 つまり、プレーンテキストに書かれていてコンパイルされていないので変更は簡単にできましたが、変更後の動作確認をしたり、新バージョンのスクリプトのデバッグを行ったりするのは、控えめに言っても面倒な(率直に言えばうんざりする)作業でした。

著者注
 この一昔前のスクリプト定期実行システムについて知りたい場合は、私が以前「ASP 101」に書いた古い記事「Getting Scripts to Run on a Schedule」にコンセプトが掲載されているのでそちらを参照してください。システムの実際の処理は年々改善されていますし、もちろん個々のプロジェクトによっても異なりますが、記事の「Method 3」で紹介している.vbsファイルのスケジューリングの基本プロセスは、ほとんど変わっていません。
 私はもっと良い方法があるはずだと考え、まずコマンドラインの.NETアプリケーションを作成し、それをWindowsのタスクスケジューラでスケジュール設定することを思いつきました。.NET Frameworkの機能を利用できることはもちろんですが、アプリケーションのテストとデバッグも簡単になるだろうと思ったからです。

 本稿では、実行をスケジューリングする簡単な.NETのコマンドラインアプリケーションの作成プロセスについて説明します。今回のサンプルアプリケーションは、WebサーバにHTTPリクエストを送り、返されたHTMLをメールの本文として送信します。

必要なツール

 コマンドラインアプリケーションをビルドするVisual Studioを持っていない場合は、お好みのExpress Editionをダウンロードしてインストールする必要があります。

 どれか1つあれば十分ですが、以降の解説ではVisual Basic 2008 Express Editionを使用します。別の言語を選んだ場合、コードは当然異なってきますが、考え方はまったく同じです。

 既にVisual Web Developer 2008 Express Editionを使っていても心配はいりません。Express Editionの製品を複数インストールしていても、そのまま使用できます。

コマンドラインアプリケーションの作成

 これから作成するサンプルアプリケーションは、WebサーバにHTTPリクエストを送ります。その後、サーバからHTMLを受け取り、それをメールの本文として使用します。コードは実にシンプルで、状況に応じて変更可能です。行っている処理は、実際のコーディングがどうなっているかに関わらずまったく同じです。

 Visual Basic 2008 Express Editionをインストールして使えるようにしたら、これを起動して[File]メニューから[New Project]を選択してください。[New Project]ダイアログボックスが表示されます。

 [Console Application]を選択して、アプリケーションに適当な名前を付けます。本稿では、サンプルアプリケーションの名前を「Http2Email」とします。[OK]をクリックすると、次のようなワークスペースが表示されます。

 私は、オブジェクトに分かりやすい名前を付けるのが好きなので、最初に[Solution Explorer]ペインでファイル名をModule1.vbからHttp2Email.vbへ変更します。これでプロジェクト内の該当するすべての箇所で名前が更新されます。その後、[File]メニューから[Save All..]を選んでディスクにプロジェクトを保存します。

 次に設定をいくつか変更します。[Solution Explorer]の[My Project]アイテムをダブルクリックすると、このような設定画面が表示されます。

 私の環境ではまだ.NET 2.0を使用しているWebサーバが複数あるので、まずターゲットフレームワークのバージョンを設定します。[Compile]タブで[Advanced Compile Options...]ボタンをクリックしてください。表示されたダイアログボックスの一番下に[Target framework]というオプションがあります。これを[.NET Framework 2.0]に変更してください。

 [References]タブでは、参照やインポートされた名前空間をまとめて削除できます。[System]以外のすべての参照を削除してください(別のアプリケーションをビルドしていて、他の参照が必要な場合はこの限りではありません)。

 また、Microsoft.Visual Basic、System、System.Collections、およびSystem.Collections.Genericを除くすべての[Imported Namespaces]を削除してください。

 次に、アプリケーション設定をいくつか定義します。この情報をハードコーディングする代わりに設定として定義しておくと、再度コンパイルしなくてもアプリケーションのパラメータ(ひいてはアプリケーションの動作)を変更できます。[Settings]タブで、次の8つのアプリケーションスコープの設定を定義します。

設定説明
Urlメール本文として使用するHTMLの取得元となるURL
EmailFromメールアドレス(From)
EmailToメールアドレス(To)
EmailCCメールアドレス(CC)
EmailBCCメールアドレス(BCC)
EmailSubjectメールの件名
EmailHtmlブール型。メールがHTML形式であるべきかどうかを示す
SmtpServerメールの送信に使用するSMTPサーバ名
 これらは実に単純明快です。上記の画面イメージには、私がテストに使用した値が表示されていますが、URL、メールアドレス、およびSMTPサーバには、当然、各自の設定を使用してください。

 EmailSubjectだけは、少々変わった設定になっています。[Value]列を見ると、プレースホルダとして<date>を使用しているのが分かると思います。この部分は、アプリケーションのコードによって現在の日付に置き換えられます。今回このようにしたのは、設定機能の使い方を紹介するため、またこの機能を使った場合でも動的に変化する値を指定できることを示すためです。

 これでアプリケーションの設定はすべて完了したので、次は実際にコードを記述します。下記のコード例からコピー&ペーストするのが、おそらく一番簡単な方法でしょう。

Imports System.IO
Imports System.Net

Module Http2Email

    Sub Main()
        Dim myWebRequest As WebRequest
        Dim myStreamReader As StreamReader
        Dim strSubject, strBody As String
        Dim myMailMessage As Mail.MailMessage
        Dim mySmtpClient As Mail.SmtpClient

        ' Retrieve HTML via HTTP request to use as body of email
        myWebRequest = WebRequest.Create(My.Settings.Url)
        myStreamReader = New StreamReader( _
            myWebRequest.GetResponse().GetResponseStream())
        strBody = myStreamReader.ReadToEnd
        myStreamReader.Close()

        ' Get subject from settings 
        ' and replace placeholder with current date
        strSubject = My.Settings.EmailSubject
        strSubject = strSubject.Replace("<date>", _
                                    FormatDateTime(Now(), _
                                    DateFormat.ShortDate))

        ' Create email message
        myMailMessage = New Mail.MailMessage(My.Settings.EmailFrom, _
                                        My.Settings.EmailTo, _
                                        strSubject, _
                                        strBody)
        If My.Settings.EmailCC <> "" _
                    Then myMailMessage.CC.Add(My.Settings.EmailCC)
        If My.Settings.EmailBCC <> "" _
                    Then myMailMessage.Bcc.Add(My.Settings.EmailBCC)
        myMailMessage.IsBodyHtml = My.Settings.EmailHtml

        ' Send email
        mySmtpClient = New Mail.SmtpClient()
        mySmtpClient.Host = My.Settings.SmtpServer
        mySmtpClient.Send(myMailMessage)
    End Sub

End Module 
 非常に簡単なコードなので、説明にはあまり時間をかけないことにします。慣れない人は、あらゆるところでMy.Settingsを参照している点が不思議に見えるかもしれません。これは先ほど定義した設定にアクセスするための名前空間です。

 これでひとまず形が整いました。開発環境からアプリケーションをビルドして実行し、動作を確認しましょう。[Debug]から[Start Debugging]をクリックするか、F5キーを押してください。

 エラーが起こる場合は、URLが間違っているか、SMTPサーバに接続できない、あるいはSMTPサーバがロックダウンされていることが関係していると考えられます。SMTPサーバ関連の問題を解決するには、SMTPクライアントオブジェクトに資格情報を設定する必要があるかもしれません。

 エラーがなければ、黒いコンソールウィンドウのようなものが一瞬開いてから消えます。これは期待どおりの動作です。このアプリケーションは誰もログオンしていないときに実行するよう設計されたものなので、視覚的なフィードバックは提供しません。メールがネットワークを経由して受信ボックスに送信されるまで、そのまましばらく待ってください。

 アプリケーションが期待どおりに動作したら、[Build]メニューから[Build Http2Email]を選択してください。プロジェクトフォルダのbin\Releaseサブフォルダに実行可能ファイルと設定ファイルが作成されます。

 これらのファイルを、アプリケーションの実行をスケジュールしたいコンピュータ上にコピーする必要があります。

 これまでに定義した設定を覚えておいてください。「Http2Email.exe.config」ファイルをメモ帳で開き、ファイルの一番下までスクロールすると、格納されているすべての設定と値をXML形式で見ることができます。

 テストのために1か所変更する場合、あるいは後から設定を変更する必要が出てきた場合は、このテキストファイルを編集するだけで、次回のアプリケーション起動時から新しい値が読み込まれるようになります。Visual Studioを起動したり、再コンパイルなどをしたりする必要はありません。とても便利な機能ですね!

 スケジューリングの説明に入る前にもう一度言っておきたいのは、今回のサンプルアプリケーションは単にHTTPリクエストを出してメールを送信するだけですが、読者の皆さんがコンソールアプリケーションを作成するときには何をしても自由だということです。.NET Frameworkにはフルアクセスが可能ですし、グラフィカルユーザーインターフェースがないだけで、後は自由に実装できます。

アプリケーション実行のスケジューリング

 ここまでの段階で、コマンドラインアプリケーションは期待どおりの動作をするようになりました。次のステップは、これが適切な時刻に実行されるようスケジュールすることです。

 先ほど述べたとおり、最初のステップは、実行可能ファイルと設定ファイルを目的のコンピュータにコピーすることです。格納する場所は自由ですが、専用のフォルダを作るのが一番良いでしょう。私の場合は、自分のサーバのInetpubフォルダの下にあるscheduleフォルダに置いています。Webアプリケーションに関係するものですが、wwwrootフォルダとは別の場所に置きたいからです。

 サーバにインタラクティブにログインした場合は、ファイルをコピーした後に実行可能ファイルをダブルクリックするだけで、エラーを起こさずに動作するかどうかを確認できます。エラーが発生しなければ、後はスケジュールされたタスクとして設定するだけです。

 プログラムをスケジュールされたタスクとして実行するには、コントロールパネルの[タスク]アプレットを使用します。通常は、[スタート]メニューから[コントロールパネル]を選択して[タスク]をダブルクリックします。

 既にスケジュールされているタスクと一緒に、[スケジュールされたタスクの追加]というアイテムがあるはずです。[スケジュールされたタスクの追加]をダブルクリックすると、タスクウィザードが起動します。

 [参照]ボタンをクリックし、先ほどコピーしたアプリケーションの実行可能ファイル(Http2Email.exe)を探して選択します。

 スケジュールのタイプを選択してから、アプリケーションを実行するタイミングについて詳細を設定します。

 次に、アプリケーションを実行するアカウントのユーザー名とパスワードを入力します。

 [完了]ボタンをクリックすると、[タスク]ウィンドウに新しいタスクが表示されます。ここからタスクを監視でき、さらにアプリケーションの前回の実行結果も見られます(0x0は、アプリケーションがエラーを起こさずに終了したことを示します。それ以外の場合は、通常、エラーが起こったことを意味します)。

まとめ

 コマンドラインの.NETアプリケーションを作成し、Windowsのタスクスケジューラからその実行をスケジュールすることがいかに簡単か、本稿を通じて紹介できたのではないかと思います。

 Webベースのアプリケーション構築に慣れている人は、最初はなじめないかもしれませんが、何回か試すうちにコツがつかめるでしょうし、処理をスケジュールどおりに実行できるとどれだけ便利かが実感できるでしょう。

著者紹介

John Peterson(John Peterson)
【関連記事】
MOVIDA など4社、Lotus Notes モバイル化で業務提携
「Microsoft Office Outlook Connector Beta」のアップデート版が提供開始
KDDI、au one net の WEB メールサービスを停止―他ユーザーのメールが閲覧できる不具合
電子証明書により Windows Mobile 6 を認証、ジュニパーとサイバートラストが協業
Sun、『Solaris』と『Linux』向けに『Web Stack』の提供を開始

New Topics

Special Ad

ゆりかごからロケットまで、すべての乗り物をエンジョイ
ゆりかごからロケットまで、すべての乗り物をエンジョイ えん乗り」は、ゆりかごからロケットまで、すべての乗り物をエンジョイする、ニュース、コラム、動画などをお届けします! てんこ盛りをエンジョイするのは こちらから

Hot Topics

IT Job

Interviews / Specials

Popular

Access Ranking

Partner Sites