Nejčastější dotazy

Následující části odpovídají na některé běžné problémy, se kterými se můžete setkat při implementaci LINQ.

Další problémy jsou vyřešeny v řešení potíží.

Nejde se připojit

Nemůžu se připojit k databázi.

Ujistěte se, že je váš připojovací řetězec správný a že je spuštěná instance SQL Serveru. Všimněte si také, že LINQ to SQL vyžaduje povolení protokolu Pojmenované kanály. Další informace naleznete v tématu Učení podle návodů.

Změny v databázi byly ztraceny.

Provedl(a) jsem změnu dat v databázi, ale když jsem aplikaci znovu našel, změna už tam nebyla.

Ujistěte se, že voláte SubmitChanges , abyste uložili výsledky do databáze.

Připojení k databázi: Jak dlouho bude otevřeno?

Jak dlouho zůstane připojení k databázi otevřené?

Připojení obvykle zůstane otevřené, dokud nespotřebujete výsledky dotazu. Pokud očekáváte, že zpracování všech výsledků nějakou dobu trvá a nejste proti ukládání výsledků do mezipaměti, použijte ToList pro dotaz. V běžných scénářích, kdy se každý objekt zpracovává pouze jednou, je model streamování v obou případech, tedy jak u DataReader, tak u LINQ to SQL, lepší.

Přesné podrobnosti o využití připojení závisí na následujících:

  • Stav připojení, pokud DataContext je vytvořen s objektem připojení.

  • Nastavení připojovacího řetězce (například povolení více aktivních sad výsledků (MARS). Další informace naleznete v tématu Více aktivních sad výsledků (MARS).

Aktualizace bez dotazování

Můžu aktualizovat data tabulky bez prvního dotazování databáze?

I když LINQ to SQL neobsahuje příkazy aktualizace založené na sadě, můžete k aktualizaci bez prvního dotazování použít některý z následujících technik:

  • Slouží ExecuteCommand k odesílání kódu SQL.

  • Vytvořte novou instanci objektu a inicializujete všechny aktuální hodnoty (pole), které ovlivňují aktualizaci. Pak objekt připojte k objektu DataContext pomocí Attach a upravte pole, které chcete změnit.

Neočekávané výsledky dotazu

Dotaz vrací neočekávané výsledky. Jak můžu zkontrolovat, co se děje?

LINQ to SQL poskytuje několik nástrojů pro kontrolu kódu SQL, který generuje. Jedním z nejdůležitějších je Log. Další informace naleznete v tématu Podpora ladění.

Neočekávané výsledky uložené procedury

Mám uloženou proceduru, jejíž návratová hodnota je vypočítána parametrem MAX(). Když přetáhnu uloženou proceduru na plochu O/R Návrháře, návratová hodnota není správná.

LINQ to SQL nabízí dva způsoby vrácení hodnot generovaných databází pomocí uložených procedur:

  • Pojmenováním výsledku výstupu.

  • Explicitním zadáním výstupního parametru

Následuje příklad nesprávného výstupu. Vzhledem k tomu, že LINQ to SQL nemůže namapovat výsledky, vrátí vždy hodnotu 0:

create procedure proc2

as

begin

select max(i) from t where name like 'hello'

end

Následuje příklad správného výstupu pomocí výstupního parametru:

create procedure proc2

@result int OUTPUT

as

select @result = MAX(i) from t where name like 'hello'

go

Následuje příklad správného výstupu pojmenováním výsledku výstupu:

create procedure proc2

as

begin

select nax(i) AS MaxResult from t where name like 'hello'

end

Další informace naleznete v tématu Přizpůsobení operací pomocí uložených procedur.

Chyby serializace

Při pokusu o serializaci se zobrazí následující chyba: "Type 'System.Data.Linq.ChangeTracker+StandardChangeTracker' ... není označena jako serializovatelná."

Generování kódu v LINQ to SQL podporuje DataContractSerializer serializaci. Nepodporuje XmlSerializer ani BinaryFormatter. Další informace naleznete v tématu Serializace.

Více souborů DBML

Když mám více souborů DBML, které sdílejí některé tabulky běžně, zobrazí se chyba kompilátoru.

Nastavte vlastnosti oboru názvů kontextu a oboru názvů entity z Návrháře relačních objektů na jedinečnou hodnotu pro každý soubor DBML. Tento přístup eliminuje kolizi mezi názvem a oborem názvů.

Vyhněte se explicitnímu nastavení hodnot generovaných databází při vložení nebo aktualizaci

Mám tabulku databáze se sloupcem DateCreated, který má výchozí hodnotu SQL Getdate(). Při pokusu o vložení nového záznamu pomocí LINQ to SQL se hodnota nastaví na NULL. Očekával bych, že bude nastavena na výchozí hodnotu databáze.

LINQ to SQL zpracovává tuto situaci automaticky pro sloupce identity (automatického přírůstku), rowguidcol (databází generovaného GUID) a timestamp (časového razítka). V jiných případech byste měli ručně nastavit IsDbGenerated=trueaAutoSync=Always/OnInsert/OnUpdatenastavit vlastnosti.

Více možností DataLoadOptions

Mohu zadat další možnosti načítání, aniž bych přepsal první?

Ano. První není přepsán, jak je znázorněno v následujícím příkladu:

Dim dlo As New DataLoadOptions()
dlo.LoadWith(Of Order)(Function(o As Order) o.Customer)
dlo.LoadWith(Of Order)(Function(o As Order) o.OrderDetails)
DataLoadOptions dlo = new DataLoadOptions();
dlo.LoadWith<Order>(o => o.Customer);
dlo.LoadWith<Order>(o => o.OrderDetails);

Chyby při používání SQL Compact 3.5

Při přetažení tabulek z databáze SQL Server Compact 3.5 se zobrazí chyba.

Návrhář relačních objektů nepodporuje SQL Server Compact 3.5, ačkoli runtime LINQ to SQL ano. V této situaci musíte vytvořit vlastní třídy entit a přidat příslušné atributy.

Chyby v relacích dědičnosti

Použil(a) jsem tvar dědičnosti sady nástrojů v Návrháři relací objektů k propojení dvou entit, ale dochází k chybám.

Vytvoření relace nestačí. Musíte zadat informace, jako je například diskriminační sloupec, hodnota diskriminátoru základní třídy a hodnota diskriminátoru odvozené třídy.

Model zprostředkovatele

Je k dispozici model veřejného poskytovatele?

Není k dispozici žádný model veřejného poskytovatele. V tuto chvíli LINQ to SQL podporuje pouze SQL Server a SQL Server Compact 3.5.

SQL injekční útoky

Jak je LINQ to SQL chráněné před útoky prostřednictvím injektáže SQL?

Injektáž SQL představuje významné riziko pro tradiční dotazy SQL vytvořené zřetězením uživatelského vstupu. LINQ to SQL se takovým injekcím SqlParameter vyhne v dotazech. Uživatelský vstup je převeden na hodnoty parametrů. Tento přístup brání použití škodlivých příkazů ze vstupu zákazníka.

Změna příznaku jen pro čtení v souborech DBML

Jak při vytváření objektového modelu ze souboru DBML odstraním settery z některých vlastností?

Pro tento pokročilý scénář proveďte následující kroky:

  1. V souboru .dbml upravte vlastnost změnou příznaku IsReadOnly na True.

  2. Přidejte částečnou třídu. Vytvořte konstruktor s parametry pro členy pouze pro čtení.

  3. Zkontrolujte výchozí UpdateCheck hodnotu (Never) a zjistěte, jestli je to správná hodnota pro vaši aplikaci.

    Upozornění

    Pokud v sadě Visual Studio používáte Návrhář objektů a relací, vaše změny mohou být přepsány.

APTCA

Je System.Data.Linq označený pro použití částečně důvěryhodným kódem?

Ano, sestavení System.Data.Linq.dll patří mezi sestavení rozhraní .NET Framework označená atributem AllowPartiallyTrustedCallersAttribute . Bez tohoto označení mohou být sestavení v rozhraní .NET Framework používána pouze plně důvěryhodným kódem.

Hlavní scénář v LINQ to SQL pro povolení částečně důvěryhodných volajících je umožnit přístup k sestavení LINQ to SQL z webových aplikací, kde je konfigurace důvěryhodnosti nastavena na Střední.

Mapování dat z více tabulek

Data v mé entitě pocházejí z více tabulek. Jak mám to namapovat?

V databázi můžete vytvořit zobrazení a entitu namapovat na toto zobrazení. LINQ to SQL generuje stejné SQL pro zobrazení jako u tabulek.

Poznámka:

Použití zobrazení v tomto scénáři má omezení. Tento přístup funguje nejbezpečněji, když jsou operace prováděné Table<TEntity> v podkladovém zobrazení podporovány. Jen víte, které operace jsou určené. Například většina aplikací je pouze pro čtení a značný počet provádí Create/Update/Delete operace pouze pomocí uložených procedur proti zobrazením.

Sdružování připojení

Existuje konstruktor, který může pomoct s sdružováním dat DataContext?

Nepokoušejte se opakovaně používat instance .DataContext Každý DataContext udržuje stav (včetně cache identity) pro jednu konkrétní relaci úprav nebo dotazů. Chcete-li získat nové instance na základě aktuálního stavu databáze, použijte nový DataContext.

Stále můžete použít základní ADO.NET sdružování připojení. Další informace najdete v tématu sdružování připojení SQL Serveru (ADO.NET).

Druhý DataContext se neaktualizuje.

Použil(a) jsem jednu instanci DataContext k ukládání hodnot v databázi. Druhý objekt DataContext ve stejné databázi však neodráží aktualizované hodnoty. Zdá se, že druhá instance DataContext vrací hodnoty uložené v mezipaměti.

Toto chování je záměrné. LINQ to SQL nadále vrací stejné instance a hodnoty, které jste viděli v první instanci. Při provádění aktualizací používáte optimistickou souběžnost. Původní data se používají ke kontrole aktuálního stavu databáze, aby se ověřilo, že se ve skutečnosti nezměnila. Pokud došlo ke změně, dojde ke konfliktu a vaše aplikace ji musí vyřešit. Jednou z možností vaší aplikace je resetovat původní stav do aktuálního stavu databáze a zkusit aktualizaci zopakovat. Další informace naleznete v tématu Postupy: Správa konfliktů změn.

Můžete také nastavit ObjectTrackingEnabled hodnotu False, která vypne ukládání do mezipaměti a sledování změn. Při každém dotazování pak můžete načíst nejnovější hodnoty.

Nelze volat SubmitChanges v režimu pouze pro čtení

Při pokusu o volání SubmitChanges v režimu jen pro čtení se zobrazí chyba.

Režim jen pro čtení vypne schopnost kontextu sledovat změny.