Kintoneで他のアプリからユーザー選択の値を取得する
やりたいこと
とあるアプリで、他のアプリから値を取得して任意のフィールドに設定したいのです。
- [社員名簿]アプリでは、「社員名」と「承認者」を紐づけている。
- [作業依頼申請]アプリでは、「申請者」とその「承認者」を入れる必要がある。
上記のような状態のアプリがあったとします。 [作業依頼申請]アプリで「承認者」を入力するのはとても面倒くさいので、[社員名簿]アプリから「承認者」を取得して設定したいです。
[社員名簿]アプリ
社員名簿 - kintone(キントーン)- すぐに使えるサンプルアプリ | サイボウズの業務改善プラットフォームを使っています。 今回使うフィールドは以下です。
フィールド名 | フィールドコード | フィールドの種類 |
---|---|---|
社員名 | 社員名 | ユーザー選択 |
承認者 | 承認者 | ユーザー選択 |
[作業依頼申請]アプリ
作業依頼申請 - kintone(キントーン)- すぐに使えるサンプルアプリ | サイボウズの業務改善プラットフォームを使っています。 今回使うフィールドは以下です。
フィールド名 | フィールドコード | フィールドの種類 |
---|---|---|
申請者 | applicant | 作成者 |
承認者 | authorizer | ユーザー選択 |
JavaScriptを実装します。
レコード編集を始めるタイミングで処理を起動します。
kintone.events.on([ 'app.record.index.edit.show', 'app.record.create.show', 'app.record.edit.show' ], function(event) {
レコード編集を始めるタイミングで処理が動くようにイベントハンドラーを登録します。
イベントハンドラーを登録する
kintone.events.on(type, handler)
引数のtype
には以下のタイミングを指定します。
イベントが発生するタイミング | イベントタイプ | Promise対応 |
---|---|---|
レコード一覧画面 - インライン編集開始 | app.record.index.edit.show | o |
レコード追加画面 - 表示後 | app.record.create.show | o |
レコード編集画面 - 表示後 | app.record.edit.show | o |
表の参考元 : kintone JavaScript API(イベント)一覧 – cybozu developer network
APIの呼び出しを行うので、kintone.Promiseに対応したイベントを使います。
※ この kintone.Promise オブジェクトを return することで、kintone.api() の実行を待ってから次の処理を実行できるイベントがあります。 対応しているイベントはこちらをご参照ください。
他のアプリでの検索条件に使う値を取得する。
[社員名簿]アプリから情報を取得する検索条件に使う値を取得します。 処理を「新規作成」「新規作成以外(既に登録されているレコードの編集)」に分岐させています。
if (event.type === 'app.record.create.show') { // レコード追加時には、[申請者]フィールドにログインユーザーが設定されていないので、ログインユーザー情報を直接取得する user = kintone.getLoginUser().code; } else { // [申請者]フィールドからユーザー情報を取得する user = event.record['applicant']['value']['code']; }
検索条件に使用する[社員名簿]アプリの[申請者]フィールドには[作成者]を使用しています。
レコードを保存したユーザーが自動で設定されるフィールドです。
この[作成者]は、新規作成して初回保存時に設定されるようです。 ということで、「新規作成」の時はログインユーザーから情報を取得するようにしています。
Kintone REST APIで他のアプリからユーザー選択の値を取得する
APIを使って[社員名簿]アプリの[承認者]フィールドを取得します。検索条件は「[社員名簿]アプリの[社員名]フィールドが、[作業依頼申請]アプリの[申請者]フィールドと同じ」です。
let params = { app: 11, fields: ['承認者'], query: '社員名 in ("' + user + '")' };
表の出典 : レコードの一括取得(クエリで条件を指定) – cybozu developer network
パラメータ名 | 指定する値 | 必須 | 説明 |
---|---|---|---|
fields | 文字列の配列 | 省略可 | レスポンスに含めるフィールドコードを指定します。 省略した場合は、閲覧権限を持つすべてのフィールドの値が返されます。 |
app | 数値又は文字列 | 必須 | アプリのID を指定します。 |
query | 文字列 | 省略可 | レスポンスに含めるレコードの条件を指定するクエリ文字列です。 クエリ文字列内では、後述の演算子とオプションが使用できます。 省略した場合は、閲覧権限を持つすべてのレコードが返されます。 |
Kintone REST APIの呼び出しで、コールバック関数を指定する方法と省略する方法があります。 ここでは、コールバック関数を省略してkintone.Promise オブジェクトが返却されるようにします。
Promiseを使う利点
レコード作成時などに、処理を待ってからレコードを保存することができる(同期的処理、と呼びます) 「あるアプリAのレコードを保存時、アプリBのレコードを取得し、その値を利用」というようにレコードの保存時などにkintone APIを使って他のデータを取得したり変更したり、同期的に処理することができるようになります。
そうすることで、APIを使って[社員名簿]アプリから取得したデータを画面のフィールドに反映させることができます。
return kintone.api(kintone.api.url('/k/v1/records.json', true), 'GET', params).then( function(resp) { // API の呼び出しが成功したら実行される処理... return event; }).catch(function(error) { // API の呼び出しが失敗したら実行される処理... return event; });
ソースファイルを登録すれば出来上がりです。
- [作業依頼申請]アプリの設定画面を開く
- [適用範囲]=「すべてのユーザーに適用」を選択
- [PC用のJavaScriptファイル]の[アップロードして追加]ボタンで実装したソースファイルをアップロード
-
- 公開する前にアプリの動作テストをすることもできます。(参考 : アプリの動作テストをする - kintone ヘルプ)
できた!
こんな感じで、[作業依頼申請]アプリでレコードを追加したり編集すると[社員名簿]アプリから「承認者」を取得して自動で設定されるようになりました。
うまくいかなかったこと
APIで取得した結果を設定したのに反映されない!
原因 : ハンドラーが return してないから
return kintone.api(kintone.api.url('/k/v1/records.json', true), 'GET', params).then(function(resp) { // ...省略... event.record['authorizer']['value'] = userlist; }).catch(function(error) { console.log(error.message); });
フィールドの値を書き換える
ハンドラーが record オブジェクトのフィールドの値を書き換えて event オブジェクトを return した場合、その値でフィールドの値を更新します。
- 最後のハンドラーが return しない場合、フィールドの値を更新しません。
原因 : Promiseオブジェクトを使う方法じゃないから
return kintone.api(kintone.api.url('/k/v1/records.json', true), 'GET', params, function(resp) { // API の呼び出しが成功したら実行されるコールバック処理 return event; }, function(error) { // API の呼び出しが失敗したら実行されるコールバック処理 return event; });
コールバック関数を指定しており、kintone.Promise オブジェクトは返却されません。 というわけでなのでAPIを呼び出す処理が終わるのを待たずに画面表示処理が進んでしまいました。
このように kintone.api() はコールバック関数を省略するとPromiseオブジェクトが返り値になります。
kintone.api(kintone.api.url('/k/v1/record', true), 'GET', {app: 1, id: 1}); // これでPromiseオブジェクトが生成される
それを return してあげることによってkintone側で app.record.create.submit 時など、処理を待ってくれる仕組みをkintoneは持っています。Promiseオブジェクトを return しないと処理をまってくれないので注意しましょう。(逆に言えば、レコード詳細ページなど、処理を待たせる必要がなければPromiseオブジェクトの return は必須ではありません。)
Failed to load resource: the server responded with a status of 400 (Bad Request) - 入力内容が正しくありません。
/** @type {object} API に渡すパラメータオブジェクト. */ let params = { app: 11, fields: ['承認者'], query: '社員名 in (' + user + ')' // 正解>>> '社員名 in ("' + user + '")' };
520 (520) - 社員名フィールドのフィールドタイプには演算子=を使用できません。
/** @type {object} API に渡すパラメータオブジェクト. */ let params = { app: 11, fields: ['承認者'], query: '社員名 = "' + user + '"' // 正解>>> '社員名 in ("' + user + '")' };
フィールド又はシステム識別子 | 利用可能な演算子 | 利用可能な関数 |
---|---|---|
ユーザー選択 | in not in |
LOGINUSER() |
表の出典元 : フィールド、システム識別子ごとの利用可能な演算子と関数一覧 – cybozu developer network