Service Builder Basics
ご覧のページは、お客様の利便性のために一部機械翻訳されています。また、ドキュメントは頻繁に更新が加えられており、翻訳は未完成の部分が含まれることをご了承ください。最新情報は都度公開されておりますため、必ず英語版をご参照ください。翻訳に問題がある場合は、 こちら までご連絡ください。

モデルコード、永続性コード、およびサービスコードの生成

サービスビルダーを使用すると、モデルを簡単に定義し、モデルコード、永続性コード、およびサービスコードを生成できます。 これは、Y7G4Entryというモデルを定義し、サービスビルダーを使用してコードを生成することで体験できます。 次に、コードをDXPにデプロイし、そのコードを使用するサービスを呼び出します。

サンプルプロジェクトをダウンロードする

サンプルプロジェクトをダウンロードして解凍します。

curl https://resources.learn.liferay.com/examples/liferay-y7g4.zip -O
unzip liferay-y7g4.zip

liferay-y7g4 プロジェクトには、次の2つのモジュールがあります。

  • y7g4-api
  • y7g4-service

APIモジュール(-api)は、パブリックインターフェイスとユーティリティを提供します。 サービスモジュール(-service)は実装を提供します。

APIモジュールを調べる

APIモジュールには、bndメタデータファイルとGradleビルドファイルしかありません。

y7g4-api
 ├── bnd.bnd // Defines the module artifact, package exports, and includes the service XML file
 └── build.gradle // Declares dependencies

bnd.bndファイルは次のとおりです。

Bundle-Name: Acme Y7G4 API
Bundle-SymbolicName: com.acme.y7g4.api
Bundle-Version: 1.0.0
Export-Package:\
	com.acme.y7g4.exception,\
	com.acme.y7g4.model,\
	com.acme.y7g4.service,\
	com.acme.y7g4.service.persistence

Bundle- ヘッダーはモジュール成果物を記述します。 Export-Package ヘッダーは、公開する API パッケージを指定します。 bnd メタデータとその使用方法の詳細については、 モジュール プロジェクト を参照してください。

build.gradle ファイルは、モジュールの DXP/Portal への依存関係を宣言します。

dependencies {
	compileOnly group: "com.liferay.portal", name: "release.portal.api"
}

サービスモジュールを調べる

サービスモジュールには、bndメタデータファイル、Gradleビルドファイル、およびサービス定義ファイルがあります。

y7g4-service
 ├── bnd.bnd // Defines the module artifact, data schema version, and more
 ├── build.gradle // Declares dependencies and code generation parameters
 └── service.xml // Specifies models and their relationships

bnd.bndファイルは次のとおりです。

Bundle-Name: Acme Y7G4 Service
Bundle-SymbolicName: com.acme.y7g4.service
Bundle-Version: 1.0.0
Liferay-Require-SchemaVersion: 1.0.0
Liferay-Service: true
-dsannotations-options: inherit

もう一度言いますが、 Bundle- ヘッダーはモジュール アーティファクトを記述します。 サービスメタデータとディレクティブが続きます。

メタデータ説明
Liferay-Require-SchemaVersion: 1.0.0アプリケーションのデータ スキーマ バージョン。 データベーススキーマの変更を伴うアプリケーションのバージョンをリリースする場合、バージョンをインクリメントすることになります。
Liferay-Service: trueこのモジュールは Liferay サービスを提供します。
-dsannotations-options: inheritOSGi サービス コンポーネント クラスは、クラス階層から OSGi 宣言型サービス アノテーションを継承します。 たとえば、拡張クラスは、 @Reference アノテーションを介して祖先フィールドが参照するすべてのサービスにアクセスできます。

build.gradleファイルは次のとおりです。

buildService {
	apiDir = "../y7g4-api/src/main/java"
}

dependencies {
	compileOnly group: "com.liferay.portal", name: "release.portal.api"
	compileOnly project(":y7g4-api")
}

buildServiceタスクは、サービスのAPIクラスをapiDirで指定されたAPIモジュールのJavaソースフォルダに生成します。 サービスモジュールは、DXP/PortalおよびAPIモジュール(兄弟フォルダy7g4-api内)に依存します。

サービスモデルの定義を調べる

service.xmlファイルは、Y7G4Entryモデルエンティティを定義します。 サービスビルダーは、service.xmlファイルの仕様に従って、モデル、永続性、およびサービスクラスを生成します。

service.xmlファイルは次のとおりです。

<?xml version="1.0"?>
<!DOCTYPE service-builder PUBLIC "-//Liferay//DTD Service Builder 7.4.0//EN" "http://www.liferay.com/dtd/liferay-service-builder_7_4_0.dtd">

<service-builder dependency-injector="ds" package-path="com.acme.y7g4" short-no-such-exception-enabled="false">
	<namespace>Y7G4</namespace>
	<entity local-service="true" name="Y7G4Entry" remote-service="false">

		<!-- PK fields -->

		<column name="y7g4EntryId" primary="true" type="long" />

		<!-- Other fields -->

		<column name="description" type="String" />
		<column name="name" type="String" />
	</entity>
</service-builder>

このファイルは、ID (主キー)、名前、説明を持つ Y7G4Entry モデルを定義します。

サービスビルダー 要素

service-builder 要素の属性は、 service.xml ファイル内のすべてのモデル エンティティに影響します。

サービスビルダー 属性説明
dependency-injector依存性インジェクターのタイプを宣言します。 宣言型サービス (ds) がデフォルトです。
package-path生成されたクラスの主要なパッケージ パスを宣言します。
short-no-such-exception-enabledtrueに設定すると、 NoSuchY7G4EntryException メッセージでエンティティ名の切り捨てバージョンが使用されます。それ以外の場合は、完全なエンティティ名が使用されます。

名前空間 要素

グローバル 名前空間 要素は、すべてのモデル エンティティ データベース テーブルのプレフィックスを指定します。

エンティティ 要素

エンティティ 要素は、モデル データベース テーブルとサービス タイプを定義します。

entity 属性説明
nameエンティティの名前。 Service Builder は、命名形式 [namespace]_[name] (例: Y7G4_Y7G4Entry) を使用してエンティティ テーブルを生成します。
local-servicetrueの場合、JVM 内から呼び出すサービス クラスを生成します。
remote-servicetrueの場合、JVM 外部から呼び出すサービス クラス (Web サービス クラスを含む) を生成します。

要素

要素は、エンティティのテーブル内の列を定義します。 Y7G4Entry エンティティ列要素は次のとおりです。

説明
y7g4EntryIdモデルインスタンスの ID (長整数) と主キー。
nameインスタンスの名前 (文字列)。
descriptionインスタンスの説明 (文字列)。

service.xml 要素の詳細については、 Liferay Service Builder DTDを参照してください。

永続コードを生成する

Service Builder を呼び出して、永続コードとデータベース スクリプトを生成します。

cd liferay-y7g4
./gradlew y7g4-service:buildService

出力:

> Task :y7g4-service:buildService
Building Y7G4Entry
Writing src/main/java/com/acme/y7g4/service/persistence/impl/Y7G4EntryPersistenceImpl.java
Writing ../y7g4-api/src/main/java/com/acme/y7g4/service/persistence/Y7G4EntryPersistence.java
Writing ../y7g4-api/src/main/java/com/acme/y7g4/service/persistence/Y7G4EntryUtil.java
Writing src/main/java/com/acme/y7g4/service/persistence/impl/Y7G4EntryModelArgumentsResolver.java
Writing src/main/java/com/acme/y7g4/model/impl/Y7G4EntryModelImpl.java
Writing src/main/java/com/acme/y7g4/model/impl/Y7G4EntryBaseImpl.java
Writing src/main/java/com/acme/y7g4/model/impl/Y7G4EntryImpl.java
Writing ../y7g4-api/src/main/java/com/acme/y7g4/model/Y7G4EntryModel.java
Writing ../y7g4-api/src/main/java/com/acme/y7g4/model/Y7G4Entry.java
Writing src/main/java/com/acme/y7g4/model/impl/Y7G4EntryCacheModel.java
Writing ../y7g4-api/src/main/java/com/acme/y7g4/model/Y7G4EntryWrapper.java
Writing ../y7g4-api/src/main/java/com/acme/y7g4/model/Y7G4EntrySoap.java
Writing ../y7g4-api/src/main/java/com/acme/y7g4/model/Y7G4EntryTable.java
Writing src/main/java/com/acme/y7g4/service/impl/Y7G4EntryLocalServiceImpl.java
Writing src/main/java/com/acme/y7g4/service/base/Y7G4EntryLocalServiceBaseImpl.java
Writing ../y7g4-api/src/main/java/com/acme/y7g4/service/Y7G4EntryLocalService.java
Writing ../y7g4-api/src/main/java/com/acme/y7g4/service/Y7G4EntryLocalServiceUtil.java
Writing ../y7g4-api/src/main/java/com/acme/y7g4/service/Y7G4EntryLocalServiceWrapper.java
Writing src/main/resources/META-INF/module-hbm.xml
Writing src/main/resources/META-INF/portlet-model-hints.xml
Writing ../y7g4-api/src/main/java/com/acme/y7g4/exception/NoSuchY7G4EntryException.java
Writing src/main/java/com/acme/y7g4/service/persistence/impl/constants/Y7G4PersistenceConstants.java
Writing src/main/resources/META-INF/sql/tables.sql
Writing src/main/resources/META-INF/sql/tables.sql
Writing src/main/resources/service.properties

BUILD SUCCESSFUL in 3s
1 actionable task: 1 executed

サービスビルダーは、モデル、永続性、およびサービス用のJavaクラス、データベーススクリプト、および構成ファイルを生成します。 ファイルパスは、y7g4-serviceモジュールからの相対パスです。

生成されたストラクチャーの概要は次のとおりです。

liferay-y7g4
├── y7g4-api
│   └── src
│       └── main
│           └── java
│               └── com
│                   └── acme
│                       └── y7g4
│                           ├── exception // Public exception classes & interfaces
│                           ├── model // Public model classes & interfaces
│                           └── service // Public persistence and service classes
│                                       // & interfaces
└── y7g4-service
    └── src/main
        ├── java/com/acme/y7g4
        │                 ├── model // Model implementation
        │                 └── service // Persistence and service implementation
        └── resources
            ├── META-INF
            │   ├── module-hbm.xml // Hibernate object relational map configuration
            │   ├── portlet-model-hints.xml // Provides field type information for the UI
            │   └── sql
            │       ├── indexes.sql
            │       ├── sequences.sql
            │       └── tables.sql
            └── service.properties // Tracks the service build version

モデル、永続性、およびサービス実装クラスは、Javaパッケージパスcom.acme.y7g4に対して生成されました。 生成されたクラスの理解と拡張でクラスについて学習します。

SQLスクリプトと永続性構成がresources/META-INFフォルダに生成されました。

module-hbm.xmlファイルは、Hibernateオブジェクトリレーショナルマップを指定します。

<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">

<hibernate-mapping auto-import="false" default-lazy="false">
    <import class="com.acme.y7g4.model.Y7G4Entry" />
    <class name="com.acme.y7g4.model.impl.Y7G4EntryImpl" table="Y7G4_Y7G4Entry">
        <id access="com.liferay.portal.dao.orm.hibernate.LiferayPropertyAccessor" name="y7g4EntryId" type="long">
            <generator class="assigned" />
        </id>
        <property access="com.liferay.portal.dao.orm.hibernate.LiferayPropertyAccessor" name="description" type="com.liferay.portal.dao.orm.hibernate.StringType" />
        <property access="com.liferay.portal.dao.orm.hibernate.LiferayPropertyAccessor" name="name" type="com.liferay.portal.dao.orm.hibernate.StringType" />
    </class>
</hibernate-mapping>

module-hbm.xmlファイルは、Y7G4EntryImplオブジェクトをY7G4_Y7G4Entryテーブルにマップします。 Hibernate を使用したマッピングの詳細については、 Hibernateを参照してください。

tables.sqlスクリプトは、Y7G4_Y7G4Entryテーブルを指定します。

create table Y7G4_Y7G4Entry (
    y7g4EntryId LONG not null primary key,
    description VARCHAR(75) null,
    name VARCHAR(75) null
);

y7g4EntryIdはプライマリーキーです。 namedescriptionは属性です。 モジュールをデプロイすると、DXP/Portalはtables.sqlスクリプトを実行してテーブルを作成します。

このservice.xmlファイルの要素はインデックスまたはシーケンスを指定しないため、indexes.sqlまたはsequences.sqlスクリプトは空です。

永続レイヤーとサービスをデプロイする

次に、生成されたコードをDXPサーバーにデプロイして、永続レイヤーとサービスを作成します。 サーバーは別の MariaDB データベース サーバー上のデータ ソースを使用します—バンドルされている Hypersonic サーバーよりも MariaDB 上のデータベースを調べる方が簡単です。 すべてをデプロイした後、テーブルを検証し、サービスをテストします。

データベースを作成する

  1. MariaDB Dockerコンテナを起動します。

    dockertable and install the -e MYSQL_ROOT_PASSWORD=my-secret-pw -d mariadb:10.2
    
  2. MariaDB Docker コンテナ内から DXP データベース を作成します。

    データベースサーバーにサインインします。

    docker exec -it some-mariadb bash -c "/usr/bin/mysql -uroot -pmy-secret-pw"
    

    DXP用のデータベースを作成します。

    create database dxp_db default character set utf8 collate utf8mb4_unicode_ci;
    

    データベースセッションを終了します。

    quit
    
  3. デフォルトネットワーク(bridge)で Docker の network inspect コマンドを呼び出して、MariaDB コンテナの IP アドレスを取得します。

    docker network inspect bridge
    

    出力例:

    "Containers": {
       "162f5350ee9ba7c47c1ba91f54a84543aeada7feb35eb8153743b13ef54cb491": {
          "Name": "some-mariadb",
          "EndpointID": "8e97e35fb118e2024a52f2ecbfd40b0a879eba8dc3bc5ffceea8bb117c10bebc",
          "MacAddress": "02:42:ac:11:00:02",
          "IPv4Address": "172.17.0.2/16",
          "IPv6Address": ""
       }
    }
    

some-mariadbコンテナのIPv4Address値の最初の部分を使用します。 例のIPアドレスは172.17.0.2です。

サーバーを起動する

別の端末で、次のコマンドを使用してDXPを起動します。 必ず[IP address]some-mariadbコンテナのIPアドレスに置き換えてください。

docker run -it \
--add-host some-mariadb:[IP address] \
-e LIFERAY_JDBC_PERIOD_DEFAULT_PERIOD_JNDI_PERIOD_NAME="" \
-e LIFERAY_JDBC_PERIOD_DEFAULT_PERIOD_DRIVER_UPPERCASEC_LASS_UPPERCASEN_AME=org.mariadb.jdbc.Driver \
-e LIFERAY_JDBC_PERIOD_DEFAULT_PERIOD_URL="jdbc:mariadb://some-mariadb:3306/dxp_db?useUnicode=true&characterEncoding=UTF-8&useFastDateParsing=false" \
-e LIFERAY_JDBC_PERIOD_DEFAULT_PERIOD_USERNAME=root \
-e LIFERAY_JDBC_PERIOD_DEFAULT_PERIOD_PASSWORD=my-secret-pw \
-m 8g \
-p 8080:8080 \
liferay/portal:7.4.2-ga3

モジュールをデプロイする

モジュールをデプロイしてデータベース テーブルを作成し、サービスをインストールします。

./gradlew deploy -Ddeploy.docker.container.id=$(docker ps -lq)

コンソール出力:

STARTED com.acme.y7g4.service_1.0.0 [1423]
STARTED com.acme.y7g4.api_1.0.0 [1422]

テーブルを確認する

データベーステーブルを確認し、検証します。

  1. データベースサーバーにサインインします。

    docker exec -it some-mariadb bash -c "/usr/bin/mysql -uroot -pmy-secret-pw"
    
  2. データベースに接続します。

    connect dxp_db;
    
  3. データベーステーブルを一覧表示して、Y7G4_Y7G4Entryテーブルを確認します。

    show tables;
    

    結果:

    +--------------------------------+
    | Tables_in_dxp_db               |
    +--------------------------------++
    | AMImageEntry                   |
    | AccountEntry                   |
    | AccountEntryOrganizationRel    |
    | ...                            |
    | Y7G4_Y7G4Entry                 |
    +--------------------------------+
    
  4. Y7G4_Y7G4Entryテーブルの列を一覧表示します。

    SHOW COLUMNS FROM Y7G4_Y7G4Entry;
    

    結果:

    +-------------+-------------+------+-----+---------+-------+
    | Field       | Type        | Null | Key | Default | Extra |
    +-------------+-------------+------+-----+---------+-------+
    | y7g4EntryId | bigint(20)  | NO   | PRI | NULL    |       |
    | description | varchar(75) | YES  |     | NULL    |       |
    | name        | varchar(75) | YES  |     | NULL    |       |
    +-------------+-------------+------+-----+---------+-------+
    

    すべてが揃っています。

  5. データベースセッションを終了します。

    quit
    

サービスをテストする

サービスを呼び出して、データベースにY7G4Entryデータを入力します。

  1. ブラウザでDXPにアクセスします(http://localhost:8080)。

  2. デフォルトの認証情報を使用してサインインします。

    ユーザー名: test@liferay.com

    パスワード: テスト

  3. コントロール パネルサーバー管理スクリプトでスクリプト コンソールに移動します。

  4. 次のスクリプトを実行して、エントリーを追加します。

    import com.acme.y7g4.service.Y7G4EntryLocalServiceUtil;
    
    import com.liferay.portal.kernel.dao.orm.QueryUtil;
    
    entry = Y7G4EntryLocalServiceUtil.createY7G4Entry(1234);
    
    entry.setName("Mop floors");
    entry.setDescription("Mop the kitchen and bathroom floors with soap and water.");
    
    Y7G4EntryLocalServiceUtil.addY7G4Entry(entry);
    
    entries = Y7G4EntryLocalServiceUtil.getY7G4Entries(QueryUtil.ALL_POS, QueryUtil.ALL_POS);
    
    for (entry in entries){
       out.println(entry);
    }
    

    出力:

    {y7g4EntryId=1234, description=Mop the kitchen and bathroom floors with soap and water., name=Mop floors}
    

    新しく追加されたY7G4EntryはJSON形式で印刷されます。

スクリプトが行ったことは次のとおりです。

  1. 生成された静的ユーティリティクラス Y7G4EntryLocalServiceUtil をインポートしました。
  2. ID(long1234Y7G4Entryインスタンスを作成しました。
  3. Y7G4Entryインスタンスのnamedescriptionの属性を入力しました。
  4. Y7G4Entryをデータベースに追加しました。
  5. データベースからすべてのY7G4Entryインスタンスを取得し、それらを印刷しました。

次のステップ

モデルを定義し、その永続コードとサービスコードを生成する方法がわかったので、生成されたサービスクラスを調べる必要があります。 生成されたクラスの理解と拡張に進みます。