Настройка ключей

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

По умолчанию в качестве ключа используется свойство, которое называется Id или [имя_класса]Id. Например:

public class User
{
    public int Id { get; set; }
    //.........................
}

или

public class User
{
    public int UserId { get; set; }
    //.........................
}

Для установки свойства в качестве первичного ключа с помощью аннотаций применяется атрибут [Key]:

using System.ComponentModel.DataAnnotations;

public class User
{
	[Key]
    public int Ident { get; set; }
    public string? Name { get; set; }
}

Для конфигурации ключа с Fluent API применяется метод HasKey():

using Microsoft.EntityFrameworkCore;

public class ApplicationContext : DbContext
{
    public DbSet<User> Users { get; set; } = null!;
    public ApplicationContext()
    {
        Database.EnsureDeleted();
        Database.EnsureCreated();
    }
    protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
    {
        optionsBuilder.UseSqlite("Data Source=helloapp.db");
    }
    protected override void OnModelCreating(ModelBuilder modelBuilder)
    {
        modelBuilder.Entity<User>().HasKey(u => u.Ident);
    }
}
public class User
{
    public int Ident { get; set; }
    public string? Name { get; set; }
}

Дополнительно с помощью Fluent API можно настроить имя ограничения, которое задается для первичного ключа. Для этого применяется метод HasName():

protected override void OnModelCreating(ModelBuilder modelBuilder)
{
	modelBuilder.Entity<User>().HasKey(u => u.Ident).HasName("UsersPrimaryKey");
}

Составные ключи

С помощью Fluent API можно создать составной ключ из нескольких свойств:

public class ApplicationContext : DbContext
{
    public DbSet<User> Users { get; set; }
	public ApplicationContext()
	{
		Database.EnsureDeleted();
		Database.EnsureCreated();
	}
    protected override void OnModelCreating(ModelBuilder modelBuilder)
    {
        modelBuilder.Entity<User>().HasKey(u => new { u.PassportSeria, u.PassportNumber});
    }
	protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
    {
        optionsBuilder.UseSqlServer(@"Server=(localdb)\mssqllocaldb;Database=efbasicsappdb;Trusted_Connection=True;");
    }
}

public class User
{
    public string? PassportNumber { get; set; }
    public string? PassportSeria { get; set; }

    public string? Name { get; set; }
}

Составной ключ можно создать только с помощью Fluent API. Применение подобного ключа:

using (ApplicationContext db = new ApplicationContext())
{
    db.Users.Add(new User { PassportSeria = "1234", PassportNumber = "345678", Name="Tom" });
    db.Users.Add(new User { PassportSeria = "1234", PassportNumber = "345679", Name="Bob" });
    db.SaveChanges();

    var users = db.Users.ToList();
    foreach (var u in users)
        Console.WriteLine($"{u.Name} : {u.PassportSeria} {u.PassportNumber}");
}

На уровне базы данных в случае с SQLite будет создаваться следующая таблица:

CREATE TABLE "Users" (
	"PassportNumber"	TEXT NOT NULL,
	"PassportSeria"	TEXT NOT NULL,
	"Name"	TEXT,
	CONSTRAINT "PK_Users" PRIMARY KEY("PassportSeria","PassportNumber")
);

Альтернативные ключи

Альтернативные ключи представляют свойства, которые также, как и первичный ключ, должны иметь уникальное значение. В то же время альтернативные ключи не являются первичными. На уровне базы данных это выражается в установке для соответствующих столбцов ограничения на уникальность.

Для установки альтернативного ключа используется метод HasAlternateKey():

using Microsoft.EntityFrameworkCore;

public class ApplicationContext : DbContext
{
    public DbSet<User> Users { get; set; } = null!;
    public ApplicationContext()
    {
        Database.EnsureDeleted();
        Database.EnsureCreated();
    }
    protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
    {
        optionsBuilder.UseSqlite("Data Source=helloapp.db");
    }
    protected override void OnModelCreating(ModelBuilder modelBuilder)
    {
        modelBuilder.Entity<User>().HasAlternateKey(u => u.Passport);
    }
}

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

В данном случае свойство Passport (серия и номер паспорта) будет альтернативным ключом. Созданная таблица Users в случае SQLite будет описываться следующим SQL-скриптом:

CREATE TABLE "Users" (
	"Id"	INTEGER NOT NULL,
	"Name"	TEXT,
	"Passport"	TEXT NOT NULL,
	CONSTRAINT "AK_Users_Passport" UNIQUE("Passport"),
	CONSTRAINT "PK_Users" PRIMARY KEY("Id" AUTOINCREMENT)
);

Альтернативные ключи также могут быть составными:

using Microsoft.EntityFrameworkCore;

public class ApplicationContext : DbContext
{
    public DbSet<User> Users { get; set; } = null!;
    public ApplicationContext()
    {
        Database.EnsureDeleted();
        Database.EnsureCreated();
    }
    protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
    {
        optionsBuilder.UseSqlite("Data Source=helloapp.db");
    }
    protected override void OnModelCreating(ModelBuilder modelBuilder)
    {
        modelBuilder.Entity<User>().HasAlternateKey(u => new { u.Passport, u.PhoneNumber });
    }
}

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

В этом случае в SQLite будет создаваться следующая таблица:

CREATE TABLE "Users" (
	"Id"	INTEGER NOT NULL,
	"Name"	TEXT,
	"Passport"	TEXT NOT NULL,
	"PhoneNumber"	TEXT NOT NULL,
	CONSTRAINT "AK_Users_Passport_PhoneNumber" UNIQUE("Passport","PhoneNumber"),
	CONSTRAINT "PK_Users" PRIMARY KEY("Id" AUTOINCREMENT)
);
Помощь сайту
Юмани:
410011174743222
Перевод на карту
Номер карты:
4048415020898850