Java Advent Calender 2012 4日目の記事です。
Project LombokはJavaBeanのGetter/Setterのようなboilerplateをなくすためのアノテーション群です。
クラスやフォールドにアノテーションを付けるだけでGetter/Setterやコンストラクタ、toStirng、hashCode/equalsといったお決まりコードを省略できます(自動でバイトコードを生成します)。 サポートしているアノテーションはこんな感じ。
@Data
をつけると、getter/setter/toString/hashCodeやらなんやら全部ついてきます。
package com.example.lombok.domain;
import java.io.Serializable;
import java.util.Date;
import lombok.Data;
@Data
public class Employee implements Serializable {
private static final long serialVersionUID = 1L;
private Long id;
private String firstName;
private String lastName;
private String dept;
private String gender;
private Date birthDay;
}
もちろんこれまでもEclipseで自動生成することはできていましたが、自動生成にくらべてのメリットはフィールドの変更に強いということです。フィールド名や型が変わってもGetter/Setterを直す手間がかかりません。
インストール
基本的にはlombokのjarをクラスパスに追加して、アノテーションを付けるだけで良いのですが、IDEと連携するには少し設定が必要です。
http://projectlombok.org/download.htmlからjarをダウンロードしてダブルクリックします。インストーラーが自動でIDEの場所を検出し、設定ファイルを書き換えてくれます。
MacのSTSの場合springsource/sts-3.1.0.RELEASE/STS.app/Contents/MacOS/
以下にlombok.jarがコピーされ、STS.iniに
-javaagent:lombok.jar
-Xbootclasspath/a:lombok.jar
が追加されていました。
IDEを再起動すれば、@Data
をつけるとアウトラインに各種Getter/Setterが出現します。
サンプル
IDEサポートが完了すればあとはプロジェクト側でlombokのjarを追加すればOKです。Mavenの場合はpom.xmlに以下を追加
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>0.11.6</version>
<scope>provided</scope>
</dependency>
@Dataの例
JavaBean
package com.example.lombok.domain;
import java.io.Serializable;
import java.util.Date;
import lombok.Data;
@Data
public class Employee implements Serializable {
private static final long serialVersionUID = 1L;
private Long id;
private String firstName;
private String lastName;
private String dept;
private String gender;
private Date birthDay;
}
JUnit
package com.example.lombok.domain;
import static org.junit.Assert.*;
import static org.hamcrest.CoreMatchers.*;
import java.util.Date;
import org.junit.Test;
public class EmployeeTest {
@Test
public void testToString() {
Employee e = new Employee();
e.setId(1L);
e.setFirstName("Toshiaki");
e.setLastName("Maki");
e.setDept("R&D");
e.setGender("male");
e.setBirthDay(new Date(0));
assertThat(e.getId(), is(1L));
assertThat(e.getFirstName(), is("Toshiaki"));
assertThat(e.getLastName(), is("Maki"));
assertThat(e.getDept(), is("R&D"));
assertThat(e.getGender(), is("male"));
assertThat(e.getBirthDay(), is(new Date(0)));
assertThat(
e.toString(),
is("Employee(id=1, firstName=Toshiaki, lastName=Maki, dept=R&D,"
+ " gender=male, birthDay=Thu Jan 01 09:00:00 JST 1970)"));
}
}
ToStringの内容を絞る例
JavaBean
package com.example.lombok.domain;
import java.io.Serializable;
import java.util.Date;
import lombok.Getter;
import lombok.Setter;
import lombok.ToString;
@Getter
@Setter
@ToString(of = { "firstName", "lastName" })
public class Employee2 implements Serializable {
private static final long serialVersionUID = 1L;
private Long id;
private String firstName;
private String lastName;
private String dept;
private String gender;
private Date birthDay;
}
JUnit
package com.example.lombok.domain;
import static org.hamcrest.CoreMatchers.is;
import static org.junit.Assert.*;
import java.util.Date;
import org.junit.Test;
public class Employee2Test {
@Test
public void testToString() {
Employee2 e = new Employee2();
e.setId(1L);
e.setFirstName("Toshiaki");
e.setLastName("Maki");
e.setDept("R&D");
e.setGender("male");
e.setBirthDay(new Date(0));
assertThat(e.getId(), is(1L));
assertThat(e.getFirstName(), is("Toshiaki"));
assertThat(e.getLastName(), is("Maki"));
assertThat(e.getDept(), is("R&D"));
assertThat(e.getGender(), is("male"));
assertThat(e.getBirthDay(), is(new Date(0)));
assertThat(e.toString(),
is("Employee2(firstName=Toshiaki, lastName=Maki)"));
}
}
Immutableな例
JavaBean?
package com.example.lombok.domain;
import java.io.Serializable;
import java.util.Date;
import lombok.AllArgsConstructor;
import lombok.Getter;
import lombok.ToString;
@Getter
@AllArgsConstructor
@ToString
public class Employee3 implements Serializable {
private static final long serialVersionUID = 1L;
final private Long id;
final private String firstName;
final private String lastName;
final private String dept;
final private String gender;
final private Date birthDay;
}
JUnit
package com.example.lombok.domain;
import static org.junit.Assert.*;
import static org.hamcrest.CoreMatchers.*;
import java.util.Date;
import org.junit.Test;
public class Employee3Test {
@Test
public void testToString() {
Employee3 e = new Employee3(1L, "Toshiaki", "Maki", "R&D", "male", new Date(0));
assertThat(e.getId(), is(1L));
assertThat(e.getFirstName(), is("Toshiaki"));
assertThat(e.getLastName(), is("Maki"));
assertThat(e.getDept(), is("R&D"));
assertThat(e.getGender(), is("male"));
assertThat(e.getBirthDay(), is(new Date(0)));
assertThat(
e.toString(),
is("Employee3(id=1, firstName=Toshiaki, lastName=Maki, dept=R&D,"
+ " gender=male, birthDay=Thu Jan 01 09:00:00 JST 1970)"));
}
}
ちなみに実行するだけならIDEサポート入りません。
package com.example.lombok.app;
import java.util.Date;
import com.example.lombok.domain.Employee;
public class Main {
public static void main(String[] args) {
Employee e = new Employee();
e.setId(1L);
e.setFirstName("Toshiaki");
e.setLastName("Maki");
e.setDept("R&D");
e.setGender("male");
e.setBirthDay(new Date(0));
System.out.println(e);
}
}
実行
$ mvn exec:java -Dexec.mainClass=com.example.lombok.app.Main
Employee(id=1, firstName=Toshiaki, lastName=Maki, dept=R&D, gender=male, birthDay=Thu Jan 01 09:00:00 JST 1970)
明日は5日目@nabedgeさんの番です!