運営: Edamame Inc. · 東京・マニラ · Kintone運用2019年より
ジャーナル

Kintoneルックアップが遅い時 — 50,000件スケールでの高速化

2026年4月18日 · 読了時間 約8分 · Tom Arai · Edamame Inc. 代表

Kintoneアプリのレコード数が数千件を超えた頃から、ルックアップが「重い」と感じ始めます。1万件を超えると明確に遅く、5万件になるとユーザーがストレスを口にし始めます。この記事では、大規模Kintone環境でルックアップを高速に動かすための具体的な手法を、実際の検証データとともに整理します。

この記事の要点

Kintone標準のルックアップは、1万件を超えると明確に遅くなります。原因は、レコード取得API(/k/v1/records.json)のオフセット制限(10,000件)とUI側のレンダリングコスト。解決策は3つあります:絞り込みを最初に効かせる、プログレッシブローディング、専用プラグインの導入。50,000件規模で検証済みの実装例を解説します。

標準機能が遅くなる理由

Kintoneのルックアップフィールドは、参照先アプリから候補レコードを取得して、ユーザーに選ばせる仕組みです。標準機能の動作フローは:

  1. ユーザーがルックアップのアイコンをクリック
  2. Kintoneが参照先アプリのレコードをAPI経由で取得
  3. 取得したレコード一覧をモーダルで表示
  4. ユーザーがレコードを選択して、値が取り込まれる

問題は、ステップ2と3です。

API側のボトルネック:offset制限

Kintone REST APIの/k/v1/records.jsonには、offsetの上限が10,000件という制限があります。これは、レコード数が10,000を超えるアプリでは、標準APIでは後半のレコードを取得する方法が実質ない、ということです。

2万件・5万件のアプリをルックアップ先にした場合、「このレコードがあるはずなのに、検索しても出てこない」という現象が発生します。これはプラグインやUIのバグではなく、API仕様の制約です。

UI側のボトルネック:全件ロード

Kintone標準のルックアップモーダルは、候補レコードを一括でロードしようとします。レコード数が多い場合、ブラウザのレンダリングに時間がかかり、「クリックしてから表示されるまで数秒」という遅延が発生します。

実測値(一般的なPCブラウザ・社内ネットワーク):

レコード数ルックアップ表示までの時間体感
1,000件0.3秒即座
5,000件1.2秒若干待つ
10,000件3~5秒明らかに遅い
30,000件10秒~実用困難
50,000件検索不能(offset制限)標準機能では運用不可

解決策1:絞り込みを最初に効かせる

最もシンプルな対策は、ルックアップの呼び出し時に、絞り込み条件を予め適用することです。例えば「顧客マスター」アプリが50,000件あっても、多くの場合、発注伝票作成時に必要な顧客は、現在ログイン中のユーザーの担当顧客だけです。

Kintoneのルックアップ設定で「条件式」に担当営業 = LOGINUSER()を指定すると、取得対象が絞られ、速度が劇的に改善します。

ただし、この方法には限界があります:

  • 絞り込み条件がビジネスロジック的に複雑な場合(例:顧客の最終購入日から30日以内、かつ担当ランクがA・B)、条件式では表現できない
  • 動的な絞り込み(他のフィールドの値に応じて変更)は条件式では書けない
  • 組織全体で共有する「全顧客マスター」のような使い方では、絞り込みが効かない

解決策2:プログレッシブローディング(JavaScript実装)

JavaScript側で、ユーザーの検索入力に合わせてレコードを段階的に取得する方法です。初期状態では0件、ユーザーが2文字以上入力したら検索API呼び出し、結果を100件ずつ返す、という仕組みです。

// 概念コード(実際の実装はもっと複雑)
searchInput.addEventListener('input', debounce(async (e) => {
  const query = e.target.value;
  if (query.length < 2) return;

  const records = await kintone.api('/k/v1/records', 'GET', {
    app: LOOKUP_APP_ID,
    query: `顧客名 like "${query}" limit 100`
  });

  renderResults(records);
}, 300));

この実装のポイント:

  • debounce処理:ユーザーの入力中に毎回APIを叩かない。入力停止後300ms待ってから検索実行。
  • limit指定:1回の取得は100件に制限。それ以上は「もっと表示」ボタンで追加取得。
  • query絞り込み:検索クエリを直接queryパラメータに含めることで、サーバー側で絞り込む。

ただし、この方法もoffset制限の影響を受けます。クエリに一致するレコードが10,000件を超える場合、やはり10,001件目以降は取得できません。

解決策3:cursor API を使った大規模検索

Kintoneの/k/v1/records/cursor.jsonエンドポイントは、offset制限を回避して大量レコードを取得する方法です。

// 1. カーソル作成
const cursor = await kintone.api('/k/v1/records/cursor', 'POST', {
  app: LOOKUP_APP_ID,
  query: `顧客名 like "${query}"`,
  size: 500  // 1回の取得件数
});

// 2. カーソルを使って繰り返し取得
let allRecords = [];
let next = true;
while (next) {
  const result = await kintone.api('/k/v1/records/cursor', 'GET', {
    id: cursor.id
  });
  allRecords = allRecords.concat(result.records);
  next = result.next;
}

カーソルAPIは、offset制限を超えた大規模検索が可能です。ただし、カーソルの有効期限(10分)、同時オープン可能なカーソル数(1サブドメインあたり10個)、などの制約があります。

解決策4:専用プラグインの導入

上記3つの手法を自前で実装するのは、開発工数が大きく、保守も継続的に必要です。特に、全フィールド横断の検索、サブテーブル対応、モバイル対応、検索結果のプレビュー表示、などの要件が加わると、実装は簡単ではありません。

Smart Lookup等の専用プラグインは、これらを実装済みで、設定だけで利用できます。代表的な機能:

  • 全フィールド横断の全文検索(標準の「ルックアップ取得フィールド」だけでなく、指定した全フィールドから検索)
  • プログレッシブローディング(検索結果を段階的に表示、初回レンダリング100ms以内)
  • サブテーブル内のルックアップにも対応
  • モバイル(/k/m/)でデスクトップと同等のUX
  • カーソルAPI使用で、レコード数の制限が実質なし

50,000件での実測検証

kinplugのSmart Lookupプラグインについて、50,000件のテストアプリで実際に検証したデータ:

操作所要時間
ルックアップモーダル初期表示80~120ms
検索クエリ入力→結果表示250~400ms
100件追加取得(スクロール時)150~250ms
サブテーブル10行のルックアップ100~150ms(各)
モバイル環境でも同等パフォーマンス概ね同等(ネットワーク依存)

5万件規模では、標準機能は実用困難な反面、プラグイン側の実装次第では体感的な遅延なしに運用できます。

運用時の注意点

ルックアップ先アプリのレコード増加を想定する

導入時は1万件でも、数年運用すると5万件を超えるケースが多くあります。「今は遅くないから大丈夫」ではなく、将来の成長を想定したアーキテクチャを選ぶことが重要です。

インデックス設計は難しい

Kintoneは内部的にインデックスを持っていますが、カスタマイズは不可能です。クエリが遅い場合、「このフィールドにインデックスを張る」ことはできません。代わりに、アプリの分割やルックアップ先の見直しを検討します。

サブテーブルのルックアップは特に重い

サブテーブルの各行にルックアップフィールドがある場合、行数 × 候補レコード数のレンダリングコストが発生します。10行のサブテーブルで、それぞれ10,000件のルックアップ先を参照している場合、標準機能では実質運用困難です。専用プラグインでの解決がほぼ必須です。

まとめ

Kintoneのルックアップが遅い原因は、API側のoffset制限とUI側のレンダリングコストです。小規模データでは標準機能で十分ですが、10,000件を超えた時点で対策が必要になります。絞り込み・プログレッシブローディング・カーソルAPI・専用プラグインの、いずれか1つ以上を採用することで、50,000件規模でも快適に運用できます。

関連記事・製品

次のステップ

kinplug を14日間無料で試す

クレジットカード不要。GoogleかMicrosoftでサインインして、Kintoneサブドメインを入力。90秒で稼働開始します。

無料で始める プラグインを見る
はじめる

14日間、全機能、
クレジットカード不要。

GoogleかMicrosoftでサインイン、Kintoneサブドメインを入力、プラグインをインストール。90秒で稼働開始。