Japan Dynamics CRM Team Blog

Microsoft Dynamics CRM technical information for partners and customers

Dynamics CRM 2011 サンプル紹介 REST エンドポイントとページング

Dynamics CRM 2011 サンプル紹介 REST エンドポイントとページング

  • Comments 0

みなさん、こんにちは。

東京では先週末に桜が満開だったようです。桜を見ると気分が和らぎますね。

さて今回は、REST エンドポイントサンプルの締めくくりとして、ページングの
サンプルに触れたいと思います。

REST エンドポイントの制限とページング

REST エンドポイントでは、一度に付き最大 50 件のデータを返します。これは
パフォーマンスを考慮しての制限です。逆に、50 件以上のデータを取得して
画面に表示させたい場合には、続きのレコードから再度取得し、結果を
結合していく必要があります。

REST エンドポイントは、データを返す際に、まだデータがある場合には
そうと分かるように追加で情報を渡しています。その情報を利用して
続きのレコードから再度 50 件まで結果を取得できます。

事前準備

検証を行うためには、50 件以上の取引先企業データが必要となります。
サンプルデータは 50 件もありませんので、手元で 50 件以上のデータを
作成してください。

- UI から手動での作成
- サンプルデータ用の CSV を作成し、インポート
- SDK 利用

もっとも簡単にできるのは、2 番目かとおもいますが、REST サンプルを
紹介してきましたので、是非 3 番目も試してください。私の手元では、
Sample Account 01 ~ 99 と、既存のサンプルデータが存在する環境を
利用します。

付加情報の確認

では早速ページングの情報がどのように返るか見ていきましょう。

1. Internet Explorer を起動して、 REST エンドポイントを利用して
取引先企業を取得する。表示を簡潔にするため、名前のみ表示
…組織URL…./XRMServices/2011/OrganizationData.svc/AccountSet?$select=Name

2. 画面で結果を確認。私の環境では、サンプルデータから始まり、
Account Sample 36 までの合計 50件が表示。
image

3. 画面最下部に <link ref=”next” href=”<url>” /> があることを確認。これが
ページング情報です。URL 部のみをコピーして、Internet Explorer のアドレスに
貼り付け。実行してください。
image

結果は Sample Account 37 以降の 50 件を取得できました。これを繰り返し、取得できる
レコードが 50 件以下になった時点で、<link ref> はなくなります。

URL には何ページ目かを示す $skiptoken も付属しています。さて、これらの知識を
前提に、サンプルを紹介します。

サンプルは、sdk\samplecode\js\restendpoint\restendpointpaging に
あるものを利用します。動作を試すために、事前にこのフォルダにある
restendpointpagingjscript_1_0_0_0_managed.zip ファイルを、ソリューションとして
インポートしておいてください

このサンプルは、指定した数の取引先企業を取得できるもので、指定できる数が
50 より大きい、100、300、600、900 となっています。

image

このサンプルは以下のファイルで構成されています。
restendpointpaging.htm - 上記スクリーンショットの画面を提供
sdk.restendpointpaging.js - ページングを利用したデータの取得用
json2.js - JSON ライブラリ
restendpointpaging.css - スタイルシート

HTML ファイル

HTML ファイルでは画面の作成とスクリプトを保持しています。

スクリプトの読み込み
restendpointpaging.htm ファイルでは、まずスクリプト類の読み込みが指定されます。
またスタイルシートファイルもここで指定します。

<script src="../ClientGlobalContext.js.aspx"></script>
<script src="Scripts/SDK.RestEndpointPaging.js" type="text/javascript"></script>
<script src="Scripts/json2.js" type="text/javascript"></script>
<link href="Styles/RestEndpointPaging.css" rel="stylesheet" type="text/css" />

独自スクリプト
各種ファイル読み込み後、独自のスクリプトが定義されています。

<script type="text/javascript">
  var accountsGrid; // 画面に出力する際の、 tbody 要素を保持
  var numberOfAccountsToRetrieve; // 取得する取引先企業数 (100、300、600、900)
  var btnRetrieveAccounts; // 取得実行ボタン
  onload = function () {

   // 画面から btnRetrieveAccounts ボタンを取得
   btnRetrieveAccounts = document.getElementById("btnRetrieveAccounts");
   // 画面から、accountsGrid を取得
   accountsGrid = document.getElementById("accountsGrid");
   // 画面から、 numberOfAccountsToRetrieve を取得
   numberOfAccountsToRetrieve = document.getElementById("numberOfAccountsToRetrieve");
   // ボタンのクリックイベントに retrieveAccounts 関数をセット
   btnRetrieveAccounts.onclick = retrieveAccounts;
   btnRetrieveAccounts.click();
  }

  function retrieveAccounts() {
   clearaccountsGrid(); // accountsGrid のデータをクリア

   // numberOfAccountsToRetrieve から検索数を取得して数値に変換
   var number = parseInt(numberOfAccountsToRetrieve.options[numberOfAccountsToRetrieve.selectedIndex].value, 10);
   // 取得列として名前と電話番号、また検索数を設定
   var filter = "/AccountSet?$select=Name,Telephone1&$top=" + number;
   // 別 JScript ファイルの RetrieveRecords 関数を、フィルターおよびコールバックを指定して実行
   SDK.RestEndpointPaging.RetrieveRecords(filter, retrieveAccountsCallBack);
  }

  function retrieveAccountsCallBack(retrievedAccounts) {
   // 取得した取引先企業の数だけループ
   for (var i = 0; i < retrievedAccounts.length; i++) {
    // 取引先企業を取得
    var account = retrievedAccounts[i];
    // 結果表示テーブル用の行を作成
    var row = document.createElement("tr");
    // 行にセットする名前用の列を作成
    var nameCell = document.createElement("td");
    // 名前の列に取引先企業名をセット
    nameCell.innerText = account.Name;
    // 行に作成した名前用の列を追加
    row.appendChild(nameCell);
    // 同じように電話番号列も作成して追加
    var mainPhoneCell = document.createElement("td");
    mainPhoneCell.innerText = (account.Telephone1 == null) ? "" : account.Telephone1;
    mainPhoneCell.className = "rightColumn";
    row.appendChild(mainPhoneCell);
    // グリッドに作成した行を追加
    accountsGrid.appendChild(row);
   }
  }

  function clearaccountsGrid() {
   // グリッドの全部の列を削除
   for (var i = accountsGrid.rows.length - 1; i >= 0; i--) {
    accountsGrid.deleteRow(i);
   }
  }
</script>

UI 部分
UI 部分として、グリッド、ボタン、ドロップダウンを作成しています。ドロップダウンには
取得件数を指定できるよう、100、300、600、900 の数値がハードコードされています。

sdk.restendpointpaging.js ファイル

ではスクリプトファイルを確認しましょう。今までのサンプル同様、REST エンドポイントを
利用して、データの取得を行っているだけですが、コールバック部分でページングの
処理を追加してあります。

RetrieveRecordsCallBack: function (retrieveRecordsReq, callback) {
  // HTTP リクエストのステータスから、処理結果を確認
  if (retrieveRecordsReq.readyState == 4 /* complete */) {
   if (retrieveRecordsReq.status == 200) {
    // 成功の場合、JSON 形式からオブジェクトへ変換
    var retrievedRecords = JSON.parse(retrieveRecordsReq.responseText).d;
    /// HTML 側にあるコールバック関数が呼ばれる
    callback(retrievedRecords.results);

    // 結果として取得したオブジェクトに __next の値がある場合はページング処理
    if (null != retrievedRecords.__next) {
     // 次のページ用に OData パス以降の部分のみ切り出して、フィルターに指定
     var filter = retrievedRecords.__next.replace(SDK.RestEndpointPaging.GetODataPath(), "");
     // 再度 RetrieveRecords 関数呼び出して、このコールバックに戻ってくる
     SDK.RestEndpointPaging.RetrieveRecords(filter, callback);
    }
   }

以上のように、結果からページングの情報の有無を確認し、存在する場合には
新しい URL (上記の場合はフィルタ部分のみ活用) を利用して続きのデータを
取得しています。

まとめ

ページング処理は通常、開発者側がパフォーマンスを考慮して設定するものですが、
Dynamics CRM 2011 では既定でページング処理が存在するため、そこをハンドリングして
ページングの境界を越えたデータの取得を処理する必要があります。

これは Silverlight アプリケーションのも言えますが、同様のサンプルが Silverlight
バージョンも存在しますので、是非試してください。

- Dynamics CRM サポート 中村 憲一郎

  • Loading...
Leave a Comment
  • Please add 6 and 3 and type the answer here:
  • Post