FRUCtoSアダプタ開発ガイド
最終更新日 2022年11月30日
本ガイドの目的
本ガイドは、HL7 FHIR標準(以下、FHIR)に準拠したFRUCtoSのRESTful APIを通じて、電子カルテシステムなどのデータを読み出すことのできる「アダプタ」を開発するための手順を記載しています。
現在は、アダプタ開発の最初のステップとして、主に電子カルテシステムの患者データをFHIRのPatientリソースとして取得するまでの手順を記載しています。
本ガイドは、以下に関する基本的な知識を有するシステム開発者を対象としています。
- FHIR
- 電子カルテシステムのDBスキーマ
- Java 11
- Apache Maven
- Spring Framework(以下、Spring)
- Lombok
- Docker
- Docker Compose
アダプタ開発に必要なソフトウェア
アダプタの開発作業を行うPCに、以下のソフトウェアがインストールされている必要があります。
- IDE(統合開発環境)※Pleiades All in One(Eclipse)またはIntelliJ IDEAを推奨
- Apache Maven 3.6.3
- Lombok 1.18.16 以降
アダプタの概要
FRUCtoSは、以下の3つの層から構成されており、各層の境界インターフェイスは、Springコンポーネントとして実装されています。
- インターフェイス層 - RESTful APIの提供など
- サービス層 - データバリデーションなど
- リポジトリ層 - データ検索処理やO/Rマッピングなど
アダプタは、このリポジトリ層のSpringコンポーネントを置き換える形で動作します。
具体的には、アダプタプロジェクトをビルドして作成したjarファイルを、FRUCtoSのWebアプリケーションに組み込むことで、リポジトリ層のSpringコンポーネントを置き換えます。
FRUCtoSのインターフェイス層およびサービス層の機能については、アダプタ側で特に意識することなくそのまま利用できます。
またアダプタでは、電子カルテシステムDBの値を保持するクラスと、FHIRリソースのマッピングをサポートするための各種アノテーションや、アダプタ用のコード生成ツールなどを利用できます。
アダプタ開発資源の入手
まずはFRUCtoS 公式サイトにて、製品版FRUCtoSのご利用をお申し込みください。アダプタサンプルプロジェクトを含む製品版FRUCtoSのご利用に必要な諸手続きについて、担当者よりご案内させていただきます。
アダプタサンプルプロジェクトを含む、製品版FRUCtoSのご利用の際には ソフトウェア利用許諾契約 の締結が必要となります。
アダプタプロジェクトの作成
- ダウンロードしたアダプタサンプルプロジェクトの圧縮ファイル
repository-adapter-sample.zip
を解凍します。 - 解凍したファイル内のフォルダ(
repository-adapter-sample
)を任意の名称に変更します。
例:repository-adapter-xxx(xxxは電子カルテ製品名やベンダー名など)
プロジェクトのインポート
Pleiades All in One(Eclipse)やIntelliJ IDEAなどのIDE(統合開発環境)でLombokを利用可能な状態にした後、アダプタプロジェクトをMavenプロジェクトとしてインポートします。
インポートしたプロジェクトの動作確認
IDE上でアダプタプロジェクトのビルドが完了した後、次のユニットテストを実行して、全てのテストが成功することを確認します。
com.example.impl.ResourceRepositoryImplPatientTest
テストが失敗する場合は、プロジェクトのインポート方法やビルド設定などに誤りがないかを確認してください。
Maven設定ファイルの修正
プロジェクトフォルダ内にあるpom.xml
の、groupId
、artifactId
、name
などを修正します。
「修正前」
<groupId>com.example</groupId>
<artifactId>fructos-repository-adapter-sample</artifactId>
<version>0.0.1.${buildDate}-${revision}</version>
<name>FRUCtoS Repository Adapter Sample</name>
「修正後(例)」
<groupId>jp.co.xxx</groupId>
<artifactId>fructos-repository-adapter-xxx</artifactId>
<version>0.0.1.${buildDate}-${revision}</version>
<name>FRUCtoS Repository Adapter for XXX</name>
pom.xml
のdependencies
で定義されている依存ライブラリの他に、使用したいライブラリやフレームワークなどがある場合は、dependency
を追加します。
例えば、以下のようなライブラリなどを追加することが考えられます。
- 電子カルテシステムDB用のJDBCドライバライブラリ
- サンプルプロジェクトで使用しているMyBatis以外のORMライブラリ
「PostgreSQLのJDBCドライバを追加する例」
<dependencies>
(中略)
<!-- https://mvnrepository.com/artifact/org.postgresql/postgresql -->
<dependency>
<groupId>org.postgresql</groupId>
<artifactId>postgresql</artifactId>
<version>42.2.18</version>
</dependency>
</dependencies>
DBテーブルの値を保持するクラスの作成
電子カルテシステムDBのテーブルの値を保持するクラス(一般的にEntityやDTOと呼ばれるクラス)を作成します。
※以降はこのクラスを「DBエンティティ」と記載します。
実装例:アダプタサンプルプロジェクトのcom.example.adapter.entity.PatientEntity
DBエンティティには、DBテーブルのカラムに対応したフィールドと、各フィールドのgetterおよびsetterを作成してください。
アダプタサンプルプロジェクトでは、Lombokアノテーションを使用してgetterとsetterを作成しています。
アダプタサンプルプロジェクトのサンプルDBスキーマは、src/main/resources/mybatis_settings/schema.sql
で定義されています。
DBアクセスクラスの作成
電子カルテシステムDBへアクセスするためのクラス(一般的にDAOやRepositoryと呼ばれるクラス)を作成します。
実装例:アダプタサンプルプロジェクトのcom.example.adapter.entity.PatientEntityMapper
まずは、電子カルテシステムDBの患者情報を保持するテーブルから、主キー(患者IDなど)を指定してデータを取得するメソッドを作成することをおすすめします。
アダプタサンプルプロジェクトでは、ORM(Object Relational Mapping)ライブラリとしてMyBatisを使用していますが、その他のお好みのライブラリを使用することも可能です。
アダプタサンプルプロジェクトのMyBatis Mapperクラスを修正して使用する場合は、アダプタプロジェクトのpackage構成に合わせて、com.example.adapter.config.MyBatisConfig
の以下の行を修正してください。
@MapperScan(basePackages = { "com.example.adapter.entity" })
MyBatis MapperクラスのDB接続情報は、src/main/resources/mybatis_settings/repository_context.properties
に設定されています。
datasource.driver-class-name=org.h2.Driver
#datasource.driver-class-name=org.postgresql.Driver
datasource.url=jdbc:postgresql://localhost:5432/sample
datasource.username=sample
datasource.password=sample
コンバータクラスの作成
DBエンティティの各フィールドの値を、対応するFHIRリソースのプロパティの値に変換するためのメソッド群を定義した、コンバータクラスを作成します。
実装例:アダプタサンプルプロジェクトのcom.example.adapter.conversion.impl.CommonConverter
とcom.example.adapter.conversion.impl.PatientPropertyConverter
コンバータクラスの詳細は「コンバータクラス」を参照してください。
ResourceKey
インターフェイスの実装クラスの作成
アダプタの共通インターフェイスとして用意されている、ResourceKey
インターフェイスの実装クラスを作成します。
このクラスは、あるFHIRリソースを構成するのに必要な、電子カルテシステムDBテーブルのレコードを特定する主キーの値を保持します。
例えば、FHIRのPatientリソースを構成するのに「患者テーブル」のレコードが必要な場合は、ResourceKey
インターフェイスを実装したPatientResourceKey
クラスを作成し、フィールドに「患者テーブル」の主キー(患者IDなど)を持たせます。
実装例:アダプタサンプルプロジェクトのcom.example.adapter.conversion.impl.PatientResourceKey
ResourceResource
インターフェイスの実装クラスの作成
アダプタの共通インターフェイスとして用意されている、ResourceResource
インターフェイスの実装クラスを作成します。
このクラスは、あるFHIRリソースを構成するのに必要なResourceKey
と、ResourceKey
を使って読み出される全てのDBエンティティを保持します。
例えば、FHIRのPatientリソースを構成する場合は、ResourceResource
インターフェイスを実装したPatientResourceResource
クラスを作成し、フィールドにPatientResourceKey
とPatientEntity
を持たせます。
実装例:アダプタサンプルプロジェクトのcom.example.adapter.impl.PatientResourceResource
DBエンティティのフィールドには、getterおよびsetterを作成してください。
アダプタサンプルプロジェクトでは、Lombokアノテーションを使用してgetterとsetterを作成しています。
マッピングアノテーションの付与
作成したDBエンティティとResourceResource
インターフェイスの実装クラスに、アダプタ用のマッピングアノテーション付与します。
実装例:アダプタサンプルプロジェクトのcom.example.adapter.entity.PatientEntity
とcom.example.adapter.impl.PatientResourceResource
マッピングアノテーションの詳細は「マッピングアノテーション」を参照してください。
MapperGeneratorの実行
アダプタ用のコード生成ツールである「MapperGenerator」を実行して、マッピングアノテーションを付与したクラスを元に、リソースマッピングクラスを生成します。
生成例:アダプタサンプルプロジェクトのcom.example.adapter.gen.PatientResourceResourceMapper
生成されたリソースマッピングクラスには、ResourceResource
インターフェイスの実装クラスが保持するDBエンティティを、FHIRのリソースクラスにマッピングするためのメソッド(map
)が作成されます。
このマッピングメソッドの実行時に、DBエンティティのマッピングアノテーションで指定した、コンバータクラスの変換メソッドが適用されます。
MapperGeneratorの実行方法は「MapperGenerator」を参照してください。
Searcher
インターフェイスの実装クラスの作成
アダプタの共通インターフェイスとして用意されている、Searcher
インターフェイスの実装クラスを作成します。
Searcher
インターフェイスには、検索(絞り込み)のためのfilter
メソッド群と、検索結果を確定するgetResult
メソッドが定義されています。
初めから全てのfilter
メソッド群を実装するのではなく、順次実装していくことをおすすめします。
Searcher
インターフェイスの実装クラスには、Springの@Component
アノテーションを付与してください。
実装例:アダプタサンプルプロジェクトのcom.example.adapter.impl.AbstractSearcherImpl
とcom.example.adapter.impl.PatientSearcherImpl
SearcherFactory
インターフェイスの実装クラスの作成
アダプタの共通インターフェイスとして用意されている、SearcherFactory
インターフェイスの実装クラスを作成します。
SearcherFactory
インターフェイスには、検索範囲の異なるSearcher
を生成するためのcreate
メソッド群が定義されています。
Searcher
のインスタンスは、SpringのObjectFactory
を利用して生成してください。
※Searcher
はシングルトンではなく状態を持ったコンポーネントになるため、create
メソッドが呼び出されるたびにインスタンスを生成する必要があります。
初めから全てのcreate
メソッド群を実装するのではなく、順次実装していくことをおすすめします。
SearcherFactory
インターフェイスの実装クラスには、Springの@Component
アノテーションを付与してください。
実装例:アダプタサンプルプロジェクトのcom.example.adapter.impl.SearcherFactoryImpl
ResourceKeyResolver
インターフェイスの実装クラスの作成
アダプタの共通インターフェイスとして用意されている、ResourceKeyResolver
インターフェイスの実装クラスを作成します。
ResourceKeyResolver
インターフェイスには、ResourceKey
を元にFHIRリソースを取得するためのメソッド群が定義されています。
ResourceKeyResolver
インターフェイスの実装クラス内で、DBアクセスクラスとリソースマッピングクラスを使用することを想定しています。
初めから全てのメソッドを実装するのではなく、順次実装していくことをおすすめします。
ResourceKeyResolver
インターフェイスの実装クラスには、Springの@Component
アノテーションを付与してください。
実装例:アダプタサンプルプロジェクトのcom.example.adapter.impl.ResourceKeyResolverImpl
ResultResourceKeyList
インターフェイスの実装クラスの作成
アダプタの共通インターフェイスとして用意されている、ResultResourceKeyList
インターフェイスの実装クラスを作成します。
ResultResourceKeyList
インターフェイスには、Searcher
のメソッドの呼び出し結果として得られるResourceKey
を追加するメソッドや、And検索のための集合演算を行うためのメソッドなどが定義されています。
ResultResourceKeyList
インターフェイスの実装クラスは、Searcher
のメソッドの呼び出し結果として得られるResourceKey
のリストを保持します。
実装例:アダプタサンプルプロジェクトのcom.example.adapter.impl.ResultResourceKeyListImpl
ResultResourceKeyListProcessor
インターフェイスの実装クラスの作成
アダプタの共通インターフェイスとして用意されている、ResultResourceKeyListProcessor
インターフェイスの実装クラスを作成します。
ResultResourceKeyListProcessor
インターフェイスには、ページングや以下の検索結果に対するパラメータを処理するためのメソッドが定義されています。
- _sort
- _total
- _count
- _include
- _revinclude
- _contained
- _containedType
ResultResourceKeyListProcessor
インターフェイスの実装クラスには、Springの@Component
アノテーションを付与してください。
実装例:アダプタサンプルプロジェクトのcom.example.adapter.impl.ResultResourceKeyListProcessorImpl
ResourceRepository
インターフェイスの実装クラスの作成
FRUCtoSのリポジトリ層インターフェイスである、ResourceRepository
インターフェイスの実装クラスを作成します。
ResourceRepository
インターフェイスの各メソッドは、FRUCtoSのサービス層から呼び出されます。
ResourceRepository
インターフェイスの実装クラスには、Springの@Repository
アノテーションを付与してください。
ResourceRepository
インターフェイスのsearch
メソッドを実装する際には、アダプタの共通クラスとして用意されているjp.fructos.repository.adapter.common.SearchCaseDispatcher
クラスを利用できます。
SearchCaseDispatcher
は以下のような機能を持っています。
- 検索パラメータに応じて、
SearcherFactory
から適切なSearcher
を生成する。 - chain検索の検索パラメータを分解する。
- 分解した各検索パラメータに応じて、一連の適切な
Searcher
メソッドを呼び出し、検索結果としてResultResourceKeyList
を返す。
実装例:アダプタサンプルプロジェクトのcom.example.impl.ResourceRepositoryImpl
アダプタで最低限実装する必要があるのは、このResourceRepository
インターフェイスと、以下に説明するAuditRepository
とTerminologyRepository
インターフェイスです。
その他のアダプタ共通インターフェイスについては、必ずしも実装する必要はなく、ResourceRepository
インターフェイスの各メソッドの処理は、全てアダプタで独自に実装することも可能です。
例えば、アダプタのマッピングアノテーションと、MapperGeneratorによるリソースマッピングクラスの生成機能のみ利用し、それ以外の処理は全てアダプタで独自に実装するといったケースも考えられます。
AuditRepository
インターフェイスの空実装クラスの作成
FRUCtoSのリポジトリ層インターフェイスである、AuditRepository
インターフェイスの空実装クラスを作成します。
AuditRepository
インターフェイスの空実装クラスには、Springの@Repository
アノテーションを付与してください。
実装例:アダプタサンプルプロジェクトのcom.example.impl.AuditRepositoryImpl
TerminologyRepository
インターフェイスの空実装クラスの作成
FRUCtoSのリポジトリ層インターフェイスである、TerminologyRepository
インターフェイスの空実装クラスを作成します。
TerminologyRepository
インターフェイスの空実装クラスには、Springの@Repository
アノテーションを付与してください。
実装例:アダプタサンプルプロジェクトのcom.example.adapter.terminology.TerminologyRepositoryImpl
アダプタの実行準備
初めに、Mavenコマンドでアダプタプロジェクトをビルドして、jarファイルを作成します。
mvn clean package
続いて、アダプタサンプルプロジェクトに同梱されている、fructos_adapter_docker/tomcat/webapps/fructos-adapter/WEB-INF/lib
フォルダに、ビルドしたアダプタプロジェクトのjarを追加します。
アダプタプロジェクトのpom.xml
に独自に追加したdependency
がある場合は、それらのjarも追加してください。
fructos_adapter_docker/tomcat/webapps/fructos-adapter/WEB-INF/dispatcher-servlet.xml
をテキストエディタなどで開いて、Springのコンポーネントスキャン対象パッケージに、アダプタのJavaパッケージを追加します。
<!-- com.example部分をアダプタのJavaパッケージに変更してください -->
<context:component-scan base-package="jp.fructos,com.example"/>
アダプタの実行(Dockerを使用する場合)
fructos_adapter_docker/.env
をテキストエディタなどで開いて、DB接続情報をアダプタの接続先DBに合わせて修正します。
DB_DRIVER=org.postgresql.Driver
DB_URL=jdbc:postgresql://xxx.xxx.xxx.xxx:5432/sample
DB_USER=sample
DB_PASSWORD=sample
fructos_adapter_docker
フォルダで以下のコマンドを実行します。
注意
docker-composeのバージョンがv2.0.0以上の場合、docker-compose
コマンドをdocker compose
コマンドに読み替えて実行してください。
docker-compose up -d --build
アダプタの実行(Dockerを使用しない場合)
fructos_adapter_docker/tomcat/webapps/fructos-adapter
フォルダを、別途セットアップしたTomcat(バージョン9.0.43以上)のwebapps
フォルダに追加して実行します。