LoginSignup
34
34

More than 5 years have passed since last update.

いますぐ採用すべきJavaフレームワークDropWizard(その2)

Last updated at Posted at 2014-06-08

Dropwizardについての続きです。
前回は以下の説明をしました。

  • mavenでのbuild
  • Configurationクラス
  • Applicationクラス
  • Resourceクラス
  • Representationクラス
  • HealthCheck機能

今回は前回のサンプルに以下を追加していきます。

  • 静的ファイルの表示
  • テンプレートエンジンによる動的ファイルの表示
  • ssl通信
  • 認証

静的ファイルと動的ファイル

maven設定

静的ファイルはdropwizard-assets
動的ファイルはdropwizard-views-freemarker、またはdropwizard-views-mustache
に依存させます。

pom.xml
    <dependency>
      <groupId>io.dropwizard</groupId>
      <artifactId>dropwizard-assets</artifactId>
      <version>${dropwizard.version}</version>
    </dependency>    
    <dependency>
      <groupId>io.dropwizard</groupId>
      <artifactId>dropwizard-views-freemarker</artifactId>
      <version>${dropwizard.version}</version>
    </dependency>
    <dependency>
      <groupId>io.dropwizard</groupId>
      <artifactId>dropwizard-views-mustache</artifactId>
      <version>${dropwizard.version}</version>
    </dependency> 

Resourceクラス

ポイントは@Producesでリソースから返されるMIMEタイプを指定することくらいです。

ViewResource.java
@Path("/views")
public class ViewResource {
    @GET
    @Produces("text/html;charset=UTF-8")
    @Path("/freemarker")
    public View freemarkerUTF8() {
        return new View("/views/ftl/utf8.ftl", Charsets.UTF_8) {
        };
    }

    @GET
    @Produces("text/html;charset=UTF-8")
    @Path("/mustache")
    public View mustacheUTF8() {
        return new View("/views/mustache/utf8.mustache", Charsets.UTF_8) {
        };
    }
}

上記で利用しているViewクラスはDropwizardでViewを表現するためのabstractクラスになります。
HTMLを表示したい場合は、このViewクラスでpublicなオブジェクトを返すGetterメソッドを作ります。
例えば、以下のようにPersonクラスを返して、templateで表示します。

public class PersonView extends View {
・・・
    public Person getPerson() {
        return person;
    }
}
<html>
    <body>
        <h1>Hello {{person.fullName}}</h1>
    </body>
</html>

Viewクラス自身のpublicメソッドは@JsonIgnoreが指定されているので、jsonでは表示されないようになっています。

io.dropwizard.views.View.java
    @JsonIgnore
    public String getTemplateName() {
        return templateName;
    }
    @JsonIgnore
    public Optional<Charset> getCharset() {
        return Optional.fromNullable(charset);
    }

テンプレート

src/main/resources/views/utf8.ftl
<html>
<body>
<h1>This is an example of a freemarker</h1>
文字コード:${charset}
</body>
</html>
src/main/resources/views/utf8.mustache
<html>
<body>
<h1>This is an example of a mustache</h1>
文字コード:{{charset}}
</body>
</html>

Applicationクラス

BundleクラスとResourceクラスを登録します。
AssetsBundleクラスとViewBundleクラスはDropwizardで用意されているクラスになります。
BasicAuthProviderは、Basic認証用の組み込みクラスになります。

HelloWorldApplication.java
    @Override
    public void initialize(Bootstrap<HelloWorldConfiguration> bootstrap) {
        bootstrap.addBundle(new AssetsBundle());
        bootstrap.addBundle(new ViewBundle());
    }
    @Override
    public void run(HelloWorldConfiguration configuration,
            Environment environment) throws ClassNotFoundException {
            ・・・
            environment.jersey().register(new ViewResource());
            ・・・
    }

静的ファイル

静的ファイルはassetsディレクトリに置きます。
これはAssetsBundleクラスのデフォルトです。コンストラクタで変更できます。

src/main/resources/assets/js/example.js
alert('sample');

動作確認

mvn packageでjarを作成後、起動すると新しく登録したResourceのURIが表示されています。

$ java -jar target/spike-dropwizard-1.0-SNAPSHOT.jar server example.yml
INFO  [2014-06-08 13:30:34,302] io.dropwizard.jersey.DropwizardResourceConfig: The following paths were found for the configured resources:
・・・
    GET     /views/freemarker (com.github.ko2ic.resources.ViewResource)
    GET     /views/mustache (com.github.ko2ic.resources.ViewResource)

対応するURIを呼び出すと変換されたHTMLが表示されます。

$ curl http://localhost:8080/views/freemarker
<html>
<body>
<h1>This is an example of a freemarker</h1>
文字コード:Optional.of(UTF-8)
</body>
</html>

$ curl http://localhost:8080/views/mustache
<html>
<body>
<h1>This is an example of a mustache</h1>
文字コード:Optional.of(UTF-8)
</body>
</html>

静的ファイルは/assets/ファイルパスで呼び出します。

$ curl http://localhost:8080/assets/js/example.js
alert('sample');

SSLと認証

SSL

SSLは、keystoreを作成して設定をするだけでアクセスできました。
https://localhost:8443/hello-world

example.yml
server:
・・・
    - type: https
      port: 8443
      keyStorePath: example.keystore
      keyStorePassword: example
      validateCerts: false

以上です。次は認証です。

maven設定

dropwizard-authの依存を追加します。

pom.xml
    <dependency>
      <groupId>io.dropwizard</groupId>
      <artifactId>dropwizard-auth</artifactId>
      <version>${dropwizard.version}</version>
    </dependency>   

Representationクラス

ただのドメインクラスです。

public class User {
    private final String name;

    public User(String name) {
        this.name = name;
    }

    public String getName() {
        return name;
    }
}

Authenticator

認証用のインターフェイスAuthenticatorを実装します。
認証OKの場合にOptional.of(p)、NGの場合はOptional.absent()を返します。
ここで引数になっているBasicCredentialsはDropwizardのBasic認証用のクラスになります。
このサンプルの場合は、user/passでbasic認証が通ります。

ExampleAuthenticator.java
public class ExampleAuthenticator implements
        Authenticator<BasicCredentials, User> {
    @Override
    public Optional<User> authenticate(BasicCredentials credentials)
            throws AuthenticationException {
        if ("user".equals(credentials.getUsername())
                && "pass".equals(credentials.getPassword())) {
            return Optional.of(new User("ko2ic " + credentials.getUsername()));
        }
        return Optional.absent();
    }
}

Resourceクラス

メソッドの引数に@Authを付けることで認証対象のメソッドになり、Authenticator#authenticate()の戻り値が渡されます。

ProtectedResource.java
@Path("/protected")
@Produces(MediaType.TEXT_PLAIN)
public class ProtectedResource {
    @GET
    public String showSecret(@Auth User user) {
        return String.format("Hey there, %s. You know the secret!",
                user.getName());
    }
}

Applicationクラス

HelloWorldApplication.java
    @Override
    public void run(HelloWorldConfiguration configuration,
            Environment environment) throws ClassNotFoundException {
            ・・・
            environment.jersey().register(
                new BasicAuthProvider<>(new ExampleAuthenticator(),
                        "SUPER SECRET STUFF"));
            environment.jersey().register(new ProtectedResource());
            ・・・
    }

動作確認

$ curl -u user:pass http://localhost:8080/protected
Hey there, ko2ic user. You know the secret!
34
34
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
34
34