だから私はこれについて興味があります:
DataMapperは、モデルにミックスインを使用します
class Post
include DataMapper::Resource
アクティブレコードは継承を使用しますが
class Post < ActiveRecord::Base
DataMapperがそのように選択した理由(またはARが選択しなかった理由)を誰かが知っていますか?
だから私はこれについて興味があります:
DataMapperは、モデルにミックスインを使用します
class Post
include DataMapper::Resource
アクティブレコードは継承を使用しますが
class Post < ActiveRecord::Base
DataMapperがそのように選択した理由(またはARが選択しなかった理由)を誰かが知っていますか?
DM クラスではない別のクラスから継承できます。
また、DM 機能をその場でクラスに追加することもできます。これは、私が現在取り組んでいるモジュールのクラス メソッドです。
def datamapper_class
klass = self.dup
klass.send(:include, DataMapper::Resource)
klass.storage_names[:default] = @table_name
klass.property(:id, DataMapper::Types::Serial)
klass.property(:created_at, DateTime, :nullable => false)
klass.property(:updated_at, DateTime, :nullable => false)
columns_with_types { |n, t| klass.property(n, t, :field => n.to_s) }
klass
end
これにより、SAXMachine クラス (非常に軽量) を取得して、その場で Datamapper クラスに変換し、DataMappery を実行できます。オブジェクトのシングルトン クラスにすることもできます。
これにより、XML から 10 万個のオブジェクトをインポートするときにメモリ フットプリントが削減され (大量のインポートに DM は使用しません)、必要なときにだけ、より複雑なデータベース関数を混在させることができると想像するのが好きです。
DataMapperパターンは、ドメインオブジェクトモデルがスキーマから分岐できるようにするレイヤーを提供することを目的としています。ActiveRecordは、オブジェクトモデルとリレーショナルデータベース構造を統合します。
マーティンファウラーによる:
オブジェクトとリレーショナルデータベースには、データを構造化するための異なるメカニズムがあります。コレクションや継承など、オブジェクトの多くの部分は、リレーショナルデータベースには存在しません。多くのビジネスロジックを使用してオブジェクトモデルを構築する場合、これらのメカニズムを使用して、データとそれに伴う動作をより適切に整理することが重要です。そうすることで、バリアントスキーマが作成されます。つまり、オブジェクトスキーマとリレーショナルスキーマが一致していません。
それでも2つのスキーマ間でデータを転送する必要があり、このデータ転送はそれ自体が複雑になります。インメモリオブジェクトがリレーショナルデータベース構造を認識している場合、一方の変更が他方に波及する傾向があります。
データマッパーは、メモリ内のオブジェクトをデータベースから分離するソフトウェアのレイヤーです。その責任は、2つの間でデータを転送し、それらを互いに分離することです。データマッパーを使用すると、インメモリオブジェクトはデータベースが存在することさえ知る必要がありません。SQLインターフェイスコードは必要なく、データベーススキーマの知識も必要ありません。(データベーススキーマは、それを使用するオブジェクトを常に認識しません。)これはマッパー(473)の形式であるため、データマッパー自体はドメインレイヤーにも認識されません。
ActiveRecord は、データベースに裏打ちされた側面をモデル クラスの重要な機能と見なし、その動作を継承するという考え方だと思います。DataMapper は、データベースに裏打ちされていることを、クラスに追加できるクラスの側面であると見なしているように見えます。
それは私の推測です。イェフダ・カッツははっきりとあなたに言うことができました.
これは、継承と構成の選択の問題です。
クラスとオブジェクトを構築するより自然な方法であるように見えるので、私は個人的に構成を好みます。
コンポジションを使用すると、クラスに含める動作をより詳細に制御できます。継承に関しては、すべてを取得するか、何も取得しないかのいずれかです。コンポジションを使用すると、必要な動作を自由に選択できます。
ActiveRecord は実際には継承を使用するべきではなく、モデル/クラスに動作 (主に永続性) を追加するモジュールを含める必要があります。ActiveRecord は単に間違ったパラダイムを使用しています!
同じ理由で、私は MongoMapper よりも MongoId を非常に気に入っています。なぜなら、問題のドメインで意味のあるものをモデル化する方法として継承を使用する機会が開発者に残されるからです。
残念なことに、Rails コミュニティで「Ruby 継承」を本来の使用方法 (単に動作を追加するためではなく、クラス階層を定義するため) で使用している人はほとんどいません。