kintoneプラグイン開発でつまずきやすいポイント

著者名:武井 琢治

目次

はじめに

ここでは、kintoneでプラグインを開発する際によくつまずいてしまうポイントや、プラグイン開発において避けては通れない道など、あるあるネタを中心としたTipsをまとめていきたいと思います。

なお、基本的な開発手順につきましては、 kintoneプラグイン開発手順 を参照してください。

①すでに設定値がある場合は、プラグイン設定画面を表示した時に設定値をセットする

せっかくプラグイン設定画面で規定値をセットしてもらっても、プラグイン設定画面を再表示した時に、何を設定していたか表示してあげないと不親切ですね。
(例:プラグイン設定で「埼玉県」を選択したのに、再びプラグイン設定画面を開いた時にデフォルトの「北海道」に戻ってしまう)

これはプラグインのプラグイン設定画面に対するJavaScriptの中に、以下のような記述をすることで解決できます。

 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
/*
 * すでに設定値がある場合は、プラグイン設定画面を表示した時に設定値をセットする サンプルプログラム
 * Copyright (c) 2025 Cybozu
 *
 * Licensed under the MIT License
 * https://opensource.org/license/mit/
*/

(function(PLUGIN_ID) {
  'use strict';

  document.addEventListener('DOMContentLoaded', () => {
    // プラグインIDの設定
    const conf = kintone.plugin.app.getConfig(PLUGIN_ID);

    // 既に値が設定されている場合はフィールドに値を設定する
    if (typeof conf.elm !== 'undefined') {
      const element = document.getElementById('element');
      if (element) {
        element.value = conf.elm;
      }
    }
  });

})(kintone.$PLUGIN_ID);

この場合、保存時にconf.elmsetConfig関数で保存しておき、それが入っていれば、これは2度目以降のアクセスなのだということが分かります。
したがって、IDがelementの要素は入力必須か、必須でない場合は保存時conf.elmにデフォルト値を入れてあげる必要があります。

warning
注意

  • 上記は文字列フィールド等の場合で、プルダウンやチェックボックス等の場合にはデータの授受方法がやや異なります。

②プラグインで使用するフィールドを自動的に追加する

既存のアプリではなく、新規アプリを作成してもらうことを前提としたプラグインというものがよくあります。
その場合、フィールドまで作ってもらうのは少々気が引けます。

そこで、以下のコードを書くことで、プラグインで使用するフィールドを自動的に追加してしまいましょう。

 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
/*
 * プラグインで使用するフィールドを自動的に追加する サンプルプログラム
 * Copyright (c) 2025 Cybozu
 *
 * Licensed under the MIT License
 * https://opensource.org/license/mit/
*/
// 初回プラグイン設定時のみ必要なフィールドを自動追加する
kintone.api(kintone.api.url('/k/v1/preview/app/form/fields.json', true), 'POST', {
  app: kintone.app.getId(),
  properties: {
    Name: {
      code: 'Name',
      label: '名前',
      type: 'SINGLE_LINE_TEXT'
    },
    ID: {
      code: 'ID',
      label: 'ID',
      type: 'NUMBER'
    }
  }
}, (resp) => {
  location.reload();
});

この例では「名前」という文字列フィールドと、IDという数値フィールドを追加しています。

なお、追加処理の終了後にリロードしているのは、次の章段で説明するような、作ったフィールドをすぐにプラグイン設定画面で使用したいためです。
もし「フィールドは作るだけで、別にプラグイン設定画面では使わないよ」という場合、リロードは不要です。

③プラグインで使用するフィールドコードを直接入力させず、存在するフィールドの中からプルダウンで選択させる

これはすなわち下図のようなUIです。

フィールドコードを直接入力させると、開発者側は楽なのですが、ユーザー側としては「フィールドコードを確認して入力する」という手間が発生してしまいます。

これは以下のようなHTML、コードにて実現可能です。

HTML

 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
<!--
 * プラグインで使用するフィールドを自動的に追加する サンプルプログラム
 * HTML 
 * Copyright (c) 2025 Cybozu
 *
 * Licensed under the MIT License
 * https://opensource.org/license/mit/
-->
<div>
    <div class="block">
        <label class="kintoneplugin-label">
        <span id ="container_label">イベント名フィールド</span>
        <span class="kintoneplugin-require">*</span>
    </label>
        <div class="kintoneplugin-row">イベント名として使用する文字列フィールドのフィールド名を選択して下さい。</div>
        <div class="kintoneplugin-select-outer">
            <div class="kintoneplugin-select">
                <select id="name_code">
                </select>
            </div>
        </div>
    </div>
    <div class="block">
        <label class="kintoneplugin-label">
        <span id ="container_label">開始日時フィールド</span>
        <span class="kintoneplugin-require">*</span>
    </label>
        <div class="kintoneplugin-row">イベント開始日時として使用する日時フィールドのフィールド名を選択して下さい。</div>
        <div class="kintoneplugin-select-outer">
            <div class="kintoneplugin-select">
                <select id="start_datetime_code">
                </select>
            </div>
        </div>
    </div>
    <div class="block">
        <label class="kintoneplugin-label">
        <span id ="container_label">終了日時フィールド</span>
        <span class="kintoneplugin-require">*</span>
    </label>
        <div class="kintoneplugin-row">イベント終了日時として使用する日時フィールドのフィールド名を選択して下さい。</div>
        <div class="kintoneplugin-select-outer">
            <div class="kintoneplugin-select">
                <select id="end_datetime_code">
                </select>
            </div>
        </div>
    </div>
</div>

プラグイン設定画面のJavaScript

 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
/*
 * プラグインで使用するフィールドを自動的に追加する サンプルプログラム
 * プラグイン設定画面のJavaScript
 * Copyright (c) 2025 Cybozu
 *
 * Licensed under the MIT License
 * https://opensource.org/license/mit/
*/
// アプリのフォーム情報を取得
kintone.api(kintone.api.url('/k/v1/app/form/fields.json', true), 'GET', {
  app: kintone.app.getId()
}, (resp) => {
  const nameCodeSelect = document.getElementById('name_code');
  const startDatetimeSelect = document.getElementById('start_datetime_code');
  const endDatetimeSelect = document.getElementById('end_datetime_code');

  for (const key in resp.properties) {
    if (!resp.properties.hasOwnProperty(key)) {
      continue;
    }
    let confFlg = false;
    const prop = resp.properties[key];
    const label = prop.label;
    const code = prop.code;

    if (prop.type === 'SINGLE_LINE_TEXT') {
      if (typeof conf.name !== 'undefined' && code === conf.name) {
        confFlg = true;
      }
      const option = document.createElement('option');
      option.value = code; // nameではなくvalueを設定
      option.textContent = label;

      if (confFlg) {
        option.selected = true;
        nameCodeSelect.insertBefore(option, nameCodeSelect.firstChild);
      } else {
        nameCodeSelect.appendChild(option);
      }
    } else if (prop.type === 'DATETIME') {
      const optionStart = document.createElement('option');
      optionStart.value = code; // nameではなくvalueを設定
      optionStart.textContent = label;

      const optionEnd = document.createElement('option');
      optionEnd.value = code; // nameではなくvalueを設定
      optionEnd.textContent = label;

      if (typeof conf.name !== 'undefined' && code === conf.start_datetime) {
        optionStart.selected = true;
        startDatetimeSelect.insertBefore(optionStart, startDatetimeSelect.firstChild);
        endDatetimeSelect.appendChild(optionEnd);
      } else if (typeof conf.name !== 'undefined' && code === conf.end_datetime) {
        startDatetimeSelect.appendChild(optionStart);
        optionEnd.selected = true;
        endDatetimeSelect.insertBefore(optionEnd, endDatetimeSelect.firstChild);
      } else {
        startDatetimeSelect.appendChild(optionStart);
        endDatetimeSelect.appendChild(optionEnd);
      }
    }
  }
});

少々ややこしいですが、おおむね以下のような処理をしています。

  1. フォーム情報を取得
  2. フィールドの数だけ回す。
  3. そのプルダウンで表示したいフィールドタイプ(上記例の場合、文字列と日付)のものだけプルダウンに追加する。
  4. ただし、すでに規定値がある場合は、規定値が最上位へ来るようにする。

また、プラグイン設定画面の表示上は「フィールド名」にしたいため、optionタグのテキストはフィールド名を挿入し、name属性にフィールドコードを挿入しています。
これは、後のカスタマイズでこのフィールドコードを使用するためです。

プラグイン設定保存時にプルダウンで選択された選択肢のname属性をsetConfig関数で保存しておくことで、後のカスタマイズでそのフィールドコードを使用できます。

warning
注意

「51-modern-default.css」が必要です。

おまけ

@kintone/rest-api-client kintone-ui-component を使うと、上記の処理をより楽に実装できます。

  • kintone REST APIをJavaScriptで扱うときに必要な処理をまとめたライブラリ
  • kintoneライクなUIパーツを簡単に作ることができるライブラリ
    • kintone-ui-component
      JavaScript内でHTMLの要素や属性を書くことなくkintoneに調和するUIを生成できます。

④プラグインで使用するカスタマイズビューを自動的に追加する

プラグインでカスタマイズビューを使用することがありませんか?
私はよくあります。

そこで、以下のようにカスタマイズビューを自動で用意してあげたら、ユーザーは楽チンですね。
カスタマイズビューを自動で追加する方法は、 プラグインの設定でカスタムビューを作成する方法 でも紹介しているので、参考にしてみてください。

 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
/*
 * プラグインで使用するカスタマイズビューを自動的に追加する サンプルプログラム
 * Copyright (c) 2025 Cybozu
 *
 * Licensed under the MIT License
 * https://opensource.org/license/mit/
*/
kintone.api(kintone.api.url('/k/v1/preview/app/views.json', true), 'GET', {
  app: kintone.app.getId()
}).then((appResp) => {
  // 深いコピーはスプレッド演算子ではできないため、JSONで代用
  const req = JSON.parse(JSON.stringify(appResp));
  req.app = kintone.app.getId();

  // 作成したビューが存在するか
  const existFlg = Object.values(req.views).some(view => view.id === conf.viewId);

  if (!existFlg) {
    // すべてのビューのindexを1つずつ増やす
    Object.values(req.views).forEach(view => {
      view.index = Number(view.index) + 1;
    });

    req.views.VIEW_NAME = {
      type: 'CUSTOM',
      name: 'VIEW_NAME',
      html: '<div id="tree"></div>',
      filterCond: '',
      pager: true,
      index: 0
    };

    return kintone.api(kintone.api.url('/k/v1/preview/app/views', true), 'PUT', req)
      .then((putResp) => {
        // 作成したビューIDを保存する
        const viewId = putResp.views.VIEW_NAME.id;
        config.viewId = viewId;
        kintone.plugin.app.setConfig(config);
      });
  }
  kintone.plugin.app.setConfig(config);

});

終わりに

プラグイン開発のあるあるTipsをお送りしましたが、いかがでしたでしょうか。
おおむねどれもプラグインを作ろうと思うと通る道かと思います。

皆様のすばらしいkintoneプラグイン開発ライフの一助になれたら幸いでございます。

information

このTipsは、2025年7月版kintoneで動作を確認しています。