简体   繁体   English

MCV3实体框架4代码优先:将子对象添加到数据库

[英]MCV3 Entity Framework 4 Code First: Adding Sub Objects to the db

I am trying to teach my self MVC3 and EF4 using code first and the DbContext generator, so forgive me if this is a silly question. 我试图首先使用代码和DbContext生成器来教我自己的MVC3和EF4,所以如果这是一个愚蠢的问题,请原谅我。

Basically I have a user class, and an email class; 基本上我有一个用户类和一个电子邮件类; this is because i want each user to be able to have multiple email addresses. 这是因为我希望每个用户都能拥有多个电子邮件地址。 the classes are set up like this: 这些类的设置如下:

public class User
{
    [Key]    
    public int Id { get; set; }    
    public string User_Name { get; set; }
    public string Password { get; set; }
    public string First_Name { get; set; }
    public string Last_Name { get; set; }

    public virtual ICollection<Email> Emails { get; set; }
}

public class Email
{
    [Key]
    public int Id { get; set; }
    public string Address { get; set; }

    public User User { get; set; }        
}

I am happily manipulating the user class using the CRUD methods build by MVC3 and inserting users programmatically to "seed" the db with test data, the latter i am doing like so by overriding the Seed method in the DropCreateDatabaseAlways class like so: 我很高兴使用MVC3构建的CRUD方法操作用户类,并以编程方式插入用户以使用测试数据“播种”db,后者我这样做是通过重写DropCreateDatabaseAlways类中的Seed方法,如下DropCreateDatabaseAlways

public class dbInitializer : DropCreateDatabaseAlways<UserContext>
{
    protected override void Seed(UserContext context)
    {
        var Users = new List<User>
        {
            new User {  User_Name = "uname",
                        Password = "pword",
                        First_Name = "fname",
                        Last_Name = "sname",
            }
        };

        Users.ForEach(u => context.Users.Add(u));
    }
}

Now i would also like to add so email addresses, and because of the way i set up my classes code first obviously realises that each user can have multiple email addresses and each email addresses can belong only to one user because when creating a new user or email object the intellisense (VS10) presents me with Emails and User properties that are not actually part of either class. 现在我还想添加这样的电子邮件地址,并且由于我设置类代码的方式首先明显地意识到每个用户可以有多个电子邮件地址,并且每个电子邮件地址只能属于一个用户,因为在创建新用户时或电子邮件对象intellisense(VS10)向我提供了实际上不属于任何一个类的EmailsUser属性。

My question is this: How do i add an email address to a user as its created, and how do i add an email address to a user that has been created previously? 我的问题是:如何在创建时向用户添加电子邮件地址,以及如何向之前创建的用户添加电子邮件地址?

Add emails to user as it is created: 在创建用户时添加电子邮件:

protected override void Seed(UserContext context)
{
    var Users = new List<User>
    {
        new User {  User_Name = "uname",
                    Password = "pword",
                    First_Name = "fname",
                    Last_Name = "sname",
                    Emails = new[]
                    {
                        new Email { Address = "email1@domain.tld" },
                        new Email { Address = "email2@domain.tld" },
                    }
        }
    };

    Users.ForEach(u => context.Users.Add(u));
}

To add an email to a previously created user, you first need a reference to the user: 要向以前创建的用户添加电子邮件,首先需要对用户的引用:

var user = Users.First();
user.Emails.Add(new Email { Address = "email3@domain.tld" });

Reply to comments: 回复评论:

new[] is shorthand for new Email[] (new Email array). new[]new Email[] (新电子邮件阵列)的简写。

Technically Eranga's answer is a little more flexible. 从技术上讲,Eranga的答案更灵活一些。 In mine, since arrays are fixed length, you can't add an Email to the Emails collection after it has been initialized as an array. 在我的数据库中,由于数组是固定长度的,因此在将数据库初始化为数组后,无法将Email添加到Emails集合中。 You would need to either use List<Email> as in Eranga's answer, or convert to a list like so before invoking .Add() : 您需要在Eranga的答案中使用List<Email> ,或者在调用.Add()之前转换为类似的列表:

user.Emails.ToList().Add(new Email { Address = "email3@domain.tld" });

I prefer arrays when possible because they are easier to type, less verbose in the code, and I generally add everything in the object initializer, so I don't need to add it again later. 我尽可能喜欢数组,因为它们更容易键入,在代码中更简洁,我通常在对象初始化程序中添加所有内容,因此我不需要在以后再添加它。

That said, after you save the User and get it back out of the db, your Emails collection property will not be a fixed-length array, and can be added to without having to invoke .ToList() . 也就是说,在保存User并将其从数据库中取回之后,您的Emails集合属性将不是固定长度的数组,并且可以添加到其中而无需调用.ToList()

Adding Email to a new user 将电子邮件添加到新用户

protected override void Seed(UserContext context)
{
    var Users = new List<User>
    {
        new User {  User_Name = "uname",
                    Password = "pword",
                    First_Name = "fname",
                    Last_Name = "sname",
                    Emails = new List<Email> { new Email { Addess = "foo@bar.baz" } }
        }
    };

    Users.ForEach(u => context.Users.Add(u));
}

Similarly for existing user. 对于现有用户也是如此

user.Emails.Add(new Email { Addess = "foo@bar.baz" });

user.Emails.Add will issue a database request to load the Email collection (ie. Lazy Loading). user.Emails.Add将发出数据库请求以加载电子邮件集合(即延迟加载)。 Alternate way to do this is 替代方法是这样做

var email = new Email { Addess = "foo@bar.baz", User = user };
context.Emails.Add(email);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM