サービス詳細
【NADP】Fuse Onlineに見るコントラクトファーストの考え - Natic | Application Modernization Platform – 日商エレクトロニクス

【NADP】Fuse Onlineに見るコントラクトファーストの考え

はじめに

こんにちは、NADPの原木です。

昨今のシステム開発では、異なるシステムを組み合わせることで新規ビジネスを生み出すシステム間連携は欠かせません。システム間連携とは単純にシステム同士を繋ぐという話のみならず、そのシステムを裏で支えているチーム同士を繋ぐということでもあります。技術だけに留まらず開発プロセスや、コミュニケーション、マネジメントに至るまで意外と奥が深い話です。

そんなシステム間連携に伴う案件で困ることの一つが、異なるチーム同士でのデータのやり取り=API設計をどのように策定していくかというプロセスです。

この記事では、システム間連携をサポートするために開発されたツールであるFuse Onlineを通して、API設計の進め方の考えの一つであるコントラクトファーストという考え方を紹介したいと思います。

この記事では紹介しませんが、Fuse Onlineの重要な設計思想の一つに、「Enterprise Integration Patterns」(以下、略称EIP)があります。

EIPとは、Gregor Hohpe氏によりまとめられたシステム間連携に関するアーキテクチャパターンです。Fuse Online及びFuseがベースとしているCamelフレームワークはEIPの実現を手助けするために開発されました。

この記事ではEIPの詳細には踏み込みませんが、Fuse Onlineを理解するために必要な知識です。詳しく知りたい方はGregor Hohpe氏が運営されている下記のウェブサイトをご参照ください。
Enterprise Integration Patterns

モダナイゼーションの文脈でAPIの名前をよく聞く理由

一般的にモダナイゼーションなどのシステムへの投資は、

  • システムの投資によりどのようなビジネスの機会が生まれるのかアイディアを着想する
  • 着想したアイディアに基づき、経営者やアナリストが戦略を描く
  • 描かれた戦略に基づき、具体的な要件をシステムに落とし込んでいく

といったステップで行われます。

ここで重要なのが、経営戦略から降りてきた構想にシステムの具体的な実装方法やデータ形式への詳細な規定がないことです。最近はフィジビリティやPoCなどのステップにより実現可能性を検討してからこのフェーズに入るのが通常ですが、それでもこのフェーズでシステム要件を作成する際に初めて直面する課題は減りません。

その中でよく議論に上がるのがAPIの設計、つまり、システム間でどのようにデータのやり取り、あるいは呼び出し方を規定するか?という話です。

すべての機能が入ったフルパッケージのシステムを1から開発することが昨今は非常に少なくなっています。既存のレガシーな業務アプリケーションを活用しつつ、一方で最先端のSaaS(例えばSalesforce等)をうまく組み合わせることでシステム投資を抑えつつ、新たなビジネスの創作を可能にするシステム連携を前提とした開発が主流です。

その場合、システムごとに開発者が違うケースは珍しいことではありません。したがってシステム間連携を実現するにあたり、チーム同士のコミュニケーションを円滑に図るため共通認識を作ることは非常に重要な観点です。システム間連携を支えるAPI設計においても、どのように作業を進めれば良いかAPIの具体的な実装方法と共に長い間思案されてきました。

契約が先か?実装が先か?

システム間でのAPIの設計に関して、進め方は一般的に二種類あるといわれています。

  • コントラクトファースト開発(スキーマファースト開発)
  • コードファースト開発

例えば、コンソール画面からデータを取得する簡単なウェブアプリケーションを想像してみます。

契約か実装かを示した図 図1: 契約か実装か

コントラクトファースト開発では、どのようなデータを取得できるか、そしてその取得のためにどのような手順を描けばよいか、いわゆるインターフェースについて開発の最初に綿密な設計を行い(図1-1)、それに従うようにデータの入出力を行う具体的な処理を検討します(図1-2)。

コードファースト開発では、その逆です。データの処理方法について最初に実装を行い、その後インターフェースについて設計します。

両者にはそれぞれメリット・デメリットが存在し、APIで解決したい技術的・戦略的ニーズによって選択する開発手法は異なります。OpenAPIと呼ばれるRESTful APIをドキュメント化する仕様策定に携わったSwagger社により、次のように説明されています*1

デザインファースト開発(注: コントラクトファースト開発のこと)を選択したいケース
  • 開発者エクスペリエンスが重要な場合
  • ミッションクリティカルなAPIを提供する場合
  • APIの使用者と実装者の間で良好なコミュニケーションを確保する場合
コードファースト開発を選択したいケース
  • APIを開発する速度感を重視したい場合
  • チームや会社など内部で使用するAPIを開発したい場合

これから紹介するシステムインテグレーションツールであるFuse Onlineは、コントラクトファーストアプローチに従って製品が開発されています。

Fuse Onlineにみる、コントラクトファーストアプローチ

Fuse OnlineでAPIを開発する場合を例に、コントラクトファーストアプローチを体感してみます。

例えば、ERPシステムであるGranditのデータベースから得意先企業のコード情報に紐づく見積り情報の一覧を取得するAPIサービスをFuse Onlineで構築してみるケースについて順を追って確認してみましょう。

ユーザーワークフローによる全体過程の確認

図2: Fuse OnlineでAPIサービスを構築した時のユーザーワークフロー*2

Fuse Onlineでは、APIサービスの作成は大きく三つのフェーズに分けられます。

  1. Provide API definitionAPIの定義を最初に行い、API仕様書を作成します。
  2. Navigate flowsAPIのエンドポイント、つまり各URIについてそれぞれフロー=処理内容を決めます。
  3. Configure flowsフローの構成。フロー図の内容を実装します。

1. Provide API definition

それではFuse OnlineでAPI定義のやり方について詳しく見てみましょう。「新しいIntegrationの作成」、「API Provider」の選択後、API仕様書を作成するところからすべては始まります。

既にOpenAPI仕様の設定ファイル(yaml/json)があればそれをロードすることもできますが、ない場合はGUI操作により手組みでAPIを設計することが可能です。

図3: API DesignerによるAPI仕様書の作成 図3: API DesignerによるAPI仕様書の作成

図3では、API仕様書をFuse Onlineに組み込まれたAPI Designerというローコードツールで作成しています。ここで作成された内容は最終的にFuse OnlineのIntegrationに組み込まれます。

2. Navigate flows

図4: APIエンドポイントの一覧 図4: APIエンドポイントの一覧

API仕様書を作成した後に進むのが「2. Navigate flows」という工程です。こちらでは、APIのエンドポイントごとに「Create flow」ボタンを押して、flowを作成していきます。図4では /estimateitems に対してHTTP GETメソッドを投げた処理の設定を行います。

3. Configure flows

具体的なflowsの内容を決めるのが「3. Configure flows」です。APIサービスのインターフェース部分が Navigate flows の工程だとすれば、APIサービスの実装=どんな処理をするか決めるのが Configure flows になります。

図5: Configure flowsの詳細 図5: Configure flowsの詳細

図5に、 Configure flows の詳細情報を記載しました。ここで一番重要なのが「Choose a connection」という工程で、実際にAPIサービスの処理内容を決める箇所になります。

Data Mapperでは、インプットとアウトプットのパラメータに対して紐づけを行います。

図6: Data Mapper 図6: Data Mapper

図6では、Fuse Onlineがウェブリクエストを通じて受け取ったパラメータ cust_code をデータベース検索のキーである CUST_CODE に紐づける処理を行っています。

Invoke SQLでは、データベースからSQLでデータを取得する処理を行います。

図7: SQLの実行 図7: SQLの実行

図7では、得意先企業コードを検索キーとして見積りテーブルを検索するSQLを実行しています。

これら Data Mapper や Invoke SQL などを、図7のフローに組み合わせた完成図が図8-2となります。

図8-1: 最初のフロー 図8-1: 最初のフロー

図8-2: 完成したフロー 図8-2: 完成したフロー

ここで注目すべきはフローを作り始めた図7で既に「Provided API」と「Provided API Return Path」のタスクがあることです。API仕様書を最初に設計することで、フローにおけるデータの “入り口” と “出口” を先に決めることでそれに合わせてどのようにデータを加工するのかを「Choose a connection」でやっていると考えるとわかりやすいかと思います。

Data Mapper の処理が二回出てくるのは、APIが呼ばれたときに渡されたパラメータをDBの検索キーに変換する処理とDBの検索結果であるSQLリザルトをAPIのレスポンスに変換する処理があるためです。このあたりは冗長に思えるかもしれませんが、各ステップが独立することで高い柔軟性を実現するためにあえてこのような処理を入れています。

まとめ

API設計の進め方においてコントラクトファーストアプローチという考え方があることと、その思想に基づいてFuse Onlineが設計されていることを説明しました。

コントラクトファーストアプローチを採用することで、APIの利用者側と提供者側でAPI仕様に基づいたコミュニケーションが可能になり、システム結合でトラブルがちなIF仕様に関する問題は改善されるでしょう。

API仕様を基づいたコミュニケーションが互いの共通認識として一般的になると、次はAPI仕様書を定期的にメンテナンスし、それをシステムに自動的に反映させて共有する仕組みが課題になるかと存じます。

弊社ではGitHub上でOpenAPI形式のファイルを更新すると、自動的にApicurio Registryという成果物管理サービスに反映する仕組みを構築しました。こちらは次回のブログで紹介したいと思います。

本記事がご参考になれば幸いです。

参考文献

Contract-First API Design with Apicurio and Red Hat Fuse/Camel

補足

*1 Design First or Code First: What’s the Best Approach to API Development? (swagger.io)

*2 Fuse OnlineのデザインにかかわったWangさんのブログ “Red Hat Fuse Online API Driven Integration” の絵をベースに作成


記事担当者:アプリケーション企画開発部 原木
最終更新日:2021/07/07