Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
396 views
in Technique[技术] by (71.8m points)

domain driven design - What are the benefits of Persistence Ignorance?

I am a newbie in the DDD+TDD World. But I have been in programming for almost 9 years.

Can someone please explain me the benefits of persistance ignornace ? Typical nHibernate application just pushes the dependency between class and database to mapping files.

If I change Class files or Database, I have to change the mapping files. So isn't it just pushing the dependency by adding one more abstraction layer? In my opinion so far I don't think it's anything revolutionary. But I am not sure if I am missing something.

Finally How can I test the mapping files ? There are chances bugs will appear from mapping files, how can I test them?

Question&Answers:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

Let me explain this with an example. Lets assume your are implementing an application using a classical SQL approach. You open recordsets, change data and commit it.

Pseudo code:

trx = connection.CreateTransaction();
query = connection.CreateQuery("Select * from Employee where id = empid");
resultset = query.Run();
resultset.SetValue("Address_Street", "Bahnhofstrasse");
resultset.SetValue("Address_City", "Zürich");
trx.Commit();

With NHibernate it would look something like this:

emp = session.Get<Employee>(empid);

// persistence ignorant 'logic'
emp.Address.Street = "Bahnhofstrasse";
emp.Address.City = "Zürich";

session.Commit();

Persistence Ignorance means that the business logic itself doesn't know about persistence. Or in other words, persistence is separated from logic. This makes it much more reusable.

Move 'logic' to a reusable method:

void MoveToZuerichBahnhofstrasse(Employee emp)
{
  // doesn't have anything to do with persistence
  emp.Address.Street = "Bahnhofstrasse";
  emp.Address.City = "Zürich";
}

Try to write such a method using resultsets and you know what persistence ignorance is.

If your are not convinced, see how simple a unit test would be, because there aren't any dependencies to persistence related stuff:

Employee emp = new Employee();
MovingService.MoveToZuerichBahnhofstreasse(emp);
Assert.AreEqual("Bahnhofstrasse", emp.Address.Street);
Assert.AreEqual("Zürich", emp.Address.City);

DDD is something different. There you build up your domain model first (class model) and create the database design according to it. With NH this is very simple, because - thanks to persistence ignorance - you can write and unit test the model and logic before having a (definitive) database model.


Testing: We are testing mappings by creating an instance of the entity, storing it to the database, getting it back and compare it. This is done automatically with lots of reflection. But you don't need to go so far. most of the typical errors show up when trying to store an entity.

You could do the same with queries. Complex queries deserve a test. It's most interesting if the query gets compiled at all. You don't even need any data for this.

For database integration tests, we are using Sqlite. This is pretty fast. NH produces the in-memory database on the fly using SchemaExport (before each test).


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...