Chyba #: 50003167 (oprava hotfix SQL)
Další informace o hlavním seznamu buildů, které byly vydány po vydání jazyka SQL, naleznete v následujícím článku znalostní báze znalostní báze Microsoft Knowledge Base:
957826 Kde můžete najít další informace o buildech SQL Server 2008 vydaných po SQL Server 2008 a buildech SQL Server 2005 vydaných po SQL Server 2005 Service Pack 2
Příznaky
V systému Microsoft SQL Server 2008 nemusí být omezení cizího klíče vynuceno při splnění následujících podmínek:
- Je vydán příkaz MERGE.
- Cílový sloupec aktualizace má neclusterovaný jedinečný index.
Podívejte se na tento scénář: Příkaz aktualizuje jedinečný sloupec s názvem Sloupec1 tabulky s názvem Tabulka1. Na Tabulku1 odkazuje omezení cizího klíče z tabulky s názvem Tabulka2.
Výsledkem je, že řádky v Tabulce1 se změní, i když by k tomu neměly. Tabulka2 bude navíc obsahovat řádky, které mají nadbytečné odkazy na tabulku1.
K tomuto problému dochází v tomto scénáři v případě, že jsou splněny následující podmínky:
Odkazovaný sloupec Sloupec1 v Tabulce1 není součástí clusterovacího klíče Tabulky1.
Sloupci Sloupec1 lze přiřadit pouze jednu možnou hodnotu. Nastane například jeden z následujících scénářů:
Zdrojem sloučení je jeden řádek dat. Zdroj sloučení například pochází z jednoho z následujících příkazů select:
-
select <ConstantValues> -
select <Parameters>
Poznámka: Tento scénář je nejpravděpodobnější.
-
Zdrojem sloučení je ve skutečnosti jeden řádek dat. Zdroj sloučení například pochází z jednoho z následujících příkazů select:
-
select <ColumnName> from <TableName> where <TableName>.<ColumnName> = 1Všimněte si< TableName>.<Optimalizátor dotazů ví, že jde o jedinečnou hodnotu ColumnName>.
-
select top 1 <ColumnName> from <TableName>
-
Spojení mezi zdrojem sloučení a cílem sloučení má predikát, který zaručuje, že bude aktualizován jeden řádek.
Klauzule update nastaví sloupec Sloupec1 na konstantní hodnotu bez ohledu na zdroj sloučení.
U omezení cizího klíče v tabulce 2 není povolená možnost Kaskáda při aktualizaci.
Poznámka: Tuto opravu hotfix doporučujeme použít, pokud používáte příkaz MERGE k aktualizaci sloupců s neclusterovanými jedinečnými indexy, na které odkazují omezení cizího klíče.
Řešení
Oprava tohoto problému byla poprvé vydána v kumulativní aktualizaci 1. Další informace o získání tohoto balíčku kumulativních aktualizací pro SQL Server 2008 naleznete v následujícím článku znalostní báze znalostní báze Microsoft Knowledge Base:
956717 Balíček kumulativní aktualizace 1 pro SQL Server 2008
Poznámka: Vzhledem k tomu, že sestavení jsou kumulativní, obsahuje každá nová verze opravy všechny opravy hotfix a všechny opravy zabezpečení, které byly součástí předchozího vydání opravy pro SQL Server 2008. Doporučujeme zvážit použití nejnovější verze opravy, která obsahuje tuto opravu hotfix. Další informace naleznete v následujícím článku znalostní báze znalostní báze Microsoft Knowledge Base:
956909 Buildy SQL Server 2008, které byly vydány po vydání SQL Server 2008
Alternativní řešení
Balíček oprav hotfix tento problém odstraňuje. Použijete-li příkaz MERGE ve scénáři popsaném v části "Příznaky" a rozhodnete se opravu hotfix nepoužít, odstraňte tento problém následujícím postupem:
Přepište příkaz MERGE tak, aby hodnoty pro zdroj hromadné korespondence byly v tabulce, dočasné tabulce nebo proměnné tabulky, a ne vložené v dotazu.
Použijte trasovací příznak 8790. Tento příznak sledování přinutí optimalizátor, aby použil druh plánu, který se nazývá plán široké aktualizace. Široké plány aktualizací tento problém nemají. Tento krok s sebou nese rizika výkonu u všech příkazů DML. Proto byste se měli tomuto kroku vyhnout, pokud není možné aplikaci změnit.
Následující skript jazyka Transact-SQL ukazuje jeden ze způsobů, jak změnit skript a vyřešit tak tento problém, pokud nelze použít tuto opravu hotfix.
Máte například skript, který se podobá následujícímu:
use tempdb;
drop table sale, product;
create table product(pno int not null primary key, name char(30), pAlternateKey char(6) not null unique);
create table sale(sno int not null primary key, pAlternateKey char(6) not null references product(pAlternateKey));
insert product values(1, 'Office Chair', 'ochair');
insert sale values(1, 'ochair')
-- No violation of foreign key constraint is detected. However, one should be.
merge into product
using (select 'Office Chair2' as name, 1 as pno, 'oxx' as pAlternateKey) as src
on product.pno = src.pno
when matched then
update set product.pAlternateKey = src.pAlternateKey,
product.name = src.name
when not matched then
insert values(src.pno, src.name, src.pAlternateKey);
Změňte skript tak, aby vypadal nějak takto:
insert product values(1, 'Office Chair', 'ochair');
insert sale values(1, 'ochair')
-- A foreign key constraint violation is detected, and the update fails.
declare @source table
(name nchar(30), pno int, pAlternateKey nchar(30));
insert into @source values('Office Chair2',1,'oxx');
merge into product
using @source as src
on product.pno = src.pno
when matched then
update set product.pAlternateKey = src.pAlternateKey,
product.name = src.name
when not matched then
insert values(src.pno, src.name, src.pAlternateKey);
Stav
Společnost Microsoft potvrdila, že se jedná o problém produktů Microsoft, které jsou uvedeny v sekci Platí pro.
Další informace
Další informace o měněných souborech a o všech předpokladech použití balíčku kumulativní aktualizace obsahujícího opravu hotfix popsaného v tomto článku znalostní báze znalostní báze Microsoft Knowledge Base naleznete v následujícím článku znalostní báze znalostní báze Microsoft Knowledge Base:
956717 Balíček kumulativní aktualizace 1 pro SQL Server 2008
Reference
Další informace o seznamu buildů, které jsou dostupné po vydání verze systému SQL Server 2008, naleznete v následujícím článku znalostní báze znalostní báze Microsoft Knowledge Base:
956909 Buildy SQL Server 2008, které byly vydány po vydání SQL Server 2008
Další informace o modelu přírůstkové údržby pro SQL Server naleznete v následujícím článku znalostní báze znalostní báze Microsoft Knowledge Base:
935897 Tým SQL Server poskytuje k poskytování oprav hotfix pro hlášené problémy model přírůstkové údržby
Další informace o schématu pojmenování aktualizací pro aktualizace serveru SQL Server naleznete v následujícím článku znalostní báze znalostní báze Microsoft Knowledge Base:
822499 Nové schéma pojmenovávání balíčků aktualizací softwaru Microsoft SQL Server
Další informace o terminologii aktualizací softwaru naleznete v následujícím článku znalostní báze znalostní báze Microsoft Knowledge Base:
824684 Popis standardní terminologie používané k popisu aktualizací softwaru společnosti Microsoft
Neclusterované indexy v systému SQL Server 2008
Další informace o neclusterovaných indexech v systému SQL Server 2008 naleznete na následujícím webu služby MSDN (web MSDN (Microsoft Developer Network)):