この記事のモジュール: Integration Flow Helper
SAP CPI の OData レシーバー:$select、$filter、$expand、$orderby をミスなく書く
SAP CPI の OData レシーバーのクエリオプションを書く:$select、$filter、$expand、$orderby、$top の例、V2 と V4 の違い、HTTP 400 の原因になるミスを解説します。

SAP CPI の OData レシーバーアダプターは、Resource Path と 1 行のクエリオプションを、SAP S/4HANA の API などの OData サービスへの呼び出しに変換します。クエリオプションはどの項目、どの行、どの関連エンティティが返されるかを決めますが、プロパティ名を 1 つ間違えるだけでサービスは呼び出しを拒否します。
この記事では、$select、$filter、$expand、$orderby を例を使って順に説明し、つまずきやすい OData V2 と V4 の違い、そして名前を正しく保つ方法を紹介します。
OData レシーバーでクエリオプションを書く場所
アダプターの Processing タブで操作を選び、Resource Path(呼び出すエンティティセットまたはエンティティ)と Query Options(URL の ? より後ろのすべて)を設定します。アダプターのクエリウィザードはサービスのメタデータからこの両方を作成でき、そのメタデータである EDMX ファイルを iFlow のリソースに保存します。
クエリオプションには Simple 式を含められるので、値をメッセージから取ることができます。例:$filter=SoldToParty eq '${property.customerId}'。次の例は、OData V2 サービスである API_SALES_ORDER_SRV から受注とその明細を読み取ります。
Resource Path: A_SalesOrder
Query Options: $select=SalesOrder,SoldToParty,CreationDate,to_Item/SalesOrderItem,to_Item/Material
&$expand=to_Item
&$filter=SoldToParty eq '${property.customerId}' and CreationDate ge datetime'2026-01-01T00:00:00'
&$orderby=CreationDate desc
&$top=50アダプターではクエリオプションは 1 行で書きます。ここでは読みやすさのためだけに分けています。
4 つのオプションを 1 つずつ
| オプション | 働き | 例 |
|---|---|---|
$select | 指定したプロパティだけを返し、レスポンスを小さく保つ | $select=SalesOrder,SoldToParty |
$filter | 条件に合う行だけを返す | $filter=SalesOrderType eq 'OR' |
$expand | ナビゲーションプロパティを通じて関連エンティティを含める | $expand=to_Item |
$orderby | 行を並べ替える(デフォルトは昇順) | $orderby=CreationDate desc |
$top と $skip は結果の件数を制限し、ページングします。OData V2 では、展開したエンティティのプロパティを to_Item/Material のようなパスで選択し、そのナビゲーションプロパティも $expand に含める必要があります。
$filter には独自の演算子があります。eq、ne、gt、ge、lt、le で、and、or、not で組み合わせます。テキストの値はシングルクォートで囲み、日付にはサービスのバージョンが求めるリテラル形式が必要です。
OData V2 と V4 は書き方が違う
OData アダプターは両方のバージョンに対応しており、多くの SAP API も両方のバージョンで提供されています。あるバージョンのクエリを別のバージョンにコピーするのは、よくあるミスの原因です。
OData V2: $inlinecount=allpages
$filter=substringof('Smith',CustomerName)
$filter=CreationDate ge datetime'2026-01-01T00:00:00'
OData V4: $count=true
$filter=contains(CustomerName,'Smith')
$filter=CreatedAt ge 2026-01-01T00:00:00Z
$expand=_Item($select=Product,Quantity)- 行数のカウント:V2 は
$inlinecount=allpages、V4 は$count=true。 - テキスト内の検索:V2 は
substringof('Smith',CustomerName)、V4 はcontains(CustomerName,'Smith')。引数の順序が逆なので注意してください。 - 日付:V2 は
datetime'2026-01-01T00:00:00'と書き、V4 は接頭辞なしで値を書きます。 - 展開したプロパティ:V2 はパスで選択し、V4 は
$expand=_Item($select=Product,Quantity)のように expand の中にオプションを入れ子にします。
HTTP 400 の原因になるタイプミス
クエリオプションが間違っていると、サービスはたいてい HTTP 400 を返し、読み取れなかった部分を示します。その原因となるミスは、ほとんどいつも同じです。
- 大文字と小文字の誤り:OData の名前は大文字と小文字を区別するため、
soldToPartyはSoldToPartyではありません。 - ナビゲーションプロパティを書くべき場所にエンティティセットを書いている:
$expand=to_Itemではなく$expand=A_SalesOrderItemと書いている。 - 別のエンティティ、またはサービスの別バージョンにしか存在しないプロパティ。
- テキストの値を囲むクォートがない、または V2 の日付リテラルを V4 のサービスに送っている。
- 区切り文字の問題:オプションは
&でつなぎ、各オプション名は$で始まります。
式にも固有のリスクがあります。${property.customerId} が空だと、フィルターは SoldToParty eq '' になり、エラーではなく 0 行を黙って返します。こうした値の読み取り方は Simple 式の記事で説明しています。
クエリとサービスを同期させる
- 名前の拠り所は iFlow のリソースにある EDMX とし、サービスが変わったら更新します。
- マッピングする項目だけを選択します。レスポンスが小さいほど速く、Trace でも読みやすくなります。
- 大量の読み取りでは、巨大なレスポンスを 1 回で受け取るのではなく、アダプターのページ単位処理のオプションを使います。
- 実際のメッセージが入れるのとまったく同じ値で、クエリを一度テストします。
OData サービスではなく REST API を呼び出す場合は、Postman と OpenAPI の記事で HTTP レシーバーを説明しています。
Kitegra でできること
ブラウザー拡張機能 Kitegra は、OData レシーバーチャネル用に iFlow がすでに持っている EDMX を読み取ります。デザイナーでは、その EDMX から Resource Path と、$select、$filter、$expand、$orderby 用のプロパティ名とナビゲーション名を候補表示するので、名前を入力するのではなく選ぶだけで済みます。
Lint パネルは、EDMX にない OData の名前に加え、閉じていない ${ や、どこでも設定されていない header やプロパティを指摘します。あるチャネルで候補が出ない場合は、その EDMX が iFlow のリソースにあるか確認してください。拡張機能が iFlow の内容を保存、デプロイ、編集することはありません。tenant が変更されるのは、名前の付いた 4 つの操作のいずれかをクリックしたときだけで、これらの操作はオフにすることもできます。
OData サービスが実際に何を返したのかを確かめるには、メッセージをステップごとにトレースし、呼び出し後のボディを確認してください。
Kitegra アカウントがなくても、モジュールごとに 5 つの iFlow で使えます。Free プランは 50、Starter は 100、Pro は 300 まで対応し、Business は上限なしです。プランを比較する。
次の iFlow で試してみましょう
Kitegra が SAP Integration Suite のデザイナーで何をするのかを読むか、Kitegra のほかの Chrome 拡張機能と並べて確認できます。
よくある質問
SAP CPI の OData アダプターでは $filter をどこに書きますか?
レシーバーチャネルの Processing タブにある Query Options 欄に、ほかのオプションと一緒に書きます。例:$select=SalesOrder&$filter=SalesOrderType eq 'OR'。
OData のフィルターの中で header やプロパティを使えますか?
使えます。クエリオプションは Simple 式を受け付けます。例:$filter=SoldToParty eq '${property.customerId}'。値が空だとフィルターは 1 行も返さないので、事前にチェックしてください。
$inlinecount と $count の違いは何ですか?
$inlinecount=allpages は OData V2 のもので、$count=true は OData V4 での書き方です。どちらも結果と一緒に、条件に合う行の総数を返します。
substringof が自分のサービスで失敗するのはなぜですか?
substringof は OData V2 にしかありません。OData V4 のサービスでは contains(Property,'text') を使い、引数の順序は逆になります。
サービスが HTTP 400 を返すのはなぜですか?
たいていは、クエリ内の名前がそのエンティティに存在しないためです。原因は大文字と小文字の誤り、ナビゲーションプロパティとエンティティセットの取り違え、もう一方の OData バージョンの構文の使用であることが多いです。
SAP CPI は OData のメタデータをどこに保存しますか?
クエリウィザードがサービスの EDMX ファイルを iFlow のリソースに保存します。名前が正しいままになるよう、サービスが変わったら更新してください。