システム開発で思うところ

Javaで主にシステム開発をしながら思うところをツラツラを綴る。主に自分向けのメモ。EE関連の情報が少なく自分自身がそういう情報があったら良いなぁということで他の人の参考になれば幸い

【考察】FormとEntityの類似点

Formに関して、アレコレ考えていると、Entityとの類似点が多いように思えてきた。

つらつらと思いついたことをメモ。

Identification

画面のどこの何、という意味で「ここのこのフィールド」という一意な場所が必要。

姓と名が同じ値だった場合(そんな名前の人はいないとは思うけど)、入れ替えても良いかというと それはダメ、みたいな話。

Mutable

identificationとほぼ同じこと。

画面項目として重要なのは同値性ではなくて一意性。

値については書き換えが可能。

実装面においても、JSFの場合、Formに相当するフィールドはmutable(プロパティにset)。

Persistent

厳密な意味でのPersistent(永続化)とは違うけど、クライアント(ブラウザ)上のメモリに保持されているという意味では 永続化しているともいえる。

DBはストレージに存在しつづける限りは生存するのと同じように、Formもブラウザを閉じるまでは生存しているという見方もできなくはない。

Aggregate

Formの AggregateのRoot Entityに相当するものが、画面。

考察(1)

考えるきっかけは、Formにおけるエラーツールチップの実装を考えている中で、対象セル(フォーム)の位置を特定するための情報を持っておかないといけないなぁ、と考えたところから。

フォームにおけるidentificationをどうしたものかな、と考えていて なんとなく 類似点を感じた。

ただ、全く同じかというと それは違って IDの採番はFormとEntityでは異なる。そして、それが現状悩み中のところ。

EntityはTable単位でIDが一意であれば問題ないけど、Formの場合は集約(画面)単位で一意じゃないといけない。 *1

なので、全く同じというわけでもない。

検証は、クライアント側だけではなく、ビジネスロジックによる検証(既存データの存在確認など)もあって、その結果をイイ感じに集約して 最終的にクライアントの入力フォームへ反映させる という仕組みが見いだせず。

クライアントだけならUIComponent使ったら 出来る方法が無いわけではないみたいだけれど、そのためにはxhtmlに記述がいるみたいで(ComponentIdとValidationの対象を明示するため)、個人的には そういうxhtmlに何かを記述するという やり方も出来れば避けたい。

単項目単位でDBへアクセスして検証する、というのもありといえば ありかもしれないけれど、やはり N+1問題が絶対に発生する方式というのは 個人的に許容したくない。

以前、それっぽいものを自作はしたけれど、結局 Formの情報をビジネスロジックまで蜜結合させた実現方式であったため(フォームのプロパティ名をEntity(またはDxo)と一致させる)、今から振り返ると かなり良くない。

単純なCRUDだったら、それでも良いかもしれないけれど、単純なCRUDにのみ限定されない仕組みを考えたい。

また、単項目の関連制御だけではなくて、一覧のような繰り返しも 適用範囲にしたい*2

現状、落としどころが見いだせておらず悩みは尽きず。

なーんか、パチッとくるアイディアが閃かないものか。。

考察(2)

クライアントサイドのモデルとは何か 後編 ~ 単方向データフローと参照透過性 - mizchi's blog

正直なところ、ちゃんと理解はできていないけど 何かヒントになりそうな気がする。

部分更新をするんじゃなくて、FormのRootへのCRUDとなるactionを通じてのみ 詳細への更新をすれば 良いのかも?

つまり常にRootから作り直すイメージ。

これくらい割り切ったら、最悪 FormIDも毎回 採番しなおしても問題なさそうかも。

変に「前回のIDとの関連付け」を やろうとしているから悩みが深くなっていたような気がする。

ただ、そうするとクライアント側でJacaScriptで表示順を変えたり、動的に要素を追加したりしたら どうなるかな?

JSFだと、そのあたりのズレが地味に困ったりするんだよなぁ。

ただそれもSubmitでAggregate全体を更新すれば大丈夫かな?

手を動かしつつ、更に色々考えてみよう。

*1:Entityもシステム全体でIDをUUIDにするとか、すれば それは一意になるかもしれないけど、普通 そういうことはしないように思うので、できる と やる は別で考えるべき

*2:これも過去の実装では、なんとか実現していたけれど、結局 方式は上述の「プロパティ名を一致させる」という方式なのでダメ