it-swarm-eu.dev

SQL Server - Kolik typů timeoutů se může stát a jak?

Při práci s SQL Serverem může mít více hostitelských aplikací přístup a každá aplikace může mít jedno nebo více připojení. Každé připojení může mít více transakcí (opravte mě, pokud se mýlím). Každá transakce může provést dotaz SQL nebo bez dotazu SQL.

Podle mých zkušeností snadno narazím na časový limit, pokud dotazuji tabulku, která je výhradně uzamčena. Také jsem viděl SQL Server detekovat a vyvolávat výjimku zablokování namísto timeoutu, pokud dvě různé aplikace zamkly stejný zdroj. Také zobrazuji přestavbu vypršení časového limitu indexu, což je možné kvůli tomu, že někdo má stále připojení k tabulce.

Také se však setkávám s nějakým zablokováním, kde jej SQL Server nezjistí nebo vyprší časový limit. V této aplikaci otevřela dvě připojení, dvě samostatné transakce, kde 1. transakce zamkla prostředek a 2. transakce se pokusila o přístup ke stejnému prostředku, ale nezavřela první transakci.

Pokud by někdo poskytl seznam typů časových limitů a/nebo zablokování, pomohlo by mi vyhnout se těmto druhům případů při práci na aplikaci.

8
dsum

Z aplikačního hlediska existují:

  • časový limit připojení (jak dlouho je aplikace ochotna čekat na navázání připojení k serveru SQL)
  • časový limit příkazu (jak dlouho je aplikace ochotna čekat na dokončení příkazu, včetně stažení výsledků dolů ze serveru SQL)

V mých klasických ASP dnech, výchozí hodnoty pro tyto byly 15 a 30 sekund , nemám ponětí, jaké jsou ve výchozím nastavení .NET dnes.

SQL Server má vlastní sadu timeoutů, například:

  • Časový limit vzdáleného dotazu. Výchozí nastavení je 600 sekund (10 minut).
  • Časový limit vzdáleného přihlášení. Výchozí hodnota je 10 sekund.
  • Dotaz čekat. Výchozí hodnota je -1 (25 x náklady na dotaz).
  • Vypršení časového limitu obsluhy fulltextového protokolu. Výchozí nastavení je 60 sekund.

Tyto hodnoty pro váš systém můžete vidět zde:

SELECT * FROM sys.configurations
WHERE configuration_id IN (1519,1520,1541,1557);

K dispozici je také @@LOCK_TIMEOUT (výchozí hodnota -1 (nekonečno)). To je, jak dlouho bude SQL Server čekat na blokovaný prostředek. Můžete to přepsat pro konkrétní relaci pomocí SET LOCK_TIMEOUT . Více podrobností zde .

Předpokládám, že by se do této kategorie mohli dostat i mrtvoly. Systém prohledává situace zablokování každých 5 sekund a neexistuje žádný magický vzorec, který by určoval, kdy dojde k zablokování v souvislosti s okamžikem zahájení kterékoli z příslušných požadavků. Důvodem je, že SQL Server nenechá vyhrát nejstarší transakci; vybere oběť na základě DEADLOCK_PRIORITY a odhadovaného množství zdrojů potřebných k vrácení oběti zpět. Více podrobností zde .

K dispozici je také časový limit udělení paměti (který lze upravit pomocí nástroje Resource Governor). V závislosti na souběžnosti nebude dotaz nutně selhat, pokud dosáhne časového limitu před získáním veškeré požadované paměti, bude spuštěn pouze s přidělenou částkou (a proto může být méně efektivní). Pokud selže, pravděpodobně uvidíte Msg 8645.

Můžete získat představu o dalších možných scénářích časového limitu, které se mohou vyskytnout v rámci serveru SQL, prostudováním těchto chybových zpráv:

SELECT message_id, [text]
  FROM sys.messages 
  WHERE language_id = 1033 
  AND ([text] LIKE '%timeout%' OR [text] LIKE '%time out%')

Nemyslím si však, že je praktické, proveditelné nebo produktivní, aby se kdokoli pokusil poskytnout vám úplný a vyčerpávající seznam každé možné časové prodlevy. Vyřešte problémy, které máte, spíše než předčasně vyřešte spoustu problémů, které pravděpodobně nikdy nebudete ...

13
Aaron Bertrand

Jsou zde zmíněny tři různé pojmy. Doufejme, že to dá dobré vysvětlení toho, co jsou, a odtud můžete přijít na to, jak se jim vyhnout.

Blokování (aka živé uzamčení)
Blokování nastane, když se dotaz pokusí získat zámek, ale musí před vyčkáním zámku čekat v uzamykací frontě. Z vnějšího pohledu se může zdát, že dotaz nedělá nic, protože čeká, až ostatní procesy uvolní zámek před frontou ve frontě. Blokování může způsobit zablokování, pokud jsou zámky získány v určitém pořadí (popisuji to níže).

Časové limity
K vypršení časového limitu dojde, když klient požádá o zdroj a čeká na odpověď. Pokud v daném časovém období není přijata žádná odpověď, je klientem namísto věčného čekání vyvolána chyba. Časový limit může nastat z různých důvodů (blokování nebo dotaz, který dělá spoustu práce, nebo síť byla opravdu pomalá, nebo ...), ale nakonec, protože klient čekal a rozhodl se, že to nechce čekat ještě víc.

Deadlock
K uváznutí dojde, když dva nebo více procesů drží zámky na zdrojích a také se pokouší uzamknout prostředky držené jinými procesy. To vytváří situaci tak, že žádný dotaz nemůže pokračovat, dokud není jeden z nich ukončen/vrácen zpět. Ukázalo se, jak to funguje v demo videu zde .

1
Jon Seigel