Preskočiť na obsah
Návod

Spill do tempdb – Sort a Hash Warning, memory grant feedback

Spill do tempdb v pláne: varovanie SpillToTempDb pri Sort a Hash Match, spill level, prečo vzniká (podhodnotený odhad a memory grant) a čo pomôže vrátane memory grant feedback (2017 / 2019 / 2022).

4 min čítania 5 krokov 1 obrázok SQL Server 2016+
> [!TIP]
> Recept z [kuchárky exekučných plánov](script.php?id=64&s=exekucne-plany-kucharka-zacni-tu). Ukážky bežia v testovacej databáze [PlanLab](script.php?id=65&s=planlab-testovacia-databaza-pre-recepty-exekucnych-planov) – nikdy ich nespúšťaj na produkcii.

## Ako to vyzerá v pláne

![Spill do tempdb pri Sort s malým memory grantom](uploads/2026/11/plan-p7.svg "Grant podľa zlého odhadu nestačí – zvyšok ide do tempdb")

V **skutočnom** pláne žltý trojuholník pri **Sort** alebo **Hash Match** (príp. pri exchange operátore paralelizmu). Vo *Warnings*: *Operator used tempdb to spill data during execution with spill level N and M spilled thread(s)*; v XML `SpillToTempDb`, `SortSpillDetails` / `HashSpillDetails`. V odhadovanom pláne spill nevidíš – vzniká až za behu.

## Čo to znamená

Sort a Hash Match pracujú v pamäti, ktorú dotaz dostane **pred štartom** (memory grant). Veľkosť sa vypočíta z **odhadu** počtu a šírky riadkov. Keď príde viac dát, operátor časť odloží do **tempdb** a neskôr ju číta späť – **spill**. Výsledok je správny, ale pomalší (diskové I/O, ďalšie prechody pri vyššom *spill level*).

### Do hĺbky

- **Spill level** – koľko kôl rozdeľovania a zápisu bolo treba. Level 1 býva mierny, vyššie levely sú drahé.
- Príčina je takmer vždy **podhodnotený odhad** ([zlé odhady](script.php?id=84&s=zle-odhady-riadkov-odhad-vs-skutocnost-a-statistiky), [table variable](script.php?id=86&s=table-variable-vs-temp-tabulka-odhady-a-deferred-compilation-2019), [parameter sniffing](script.php?id=87&s=parameter-sniffing-jeden-plan-pre-rozne-hodnoty-psp-2022-oppo-2025)) – alebo grant obmedzený hintom či Resource Governorom.
- **Memory grant feedback** upraví grant pre ďalšie spustenia toho istého plánu: batch mode od SQL Server 2017 (compat 140), row mode od 2019 (compat 150), percentile a uloženie do Query Store od 2022. V skutočnom pláne na SELECT vlastnosť *IsMemoryGrantFeedbackAdjusted* (napr. `Yes: Adjusting`, `Yes: Stable`, `No: First Execution`). Podľa tabuľky funkcií SQL Server 2022 je feedback v Enterprise edícii.
- Spill sa ukáže aj v STATISTICS IO (*Worktable* / *Workfile*) a v čakaniach (zápis a čítanie tempdb).
- Spill pri exchange operátore (paralelizmus) má inú príčinu – nerovnomerné vlákna, order-preserving exchange ([paralelizmus v pláne](script.php?id=79&s=paralelizmus-v-plane-distribute-repartition-a-gather-streams)).

## Kedy je to v poriadku / kedy problém

| V poriadku | Problém |
|---|---|
| ojedinelý spill level 1 pri veľkom reporte | spill pri častom OLTP dotaze |
| feedback grant upravil, ďalšie behy bez spillu | vysoký spill level, rastúca spotreba tempdb |
| | grant oscilujúci medzi spusteniami (feedback sa vypne) |

## Ako si to vyskúšať

```sql
USE PlanLab;
SET STATISTICS IO, TIME ON;

-- Podhodnotený odhad cez table variable (compat 140) → malý grant → spill pri Sort
ALTER DATABASE PlanLab SET COMPATIBILITY_LEVEL = 140;
GO
DECLARE @t TABLE (OrderID int NOT NULL);
INSERT @t SELECT OrderID FROM dbo.Orders;
SELECT t.OrderID, o.Note, o.AccountCode
FROM @t AS t JOIN dbo.Orders AS o ON o.OrderID = t.OrderID
ORDER BY o.Note, o.AccountCode;
GO
-- Spill vynútený malým grantom (len na ukážku)
SELECT OrderID, Note, AccountCode FROM dbo.Orders ORDER BY Note, AccountCode
OPTION (MAX_GRANT_PERCENT = 0.01);
GO
ALTER DATABASE PlanLab SET COMPATIBILITY_LEVEL = 150;   -- alebo pôvodná hodnota
```

Spusti s **Include Actual Execution Plan** (Ctrl+M). Pri Sort nájdi varovanie a *spill level*, na SELECT *Memory Grant Info* (Granted vs. MaxUsed). Na 2019+ spusti druhý dotaz (bez hintu) dvakrát a sleduj *IsMemoryGrantFeedbackAdjusted*.

## Čo s tým

1. Oprav **odhad** (štatistiky, #temp namiesto table variable, parametre) – grant sa opraví s ním.
2. Zúž triedené / hashované dáta: menej stĺpcov, užšie typy (nie `varchar(max)` v ORDER BY).
3. Ušetri Sort indexom v potrebnom poradí ([Sort](script.php?id=75&s=sort-top-a-top-n-sort-zoradovanie-a-pamat)).
4. Využi memory grant feedback (compat 150+ / 160+); `MIN_GRANT_PERCENT` ako hint až na záver.
5. Sleduj, [kto spotrebúva tempdb](script.php?id=20&s=kto-spotrebuva-tempdb) a [konfiguráciu tempdb](script.php?id=13&s=konfiguracia-tempdb-subory-velkost-autogrowth).

## Súvisiace

- [Memory grant](script.php?id=91&s=memory-grant-kolko-pamate-dostal-dotaz-privela-alebo-primalo)
- [Sort, Top a Top N Sort](script.php?id=75&s=sort-top-a-top-n-sort-zoradovanie-a-pamat)
- [Hash Match](script.php?id=73&s=hash-match-hash-join-a-hash-aggregate-build-a-probe)
- [Zlé odhady riadkov](script.php?id=84&s=zle-odhady-riadkov-odhad-vs-skutocnost-a-statistiky)
- [Kto spotrebúva tempdb](script.php?id=20&s=kto-spotrebuva-tempdb)
- [Konfigurácia tempdb](script.php?id=13&s=konfiguracia-tempdb-subory-velkost-autogrowth)

## Zdroje

- [Microsoft Learn – Memory grant feedback](https://learn.microsoft.com/sql/relational-databases/performance/intelligent-query-processing-memory-grant-feedback)
- [Microsoft Learn – Showplan Logical and Physical Operators Reference](https://learn.microsoft.com/sql/relational-databases/showplan-logical-and-physical-operators-reference)
- [Microsoft Learn – Editions and supported features of SQL Server 2022](https://learn.microsoft.com/sql/sql-server/editions-and-components-of-sql-server-2022)
- [Erik Darling – blog (plány, memory grants, parameter sniffing)](https://erikdarling.com/)

_Texty sú vlastné, tvrdenia overené proti uvedeným zdrojom (11/2026). T-SQL je staticky skontrolovaný, nie spustený na živom serveri – vyskúšaj ho najprv v PlanLab._