我正在使用一種模式,其中實現接口的具體ViewModel被傳遞給存儲庫,然後該存儲庫填充ViewModel對象,但僅使用接口。這使得存儲庫稍重一些,但允許存儲庫在不同情況下重用。例如,具體實現可以是MVC ViewModel,或者它可以是實現接口的asp.net Page,其中每個proeprty的set訪問器實際上將值放入GUI中,例如文本框。接口的實現作爲映射並消除了複製的額外步驟。在廣泛使用AutoMapper並且現在暴露於這種模式之後,我更喜歡這一點。通過接口/工廠填充集合?
public interface IPerson
{
int Id{set};
string Name{set};
string Address{set};
}
public class PersonRepository
{
GetPerson(int id, IPerson person)
{
//query...
person.Id = result.Id;
person.Name = result.Name;
person.Address = result.Address;
}
}
//...controller action
PersonViewModel person = new PersonViewModel();
rep.GetPerson(5, person);
雖然這裏有棘手的部分。有時ViewModel需要一個項目集合,可以是索引頁面,也可以是下拉菜單,或者顯示一組嵌套的子對象。存儲庫不能實例化一個接口,所以我們提供它是一個工廠。與協方差一段時間戰鬥,我放棄了暴露任何類型的集合,並結束了與這兩個創建並添加收藏項目的方法:
public interface IPerson
{
//...
IJobRole CreateAndAddJobRole();
}
public class PersonViewModel:IPerson
{
//collection not part of the interface
ICollection<JobRoles> JobRoles {get;set;} //= new List<JobRoles> in constructor
public CreateAndAddJobRole()
{
role = new JobRole();
JobRoles.Add(role);
return role;
}
}
public class PersonRepository
{
GetPerson(int id, IPerson person)
{
//...
foreach(var result...)
{
IJobRole role = person.CreateAndAddJobRole();
role.SomeProperty = //...
}
}
}
顯然,我可能有一個處理的工作角色倉庫實際上是填充集合的人。我可能實際上有更多的粒度接口,以便不同的存儲庫負責填充他們處理的數據。 ViewModel只會實現多個接口。也就是說,我意識到還有改進的餘地,但我特意在這裏,因爲我沒有處理收集問題的好主意。
這種設計的一個好處是沒有可能被倉庫濫用的集合。從來沒有猜測誰是負責實例化集合本身,誰負責它,或者如果你只是一個getter,存儲庫可以獲取集合並以無效的方式修改它。我認爲這些將是罕見的事件,因爲球隊會知道這種模式,但總是很好,根本沒有陷阱,而不是在那裏有每個人都必須記住不要插手的陷阱。
事實上,感覺有點不舒服。
如何設計/展示具體類型被實例化並添加到集合中的能力,當這樣做的方法只知道接口時?
是'IPerson()其中TJob:IJobRole'完全可行嗎? –
Bobson
這是可能的,我想,但我很好奇你要去那裏。這是否會使IPerson可以爲該集合聲明一個具體的類型,即'new TJob()'? (花了我幾分鐘)如果是這樣,這很有意義,但可能會混淆ViewModel上的大量集合,因爲這可能與IPerson類似。也許可以通過讓其他倉庫負責他們自己的類型來解決(例如IJobRole)。給我另一個想法。 –
AaronLS
非常。我會把它充實成一個完整的答案。 – Bobson