Excel JavaScript APIの中核概念Excel JavaScript API core concepts

この記事では、 Excel JavaScript API を使用して Excel 2016 のアドインを構築する方法について説明します。This article describes how to use the Excel JavaScript API to build add-ins for Excel 2016. ここでは API の使用の基本となる中心概念について説明し、広い範囲に対する読み取り、書き込み、一定範囲内すべてのセルの更新など、特定のタスクを実行するためのガイダンスを提供します。It introduces core concepts that are fundamental to using the API and provides guidance for performing specific tasks such as reading or writing to a large range, updating all cells in range, and more.

Excel API の非同期性Asynchronous nature of Excel APIs

Web ベースの Excel アドインは、Office for Windows などのデスクトップ ベースのプラットフォーム上にある Office アプリケーションに組み込まれ、Office Online の HTML iFrame 内で実行されるブラウザー コンテナー内で実行されます。The web-based Excel add-ins run inside a browser container that is embedded within the Office application on desktop-based platforms such as Office for Windows and runs inside an HTML iFrame in Office Online. サポートされているすべてのプラットフォームで Office.js API が Excel ホストと同期的に対話することは、パフォーマンスの観点からうまくいきません。Enabling the Office.js API to interact synchronously with the Excel host across all supported platforms is not feasible due to performance considerations. このため、Office.js 内の sync() API の呼び出しにより promise が返され、それは Excel アプリケーションが要求された読み取りまたは書き込み操作を完了したときに解決されます。Therefore, the sync() API call in Office.js returns a promise that is resolved when the Excel application completes the requested read or write actions. また、操作ごとに別個の要求として送信する代わりに、プロパティの設定やメソッドの起動など、複数の操作をキューに登録し、sync() の 1 回の呼び出しでコマンドのバッチとしてそれらを実行することもできます。Also, you can queue up multiple actions, such as setting properties or invoking methods, and run them as a batch of commands with a single call to sync(), rather than sending a separate request for each action. 次のセクションでは、Excel.run()sync() API を使用してこれを実行する方法について説明します。The following sections describe how to accomplish this using the Excel.run() and sync() APIs.

Excel.runExcel.run

Excel.run は Excel オブジェクト モデルに対して実行する操作を指定した関数を実行します。Excel.run executes a function where you specify the actions to perform against the Excel object model. Excel.run は Excel オブジェクトと対話するために使用できる要求コンテキストを自動的に作成します。Excel.run automatically creates a request context that you can use to interact with Excel objects. Excel.runが完了すると、Promose が解決され、実行時に割り当てられたすべてのオブジェクトが自動的に解放されます。When Excel.run completes, a promise is resolved, and any objects that were allocated at runtime are automatically released.

次の例は、Excel.run の使用方法を示しています。The following example shows how to use Excel.run. Catch ステートメントは Excel.run 内で発生するエラーをキャッチし、ログに記録します。The catch statement catches and logs errors that occur within the Excel.run.

Excel.run(function (context) {
  // You can use the Excel JavaScript API here in the batch function
  // to execute actions on the Excel object model.
  console.log('Your code goes here.');
}).catch(function (error) {
  console.log('error: ' + error);
  if (error instanceof OfficeExtension.Error) {
    console.log('Debug info: ' + JSON.stringify(error.debugInfo));
  }
});

要求コンテキストRequest context

Excel とユーザーのアドインは、2 つの異なるプロセスで実行されます。それらは異なるランタイム環境を使用するため、Excel アドインでは、ワークシート、範囲、グラフ、表など、Excel のオブジェクトにユーザーのアドインを接続するために RequestContext オブジェクトが必要です。Excel and your add-in run in two different processes. Since they use different runtime environments, Excel add-ins require a RequestContext object in order to connect your add-in to objects in Excel such as worksheets, ranges, charts, and tables.

プロキシ オブジェクトProxy objects

アドインで宣言し、使用する Excel JavaScript オブジェクトはプロキシ オブジェクトです。The Excel JavaScript objects that you declare and use in an add-in are proxy objects. 起動するメソッドや、プロキシ オブジェクトに設定または読み込まれるプロパティは、保留中のコマンドのキューに単純に追加されます。Any methods that you invoke or properties that you set or load on proxy objects are simply added to a queue of pending commands. など、要求コンテキスト上で sync() メソッドを呼び出すと、キューに入れられたコマンドは Excel にディスパッチされて実行されます。context.sync()When you call the sync() method on the request context (for example, context.sync()), the queued commands are dispatched to Excel and run. Excel の JavaScript API では、基本的にバッチを中心としています。The Excel JavaScript API is fundamentally batch-centric. 要求コンテキストに必要なだけ変更内容をキューに登録し、sync() メソッドを呼び出して、キューに入れられたコマンドをバッチで実行することができます。You can queue up as many changes as you wish on the request context, and then call the sync() method to run the batch of queued commands.

たとえば、次のコード スニペットでは、ローカル JavaScript オブジェクト selectedRange が Excel ドキュメント内の選択範囲を参照することを宣言し、そのオブジェクトでいくつかのプロパティを設定します。For example, the following code snippet declares the local JavaScript object selectedRange to reference a selected range in the Excel document, and then sets some properties on that object. selectedRange オブジェクトはプロキシ オブジェクトであるため、設定されたプロパティと、そのオブジェクトに対して呼び出されたメソッドは、ユーザーのアドインが context.sync() を呼び出すまで Excel ドキュメントには反映されません。The selectedRange object is a proxy object, so the properties that are set and method that is invoked on that object will not be reflected in the Excel document until your add-in calls context.sync().

const selectedRange = context.workbook.getSelectedRange();
selectedRange.format.fill.color = "#4472C4";
selectedRange.format.font.color = "white";
selectedRange.format.autofitColumns();

sync()sync()

要求コンテキストで sync() メソッドを呼び出すと、プロキシ オブジェクトと Excel ドキュメント内のオブジェクトの状態が同期されます。Calling the sync() method on the request context synchronizes the state between proxy objects and objects in the Excel document. sync() メソッドは、要求コンテキストのキューに登録されたすべてのコマンドを実行し、プロキシ オブジェクトに読み込まれるプロパティの値を取得します。The sync() method runs any commands that are queued on the request context and retrieves values for any properties that should be loaded on the proxy objects. sync() メソッドは非同期で実行されて promise を返します。これは、sync() メソッドが完了すると解決されます。The sync() method executes asynchronously and returns a promise, which is resolved when the sync() method completes.

次の例は、ローカル JavaScript proxy オブジェクト (selectedRange) を定義し、そのオブジェクトのプロパティを読み込み、JavaScript の Promises パターンを使用して context.sync() を呼び出し、プロキシ オブジェクトと Excel ドキュメント内のオブジェクトの状態を同期するバッチ関数を示しています。The following example shows a batch function that defines a local JavaScript proxy object (selectedRange), loads a property of that object, and then uses the JavaScript Promises pattern to call context.sync() to synchronize the state between proxy objects and objects in the Excel document.

Excel.run(function (context) {
  const selectedRange = context.workbook.getSelectedRange();
  selectedRange.load('address');
  return context.sync()
    .then(function () {
      console.log('The selected range is: ' + selectedRange.address);
  });
}).catch(function (error) {
  console.log('error: ' + error);
  if (error instanceof OfficeExtension.Error) {
    console.log('Debug info: ' + JSON.stringify(error.debugInfo));
  }
});

前の例では、selectedRange が設定され、context.sync() が呼び出されるとその address プロパティが読み込まれます。In the previous example, selectedRange is set and its address property is loaded when context.sync() is called.

sync() は Promise を返す非同期の操作であるため、常に Promise を (JavaScript で) 返す必要があります。Because sync() is an asynchronous operation that returns a promise, you should always return the promise (in JavaScript). このようにして、スクリプトの実行を継続する前に、sync() 操作を完了します。Doing so ensures that the sync() operation completes before the script continues to run. sync() を用いたパフォーマンスの最適化の詳細については、「 Excel JavaScript API のパフォーマンス最適化」を参照してください。For more information about optimizing performance with sync(), see Excel JavaScript API performance optimization.

load()load()

プロキシ オブジェクトのプロパティを読み取るには、まず Excel ドキュメントからプロキシ オブジェクトとデータを入力するプロパティを明示的に読み込み、それから context.sync() を呼び出す必要があります。Before you can read the properties of a proxy object, you must explicitly load the properties to populate the proxy object with data from the Excel document, and then call context.sync(). たとえば、選択範囲を参照するプロキシ オブジェクトを作成した後、選択範囲の address プロパティを読み取る必要がある場合、読み取る前に address プロパティを読み込む必要があります。For example, if you create a proxy object to reference a selected range, and then want to read the selected range's address property, you need to load the address property before you can read it. プロキシ オブジェクトのプロパティを読み込むよう要求するには、オブジェクトに対して load() メソッドを呼び出し、読み込むプロパティを指定します。To request properties of a proxy object be loaded, call the load() method on the object and specify the properties to load.

注意

プロキシ オブジェクト上でメソッドを呼び出す、またはプロパティを設定するだけの場合は、load() メソッドを呼び出す必要はありません。If you are only calling methods or setting properties on a proxy object, you do not need to call the load() method. load() メソッドは、プロキシ オブジェクト上でプロパティを読み取る場合のみ必要です。The load() method is only required when you want to read properties on a proxy object.

プロキシ オブジェクトに対してプロパティを設定、またはメソッドを呼び出す要求と同じように、プロキシ オブジェクトに対してプロパティを読み込む要求も、要求コンテキストで保留中のコマンドのキューに追加され、次回 sync() メソッドを呼び出すときに実行されます。load() の呼び出しは、必要なだけ要求コンテキストのキューに入れることができます。Just like requests to set properties or invoke methods on proxy objects, requests to load properties on proxy objects get added to the queue of pending commands on the request context, which will run the next time you call the sync() method. You can queue up as many load() calls on the request context as necessary.

次の例では、範囲の特定のプロパティのみが読み込まれます。In the following example, only specific properties of the range are loaded.

Excel.run(function (context) {
  const sheetName = 'Sheet1';
  const rangeAddress = 'A1:B2';
  const myRange = context.workbook.worksheets.getItem(sheetName).getRange(rangeAddress);

  myRange.load(['address', 'format/*', 'format/fill', 'entireRow' ]);

  return context.sync()
    .then(function () {
      console.log (myRange.address);              // ok
      console.log (myRange.format.wrapText);      // ok
      console.log (myRange.format.fill.color);    // ok
      //console.log (myRange.format.font.color);  // not ok as it was not loaded
  });
}).then(function () {
  console.log('done');
}).catch(function (error) {
  console.log('Error: ' + error);
  if (error instanceof OfficeExtension.Error) {
    console.log('Debug info: ' + JSON.stringify(error.debugInfo));
  }
});

前の例では、format/fontmyRange.load() の呼び出しで指定されていないため、format.font.color プロパティは読み取れませんでした。In the previous example, because format/font is not specified in the call to myRange.load(), the format.font.color property cannot be read.

パフォーマンスを最適化するには、「 Excel JavaScript API のパフォーマンス最適化」にあるように、load() メソッドをオブジェクトに使用する際、プロパティとリレーションシップを明示的に指定する必要があります。To optimize performance, you should explicitly specify the properties and relationships to load when using the load() method on an object. load() メソッドの詳細は、「Excel JavaScript API の高度な概念」を参照してください。For more information about the load() method, see Excel JavaScript API advanced concepts.

null または空白のプロパティ値null or blank property values

2 次元配列での null の入力null input in 2-D Array

Excel では、範囲は 2 次元配列で表され、最初のディメンションは行、2 番目のディメンションは列を示します。In Excel, a range is represented by a 2-D array, where the first dimension is rows and the second dimension is columns. 範囲内の特定のセルだけに値、数値書式、または数式を設定するには、2 次元配列内のそのセルに値、数値書式、または数式を指定し、2 次元配列内のその他のすべてのセルに null を指定します。To set values, number format, or formula for only specific cells within a range, specify the values, number format, or formula for those cells in the 2-D array, and specify null for all other cells in the 2-D array.

たとえば、範囲内の 1 つのセルの数値書式を更新し、範囲内の他のセルすべての既存の数値書式を保持する場合、更新するセルに新しい数値書式を指定し、他のセルすべてに null を指定します。For example, to update the number format for only one cell within a range, and retain the existing number format for all other cells in the range, specify the new number format for the cell to update, and specify null for all other cells. 次のコード スニペットでは、範囲内の 4 番目のセルに新しい数値書式を設定し、その前の 3 つのセルについては数値書式を変更せずに保持します。The following code snippet sets a new number format for the fourth cell in the range, and leaves the number format unchanged for the first three cells in the range.

range.values = [['Eurasia', '29.96', '0.25', '15-Feb' ]];
range.numberFormat = [[null, null, null, 'm/d/yyyy;@']];

プロパティに対する null の入力null input for a property

null は単一プロパティに有効な入力ではありません。たとえば、次のコード スニペットは、範囲の values プロパティを null に設定できないため無効です。null is not a valid input for single property. For example, the following code snippet is not valid, as the values property of the range cannot be set to null.

range.values = null;

同様に、次のコード スニペットは、nullcolor プロパティで有効ではないため無効です。Likewise, the following code snippet is not valid, as null is not a valid value for the color property.

range.format.fill.color =  null;

応答内の null プロパティ値null property values in the response

指定の範囲に複数の値がある場合、size および color などの書式設定プロパティでは、応答に null 値が含まれます。Formatting properties such as size and color will contain null values in the response when different values exist in the specified range. たとえば、範囲を取得してその format.font.color プロパティを読み込む場合:For example, if you retrieve a range and load its format.font.color property:

  • 範囲内のすべてのセルのフォントの色が同じ場合、range.format.font.color がその色を指定します。If all cells in the range have the same font color, range.format.font.color specifies that color.
  • 範囲内に複数のフォントの色がある場合、range.format.font.colornull です。If multiple font colors are present within the range, range.format.font.color is null.

プロパティに対する空白の入力Blank input for a property

プロパティに空白の値 ('' の間にスペースのない 2 つの引用符) を指定すると、プロパティをクリアまたはリセットする指示として解釈されます。例:When you specify a blank value for a property (i.e., two quotation marks with no space in-between ''), it will be interpreted as an instruction to clear or reset the property. For example:

  • 範囲の values プロパティに空白の値を指定すると、範囲のコンテンツはクリアされます。If you specify a blank value for the values property of a range, the content of the range is cleared.

  • プロパティに空白の値を指定すると、数値書式は General にリセットされます。numberFormatIf you specify a blank value for the numberFormat property, the number format is reset to General.

  • プロパティと formulaLocale プロパティに空白の値を指定すると、数式の値はクリアされます。formulaIf you specify a blank value for the formula property and formulaLocale property, the formula values are cleared.

応答内の空白のプロパティ値Blank property values in the response

読み取り操作では、応答内の空白のプロパティ値 ('' の間にスペースのない、2 つの引用符) は、セルにデータまたは値がないことを示します。For read operations, a blank property value in the response (i.e., two quotation marks with no space in-between '') indicates that cell contains no data or value. 次の 1 番目の例では、範囲内の最初と最後のセルにデータがありません。In the first example below, the first and last cell in the range contain no data. 2 番目の例では、範囲内の最初の 2 つのセルに数式がありません。In the second example, the first two cells in the range do not contain a formula.

range.values = [['', 'some', 'data', 'in', 'other', 'cells', '']];
range.formula = [['', '', '=Rand()']];

無制限の範囲への読み取りまたは書き込みRead or write to an unbounded range

無制限の範囲の読み取りRead an unbounded range

無制限の範囲のアドレスとは、列全体または行全体を指定する範囲のアドレスです。例:An unbounded range address is a range address that specifies either entire column(s) or entire row(s). For example:

  • 範囲のアドレスは、列全体で構成されます。Range addresses comprised of entire column(s):
    • C:C
    • A:F
  • 範囲のアドレスは、行全体で構成されます。Range addresses comprised of entire row(s):
    • 2:2
    • 1:4

API が無制限の範囲を取得する要求を行う場合 (getRange('C:C') など)、返される応答では、valuestextnumberFormat、または formula などのセル レベルのプロパティに null 値が含まれます。When the API makes a request to retrieve an unbounded range (for example, getRange('C:C')), the response will contain null values for cell-level properties such as values, text, numberFormat, and formula. または cellCount など、範囲のその他のプロパティには、無制限の範囲に有効な値が含まれます。addressOther properties of the range, such as address and cellCount, will contain valid values for the unbounded range.

無制限の範囲への書き込みWrite to an unbounded range

無制限の範囲では、入力要求が大きすぎるため、valuesnumberFormatformula などのセル レベルのプロパティは設定できません。You cannot set cell-level properties such as values, numberFormat, and formula on unbounded range because the input request is too large. たとえば、次のコード スニペットは、無制限の範囲に対して values を指定しようとしているため無効です。For example, the following code snippet is not valid because it attempts to specify values for an unbounded range. 無制限の範囲にセル レベルのプロパティを設定しようとすると、API からエラーが返されます。The API will return an error if you attempt to set cell-level properties for an unbounded range.

const range = context.workbook.worksheets.getActiveWorksheet().getRange('A:B');
range.values = 'Due Date';

広い範囲に対する読み取りまたは書き込みRead or write to a large range

範囲に多数のセル、値、数値書式、数式などが含まれる場合、その範囲では API 操作を実行できない場合があります。If a range contains a large number of cells, values, number formats, and/or formulas, it may not be possible to run API operations on that range. API は常に範囲に要求された操作 (特定のデータを取得または書き込む) を実行しようとしますが、広い範囲に対する読み取りや書き込みの操作は、過剰なリソース使用によるエラーになる場合があります。The API will always make a best attempt to run the requested operation on a range (i.e., to retrieve or write the specified data), but attempting to perform read or write operations for a large range may result in an API error due to excessive resource utilization. このようなエラーを避けるため、広い範囲に対して読み取りや書き取り操作を 1 回で実行するのではなく、その範囲の小さいサブセットに対して個別に読み取りまたは書き込み操作を実行することをお勧めします。To avoid such errors, we recommend that you run separate read or write operations for smaller subsets of a large range, instead of attempting to run a single read or write operation on a large range.

範囲内のすべてのセルの更新Update all cells in a range

範囲内のすべてのセルに同じ更新 (すべてのセルに同じ値を入力する、同じ数値書式を設定する、同じ数式ですべてのセルにデータを入力するなど) を適用するには、range オブジェクトの該当するプロパティを必要な 1 つの値に設定します。To apply the same update to all cells in a range, (for example, to populate all cells with the same value, set the same number format, or populate all cells with the same formula), set the corresponding property on the range object to the desired (single) value.

次の例では、20 個のセルを含む範囲を取得し、数値書式を設定してその範囲のすべてのセルに 3/11/2015 という値を設定します。The following example gets a range that contains 20 cells, and then sets the number format and populates all cells in the range with the value 3/11/2015.

Excel.run(function (context) {
  const sheetName = 'Sheet1';
  const rangeAddress = 'A1:A20';
  const worksheet = context.workbook.worksheets.getItem(sheetName);

  const range = worksheet.getRange(rangeAddress);
  range.numberFormat = 'm/d/yyyy';
  range.values = '3/11/2015';
  range.load('text');

  return context.sync()
    .then(function () {
      console.log(range.text);
  });
}).catch(function (error) {
  console.log('Error: ' + error);
  if (error instanceof OfficeExtension.Error) {
    console.log('Debug info: ' + JSON.stringify(error.debugInfo));
  }
});

エラー メッセージError messages

API エラーが発生すると、API ではコードとメッセージを含む error オブジェクトが返されます。When an API error occurs, the API will return an error object that contains a code and a message. 次の表は、API から返されるエラー一覧の定義を示します。The following table defines a list of errors that the API may return.

error.codeerror.code error.messageerror.message
InvalidArgumentInvalidArgument 引数が無効であるか、存在しません。または形式が正しくありません。The argument is invalid or missing or has an incorrect format.
InvalidRequestInvalidRequest 要求を処理できません。Cannot process the request.
InvalidReferenceInvalidReference この参照は、現在の操作に対して無効です。This reference is not valid for the current operation.
InvalidBindingInvalidBinding このオブジェクトのバインドは、以前の更新プログラムが原因で無効になっています。This object binding is no longer valid due to previous updates.
InvalidSelectionInvalidSelection 現在の選択内容は、この操作では無効です。The current selection is invalid for this operation.
認証されていませんUnauthenticated 必要な認証情報が見つからないか、無効です。Required authentication information is either missing or invalid.
AccessDeniedAccessDenied 要求された操作を実行できません。You cannot perform the requested operation.
ItemNotFoundItemNotFound 要求されたリソースは存在しません。The requested resource doesn't exist.
ActivityLimitReachedActivityLimitReached アクティビティの制限に達しました。Activity limit has been reached.
GeneralExceptionGeneralException 要求の処理中に内部エラーが発生しました。There was an internal error while processing the request.
NotImplementedNotImplemented 要求された機能は実装されていません。The requested feature isn't implemented.
ServiceNotAvailableServiceNotAvailable サービスを利用できません。The service is unavailable.
一致しませんConflict 競合のため、要求を処理できませんでした。Request could not be processed because of a conflict.
ItemAlreadyExistsItemAlreadyExists 作成中のリソースはすでに存在しています。The resource being created already exists.
UnsupportedOperationUnsupportedOperation 試行中の操作はサポートされていません。The operation being attempted is not supported.
RequestAbortedRequestAborted 実行時に要求が中止されました。The request was aborted during run time.
ApiNotAvailableApiNotAvailable 要求された API は使用できません。The requested API is not available.
InsertDeleteConflictInsertDeleteConflict 試行された挿入操作または削除操作で競合が発生しました。The insert or delete operation attempted resulted in a conflict.
InvalidOperationInvalidOperation 試行された操作は、このオブジェクトでは無効です。The operation attempted is invalid on the object.

関連項目See also