C# Academy · Lektion

CRUD-operationer med EF Core

Udfør Create-, Read-, Update- og Delete-operationer med EF Cores ændringssporing og SaveChanges.

Lektion 3 af 413 trin

CRUD-operationer med EF Core er en gratis C# Academy-lektion på CoddyKit. Dette er lektion 3 af 4. Du kan læse hele lektionen gratis nedenfor — og derefter øve dig praktisk i browseren med en indbygget kodeeditor og en AI-vejleder, der er tilgængelig døgnet rundt. Den er en del af læringsforløbet i C# Academy, og dine fremskridt synkroniseres på tværs af nettet og CoddyKit-appen. C# Academy-kurset indeholder 4 lektioner i alt.

Overblik over CRUD i EF Core

EF Core håndterer alle fire CRUD-operationer — Opret, Læs, Opdater, Slet — gennem en kombination af ændringssporing og SaveChangesAsync(). At forstå ændringssporingen er nøglen til at mestre CRUD.

Opret: tilføjelse af en ny entitet

Brug DbSet.Add() eller AddAsync() til at markere en entitet som Added. Når du kalder SaveChangesAsync(), genererer EF Core en INSERT og udfylder den automatisk inkrementerede nøgle.

var order = new Order
{
    CustomerId = 5,
    PlacedAt   = DateTime.UtcNow,
    Status     = OrderStatus.Pending
};

await _db.Orders.AddAsync(order);
await _db.SaveChangesAsync();

Console.WriteLine(order.Id); // populated by DB

Tilføjelse af en graf af entiteter

Hvis du tilføjer en overordnet entitet med underordnede entiteter i ét kald, indsættes hele objektgrafen. EF Core fastlægger automatisk FK-relationerne.

var order = new Order
{
    CustomerId = 5,
    PlacedAt   = DateTime.UtcNow,
    Lines      = new List<OrderLine>
    {
        new() { ProductId = 10, Quantity = 2, Price = 49.99m },
        new() { ProductId = 11, Quantity = 1, Price = 19.99m }
    }
};

_db.Orders.Add(order);
await _db.SaveChangesAsync();
// Inserts Order + 2 OrderLines in one transaction

Læs: forespørgsler med LINQ

EF Core oversætter LINQ-udtryk til SQL. Sammensæt forespørgsler med Where, Select, OrderBy osv., og materialisér dem derefter med ToListAsync eller FirstOrDefaultAsync.

// Read all pending orders for a customer
var orders = await _db.Orders
    .Where(o => o.CustomerId == 5 && o.Status == OrderStatus.Pending)
    .OrderByDescending(o => o.PlacedAt)
    .Select(o => new OrderSummaryDto
    {
        Id     = o.Id,
        Total  = o.Lines.Sum(l => l.Quantity * l.Price),
        Status = o.Status.ToString()
    })
    .ToListAsync();

Læs: opslag af en enkelt entitet

Til læsning af en enkelt entitet skal du bruge FindAsync (søger først i ændringssporingen) eller FirstOrDefaultAsync / SingleOrDefaultAsync med et prædikat.

// By PK (checks cache first)
var order = await _db.Orders.FindAsync(orderId);

// By predicate (always hits DB)
var latest = await _db.Orders
    .Where(o => o.CustomerId == 5)
    .OrderByDescending(o => o.PlacedAt)
    .FirstOrDefaultAsync();

Opdater: ændringssporing

Entiteter, der indlæses via EF Core, spores. Redigér egenskaberne direkte, og kald SaveChangesAsync(). EF Core registrerer forskellen og genererer en minimal UPDATE-sætning.

var order = await _db.Orders.FindAsync(orderId);
if (order is null) return;

order.Status   = OrderStatus.Shipped;
order.ShippedAt = DateTime.UtcNow;

await _db.SaveChangesAsync();
// UPDATE Orders SET Status=..., ShippedAt=... WHERE Id=orderId

Opdater: opdatering af mange poster (EF Core 7+)

ExecuteUpdateAsync opdaterer rækker direkte i databasen uden at indlæse entiteter. Det er langt mere effektivt ved operationer på mange poster.

// Mark all overdue orders as Cancelled — no loading needed
await _db.Orders
    .Where(o => o.Status == OrderStatus.Pending
             && o.PlacedAt < DateTime.UtcNow.AddDays(-30))
    .ExecuteUpdateAsync(set => set
        .SetProperty(o => o.Status, OrderStatus.Cancelled)
        .SetProperty(o => o.UpdatedAt, DateTime.UtcNow));

Slet: fjernelse af en enkelt entitet

Kald Remove() på en entitet, der spores, og kald derefter SaveChangesAsync(). Hvis du kun har id'et, skal du først finde entiteten eller bruge ExecuteDeleteAsync.

var order = await _db.Orders.FindAsync(orderId);
if (order is null) return;

_db.Orders.Remove(order);
await _db.SaveChangesAsync();
// DELETE FROM Orders WHERE Id=orderId

Slet: sletning af mange poster (EF Core 7+)

ExecuteDeleteAsync udfører en enkelt DELETE-SQL-sætning uden at indlæse entiteter — ideelt til oprydning i mange poster.

// Delete all cancelled orders older than 1 year
int deleted = await _db.Orders
    .Where(o => o.Status == OrderStatus.Cancelled
             && o.PlacedAt < DateTime.UtcNow.AddYears(-1))
    .ExecuteDeleteAsync();

Console.WriteLine($"Deleted {deleted} old orders");

Transaktioner

Alle operationer i ét SaveChangesAsync-kald er pakket ind i en transaktion. Ved operationer i flere trin på tværs af flere gemninger skal du bruge en eksplicit transaktion.

using var transaction = await _db.Database.BeginTransactionAsync();
try
{
    _db.Orders.Add(newOrder);
    await _db.SaveChangesAsync();

    inventory.Stock -= newOrder.Quantity;
    await _db.SaveChangesAsync();

    await transaction.CommitAsync();
}
catch
{
    await transaction.RollbackAsync();
    throw;
}

Praktisk eksempel: komplet CRUD-tjeneste

En komplet tjeneste indkapsler alle CRUD-operationer med korrekt fejlhåndtering og returnerer DTOs for at undgå at eksponere entiteternes interne detaljer.

public async Task<OrderDto> CreateOrderAsync(CreateOrderRequest req)
{
    var order = new Order { CustomerId = req.CustomerId, PlacedAt = DateTime.UtcNow };
    _db.Orders.Add(order);
    await _db.SaveChangesAsync();
    return new OrderDto { Id = order.Id, Status = order.Status.ToString() };
}

public async Task<bool> CancelOrderAsync(int id)
{
    int rows = await _db.Orders
        .Where(o => o.Id == id && o.Status == OrderStatus.Pending)
        .ExecuteUpdateAsync(s =>
            s.SetProperty(o => o.Status, OrderStatus.Cancelled));
    return rows > 0;
}

Hurtig kontrol

Hvad er fordelen ved ExecuteUpdateAsync / ExecuteDeleteAsync frem for at indlæse entiteter og kalde SaveChangesAsync?

Opsamling: CRUD-operationer med EF Core

Vigtigste pointer:

  • Add + SaveChangesAsync → INSERT; EF Core udfylder automatisk genererede nøgler
  • Redigér sporede entiteter + SaveChangesAsync → minimal UPDATE
  • Remove + SaveChangesAsync → DELETE for enkelte entiteter
  • ExecuteUpdateAsync / ExecuteDeleteAsync → operationer på mange poster uden indlæsning (EF Core 7+)
  • Omslut operationer i flere trin med en eksplicit transaktion for atomicitet
Gratis at komme i gang

Lær C# med en AI-underviser — gratis

Skriv og kør rigtig kode i din browser, få øjeblikkelig hjælp fra en AI-underviser døgnet rundt, og fortsæt, hvor du slap, på web eller i appen.

Kurser
93
Lektioner
346

Ofte stillede spørgsmål

Er lektionen “CRUD-operationer med EF Core” gratis?

Ja — hele teksten til “CRUD-operationer med EF Core” kan læses gratis her på nettet. Hvis du vil øve dig interaktivt med en indbygget kodeeditor og en AI-vejleder døgnet rundt og få adgang til resten af C# Academy-kurset, skal du opgradere til CoddyKit PRO. C# Academy-kurset indeholder 4 lektioner i alt.

Hvad lærer jeg i “CRUD-operationer med EF Core”?

Udfør Create-, Read-, Update- og Delete-operationer med EF Cores ændringssporing og SaveChanges. Du øver dig i C# Academy med praktisk kode, som du kører direkte i browseren, og en AI-vejleder døgnet rundt besvarer dine spørgsmål, mens du arbejder dig gennem lektionen.

Skal jeg have erfaring for at begynde på C# Academy?

Der kræves ingen tidligere erfaring. C# Academy på CoddyKit er tilrettelagt for både begyndere og øvede, så du kan starte her eller fra begyndelsen og lære i dit eget tempo. Dette er lektion 3 af 4.

Hvor lang tid tager lektionen “CRUD-operationer med EF Core”?

De fleste CoddyKit-lektioner tager cirka 5–10 minutter. Hver lektion er kort og interaktiv, så du gør løbende fremskridt og kan fortsætte, hvor du slap – på både web og app.

Kan jeg skrive og køre kode i denne C# Academy-lektion?

Ja. Alle C# Academy-lektioner har en indbygget kodeeditor, så du kan skrive og køre rigtig kode direkte i din browser og få øjeblikkelig feedback fra AI – uden lokal opsætning.

Alle lektioner i dette kursus

  1. Grundlæggende om DbContext og DbSet
  2. Migrationer og skemahåndtering
  3. CRUD-operationer med EF Core
  4. Relationer: One-to-Many og Many-to-Many
← Tilbage til C# Academy