【PlayFab】実行されたCloudScript(AzureFunctions)のログを検索する

#はじめに
PlayFabを使ったゲームで詫び石を配ることになった時、EventHistoryで詫び対象のユーザーを調べるのに手こずったのでメモです。

#環境
PlayFab : 2020/10/02時点
AzureFunctionsでゲーム固有の関数を作成し、CloudScriptは未使用

#PlayFabの通信ログの見方
PlayFabのタイトルページを開きます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/113293/838b0458-3bb4-ce34-35dd-99dbbcabc49d.png)
メニューの「Data」をクリックします。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/113293/1ed045ec-1351-3926-6a7b-49247da75e12.png)
EventHistoryというページが開きます。
下にスクロールすると時間毎のAPIコール数のグラフとリクエストのリストが見れます。

このEventHistoryでは、PlayFabの通信ログをある程度検索できます（時間やどの標準APIが呼ばれたかなど）が、AzureFunctionsやCloudScriptのログの検索は自分で検索クエリ（Kusto）を書く必要があります。

> イベント履歴の検索の構築 - PlayFab | Microsoft Docs
https://docs.microsoft.com/ja-jp/gaming/playfab/features/analytics/metrics/constructing-an-event-history-search

#（本題）任意の関数やパラメーターのログを検索するクエリ
##関数名やパラメーターをそのままクエリに入力して検索
期間を指定せずに検索する時はこの方法が手っ取り早いです。
実はEventHistoryの検索クエリは、クエリ文になっていなければ、そのままリクエストを文字列検索してくれます。
たとえば、「Gacha」という関数を呼んだログを検索したい場合は「Gacha」と検索すれば"Gacha"が含まれたリクエストを検索できます。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/113293/b1f113cd-fe5a-526c-df86-82207f0e9c3c.png)

ただこの場合、全期間のログに対して検索してしまうので、期間を指定したい時などには使えませんし、複数の文字列でand検索することもできません。
また文字列が一致しているかしか見ていないので"Gacha"を含んだ他のリクエストも引っかかってしまいます（「Gacha」というユーザ名に変更したリネームリクエストとか）

##indexof関数を使って検索
自分のケースのように補償対象ユーザーを探すといった際には期間を指定してログを見たいと思いますので、その場合はこちらの方法を使います。
たとえば、2020/9/1～2020/10/1までに「Gacha」関数を呼んだログを検索する場合は以下のクエリを入力します。

```sql:query
where Timestamp between (datetime(2020-09-01T00:00:00)..datetime(2020-10-01T00:00:00))
| where FullName_Name == 'function_executed'
| where indexof(EventData,"Gacha") > 0 
```

まず、```FullName_Name == 'function_executed'```で、AzureFunctionsの呼び出しで絞っています。
そして、indexof関数でEventDataに指定文字列があるかを検索しています。

また複数文字列の検索もできます。

```sql:query
where Timestamp between (datetime(2020-09-01T00:00:00)..datetime(2020-10-01T00:00:00))
| where FullName_Name == 'function_executed'
| where indexof(EventData,"Gacha") > 0 
| where indexof(EventData,"pickup") > 0 
```

ただ、こちらも文字列検索なので、別のリクエストにその文字列が含まれていたら、検索されてしまいます。

##parse_json関数を使って検索

今までの検索では文字列一致しているかしか見ていないので、別のリクエストが紛れ込んでしまうかもしれません。
そこでリクエストをjsonからパースしてデータとしてアクセスします。

たとえば、AzureFunctionsの「Gacha」関数を呼んでいるログを検索するクエリは以下の通りです。

```sql:query
where Timestamp between (datetime(2020-09-01T00:00:00)..datetime(2020-10-01T00:00:00))
| where FullName_Name == 'function_executed'
| extend d=parse_json(EventData) 
| extend FunctionName = d.Payload.FunctionName
| where strcmp(FunctionName,'Gacha') == 0
```

リクエストのパラメーターの絞り込みもPayloadのメンバーにアクセスすることで可能です。

# おわりに

サーバーサイド何もわからんなので、PlayFab記事もっと増えて欲しい…。

外部からEventHistoryのログにアクセスする機能なんかは開発中のようなので、自動化する際はAzureFunctions側で別途ログを取るのが良いのかも。

>Is it possible to player&#39;s history events values from cloud script? - Playfab Community
https://community.playfab.com/questions/22986/is-it-possible-to-players-history-events-values-fr.html

（2年前の投稿なので改善されていそうですが）
自分は手動でやりましたが、規模が大きくなるとそれも難しくなるので自動化する方法があれば知りたい…。

# 参考サイト

>How can I find failed player_executed_cloudscript events in Event History or Explorer? - Playfab Community
https://community.playfab.com/questions/36668/how-can-i-find-failed-player-executed-cloudscript.html

>parse_json ()-Azure データエクスプローラー | Microsoft Docs
https://docs.microsoft.com/ja-jp/azure/data-explorer/kusto/query/parsejsonfunction