如果我有一个可以有多个子文件的父文档,例如Store
可以有多个Product
,那么有更简单的方法可以在{{Product.Id
中存储Store
列表1}}文件?
目前我只是首先存储Product
个对象,然后循环遍历它们以获取Product.Id
属性的Store.ProductIds
。
商品
class Store
{
public string Id { get; set; }
public string Name { get; set; }
public IList<string> ProductIds { get; set; }
[JsonIgnore]
public IList<Product> Products { get; set; }
}
产品
class Product
{
public string Id { get; set; }
public string Name { get; set; }
}
当前工作保存方法
var store = new Store()
{
Name = "Walmart",
Products = new List<Product>
{
new Product {Name = "Ball"},
new Product {Name = "Bat"}
}
};
using (var session = DocumentStore.OpenSession())
{
foreach (var product in store.Products)
{
session.Store(product);
}
session.SaveChanges();
var list = new List<string>();
foreach (var product in store.Products)
{
list.Add(product.Id);
}
store.ProductIds = list;
session.Store(store);
session.SaveChanges();
}
答案 0 :(得分:2)
要回答您的具体问题 - 您可以使用代码简化两件事:
您可以删除第一个session.SaveChanges();
当您在产品上调用.Store()
时,系统会创建产品ID。
您可以使用某些linq收集产品ID以将其折叠为一行:
store.ProductIds = store.Products.Select(x=> x.Id).ToList();
你仍然有相同的通用方法 - 它只是简化了一些代码。
此方法将工作,但确实意识到您只是为了方便而将产品放入商店。 [JsonIgnore]
在这里可以,但它只对序列化有帮助 - 而不是反序列化。换句话说,在加载商店时,只会填充ProductIds列表。您必须单独加载它们(可能使用.Include()
)
就个人而言,我会将Products
列表完全从Store对象中取出。其他关系产品如Entity Framework和NHibernate为此目的使用虚拟成员和代理类,但它在RavenDB中没什么意义。您班级的消费者不会知道该属性被忽略,因此他们可能会误解其用法。当我看到Products
属性时,我的期望是每个Product
完全嵌入到文档中 - 在这种情况下,您不需要单独的ProductIds
列表。让他们两个被忽略只会导致混乱。
针对您提出的设计的另一个论点是,它隐含地使每个商店中的每件商品都独一无二。这是因为您正在使用商店创建产品,然后单独添加每个产品。如果确实所有产品都是独一无二的(不仅仅是“球”,而是“这个特定的球”),那么您可以在没有[JsonIgnore]
或ProductIds
列表的情况下嵌入产品,并且Product
不需要作为单独的文件存在。在更可能的情况下,产品不是唯一的(多个商店可以销售蝙蝠和球),那么你有两个选择:
class Store
{
public string Id { get; set; }
public string Name { get; set; }
public IList<string> ProductIds { get; set; }
}
class Store
{
public string Id { get; set; }
public string Name { get; set; }
public IList<Product> Products { get; set; }
}
Product
在任何一种情况下都会出现在自己的文档中 - 第二种情况将用作denormalized reference,这样您就可以在不加载产品的情况下获取产品名称。这是可以接受的,但如果产品名称可以更改,那么您需要进行大量修补。
对不起,如果没有干净的“这样做”答案。 Raven有很多选择,有时这种或那种方式更好,取决于你可能使用它的所有不同方式。我个人 - 我会保留ProductIds列表。您始终可以index the related document提取产品名称以进行查询。