HandsOnTableについて
基本的な使い方はこちらの記事が詳しいです。
https://qiita.com/opengl-8080/items/ac19deec388c357cd498
https://qiita.com/opengl-8080/items/9d25e106ff48b66cb908
Jsでこれだけきっちり動くグリッドコンポーネントは本当に使いやすいです。
今回はコンポーネントをRailsでうまいこと動かすためのプラクティスをいくつか紹介します。
前提条件の説明
今回はAjaxをバリバリ使っているので、まだJquery依存な形で作成していきます。
ページング処理には、Kaminariを利用しています。
Rails5以上推奨です。
yarn使った方が、良いので。
セットアップについては省きます。
yarnで、HansonTable入れたり、モデル作成部分は説明しません。
今回は一例として、ユーザー管理画面の作成としてみます。
まずはコントローラーから
最初の表示用にhtmlを利用し、データの取得には*.erb.jsを利用します。
コントローラー内部でうまく使い分けしています。
こうすることで、1回目の読み込み処理を遅延読み込みにし、初回表示速度を早めています。
Controller(users_contoroller.rb)
class UserssController < ApplicationController
# GET /users
def index
respond_to do |format|
format.html {}
format.js {
@users= User.page(params[:page])
}
end
end
end
index.erb.html
<div id="hot" class="cursor"></div>
<div id="paginator"></div>
<script>
var hotElement = document.querySelector('#hot');
var columns = [{
title:"ID",
data: "id",
readOnly: true,
type: 'text',
},{
title:"ユーザー名",
data: "name",
readOnly: true,
type: 'text',
}]
var hotSettings = {
data: {},
columns: columns,
};
var hot = new Handsontable(hotElement, hotSettings);
var loadData = function(){
$.ajax({type:"GET",url:"/users",dataType:"script"});
};
loadData();
</script>
HTMLについて
本来なら、JSを分けるべきですが、一旦同じファイルに記載しています。
Jsにて、HansOnTableのセットアップを行っていますが、この時点で、データは空です。
Ajaxでのデータ読み込み
このajaxでの処理がポイントになります。
dataType:"script"とすることで、index.js.erbに記載したscriptの処理を実行することができます。
この方法は、link_toなどで、remote:trueの処理を書く場合と同じ方法ですね。
View(index.js.erb)
// URLの書き換え処理
history.replaceState("permit",null,"<%= request.url %>");
// ページングと、検索条件の表示を更新
$("#paginator").html("<%= j paginate(@user,remote:true) %>");
// Gridデータを更新
hot.loadData(<%= raw ActiveModel::Serializer::CollectionSerializer.new(@user).as_json.to_json %>);
Ajaxからの読み込み処理、index.js.erbを利用したデータ描画を行います。
ここで、hansontableにJson化したUserデータを挿入しています。
加えて、URLの書き換えも行っています。初回読み込み時には必要ありませんが、
ページング処理や、検索条件の変更などがあった場合に使えます。
Kaminariを利用したページングの使い方。
今回はKaminariのデフォルトテンプレートを生かしたまま動作するようにしています。
paginateでHtmlを生成し、そのままDivの中身を差し替えしています。
remote:trueを指定することで、ページング処理から呼ばれるときも、index.js.erbで処理されるため、
レイアウトは更新されず、HandsOnTableの中身と、ページネーションだけ更新されていきます。
この方法を利用して、実運用では、検索条件のテンプレ更新も使っています。
js.erbを利用して、コンポーネントごと差し替えをしていると、Jsが破綻しないので、オススメです。
(turbolinkつかえっていう話もありますが)
まとめ
データをjson読み込んだりするのを非同期処理で書くのは難しいですが、こうしてIndex.js.erbに書くと、可読性が高く、不具合が起きにくい書き方にすることができます。
Paginationがそのままテンプレートとして、利用できるのは大きいですね。
この方法をそのまま利用して、検索条件やページごとの変動項目の書き換えなども可能です。
細かいプラクティスとしては、エラーハンドリングは書かず、別途documentでAjax:errorイベントなどを拾ったり、error.js.erbを作成して、アラートを表示させたりしています。
こうすることで、比較的Jsを書かずに、データの更新処理かけるので、ぜひ利用してみてください。