を使用したマイクロサービスの構築
59432 ワード
DropWizardメイキングマジック。😎
このチュートリアルでは、DropWizardを使用してMicroServiceを作成します.このフレームワークはWebアプリケーションを構築するためのすべての種類のライブラリを提供します.以下に示すライブラリのいくつかを示します:
Jettyサーバー:これはオープンソースのWebサーバー、軽量で、任意のアプリケーションで埋め込むのは簡単です.
ジャージ:RESTful Webサービスを作成するための実装.
JSONオブジェクトからPOJOおよびその逆の操作を許可します.
メトリック:HTTPリクエスト、データベース接続、キューなどの状態に関する情報を提供します.
グアバ:コレクション、検証、文字列などに対処する多くのクラスをサポートします.
Hibernateバリデータ:Javaオブジェクトの制約としての妥当性検査.
JDBI : JDBCをラップし、リレーショナルデータベースを操作する柔軟な方法を提供します.
Liqubase:データベースの移行とDDLの変更に最適です.
MongoDBはNOSQLデータベースとはるかに。🌳
このドキュメントのドキュメントを指向したデータベース(JSONのようなドキュメントによる)は、リレーショナルデータベースからの機能の一部を組み合わせて使いやすく、マルチプラットフォームはスケールアップのための最良のオプションであり、フォールトトレランス、ロードバランシング、マップリダクションなどがあります.
このマイクロサービスで使用される技術📝
mvn archetype:generate -DarchetypeGroupId=io.dropwizard.archetypes -DarchetypeArtifactId=java-simple -DarchetypeVersion=1.3.5 -DgroupId=com.demo -DartifactId=dropwizard-mongodb-ms -Dversion=1.0.0-SNAPSHOT -Dname=DropwizardMongoDBMicroservice
端末を開き、コマンドの前にペーストして、MavenとJavaのインストールと設定を確認します.最後の構造は次のようになります.
dropwizard-mongodb-ms/
├── README.md
├── config.yml
├── pom.xml
└── src
├── main
│ ├── java
│ │ └── com
│ │ └── demo
│ │ ├── DropwizardMongoDBMicroserviceApplication.java
│ │ ├── DropwizardMongoDBMicroserviceConfiguration.java
│ │ ├── api
│ │ ├── cli
│ │ ├── client
│ │ ├── core
│ │ ├── db
│ │ ├── health
│ │ └── resources
│ └── resources
│ ├── assets
│ └── banner.txt
└── test
├── java
│ └── com
│ └── demo
│ ├── api
│ ├── client
│ ├── core
│ ├── db
│ └── resources
└── resources
└── fixtures
プロジェクトが作成されると、pom.xml
ファイル. . .
<properties>
<dropwizard.version>1.3.5</dropwizard.version>
<mainClass>com.demo.DropwizardMongoDBMicroserviceApplication</mainClass>
<mongodb.version>3.8.2</mongodb.version>
<jdk.version>1.8</jdk.version>
<dropwizard.swagger.version>1.0.6-1</dropwizard.swagger.version>
<mockito.core.version>2.23.0</mockito.core.version>
</properties>
. . .
<dependency>
<groupId>io.dropwizard</groupId>
<artifactId>dropwizard-core</artifactId>
</dependency>
<dependency>
<groupId>org.mongodb</groupId>
<artifactId>mongodb-driver-sync</artifactId>
<version>${mongodb.version}</version>
</dependency>
<dependency>
<groupId>com.smoketurner</groupId>
<artifactId>dropwizard-swagger</artifactId>
<version>${dropwizard.swagger.version}</version>
</dependency>
<!-- Testing -->
<dependency>
<groupId>io.dropwizard</groupId>
<artifactId>dropwizard-testing</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.mockito</groupId>
<artifactId>mockito-core</artifactId>
<version>${mockito.core.version}</version>
<scope>test</scope>
</dependency>
<!-- Testing -->
. . .
ファイルにいくつかの設定を追加しましたconfiguration.yaml
, 以下のようになります.server:
maxThreads: 512
applicationContextPath: /dropwizard-mongodb-ms
applicationConnectors:
- type: http
port: 8080
adminConnectors:
- type: http
port: 8081
logging:
level: INFO
loggers:
com.demo: INFO
#You can choose the user and password what you want.
mongoDBConnection:
credentials:
username: "user_donuts"
password: "pAsw0Rd"
seeds:
- host: "mongodb"
port: 27017
database: "donuts"
swagger:
basePath: /dropwizard-mongodb-ms
resourcePackage: com.demo.resources
scan: true
info:
version: "1.0.0"
title: "Donuts API CRUD"
description: "A simple API used for expose CRUD operation on MongoDB collection"
termsOfService: "http://swagger.io/terms/"
contact:
name: "Donuts API "
license:
name: "Rich Lopez"
設定.YMLは、io.dropwizard.Configuration
以下のようになります.package com.demo;
import com.demo.db.configuration.MongoDBConnection;
import com.fasterxml.jackson.annotation.JsonProperty;
import io.dropwizard.Configuration;
import io.federecio.dropwizard.swagger.SwaggerBundleConfiguration;
public class DropwizardMongoDBMicroserviceConfiguration extends Configuration {
/**
* The data configuration for MongoDB.
*/
private MongoDBConnection mongoDBConnection;
@JsonProperty("swagger")
private SwaggerBundleConfiguration swaggerBundleConfiguration;
//Getters and setters
}
このMicroServiceは、CRUD(CREATE、READ、UPDATE、DELETE)でAPI RESTベースを公開します.私はドーナツのような製品を選びました🍩 🤤), このチュートリアルの最後にGithubリポジトリで見つけることができるコードの一部.私は、使用している
com.mongodb.client.MongoCollection
コレクションへのアクセスのインターフェイスdonuts
操作により多くの粒度を持つために、私はCRO操作を操作するためにDAO(Data Access Object)を作成しました.package com.demo.db.daos;
//imports ...
public class DonutDAO {
/** The collection of Donuts */
final MongoCollection<Document> donutCollection;
/**
* Constructor.
*
* @param donutCollection the collection of donuts.
*/
public DonutDAO(final MongoCollection<Document> donutCollection) {
this.donutCollection = donutCollection;
}
/**
* Find all donuts.
*
* @return the donuts.
*/
public List<Donut> getAll() {
final MongoCursor<Document> donuts = donutCollection.find().iterator();
final List<Donut> donutsFind = new ArrayList<>();
try {
while (donuts.hasNext()) {
final Document donut = donuts.next();
donutsFind.add(DonutMapper.map(donut));
}
} finally {
donuts.close();
}
return donutsFind;
}
/**
* Get one document find in other case return null.
*
* @param id the identifier for find.
* @return the Donut find.
*/
public Donut getOne(final ObjectId id) {
final Optional<Document> donutFind = Optional.ofNullable(donutCollection.find(new Document("_id", id)).first());
return donutFind.isPresent() ? DonutMapper.map(donutFind.get()) : null;
}
public void save(final Donut donut){
final Document saveDonut = new Document("price", donut.getPrice())
.append("flavor", donut.getFlavor());
donutCollection.insertOne(saveDonut);
}
/**
* Update a register.
*
* @param id the identifier.
* @param donut the object to update.
*/
public void update(final ObjectId id, final Donut donut) {
donutCollection.updateOne(new Document("_id", id),
new Document("$set", new Document("price", donut.getPrice())
.append("flavor", donut.getFlavor()))
);
}
/**
* Delete a register.
* @param id the identifier.
*/
public void delete(final ObjectId id){
donutCollection.deleteOne(new Document("_id", id));
}
地図のために、私はMongoDBからPOJOまでフィールドをフィルターするユーティリティクラスを使用します.package com.demo.util;
import com.demo.api.Donut;
import org.bson.Document;
public class DonutMapper {
/**
* Map objects {@link Document} to {@link Donut}.
*
* @param donutDocument the information document.
* @return A object {@link Donut}.
*/
public static Donut map(final Document donutDocument) {
final Donut donut = new Donut();
donut.setId(donutDocument.getObjectId("_id"));
donut.setFlavor(donutDocument.getString("flavor"));
donut.setPrice(donutDocument.getDouble("price"));
return donut;
}
}
その後、MongoDBの情報を操作するPOJOを作成します.package com.demo.api;
//imports ...
public class Donut implements Serializable {
/** The id.*/
@JsonSerialize(using = ObjectIdSerializer.class)
private ObjectId id;
/** The price. */
@NotNull
private double price;
/** The principal flavor.*/
@NotNull
private String flavor;
/**Constructor.*/
public Donut() {
}
//getters & setters
//hashcode, equals and toString methods
このクラスはエンドポイントに対してのみ使用されます.package com.demo.api;
//imports ...
public class Response {
/** The message.*/
private String message;
/** Constructor.*/
public Response() {
}
//getters & setters
//hashcode, equals and toString methods
ここでは変換用のユーティリティクラスorg.bson.types.ObjectId
to String
ジャクソンを使っているオブジェクト.package com.demo.util;
import java.io.IOException;
import org.bson.types.ObjectId;
import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.JsonSerializer;
import com.fasterxml.jackson.databind.SerializerProvider;
public class ObjectIdSerializer extends JsonSerializer<ObjectId> {
@Override
public void serialize(final ObjectId objectId, final JsonGenerator jsonGenerator,
final SerializerProvider serializerProvider) throws IOException {
jsonGenerator.writeString(objectId.toString());
}
}
変換用String
object to array of char
.package com.demo.util;
import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.JsonSerializer;
import com.fasterxml.jackson.databind.SerializerProvider;
import java.io.IOException;
public class PasswordSerializer extends JsonSerializer<String> {
@Override
public void serialize(final String input, final JsonGenerator jsonGenerator,
final SerializerProvider serializerProvider) throws IOException {
jsonGenerator.writeString(input.toCharArray(), 0, input.toCharArray().length);
}
@Override
public Class<String> handledType() {
return String.class;
}
}
これらのPOJOを使用して情報をマップしますconfiguration.yml
.package com.demo.db.configuration;
import java.util.Arrays;
import java.util.Objects;
import com.demo.util.PasswordSerializer;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
/**
* This class is used for credentials.
* @version 1.0.0
* @since 1.0.0
* @author Rich Lopez
*/
public class Credentials {
/** The user name.*/
private String username;
/** The password.*/
@JsonSerialize(using = PasswordSerializer.class)
private char[] password;
//getters, setters, hashcode and equals methods.
}
package com.demo.db.configuration;
import java.util.Objects;
public class Seed {
/** The host.*/
private String host;
/** The port.*/
private int port;
//getters, setters, hashcode and equals methods.
}
package com.demo.db.configuration;
import java.util.List;
public class MongoDBConnection {
/**
* The credentials user and password.
*/
private Credentials credentials;
/**
* The lis of seeds.
*/
private List<Seed> seeds;
/**
* The db.
*/
private String database;
}
MongoDBとの接続を管理するために、このクラスにYAMLファイル構成から来る情報をマップする必要がありますcom.demo.db.configuration.Credentials
, com.demo.db.configuration.MongoDBConnection
, com.demo.db.configuration.Seed
.クラス
com.demo.db.MongoDBFactoryConnection
MoogoDB用のクライアントを作成します.package com.demo.db;
//imports ...
public class MongoDBFactoryConnection {
/** The configuration for connect to MongoDB Server.*/
private MongoDBConnection mongoDBConnection;
/**
* Constructor.
*
* @param mongoDBConnection the mongoDB connection data.
*/
public MongoDBFactoryConnection(final MongoDBConnection mongoDBConnection) {
this.mongoDBConnection = mongoDBConnection;
}
/**
* Gets the connection to MongoDB.
*
* @return the mongo Client.
*/
public MongoClient getClient() {
LOGGER.info("Creating mongoDB client.");
final Credentials configCredentials = mongoDBConnection.getCredentials();
final MongoCredential credentials = MongoCredential.createCredential(
configCredentials.getUsername(),
mongoDBConnection.getDatabase(),
configCredentials.getPassword());
final MongoClient client = MongoClients.create(
MongoClientSettings.builder()
.credential(credentials)
.applyToClusterSettings(builder -> builder.hosts(getServers())).build()
);
return client;
}
/**
* Map the object {@link Seed} to objects {@link ServerAddress} that contain the information of servers.
*
* @return the list of servers.
*/
private List<ServerAddress> getServers() {
final List<Seed> seeds = mongoDBConnection.getSeeds();
return seeds.stream()
.map(seed -> {
final ServerAddress serverAddress = new ServerAddress(seed.getHost(), seed.getPort());
return serverAddress;
})
.collect(Collectors.toList());
}
DropWizardのライフサイクルでは、オブジェクトのインターフェイスで管理することができますio.dropwizard.lifecycle.Managed
そして、クラスio.dropwizard.lifecycle.MongoDBManaged
.package com.demo.db;
//imports ...
public class MongoDBManaged implements Managed {
/** The mongoDB client.*/
private MongoClient mongoClient;
/**
* Constructor.
* @param mongoClient the mongoDB client.
*/
public MongoDBManaged(final MongoClient mongoClient) {
this.mongoClient = mongoClient;
}
@Override
public void start() throws Exception {
}
@Override
public void stop() throws Exception {
mongoClient.close();
}
もう一つの重要なクラスはHealthcheckですcom.codahale.metrics.health.HealthCheck
メソッドを実装するcheck
.package com.demo.health;
//imports ...
public class DropwizardMongoDBHealthCheck extends HealthCheck {
/** A client of MongoDB.*/
private MongoClient mongoClient;
/**
* Constructor.
*
* @param mongoClient the mongo client.
*/
public DropwizardMongoDBHealthCheck(final MongoClient mongoClient) {
this.mongoClient = mongoClient;
}
@Override
protected Result check() {
try {
final Document document = mongoClient.getDatabase("donuts").runCommand(new Document("buildInfo", 1));
if (document == null) {
return Result.unhealthy("Can not perform operation buildInfo in Database.");
}
} catch (final Exception e) {
return Result.unhealthy("Can not get the information from database.");
}
return Result.healthy();
}
このマイクロサービスのエントリポイントはクラスですcom.demo.DropwizardMongoDBMicroserviceApplication
すべてのバンドルの設定、初期化クラスなどを読み込みます.io.dropwizard.Application
のうち、io.dropwizard.Configuration
.package com.demo;
import com.demo.db.MongoDBFactoryConnection;
import com.demo.db.daos.DonutDAO;
import com.demo.db.MongoDBManaged;
import com.demo.health.DropwizardMongoDBHealthCheck;
import com.demo.resources.DonutResource;
import io.dropwizard.Application;
import io.dropwizard.setup.Bootstrap;
import io.dropwizard.setup.Environment;
import io.federecio.dropwizard.swagger.SwaggerBundle;
import io.federecio.dropwizard.swagger.SwaggerBundleConfiguration;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
public class DropwizardMongoDBMicroserviceApplication extends Application<DropwizardMongoDBMicroserviceConfiguration> {
/**
* Logger class.
*/
private static final Logger LOGGER = LoggerFactory.getLogger(DropwizardMongoDBMicroserviceApplication.class);
/**
* Entry point for start Application.
*
* @param args the args.
* @throws Exception when the app can not start.
*/
public static void main(final String[] args) throws Exception {
LOGGER.info("Start application.");
new DropwizardMongoDBMicroserviceApplication().run(args);
}
@Override
public String getName() {
return "DropwizardMongoDBMicroservice";
}
@Override
public void initialize(final Bootstrap<DropwizardMongoDBMicroserviceConfiguration> bootstrap) {
bootstrap.addBundle(new SwaggerBundle<DropwizardMongoDBMicroserviceConfiguration>() {
@Override
protected SwaggerBundleConfiguration getSwaggerBundleConfiguration(
final DropwizardMongoDBMicroserviceConfiguration dropwizardMongoDBMicroserviceConfiguration) {
return dropwizardMongoDBMicroserviceConfiguration.getSwaggerBundleConfiguration();
}
});
}
@Override
public void run(final DropwizardMongoDBMicroserviceConfiguration configuration,
final Environment environment) {
final MongoDBFactoryConnection mongoDBManagerConn = new MongoDBFactoryConnection(configuration.getMongoDBConnection());
final MongoDBManaged mongoDBManaged = new MongoDBManaged(mongoDBManagerConn.getClient());
final DonutDAO donutDAO = new DonutDAO(mongoDBManagerConn.getClient()
.getDatabase(configuration.getMongoDBConnection().getDatabase())
.getCollection("donuts"));
environment.lifecycle().manage(mongoDBManaged);
environment.jersey().register(new DonutResource(donutDAO));
environment.healthChecks().register("DropwizardMongoDBHealthCheck",
new DropwizardMongoDBHealthCheck(mongoDBManagerConn.getClient()));
}
}
コマンドを使用してプロジェクトを構築するには、次の手順に従います.$ mvn clean package
アプリケーションを起動する前に、MongoDBを使用すると、ウェブサイトからダウンロードしたりDockerHubでDocker画像を使用してデータベースを持っている必要があります.MongoDBのイメージをダウンロードしたら、新しいコンテナを起動します.
$ docker run --name mongodb -d -p 27017:27017 mongo
注:情報の持続性を維持するためのボリュームの作成を確認します.次のコマンドを入力し、次のコマンドを入力します.
$ docker exec -it [container name or id] /bin/bash
$ mongo
$ use donuts
> db.createUser({ user: "user_donuts", pwd: "pAsw0Rd", roles: [ { role: "readWrite", db: "donuts"} ]});
デフォルトでは、MongoDBは認証メカニズムをscramに設定します.では、コマンドでアプリケーションを起動します.
$ java -jar target/dropwizard-mongodb-ms-1.0.0-SNAPSHOT.jar server configuration.yml
ユーザとデータベースを作成したら、次のURLでswaggerドキュメントを入力できます.http://localhost:8080/dropwizard-mongodb-ms/swagger
Dockerの作成🐳
毎日の使用者のための理由の一つは、ユニークな環境を提供し、すべての開発者は依存関係、データベース、Webサーバーなどを同期して維持する理由です.アーチファクトを構築し、展開する簡単な方法は、配信時間を短縮します.
私はDockerをアプリケーションとMongoDBサーバの起動に使用しています.
version: '3'
services:
mongodb:
image: mongo
restart: always
container_name: mongodb
environment:
MONGO_INITDB_ROOT_USERNAME: admin
MONGO_INITDB_ROOT_PASSWORD: admin
ports:
- 27017:27017
networks:
- dropw-mongodb-ntw
nginx:
image: nginx
container_name: nginx
volumes:
- ./nginx.conf:/etc/nginx/nginx.conf
ports:
- "8080:80"
- "443:443"
networks:
- dropw-mongodb-ntw
dropw-ms:
image: openjdk:8-jre
container_name: dropw-ms
volumes:
- ./target/dropwizard-mongodb-ms-1.0.0-SNAPSHOT.jar:/microservice/dropwizard-mongodb-ms-1.0.0-SNAPSHOT.jar
- ./configuration.yml:/microservice/configuration.yml
working_dir: /microservice
command: ["java", "-jar", "dropwizard-mongodb-ms-1.0.0-SNAPSHOT.jar", "server", "configuration.yml"]
ports:
- "8090:8080"
- "8091:8081"
networks:
- dropw-mongodb-ntw
networks:
dropw-mongodb-ntw:
external:
name: dropw-mongodb-ntw
コマンドでDockerネットワークを作成します.docker network create dropw-mongodb-ntw
コマンドを使用してプロジェクトを構築します$ mvn clean package
Dockerを起動する$ docker-compose up
データベースのユーザーを作成するために必要なサービスをすべて作成したら、次のコマンドでコンテナにアクセスします.$ docker exec -it [container name or id] /bin/bash
$ mongo
> use donuts
> db.createUser({ user: "user_donuts", pwd: "pAsw0Rd", roles: [ { role: "readWrite", db: "donuts"} ]});
http://localhost:8080/dropwizard-mongodb-ms/swagger 結論
DropWizardはいくつかのツールを簡単にマイクロサービスを作成するために提供します.MongoDB、Docker、Nginxのような他の技術と統合できます.すべてが要件と問題解決に依存することを忘れないでください、しかし、私にとって、これはスタートと共有経験によいです.
githubリポジトリhttps://github.com/ricdev2/dropwizard-mongodb-ms
Reference
この問題について(を使用したマイクロサービスの構築), 我々は、より多くの情報をここで見つけました https://dev.to/ricdev2/building-microservices-with-dropwizard-mongodb--docker--o30テキストは自由に共有またはコピーできます。ただし、このドキュメントのURLは参考URLとして残しておいてください。
Collection and Share based on the CC Protocol