Megjegyzés
Az oldalhoz való hozzáféréshez engedély szükséges. Megpróbálhat bejelentkezni vagy módosítani a címtárat.
Az oldalhoz való hozzáféréshez engedély szükséges. Megpróbálhatja módosítani a címtárat.
Bár a lekérdezéssel adatokat olvashat az adatbázisból, az adatok mentése azt jelenti, hogy új entitásokat ad hozzá az adatbázishoz, eltávolítja az entitásokat, vagy valamilyen módon módosítja a meglévő entitások tulajdonságait. Az Entity Framework Core (EF Core) két alapvető módszert támogat az adatok adatbázisba való mentéséhez.
1. megközelítés: változáskövetés és SaveChanges
Sok esetben a programnak le kell kérdeznie néhány adatot az adatbázisból, végre kell hajtania rajta néhány módosítást, és vissza kell mentenie ezeket a módosításokat; ezt néha "munkaegységnek" is nevezik. Tegyük fel például, hogy rendelkezik blogok készletével, és módosítani szeretné az Url
egyik tulajdonságát. Ef-ben ez általában a következőképpen történik:
using (var context = new BloggingContext())
{
var blog = await context.Blogs.SingleAsync(b => b.Url == "http://example.com");
blog.Url = "http://example.com/blog";
await context.SaveChangesAsync();
}
A fenti kód a következő lépéseket hajtja végre:
- Egy reguláris LINQ-lekérdezés használatával tölt be egy entitást az adatbázisból (lásd : Lekérdezési adatok). Az EF lekérdezései alapértelmezés szerint nyomon követettek, ami azt jelenti, hogy az EF nyomon követi a betöltött entitásokat a belső változáskövetőjében.
- A betöltött entitáspéldányt a rendszer a szokásos módon módosítja egy .NET-tulajdonság hozzárendelésével. Az EF nem vesz részt ebben a lépésben.
- Végül meghívjuk DbContext.SaveChanges() . Ezen a ponton az EF automatikusan észleli a változásokat úgy, hogy összehasonlítja az entitásokat a betöltés pillanatképével. Az észlelt módosítások megmaradnak az adatbázisban; Relációs adatbázis használata esetén ez általában magában foglalja például az SQL
UPDATE
küldését a megfelelő sorok frissítéséhez.
Vegye figyelembe, hogy a fent leírt egy tipikus frissítési művelet a meglévő adatok esetében, de az entitások hozzáadására és eltávolítására vonatkozó hasonló alapelveket is figyelembe kell venni. Az EF változáskövetőjével a DbSet<TEntity>.Add és Remove hívásával léphet kapcsolatba, így a módosítások nyomon követhetők. Az EF ezután minden korrektúrát alkalmaz az adatbázisra, amikor SaveChanges() meghívják (például SQL-en INSERT
keresztül és DELETE
relációs adatbázis használatakor).
SaveChanges() a következő előnyöket kínálja:
- Nem kell kódot írnia annak nyomon követéséhez, hogy mely entitások és tulajdonságok változtak meg – az EF automatikusan elvégzi ezt Önnek, és csak az adatbázisban lévő tulajdonságokat frissíti, javítva a teljesítményt. Képzelje el, hogy a betöltött entitások egy felhasználói felületi összetevőhöz vannak kötve, lehetővé téve a felhasználók számára a kívánt tulajdonságok módosítását; Az EF elveszi annak a terhét, hogy kiderítse, mely entitásokat és tulajdonságokat módosították ténylegesen.
- Az adatbázis módosításainak mentése néha bonyolult lehet! Ha például hozzá szeretne adni egy blogot és néhány bejegyzést a bloghoz, előfordulhat, hogy be kell kérnie az adatbázis által létrehozott kulcsot a beszúrt bloghoz, mielőtt beszúrhatja a bejegyzéseket (mivel a blogra kell hivatkozniuk). Az EF mindent megtesz önért, elveszve a bonyolultságot.
- Az EF képes észlelni az egyidejűségi problémákat, például ha valaki más módosított egy adatbázissort a lekérdezésed és a SaveChanges() közötti időszakban. További részletek az egyidejűségi ütközésekben érhetők el.
- Az azt SaveChanges() támogató adatbázisokon automatikusan több módosítást is befuttat egy tranzakcióban, így biztosítva, hogy hiba esetén az adatok konzisztensek maradnak. További részletek a Tranzakciók területen érhetők el.
- SaveChanges() emellett számos esetben több módosítást is kötegel, jelentősen csökkentve az adatbázis-lekérdezések számát, és lényegesen javítja a teljesítményt. A hatékony frissítésről további részletek érhetők el.
További információ és kódminták az alapszintű SaveChanges() használatról: Basic SaveChanges. Az EF változáskövetésével kapcsolatos további információkért tekintse meg a Változáskövetés áttekintését.
2. megközelítés: ExecuteUpdate és ExecuteDelete ("tömeges frissítés")
Bár a változások nyomon követése és SaveChanges() a módosítások mentésének hatékony módja, bizonyos hátrányokkal járnak.
SaveChanges() Először le kell kérdeznie és nyomon kell követnie a módosítani vagy törölni kívánt összes entitást. Ha például törölnie kell az összes olyan blogot, amely egy bizonyos küszöbérték alatti minősítéssel rendelkezik, le kell kérdeznie, létre kell hoznia és nyomon kell követnie egy potenciálisan nagy számú sort, és mindegyikhez létre kell SaveChanges() hoznia egy DELETE
utasítást. A relációs adatbázisok sokkal hatékonyabb alternatívát kínálnak: egyetlen DELETE
parancs küldhető el, megadva, hogy mely sorokat kell törölni egy WHERE
záradékon keresztül, de a SaveChanges() modell nem teszi lehetővé a generálást.
Ennek a "tömeges frissítésnek" a támogatásához az alábbiakat használhatja ExecuteDelete :
context.Blogs.Where(b => b.Rating < 3).ExecuteDelete();
Ez lehetővé teszi, hogy az SQL-utasítást DELETE
normál LINQ-operátorokkal fejezze ki – hasonlóan egy normál LINQ-lekérdezéshez –, amely a következő SQL-t hajtja végre az adatbázison:
DELETE FROM [b]
FROM [Blogs] AS [b]
WHERE [b].[Rating] < 3
Ez nagyon hatékonyan fut az adatbázisban anélkül, hogy bármilyen adatot betöltenek az adatbázisból, vagy az EF változáskövetőjét is érintenék. Hasonlóképpen ExecuteUpdate lehetővé teszi egy SQL-utasítás UPDATE
kifejezését is.
Még ha nem is módosítja az entitásokat tömegesen, akkor is pontosan tudja, hogy melyik entitás melyik tulajdonságát szeretné módosítani. A változáskövetési API használata a módosítás végrehajtásához túl összetett lehet, ezért entitáspéldányt kell létrehozni, nyomon követni Attacha módosításokat, és végül meghívni SaveChanges(). Az ilyen forgatókönyvek ExecuteUpdate
esetében, és ExecuteDelete
jelentősen egyszerűbb módja lehet ugyanannak a műveletnek a kifejezésére.
Végül a változáskövetés és SaveChanges() maga is bizonyos futásidejű többletterhelést ró. Ha nagy teljesítményű alkalmazást ír, a ExecuteUpdate
és a ExecuteDelete
lehetővé teszik, hogy mindkét összetevőt elkerülje, és hatékonyan létrehozza a kívánt utasítást.
Vegye figyelembe azonban, hogy ExecuteUpdate
ExecuteDelete
bizonyos korlátozásokkal is rendelkezik:
- Ezek a módszerek azonnal hajtanak végre, és jelenleg nem csoportosíthatók más műveletekkel. Másrészt SaveChanges()több műveletet is kötenek össze.
- Mivel a változáskövetés nincs benne, az Ön felelőssége pontosan tudni, hogy mely entitásokat és tulajdonságokat kell módosítani. Ez manuálisabb, alacsony szintű kódkövetést jelenthet, amit módosítani kell, és ami nem.
- Ezen kívül, mivel a változáskövetés nincs benne, ezek a metódusok nem alkalmazzák automatikusan az egyidejűség-vezérlést a módosítások megőrzésekor. Az egyidejűség-vezérlés implementálásához azonban továbbra is explicit módon adhat hozzá záradékot
Where
. - Jelenleg csak a frissítés és a törlés támogatott; a beszúrást a következőn keresztül DbSet<TEntity>.AddSaveChanges()kell elvégezni:
További információkért és kódmintákért lásd ExecuteUpdate
és ExecuteDelete
.
Összefoglalás
Az alábbiakban néhány útmutatást talál arra vonatkozóan, hogy mikor melyik megközelítést érdemes használni. Vegye figyelembe, hogy ezek nem abszolút szabályok, hanem hasznos támpontokat adnak.
- Ha nem tudja előre, hogy mely módosításokra kerül sor, használja a következőt
SaveChanges
: automatikusan észleli, hogy mely módosításokat kell alkalmazni. Példaforgatókönyvek:- "Be szeretnék tölteni egy blogot az adatbázisból, és megjelenítenem egy űrlapot, amely lehetővé teszi a felhasználó számára a módosítást"
- Ha egy objektumdiagramot (azaz több összekapcsolt objektumot) kell manipulálnia, használja
SaveChanges
azt, amely meghatározza a módosítások megfelelő sorrendjét, és azt, hogy hogyan kapcsolhat össze mindent.- "Szeretnék frissíteni egy blogot, módosítani néhány bejegyzését és törölni másokat"
- Ha egy adott feltétel alapján nagyszámú entitást szeretne módosítani, használja a
ExecuteUpdate
ésExecuteDelete
elemeket. Példaforgatókönyvek:- "Minden alkalmazottnak emelést szeretnék adni"
- "Törölni szeretném az összes olyan blogot, amelynek a neve X-vel kezdődik"
- Ha már tudja, hogy mely entitásokat szeretné módosítani, és hogyan szeretné módosítani őket, használja
ExecuteUpdate
ésExecuteDelete
. Példaforgatókönyvek:- "Törölni szeretném azt a blogot, amelynek a neve "Foo".
- Az "Id 5" azonosítójú blog nevét "Bar" névre szeretném módosítani.