RPA

【初心者向け】Power AutomateとOffice スクリプトで定型作業を自動化する

Power Automate

こんにちは、ソリューション開発部の有坂です。

Microsoft Power Automate(以降、Power Automate)とOffice スクリプトを連携すれば、Excelでのさまざまな作業を自動化できます。最近、私が所属しているプロジェクトでもExcelでの定型作業が発生したので、Power AutomateとOffice スクリプトでRPAを作成し自動化しました。

この記事では、Power AutomateでOffice スクリプトを実行して、受信メールに添付されたCSVをExcelにコピーする方法について紹介します。

受信メールに添付されたCSVをExcelにコピーする方法を知りたいという方はもちろん、Excelでの作業を自動化してみたいけど具体的な作成方法が分からない、RPAでどのようなことができるのか具体例を知りたいというITエンジニアの方々も、自動化の一例としてこの記事をご活用ください。

使用するツール・機能

Power Automate

Microsoft社が提供するRPAツールです。今回はMicrosoft OutlookやMicrosoft Excelと連携するため、Microsoft 365製品との連携が簡単なPower Automateを使用します。Power Automateについての詳細は、以下の記事がそるでぶろぐにあるので、そちらをご参照ください。

Office スクリプト

ユーザーによるExcelの操作をJavaScriptとして記録するマクロ機能のことです。

Excelの作業を自動化する点ではVBA マクロと同じですが、VBA マクロとは異なりOffice スクリプトはPower Automateから実行できます。今回はPower Automateから実行したいためOffice スクリプトを使用します。

ちなみに、Power Automate DesktopならばVBA マクロを実行できますが、別途インストールする必要があります。また、Power Automate Desktopはデスクトップフロー(デスクトップ上の操作の自動化を実現する)のサービスであるため、今回のようにクラウドフロー(クラウドサービスを組み合わせて自動化を実現する)でパソコン停止時でも実行したい場合には適しません。

Office スクリプト についての詳細は、以下の公式ドキュメントをご参照ください。

フローのイメージ

今回作成する処理の流れは以下の通りです。

  1. 指定した条件に合致するメールを受信する
  2. メールに添付されているCSVをMicrosoft OneDrive(以降、OneDrive)に保存する
  3. OneDriveに保存したCSVをExcelにコピーするスクリプトを実行する

Office スクリプトの作成

Power Automateでフローを作成する前に、まずはOffice スクリプトを作成します。

Excelをウェブ版で開き、[自動化]タブを押下します。次に[すべてのスクリプト]を押下し、[新しいスクリプト]を押下します。コードエディターが表示されるので以下のコードを記述します。

/**
 * Convert incoming CSV data into a range and add it to the workbook.
 */
function main(workbook: ExcelScript.Workbook, csv: string, csvName: string) {
  let sheet = workbook.getWorksheet(csvName);

  // Remove any Windows \r characters.
  csv = csv.replace(/\r/g, "");

  // Split each line into a row.
  let rows = csv.split("\n");
  /*
   * For each row, match the comma-separated sections.
   * For more information on how to use regular expressions to parse CSV files,
   * see this Stack Overflow post: https://stackoverflow.com/a/48806378/9227753
   */
  const csvMatchRegex = /(?:,|\n|^)("(?:(?:"")*[^"]*)*"|[^",\n]*|(?:\n|$))/g
  rows.forEach((value, index) => {
    if (value.length > 0) {
      let row = value.match(csvMatchRegex);

      // Check for blanks at the start of the row.
      if (row[0].charAt(0) === ',') {
        row.unshift("");
      }

      // Remove the preceding comma.
      row.forEach((cell, index) => {
        row[index] = cell.indexOf(",") === 0 ? cell.substr(1) : cell;
      });

      // Create a 2D array with one row.
      let data: string[][] = [];
      data.push(row);

      // Put the data in the worksheet.
      let range = sheet.getRangeByIndexes(index, 0, 1, data[0].length);
      range.setValues(data);
    }
  });

  // Add any formatting or table creation that you want.

}

上記のコードは、Microsoft公式ドキュメントのサンプルコードをもとに作成しました。

Office スクリプト作成画面
Office スクリプト作成画面

コードを入力したらスクリプトの名前を変更し、[スクリプトを保存]を押下して保存します。これでOffice スクリプトの作成は完了です。このスクリプトをPower Automateのフローから実行することで、CSVをExcelにコピーできます。

Excelシートの追加・名前変更

また、コピー元のCSVのファイル名(拡張子なし)にExcelのシート名を変更しておく必要があります。複数の添付ファイルがある場合は、ファイル数分シートを追加します。例えば、CSVが「sample1.csv」「sample2.csv」の2ファイルの場合、上の画像(Office スクリプト作成画面)のようにExcelのシート名を「sample1」「sample2」に変更します。

Power Automateフローの構築

次にPower Automateでフローを作成します。Power Automateページにアクセスするか、Microsoft 365のメニューからPower Automateアプリを選択しフローを作成します。

[作成]から[自動化したクラウドフロー]を選択し、[新しいメールが届いたとき(V3)]にチェックを入れ、作成ボタンを押下します。

[自動化したクラウドフロー]選択後の画面
[自動化したクラウドフロー]選択後の画面

トリガーの設定

編集画面に移ると、[新しいメールが届いたとき(V3)]トリガーが作成されているので、条件を指定し、添付ファイルを取り込むメールを絞ります。

[新しいメールが届いたとき(V3)]トリガーの設定画面
[新しいメールが届いたとき(V3)]トリガーの設定画面

上の画像([新しいメールが届いたとき(V3)]トリガーの設定画面)では、件名が「テストメール」で、添付ファイルのあるメールを受信したときに処理が流れます。

補足

[新しいメールが届いたとき(V3)]トリガーのメニューから[設定]を押下すると以下の画面が表示されます。

新しいメールが届いたときトリガーのメニューから[設定]を押下後の画面
新しいメールが届いたときトリガーのメニューから[設定]を押下後の画面

コンカレンシー制御の上限をオンにし、並列処理の次数を1にすると、同時にメールが届いたときに逐次処理で処理を流せます。もし今回のように並列実行する必要のない処理の場合は、逐次処理の設定にすることをおすすめします。その方が並列実行の場合を考慮に入れなくていいので、実装やテスト時の負担が減ります。

また、トリガーの条件の下にある[+追加]を押下するとテキストボックスが表示されるので、条件を指定することで、複数のキーワードを設定できます。

「件名に「件名1」か「件名2」というキーワードが含まれていたら」という条件を設定する例
@or(contains(triggerBody()?['Subject'], '件名1'),contains(triggerBody()?['Subject'], '件名2'))

アクションの追加

トリガーの設定が完了したので、ここからはアクションを追加していきます。

[変数を初期化する]アクションの追加

CSVのファイル名を設定するための変数を用意します。[変数]コネクタの中の[変数を初期化する]アクションを追加します。

[変数を初期化する]アクションの設定画面
[変数を初期化する]アクションの設定画面
  • 名前:任意の変数名を設定してください
  • 種類:[文字列]を選択してください

[Apply to each]アクションの追加

添付ファイルの数だけループする処理を作成します。[新しいステップ]を押下し[コントール]コネクタの中の[それぞれに適用する]アクションを追加します。[出力]には、[動的なコンテンツの追加]を選択し[動的なコンテンツ]から[新しいメールが届いたとき(V3)]の[添付ファイル]を選択します。

[Apply to each]アクションの設定画面
[Apply to each]アクションの設定画面
※もしCSVやExcelをMicrosoft Teamsで共有したいという場合は、ここからのOneDrive for BusinessのアクションをSharePointのアクションに変えれば、Microsoft Teams上のチームの共有フォルダーに保存することも可能です。

[ファイルの作成]アクションの追加

ここからは、Apply to eachの中にアクションを追加していきます。まずは[OneDrive for Business]コネクタから[ファイルの作成]アクションを選択します。このアクションで添付ファイルがOneDriveに保存されます。

[ファイルの作成]アクションの設定画面
[ファイルの作成]アクションの設定画面
  • フォルダーのパス:OneDriveの任意のフォルダーを選択してください
  • ファイル名:[動的コンテンツ]から[新しいメールが届いたとき(V3)]の[添付ファイル名]を選択してください
  • ファイルコンテンツ:「動的コンテンツ」から[新しいメールが届いたとき(V3)]の[添付ファイルコンテンツ]を選択してください

[ファイルコンテンツの取得]アクションの追加

スクリプトを実行する前に、ファイルコンテンツを取得する必要があります。[OneDrive for Business]コネクタから[ファイルコンテンツの取得]アクションを選択します。[ファイル]には、[動的なコンテンツ]から[ファイルの作成]の[ID]を選択します。

[ファイルコンテンツの取得]アクションの設定画面
[ファイルコンテンツの取得]アクションの設定画面

[変数の設定]アクションの追加

先ほど用意した変数に値を設定します。[変数]コネクタの中の[変数の設定]アクションを追加します。

[変数の設定]アクションの設定画面
[変数の設定]アクションの設定画面
  • 名前:[変数を初期化する]アクションで設定した変数名を選択してください
  • 値:[動的なコンテンツ]から[ファイルの作成]の[拡張子なしの名前]を選択してください

[スクリプトの実行]アクションの追加

[Excel Online (Business)]コネクタから[スクリプトの実行]アクションを選択します。このアクションで先ほど作成したOffice スクリプトが実行されます。

[スクリプトの実行]アクションの設定画面
[スクリプトの実行]アクションの設定画面
  • 場所:OneDrive for Businessを選択してください
  • ドキュメントライブラリ:OneDriveを選択してください
  • ファイル:コピー先のExcelを選択してください
  • スクリプト:実行するスクリプトを選択してください
  • csv:[動的なコンテンツ]から[ファイルコンテンツの取得]の[ファイルコンテンツ]を選択してください
  • csvName:[動的なコンテンツ]から[変数]の[CSV名]([変数の設定]アクションで設定した名前)を選択してください

最後に名前を変更し、保存ボタンを押下すれば、フローは完成です。試しに、OutlookからCSVを添付して自分宛にメールを送ってみましょう。メールを受信するとフローが動き、フローが成功するとExcelブックにCSVがコピーされています。

おまけ~処理を追加してみる~

せっかくCSVをExcelにコピーするフローを作成したので、もう少し処理を追加していこうと思います。

以下のCSVをExcelにコピーし、りんごの数をカウントしてメールで通知する処理を追加していきます。

5月.csv
5月.csv

まずは関数を使って、りんごの数量を取得します。以下の画像(コピー先のExcel)のようにコピー先のExcelでSUMIF関数を使って、検索範囲を5月シートのB列、検索条件を"りんご"、合計範囲を5月シートのD列として、りんごの数量の合計を求めます。まだ5月.csvがコピーされていないので関数の結果は0ですが、フローが動き5月.csvが5月シートにコピーされると値が入ってきます。

=SUMIF('5月'!B:B,"りんご",'5月'!D:D)
コピー先のExcel
コピー先のExcel

次にスクリプトにコードを追加します。合計数量を求めたセルの値を戻り値として取得するコードを、先ほど作成したOffice スクリプトに追加します。

//セルから値を取得し戻り値に設定
return workbook.getWorksheet("main").getRange("B2").getValue();
Office スクリプト作成画面
Office スクリプト作成画面

最後に、Power Automateのフローにアクションを追加します。[Office 365 Outlook]コネクタから[メールの送信(V2)]アクションを選択します。[宛先]には自分のメールアドレスを、[件名]には任意の文字を入力します。本文には、[スクリプトの実行]アクションで取得できる動的コンテンツ[Result]を使って文章を作成します。

[メールの送信(V2)]アクションの設定画面
[メールの送信(V2)]アクションの設定画面

これでフローは完成したので、テストしていきましょう。5月.csvを添付したメールをOutlookに送ってみます。すると数秒で「りんごの数は35個です。」と返信が来ました。正常に5月.csvのりんごの数量が取得されているようです。

※Excel Online (Business)]コネクタにある[行の取得]アクションを使用しても、セルの値を取得できます(その場合、取得する行を事前にテーブル化する必要があります)。しかし試したところ、キャッシュが残っていたのか、セルの値を取得する際に前回実行した時のデータが取得されてしまいました。もし[行の取得]アクションを使用する場合は、Office スクリプトでcalculateメソッドを用いてExcelブックを再計算した後で、[行の取得]アクションを使用する必要があります。

最後に

いかがでしたでしょうか。今回はPower AutomateでOffice スクリプトを実行して、受信メールに添付されたCSVをExcelにコピーする方法を紹介しました。CSVをExcelにコピーすることで、Excelの関数などを使ってさまざまなデータの加工や分析ができます。また、Power Automateのトリガーとアクション、Office スクリプトの内容をカスタマイズすれば、さまざまなExcelでの作業を自動化できます。

RPAを作成するにあたり、Power AutomateやOffice スクリプトだけでなく、さまざまなツールや方法があると知りました。自動化する処理に応じて適切なツールや方法を用いてRPAを作成できるよう、努めていきたいと思います。

今後もRPAに関する記事を投稿していきたいと思います。

  • Zabbix Enterprise Appliance
  • 低コスト・短納期で提供するまるごとおまかせZabbix