읽기 커밋된 격리 수준 및 테이블 제약 조건이 있는 트랜잭션
-
06-09-2019 - |
문제
동일한 트랜잭션에서 테이블 제약 조건이 실행됩니까?
테이블에 일부 행을 삽입하는 Read Committed 격리 수준의 트랜잭션이 있습니다.테이블에는 동일한 테이블에서 일부 행을 선택하는 함수를 호출하는 제약 조건이 있습니다.
트랜잭션에 대해 아무것도 모르고 함수가 실행되고 함수의 선택이 트랜잭션 이전에 있었던 테이블의 행을 반환하는 것처럼 보입니다.
해결 방법이 있나요? 아니면 누락된 것이 있나요?감사해요.
거래 및 제약 조건에 대한 코드는 다음과 같습니다.
insert into Treasury.DariaftPardakhtDarkhastFaktor
(DarkhastFaktor, DariaftPardakht, Mablagh, CodeVazeiat,
ZamaneTakhsiseFaktor, MarkazPakhsh, ShomarehFaktor, User)
values
(@DarkhastFaktor, @DariaftPardakht, @Mablagh, @CodeVazeiat,
@ZamaneTakhsiseFaktor, @MarkazPakhsh, @ShomarehFaktor, @User);
constraint expression (enforce for inserts and updates):
([Treasury].[ufnCheckDarkhastFaktorMablaghConstraint]([DarkhastFaktor])=(1))
ufnCheckDarkhastFaktorMablaghConstraint:
returns bit
as
begin
declare @SumMablagh float
declare @Mablagh float
select @SumMablagh = isnull(sum(Mablagh), 0)
from Treasury.DariaftPardakhtDarkhastFaktor
where DarkhastFaktor= @DarkhastFaktor
select @Mablagh = isnull(MablaghKhalesFaktor, 0)
from Sales.DarkhastFaktor
where DarkhastFaktor= @DarkhastFaktor
if @Mablagh - @SumMablagh < -1
return 0
return 1
end
해결책
삭제 작업에는 검사 제약 조건이 적용되지 않습니다. http://msdn.microsoft.com/en-us/library/ms188258.aspx
삭제 명령문 중에 확인 제약 조건이 검증되지 않습니다.따라서 특정 유형의 체크 제약 조건이있는 테이블에서 삭제 명령문을 실행하면 예상치 못한 결과가 발생할 수 있습니다.
편집 - 해결 방법에 대한 질문에 대답하려면 함수 호출에서 불변성이 손상되었음을 표시하는 경우 삭제 트리거를 사용하여 롤백할 수 있습니다.
편집 #2 - @reticent, 행을 추가하는 경우 검사 제약 조건에 의해 호출된 함수는 실제로 행을 확인해야 합니다.그렇지 않은 경우 제약 조건 확인은 쓸모가 없습니다.다음은 간단한 예입니다. 처음 2개의 삽입은 성공하고 세 번째는 예상대로 실패하는 것을 알 수 있습니다.
create table t1 (id int)
go
create function t1_validateSingleton ()
returns bit
as
begin
declare @ret bit
set @ret = 1
if exists (
select count(*)
from t1
group by id
having count(*) > 1
)
begin
set @ret = 0
end
return (@ret)
end
go
alter table t1
add constraint t1_singleton
check (dbo.t1_validateSingleton()=1)
go
insert t1 values (1)
insert t1 values (2)
insert t1 values (1)
제휴하지 않습니다 StackOverflow