【vte.cx入門】8.ページネーションを実装する：jQuery実践編


[データ登録](http://qiita.com/takeyama/private/80669a5ccd65e77761a2)により、場合によってはデータ量が数百、数千と膨大になっていき、一度の取得では表示しきれないことがよく起こります。そんな時は一般的にページネーションを利用します。

vte.cxにもこのページネーション機能があるので、今回はjQueryによる設定方法を以下に記します。

# 1.ajaxでデータをページ指定で取得する（GETリクエスト）
上記データをjQueryのajax通信を使用し、GETリクエストを実行します。

```lang:javascript
$.ajax({
	url: '/d/hoge?f&l=50&n=1',
	method: 'get'
}).done(function(res) {
	alert('1ページ目取得成功');
}).fail(function( jqXHR, textStatus, errorThrown ) {
	alert('1ページ目取得失敗');
});
```
## ■リクエスト
| param | 値 | 例 |
|:-----------|:------------|:------------|
|url|取得先URL?f&l={表示件数}&n={ページ数}|/d/hoge?f&l=50&n=1|
|method|GET||

### 1ページ辺りの最大表示件数を指定する
「?l」に最大表示件数を指定します。以下の指定は「50件/1ページ」ということになります。

```
?l=50

?l=100      ←   100件/1ページ
```

### 取得したいページ数を指定する
「?n」に取得したいページ数を指定します。以下の指定は「1ページ目」ということになります。

```
?n=1

?n=2      ←   2ページ目
?n=3      ←   3ページ目
?n=10     ←   10ページ目
```

## ■レスポンス
### ステータス

| ステータス | メッセージ | レスポンス |
|:-----------|:------------|:------------|
|200|OK|feed形式のデータ一覧|
|204|No entry|（空）|

204 No entryの場合は、取得先の配下に何も登録されていない状態です。

その他のエラーの場合、以下の仕様書の下部に細かく記載されています。
[HTTPステータス一覧](http://reflexworks.jp/documentation.html#taggingservice.html#H)

### 「Please make a pagination index in advance. 」400エラー
このエラーが発生した場合は以下のページネーションの初期設定を行ってください。

# ページネーションを実装するには初期設定が必要（Index生成）

実は上記の記述だけではエラーとなってしまいます。
それは、あらかじめページネーションのIndexを生成する必要があるからです。

まずは以下のURLにGETすることで、ページネーションのIndex生成を行います。

```
https://{自分のサービス}/d/hoge?f&l=50&_pagination=10
```
## 初期設定のURL解説

① まずはページネーションを設定したいデータのURLを決めてください。
仮に「/hoge」配下にするとします。

```
https://{自分のサービス}/d/hoge?f
```
② 次に1ページあたりの最大表示件数を決めます。
仮に50件とします。最大表示件数は「?l」パラメータに指定します。

```
?l=50
```
③ 次に何ページまで[index](http://reflexworks.jp/documentation.html#taggingservice.html#T4)を貼るかを設定を決めます。
仮に10ページまでindexを貼るとします。indexは「?_pagination」パラメータに指定します。

```
?_pagination=10
```

④ これを組み合わせるページネーション機能の初期設定をするためのURLができあがります。

```
https://{自分のサービス}/d/hoge?f&l=50&_pagination=10
```

このURLは
**「/hoge」に1ページ辺り最大50件まで表示するページを10ページ目まで設定**
ということになります。

### _paginationパラメータは以下のいずれかです。

 * {終了ページ番号}
 * {開始ページ番号},{終了ページ番号}

11ページ目を取得したい場合は、あらたに以下のURLをGETし、ページネーションのindexの続きを貼る必要があります。

```
https://{自分のサービス}/d/hoge?f&l=50&_pagination=11,20
```

11ページ目を取得したい場合、「?_pagination=11,20」とした方が処理の効率が良いです。
「_pagination=11」だと、1ページから11ページまでのページング情報(ページネーションのIndex)を作成します。最初に作成した10ページまでの情報がクリアされてしまいます。

# 【注意】?_paginationをしても「Please make a pagination index in advance. 」400エラーが発生する場合があります

**ページのIndexを作成するのには時間がかかります。**
例えば、100ページまでIndexを作るリクエストをした後、いきなりクライアント側が100ページ目の一覧取得を要求（GET）した時、サーバー側はまだIndexを張り終えていない場合があるため、Please make a pagination index in advance. 」エラーを返す場合があります。

その時は、**「1秒後にもう一度100ページ目を取得する」**といったリトライをする必要があります。

具体的には以下にソースを用意したのでそちらをご覧ください。

# javascriptのソース（テンプレート）
以下のページネーションに必要なロジックを準備しました。
初期設定から実際に1ページ目を取得するまでのロジックです。
このソースをコピペし、画面で実行することで、ページネーションが実装できます。

```
// 2つのグローバル変数を定義
var _pageindex = 0; // ページネーションを貼る最大index
var _maxSize = 50;  // 1ページにおける最大表示件数（例：50件/1ページ）

/****
 * ページネーションの初期設定処理
 * @page ページネーションを設定するURL
 * @page 取得したいページ
 *****/
function indexBuilding(url, page) {
	var d = new $.Deferred();

	//　ページング取得に必要な設定を行う
	var param;
	var pageindex = page + 9 > _pageindex ? page + 9 : _pageindex;
	if (pageindex > _pageindex) {
		if (_pageindex > 1) {
			param = _pageindex + ',' + pageindex;
		} else {
			param = pageindex;
		}

		// サーバにページネーション設定リクエストを送信
		$.getJSON(url + '?f&l=' + _maxSize + '&_pagination=' + param, function(){
			_pageindex = pageindex;
			d.resolve();
		}); 
	} else {
		d.resolve();
	}
	return d.promise();
}

function getFeed(url, pageNo) {
		$.ajax({
			url: url + '?f&l='+ _maxSize + '&n=' + pageNo,
			method: 'get',
			dataType: 'json'
		}).done(function(res) {

    		// 「res」にurlの1件目から50件目が格納されている
    		// pageNoが「2」だったら51件目から100件目が格納されている

		}).fail(function( jqXHR ) {

    		// エラー発生
            if (jqXHR.responseJSON.feed.title　=== 'Please make a pagination index in advance.') {

                // 1秒後にリトライする
                setTimeout(function(){
                    getFeed(url, pageNo);
                }, 1000);

            } else {
                alert('一覧取得失敗');
            }
		});
}

$(function(){

	// /hogeにページネーション設定を行います。
	var url = '/d/hoge';

	// 1ページ目（1〜50件）を取得する（これを2にすれば51から100までを取得する）
	var pageNo = 1;

	// 初期処理呼び出し（Index生成）
	indexBuilding(url, pageNo).then(function(){

		// ここからロジックを書く
		// 一覧取得
        getFeed(url, pageNo);

	});
});

```

ページネーションの実装は[vtecxblank](https://github.com/reflexworks/vtecxblank)に実際に動くものがあります。
以下のファイルを参考にしてみてください。

```
/app/demo_list.html
/app/scripts/demo_list.js
```

次回は画像の登録と参照方法を説明します。