PowerAutomateとChatGPTを使って解約手続きの自動化

# 本記事について
本記事は、弊社のとあるバックオフィス業務をノーコードで自動化する方法をまとめた記事である。

# 本記事で使うツールは3つだけ
## 1.Power Platform
https://powerplatform.microsoft.com/ja-jp/
## 2.kintone
https://kintone.cybozu.co.jp/
## 3.chatGPT
https://openai.com/blog/chatgpt

# 前提：

## 抱えている課題

お客様が弊社サービスの解約をされた際の手続きを未だ手作業で行なっている。

## 業務システムの構成

- kintone: サービスの使用状況や契約に関するデータを保管している。
- Microsoft Dataverse: DynamoDBの値を変更するために必要な情報を保管するために使用している。
- AWS DynamoDB: サービスの状態管理するために使用している。

## 現状
- 解約フォームから解約関連のデータがお客様からkintoneの「アプリ1」へ送られる。
- それを社員が確認し、お客様へ解約受付のお知らせメールを一部手作業で送信する。
- 「アプリ2」のデータから一致するレコードを探し出して、「アプリ2」にデータを手作業で更新する。
- 毎月1日にその二か月前に解約したユーザーのデータをすべて確認しながらAWS DynamoDBにあるデータを更新している。

![空白の図.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2641616/f27ef08b-0d46-8add-0f3b-56d70d1d3fd8.png)

これが毎月一つや二つなら大変ではないですが、数百にもなるとかなり大変な作業になります。

これらすべての作業の自動化を目標としてフローを作成

![test (4).png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2641616/a6e2645d-da71-2174-b5c9-34e209cd9de6.png)

以下はその詳しい手順を解説する。

# フロー1
解約レコードがkintoneに登録されたら「アプリ2」にあるレコードの更新を行って、社員とお客さんに同時にメールの送信とmicrosoftのdataverse上にデータを送信して保管する

## 1. トリガー
PowerAutomateのトリガーの一つで、kintoneの指定したアプリに何かレコードが追加された際に自動で実行されるものです。

作成手順
1. フローの作成をクリックし、
1. フローのトリガーを選択してくださいの検索バーでkintoneと入力
1. 候補として出てくる。
1. kintoneの指定したアプリのIDを入力

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2641616/2c546207-bf21-e06e-c905-7b5b07740765.png)

補足：更新、削除、コメント、管理状態などに関するトリガーも存在している。

## 2. データの取得1
kintoneから取得したすべてのフィールドコードのデータはそのまま使えるものとJSONとして出力されるものの二つに分かれる。
- 文字列や数字として取得できているものは「動的なコンテンツ」から該当するフィールド名をクリックすることで直接使うことができる。
- JSONとして出力されるもの。これに関しては少々面倒で、「JSONの解析」というアクションを利用しないと扱うのに時間がかかる。
### JSONの取得
#### 操作手順
コンテンツの枠に出力されているJSONのデータを選択して代入
そして、一度テストして、実際に出力されるJSONの値をコピーして、スキーマの「サンプルから生成」を開き、そこにペースト

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2641616/b6928bec-14cd-6fc6-0779-976c47993dc4.png)

kintoneから取得するデータの構造としては
```JSON:JSON
{
  "type": "object",
  "properties": {
    "type": {
      "type": "string"
    },
    "value": {
      "type": "string"
    }
  }
}
```
このような構造がほとんどで
propertiesがフィールド名になっていることが多い
また、typeとvalueのみで書かれている場合もあるので、その際は間違えないためにもフィールド名を選び、もう一度JSONの解析を利用してvalueを取得するという方法がわかりやすいと考えられる。

:::note warn
Apply to eachというリストを処理するアクションがあるが、その中で処理するとたまに実行されなかったり、テストした際に結果が表示されないことがあるので、
Apply to eachでJSONからほしい情報を変数に代入し終わったら、次の処理はApply to eachの外で行うほうがわかりやすいと考えられる。
:::

## 3. データの取得2
Power Automateからkintoneの中にある自分の欲しいフィールドコードのデータを取得する方法はコネクタでは用意されておらずHTTPリクエストを利用してrecordっていう名前のリストに格納されているJSONデータを取得する方法を使用している。
### HTTPアクションを追加
1. アクションを追加ボタンをクリック
2. 組み込みを選択
3. 検索バーでHTTPと入力

そうすればHTTPと書かれた緑の画像が表示される。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2641616/6a0039a5-db14-eb89-e239-b7bfd494b437.png)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2641616/5e4aa0e0-cef9-21f7-4ca1-169753af6c7e.png)[1]

- 方法：目的に応じて
  - GET
  - PUT
  - POST
  - PATCH
  - DELETE
の五つから選択
今回はkintoneのアプリからフィールドの値が同じレコードを探し出し取得するためGETを選択

:::note warn
URIの書き方
:::
ここがなかなか面倒で
今回はアプリ内の複数あるレコードから条件に合うレコードを取得するので使うのはhttps://sample.cybozu.com/k/v1/records.json?app=<アプリのID>

:::note warn
複数のレコードをからクエリを使って絞り込むのでrecordsを使用する
:::

そのあとにqueryを使って、条件から絞り込みたい場合
query=<フィールドコード> = "<一致している文字列>"
っと書きたいところですが、実際はURLエンコードを行ったものを入力する必要があります。
書き方としては
query=<フィールドコード>%20%3D%20%22<一致している文字列>%22
となります。

メモ：
|元  |URLエンコード  |
|---|---|
|スペース|%20|
|=|%3D|
|"|%22|

URLエンコードって検索すれば以下のようなサイトも見つかるので、必要に応じて使ってみてください。

https://tech-unlimited.com/urlencode.html

https://www.tagindex.com/tool/url.html

さらに条件を絞り込みたい場合

<フィールドコード>%20%3D%20%22<一致している文字列>%22 の後に and を加えます。
URIエンコードした場合：%20and%20(半角空白が必要なので前後に%20)
そのあとに同じようにquary=以降を記入すればいいです。

例：https://sample.cybozu.com/k/v1/records.json?app=186&query=Name%20%3D%20%22<名前>%22%20and%20domain%20%3D%20%22<ドメイン名>%22

JSONデータが返ってくるので、[データの取得1]を参考に必要なデータを取りだせばそのまま使えます。

## 4. メールの送信
gmailのアカウントにログインする必要があり、以降automateから送信する際にそのアカウントを選ぶことができる。
今まで受け取ったデータはすべて再利用（代入）可能となっていて
Gmailを送信アクションの使いたいところに「動的なコンテンツ」から選んでクリックすればそこに入力される。
もちろんメールアドレスの宛先にも使える。
メールの送信がすごく簡単に実装できてる。

![スクリーンショット 2023-04-21 111959.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2641616/e33ce075-c4e0-ab71-f4b6-92daedd020a1.png)

## 5. kintoneのレコードを更新
kintoneコネクタの中にある「アプリ内レコードを更新」アクションを利用することで更新が可能

自分の更新したいフィールドコードの名前だけ探し出して、その部分に手入力、または代入して。
更新しないフィールドは空白のまま置いておけば、アクションが実行された際

該当するフィールドコードの値のみが上書きされ、その他の値は元の値のまま変更されません。

:::note warn
最初にアプリIDとレコード番号が必要
:::

## 6. データをDataverseへ送信
### 手順
1. PowerAutomateの左にある「データ」をクリック
1. 「テーブル」をクリック
1. PowerAppsのテーブルのページが開かれるので、そこで左上にある「新しいテーブル」を開き、目的に合ったデータの名前を付ける
1. デフォルトではプライマリ列の名前がNameとなっているので、気になる人はそこを自分の目的に合った名前へ変更する。その際英語でも日本語でもいい。（あとで分からなくならないためにもしたほうがいいと思います）
1. 必要に応じて列を追加を選択して、格納するデータの種類を増やすことも可能
1. これでデータの格納場所がDataverse上でできたので、PowerAutomateの編集していたフローに戻り、「新しい行を追加」アクションを選択し、テーブル名で先ほど作ったテーブル名を入力する。
1. あとは自分の入力したいところにデータを代入

# フロー2
## 1. トリガー
### 手順
1. PowerAutomateのホームに戻り、左にある作成をクリック
1. 今回の目的としては毎月最初の日に実行されるフローを作りたいので、「スケジュール済みクラウドフロー」を選択
1. フロー名を決めて、開始日、時間、繰り返し間隔を設定すれば、それ通りに動くフローの雛型が完成。
1. 毎月実行したいフローを作成（今回はDataverseからデータを取得して、kintoneとDynamoDBにあるデータの値を変更）

## 2. 二か月前の計算式の作成
### 手順
1. データを格納するための変数を初期化
1. “二か月前”という名前の変数を作成し、式で二か月前の日付を取得
    1. 例1：今日が2023/04/18の場合→202304
    1. 例2：二か月前の場合→202302
1. ここでchatGPT先生の出番です。
```text:text
power automateの式で
二か月前を取得したいただし、
データの形式は整数で
202304
```
というように、
使うツールを指定し、取得したいデータを指定し、フォーマットを指定することで
chatGPT先生から返答を得られます。
```text:ChatGPTの返答
formatDateTime(subtractFromTime(utcNow(), 2, 'Month'), 'yyyyMM')
```
より正確に指定することで返答も精度を増します。

これを実際に代入してみたところ、
```text:text
The variable 'tesuto' of type 'Integer' cannot be initialized or updated with value of type 'String'. The variable 'tesuto' only supports values of types 'Integer'.
```
というエラー文が帰ってきました。

原因はint型の変数を作ろうとしているのに、文字列が作成されていることが原因です。
式の中にint型へ変換する関数が用意されているので
intの後に()で先ほどのchatGPT先生の回答を囲って更新ボタンを押せば解決。

:::note warn
chatGPT先生はあくまで確率モデルなので、返答が100%正しいとは限りません、自分で帰ってきた式を理解し、書き換えることが出来る能力が必要です。
:::

Dataverseから取得したデータの中から二か月前の日付と一致するデータを比較して、一致したもののデータのみkintoneとDynamoDB上の値の変更を行うようにすれば完成です。

DynamoDBの値を変更するHTTPリクエストの書き方やAPI gateの作り方が人それぞれなのでここでは書かないでおきます。

## 3. Dataverseから取ってきたデータをリストに変換
これには「行を一覧にする」アクションを利用する。

## 4.最後に
Dataverseから取得したデータの中から二か月前の日付と一致するデータを比較して、一致したデータのみkintoneとDynamoDB上の値の変更を行うようにすれば完成です。

手作業で何度も繰り返すめんどくさい作業もあとは請求書の発行を停止するだけ！
忙しいバックオフィスの方もこれで多少楽になる！

# 参考
[1] https://tech-blog.cloud-config.jp/2021-10-07-power-automate-json-best-friends/