Отношение один ко многим

Данное руководство устарело. Актуальное руководство: Руководство по Entity Framework Core 7

Последнее обновление: 17.11.2020

Связь один-ко-многим (one-to-many) представляет ситуацию, когда одна модель хранит ссылку на один объект другой модели, а вторая модель может ссылаться на коллекцию объектов первой модели. Например, в одной компании может работать несколько сотрудников, а каждый сотрудник в свою очередь может официально работать только в одной компании:

public class Company
{
    public int Id { get; set; }
    public string Name { get; set; }
    public List<User> Users { get; set; } = new List<User>(); // сотрудники компании
}

public class User
{
    public int Id { get; set; }
    public string Name { get; set; }

    public int CompanyId { get; set; }
    public Company Company { get; set; }  // компания пользователя
}

public class ApplicationContext : DbContext
{
    public DbSet<Company> Companies { get; set; }
    public DbSet<User> Users { get; set; }
    protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
    {
        optionsBuilder.UseSqlServer(@"Server=(localdb)\mssqllocaldb;Database=relationsdb;Trusted_Connection=True;");
    }
}

Добавление данных:

using (ApplicationContext db = new ApplicationContext())
{
	// пересоздадим базу данных
	db.Database.EnsureDeleted();
	db.Database.EnsureCreated();
	
    // создание и добавление моделей
    Company microsoft = new Company { Name = "Microsoft" };
    Company google = new Company { Name = "Google" };
    db.Companies.AddRange(microsoft, google);

    User tom = new User { Name = "Tom", Company = microsoft };
    User bob = new User { Name = "Bob", Company = microsoft };
    User alice = new User { Name = "Alice", Company = google };
    db.Users.AddRange(tom, bob, alice);
    db.SaveChanges();
}

Получение данных:

using (ApplicationContext db = new ApplicationContext())
{
    // вывод пользователей
    var users = db.Users.Include(u => u.Company).ToList();
    foreach (User user in users)
        Console.WriteLine($"{user.Name} - {user.Company?.Name}");

    // вывод компаний
	var companies = db.Companies.Include(c => c.Users).ToList();
    foreach (Company comp in companies)
    {
        Console.WriteLine($"\n Компания: {comp.Name}");
        foreach (User user in comp.Users)
        {
            Console.WriteLine($"{user.Name}");
        }
    }
}

Редактирование:

using (ApplicationContext db = new ApplicationContext())
{
	// изменение имени пользователя
    User user1 = db.Users.FirstOrDefault(p => p.Name == "Tom");
    if (user1!=null)
    {
        user1.Name = "Tomek";
        db.SaveChanges();
    }
	// изменение названия компании
    Company comp = db.Companies.FirstOrDefault(p => p.Name == "Google");
    if (comp != null)
    {
        comp.Name = "Alphabet";
        db.SaveChanges();
    }
                
    // смена компании сотрудника
    User user2 = db.Users.FirstOrDefault(p => p.Name == "Bob");
    if (user2 != null && comp!=null)
    {
        user2.Company = comp;
        db.SaveChanges();
    }
}

Удаление:

using (ApplicationContext db = new ApplicationContext())
{
    User user1 = db.Users.FirstOrDefault(p => p.Name == "Bob");
    if (user1!=null)
    {
        db.Users.Remove(user1);
        db.SaveChanges();
    }

    Company comp = db.Companies.FirstOrDefault();
    if (comp != null)
    {
        db.Companies.Remove(comp);
        db.SaveChanges();
    }
}

Следует учитывать, что если зависимая сущность (в данном случае User) требует обязательного наличия главной сущности (в данном случае Company), то на уровне базы данных при удалении главной сущности с помощью каскадного удаления будут удалены и связанные с ней зависимые сущности. Так, в данном случае для объекта User установлено обязательное наличие объекта Company:

public int CompanyId { get; set; }
public Company Company { get; set; }  // компания пользователя

Соответственно при удалении компании будут удалены и все связанные с ней пользователи.

Помощь сайту
Юмани:
410011174743222
Перевод на карту
Номер карты:
4048415020898850