Movatterモバイル変換


[0]ホーム

URL:


LoginSignup
158

Go to list of users who liked

121

Share on X(Twitter)

Share on Facebook

Add to Hatena Bookmark

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Domaの開発で大切にしている10のこと

Last updated atPosted at 2016-07-09
Page 1 of 42

自己紹介


Domaとは?


Domaの歴史

  • 2009/05: 開発開始
  • 2009/02: v1.0.0リリース (Java 6対応)
  • 2014/07: v2.0.0リリース (Java 8対応)
  • 2024/09: v3.0.0リリース(Java 17対応)
  • 2025/03: v3.6.0リリース(最新版)

1. 動かさないとわからないを減らす

  • にできるだけチェック

  • Javaコードに対して
    • 例:アノテーションの存在チェック
apt_error_1.png
  • SQLファイルに対して
    • 例:パラメータの存在チェック
apt_error_2.png
select*fromEMPwhereID=/*identity*/100

  • SQL内の式コメントに対して
    • 例: 型チェック
select*fromEMPwhereID=/*id.hoge*/100
  • コンパイル時にidInteger 型だとわかる
    • hoge への参照はコンパイルエラー

2. コードの信頼性を高める

  • SQLテンプレートでSQLインジェクションを防ぐ
select*fromempwhrerename=/* name */'taro'
  • PreparedStatementへ変換して実行するので安全
select*fromempwhrerename=?

  • リソース(Connectionとか)を自動で解放する
// トランザクション内で検索と更新をするコードtm.required(()->{Employeeemployee=dao.selectById(1);employee.setName("hoge");employee.setJobType(JobType.PRESIDENT);dao.update(employee);});

3. シンプルさを重視する

  • 例えばCriteria APIは提供しない
  • Criteria APIはシンプルさを損なう
EntityManager em = ...;CriteriaBuilder cb = em.getCriteriaBuilder();CriteriaQuery<Pet> cq = cb.createQuery(Pet.class);Root<Pet> pet = cq.from(Pet.class);cq.select(pet);TypedQuery<Pet> q = em.createQuery(cq);List<Pet> allPets = q.getResultList();

  • 利点
    • 型安全で組み立てられる
      • 文字列のタイポが発生しない
  • 欠点
    • 学習コストが高い
    • いつCriteria APIを使うべきかで迷う
      • 迷う ≒ シンプルさの欠如

4. SQLの発行場所とタイミングを明確にする

  • SQLの発行はDAOインタフェースの呼び出しで
    • 遅延ロードはサポートしない
// ここでSQLを発行するならOKDeptdept=dao.selectById(1);// ここでSQLを発行するのはNG!List<Employee>employees=dept.getEmployees();

  • キャッシュはしない
    • いつも必ずSQLを発行
    • 必要ならアプリレイヤで
// SQL発行Deptdept=dao.selectById(1);// SQL発行Deptdept=dao.selectById(1);

5. SQLの完全性を重視する

  • SQLの断片化を促進させる機能は持たない
-- こんな機能はありません!select/*%include common_select_list.sql*/fromemployeewhere/*%include common_search_condition.sql*/
  • 過剰な共通化は見通しを悪くする

6. JDBCでできることを制限しない

  • 例えばストアドプロシージャーの呼び出し
@Procedurevoidexecute(@InIntegerid,@InOutReference<BigDecimal>salary);

  • 結果セットを複数個返すようなストアドプロシージャー
@Procedurevoidexecute(@ResultSetList<Employee>employees,@ResultSetList<Department>departments,@InIntegeremployee_id,@InIntegerdepartment_id);

7. 逃げ道を用意する

  • いざという時にJDBCを自由に使えるのが重要
    • かつ呼び出し元に影響を与えないものポイント
@DaopublicinterfaceEmpDao{defaultEmpselect(){Configconfig=Config.get(this);DataSourceds=config.getDataSource();...// 自由にJDBCの機能が使える}}

  • Domaを捨てる場合にも使える
    • 他のDBアクセスライブラリへの移行する場合
  • Javaのインタフェースを使っていることの利点

8. 様々な環境で長期的に使えるようにする

  • JDK/JRE以外には依存しない
    • 依存ライブラリがJavaのバージョンに追随しないリスクを避ける
    • 依存ライブラリが他のライブラリと競合するリスクを避ける

  • 実行環境に依存しがちなところはインタフェースで実装を差し替えられるように
    • 例えば、クラスローディング周り
      • Play Framework v1
      • Spring Boot DevTools

  • バイトコードをハックしない
    • 同じ注釈処理をするライブラリでもLombokとは違うところ
    • Domaは将来のJavaでもほぼそのまま動作するはず

9. 変化(トレンド)に追随する

  • Java 8対応
    • Stream
    • Optional
    • JSR310 Date & Time API

  • Kotlin対応(実験的)
@Entity(immutable=true)data classPerson(@Id@GeneratedValue(strategy=GenerationType.IDENTITY)valid:Int?=null,valname:String,valage:Int,@Versionvalversion:Int=-1)

10. 利用者の声を聞く

  • 自分が考えた機能は2010年時点でほぼ実装完了
    • それ以降の機能追加は利用者の意見が中心
http://d.hatena.ne.jp/taedium/20101002/p2
  • 利用者の声は宝の山
    • そんな使い方があったとは!という良い意味での発見が多い
    • 7年も続けられている理由の1つ

Twitterのつぶやき

DomaのEntity annotation出指定する引数、親クラスで指定しても効かず、エンティティの子クラスで改めて指定する必要あるんだね・・・。親クラスだけNamingType必要で、子クラスのすべてのカラム名は名前を明示的に指定するからいらないと思ったけどダメだったお

— Ktz (@ktz_alias)2013年9月3日

Twitterでメンション

@nakamura_to すいません質問させてください。DomaのDomainオブジェクト定義で、全部のDomainにequalsやcompareToなどの委譲メソッドを定義するのは辛いので、https://t.co/poBhLF89 こんな風に抽象クラスを作ったのですが(続く)

— がくぞ (@gakuzzzz)2012年12月11日

Gitterへの書き込み

https://gitter.im/domaframework/doma?at=56dd0db91263673835717662

もちろんPull Requestも

https://github.com/domaframework/doma/pull/71

疑問や要望はいつでもWelcome

  • できるだけ応えたい
  • 面白いアイデアに発展するかも?

ぜひ使ってみてください


Domaの開発で大切にしている10のこと

  1. 動かさないとわからないを減らす
  2. コードの信頼性を高める
  3. シンプルさを重視する
  4. SQLの発行場所とタイミングを明確にする
  5. SQLの完全性を重視する
  6. JDBCでできることを制限しない
  7. 逃げ道を用意する
  8. 様々な環境で長期的に使えるようにする
  9. 変化(トレンド)に追随する
  10. 利用者の声を聞く

追記(2020年5月30日)

このスライドの中で「例えばCriteria APIは提供しない」と書きましたが、2020年5月、Doma 2にCriteria APIを導入することにしました(2.35.0で正式リリース)。

ひと言で言えば当時と状況が変わったからということになりますが、細かい理由は次のようなものです。


Criteria API導入の理由 1

  • SQLファイル内の大部分が条件分岐だらけになっているようなプロジェクトを度々見かけるが、非効率かつ保守性に難がある。そのようなケースではJavaでSQLを組み立てた方が適切である。

Criteria API導入の理由 2

  • Javaの複数のORMを併用する事例を見かけるが、個人的にはオーバーヘッドだと思うのでできるだけ1つのORMで済むようにしたい(Domaが機能不足であれば補いたい)

Criteria API導入の理由 3

  • GraalVMを使ってNative Imageにするためにはリフレクションに制約がかかるケースがある。SQLファイル内の式コメントはリフレクションに頼っているが、リフレクションを使わないで動的SQLを組み立てる手段を提供したい。

Criteria API導入の理由 4

  • コンパイル時(Annotation Processingの最中)にファイルを読むのは環境(ビルドツールやIDE)依存の部分がありハマりポイントになっている。できればこのハマりポイントを回避したい。Criteria APIが主流になればファイルを読むのは実行時だけにしてコンパイル時に読むのは止めてもいい(オプションにするなど)と思っている。

Criteria API導入の理由 5

  • Doma 1を作り始めた当時はJava 6がリリースされたばかりであり言語の制約上使いやすいCriteria APIを作ることができなかった。しかしJava 8で導入されたラムダ式を使えば使いやすいAPIを構築可能に思われた。

Criteria API導入の理由 6

  • Domaが関連をサポートしていないので使えないとか古いなどと言われるのがちょっと癪なので:smile:

追記(2025年4月12日)

Doma 3.1.0 で新しい Criteria API を導入。


参考情報

158

Go to list of users who liked

121
0

Go to list of comments

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
158

Go to list of users who liked

121

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?


[8]ページ先頭

©2009-2025 Movatter.jp