最近kintone漬け。
といっても、新しい機能を追加していくような楽しい作業ではなく、運用中のアプリの不具合対応(デバッグ)と細かい改良ばかりで、少し疲れてきた。
そんな中で、kintoneのデータの加工・集計をラクにやる方法はないものか? と調べていたら、
kintone でSQLを使う
という記事を発見。
alasqlというJavascript用データベースを使うと、kintoneのデータをSQLで集計できるじゃん。これすごい。
SUM(Group By)で合計値を求めたり、複数のアプリのデータをJoinで組み合わせたりできる。
(逆に言うと、こんな簡単なことがkintone標準機能ではできなかったりするのだが…)
"kintone alasql"でググるとそこそこ記事が出てくるので、もしかしてkintoneガチ勢には当たり前の話?
早速、工数管理アプリに入っている工数明細をプロジェクト単位・個人単位でSUMする画面を作ってみたので、備忘のために記事に残しておく。
元データはこんな感じ。
![]() |
Figure.1 集計元のkintoneアプリ |
設計方針
データは、event.recordsではなくAPIで取得する(event.recordsは最大でも100件しかデータが取れないので、集計目的では使えない)。 APIは生で叩くのではなく、kintone-rest-api-clientを利用。(getAllRecordsWithCursorが最強。みんな使うといいと思う。)
データの表示にはjQuery DataTablesを利用する。DataTablesを使って多機能な一覧画面を作ろう! – cybozu developer network とかが参考になる。
動作環境
アプリ設定画面の「JavaScript / CSSでカスタマイズ」にて以下URLを指定。
また、http://alasql.org/ から alasql.min.js をDLし、PC用のJavaScriptファイルにアップロードしておく(alasqlのzipをダウンロードして解凍し、distディレクトリから取り出せば良い)。
もう1点、DataTablesの見栄えをkintoneに近づけるため、DataTablesをkintoneライクにする魔法のコード - Qiitaからkintone-datatables.cssをDLし、PC用のCSSファイルにアップロードしておくとよい(作者の方に感謝)。
サンプルコード HTML
アプリに一覧「プロジェクト別集計」を作成しておく。
レコード一覧の表示形式を「カスタマイズ」にし、以下のHTMLを記述。
1 | < table id = "myTable" ></ table > |
サンプルコード js
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 | /* * project_summary.js * 工数管理アプリのデータをプロジェクト別・個人別に集計 * * required: jquery.dataTables.min.js * * required: kintone-rest-api-client * * requeired: alasql.min.js */ ( function () { "use strict" ; kintone.events.on([ 'app.record.index.show' ], function (event){ if (event.viewName !== 'プロジェクト別集計' ) return ; // Initialize kintone-rest-api-client const client = new KintoneRestAPIClient(); var myTable; var appId = kintone.app.getId(); var query = kintone.app.getQuery(); // APIでデータ取得 client.record.getAllRecordsWithCursor({ app: appId, query: query, }).then( function (response){ // kintoneのrecords(json)を、alasqlで扱える配列に変換 function convertToRows(records) { var rows = records.map( function (record){ var keys = Object.keys(record); var row = {}; keys.map( function (key){ switch (key) { case '担当者氏名' : // '担当者氏名'フィールドからname(=氏名)を取り出す row[ '担当者氏名' ] = record[key].value[0][ 'name' ]; break ; case '作業担当部署' : // '作業担当部署'フィールドからname(=部署名)を取り出す row[ '作業担当部署' ] = record[key].value[0][ 'name' ]; break ; default : // 他のフィールドはvalueを取り出す。数値の場合はNumberに変換 row[key] = record[key].type === 'NUMBER' ? Number(record[key].value) : record[key].value; } }); return row; }); return rows; } var recordSet = convertToRows(response); // sum([工数]) by alasql var sqlResult = alasql( "SELECT [プロジェクトコード], [作業担当部署], [担当者氏名], SUM([工数計_人月]) AS [工数計_人月] FROM ? GROUP BY [プロジェクトコード], [作業担当部署], [担当者氏名]" , [recordSet] ); // 表に表示するカラム(alasqlの出力結果の項目名) var columns = [ 'プロジェクトコード' , '作業担当部署' , '担当者氏名' , '工数計_人月' , ]; // 表のタイトルを好きにいじれるよう、別変数で定義。このサンプルではあまり意味がない。 var titles = { プロジェクトコード: 'プロジェクトコード' , 作業担当部署: '作業担当部署' , 担当者氏名: '担当者氏名' , 工数計_人月: '工数計' , }; // DataTables初期化 myTable = $( '#myTable' ).DataTable({ // DataTableの設定値はお好みで。 destroy: true , pageLength: 100, lengthChange: false , searching: false , info: false , data: sqlResult.map( function (record){ return columns.reduce( function (data, column){ data[column] = record[column]; return data; }, { レコード番号: record[ 'レコード番号' ] }); }), columns: columns.map( function (column){ return { title: this [column], data: column } }, titles) }); }); }); })(); |
動作イメージ
サンプルの動作結果はこんな感じ。
![]() |
Figure.2 カスタマイズ結果 |
画像にモザイクがかかりまくっていて何がなんだか分からないが、結果はとても良好。パフォーマンスも今のところ申し分ない。
今回はSUMしか使っていないが、そのうちJoinも使ってみたい。
0 コメント:
コメントを投稿