2011-03-22 5 views
3

열리스트를 두 번 이상 지정하지 않고도 감사 트리거를 생성하려고합니다.트리거 데이터의 임시 테이블을 생성하십시오.

이 목적을 위해 트리거에서 INSERTED 또는 DELETED 데이터의 내용에 대한 임시 테이블을 생성 한 다음이를 감사 테이블로 처리하려고합니다. 나는이 사용하는 경우

: 그럼

IF @ChangeType = 'D' 
    SELECT * INTO #tmp FROM DELETED 
ELSE 
    SELECT * INTO #tmp FROM INSERTED 

을 나는 테이블 #tmp이 이미 존재하는 2 SELECT * INTO에서 컴파일 오류가 발생합니다.

나는 시도하고이 사용하여 동적 SQL 약 일 경우 :

SET @Sql = 'SELECT * INTO #tmp FROM ' 
IF @ChangeType = 'D' 
    SET @Sql = @Sq + 'DELETED' 
ELSE 
    SET @Sql = @Sql + 'INSERTED' 

EXEC (@Sql) 

그럼 내가 지운 삽입 테이블이 존재하지 않는 오류가 발생합니다.

트리거의 INSERTED 및 DELETED 테이블을 임시 테이블 또는 다른 메모리 테이블로 가져 오려면 어떻게해야합니까? 때문에 해결 - 온 - 구문 분석 임시 테이블 개체에

SELECT TOP 0 * INTO #tmp FROM DELETED 

IF @ChangeType = 'D' 
    INSERT INTO #tmp SELECT * FROM DELETED 
ELSE 
    INSERT INTO #tmp SELECT * FROM INSERTED 
+0

왜 열 목록을 두 번 이상 지정하지 않으시겠습니까? SQL을 작성하는 것보다이 질문에 더 많은 시간을 할애해야 할 것입니다. :) – Tony

+0

유일한 이유는 두 번 이상 지정할 필요가 없어야하기 때문입니다. 나는 '변경시 오류 범위를 제거하는'것이 가장 좋은 설명이라고 생각합니다. – Craig

답변

4

이처럼 if 외부에서 임시 테이블을 만들어보십시오. 동일한 범위에있는 두 개의 SELECT-INTO 문을 사용하면 SQL Server에서 수건을 던집니다.

SELECT * INTO #tmp FROM DELETED WHERE 1=0 
IF @ChangeType = 'D' 
    INSERT #tmp SELECT * FROM DELETED 
ELSE 
    INSERT #tmp SELECT * FROM INSERTED 
+0

나는 항상 "WHERE 1 = 0"을 사용했으나 이것을 읽으면 나는 수치스럽게 머리를 쓰러 뜨렸다. "TOP 0"은 무엇이 수행되고 있는지에 대해 훨씬 더 명백합니다. 그래서 저는 제가 한 일보다 오히려해야 할 일에 대해 투표하고 있습니다. – MatBailie

0

내가 왜 다른 테이블에 데이터를 복사해야하는지에 관심이 있습니다. 하지만, 그게 화제가 아니야 ...

임시 테이블 (#temp)은 개념 상 디스크에 저장되며 테이블 변수 (@temp)는 개념 상 메모리에만 있으며 작은 작업에는 더 적합 할 수 있습니다. (테이블에 대한 쓰기는 일반적으로 적은 수의 행에만 적용됩니다.)

임시 테이블은 SELECT INTO 트릭을 사용하여 만들 수 있으므로 사전에 테이블 정의를 알 필요는 없습니다.

그러나 사전에 테이블 정의를 알고 있다면 간단히 다음과 같은 것을 사용할 수 있습니까? 개인적으로


DECLARE @temp TABLE (id AS INT, val as INT) 

IF @ChangeType = 'D' 
    INSERT INTO @temp SELECT * FROM DELETED 
ELSE 
    INSERT INTO @temp SELECT * FROM INSERTED 

, 난 가능하면 * 사용하지 않는 것입니다. 후속 쿼리는 특정 필드 만 사용하므로, 내가 사용했던 필드 만 복사합니다. 이것은, 인 (필드를 지정하는 장점을 ... 필드를 테이블에 추가하는 경우, 코드가 침입하지 않는 추가 혜택을 가지고

DECLARE @temp TABLE (id AS INT, val as INT) 

IF @ChangeType = 'D' 
    INSERT INTO @temp SELECT id, val FROM DELETED 
ELSE 
    INSERT INTO @temp SELECT id, val FROM INSERTED 
내 마음에


무엇 피하기를 원한다), 당신은 당신이 항상 당신이 필요로하는 것을 복사 할 수 있다는 것을 보장 할 수있다.

+0

모든 필드가 나중에 사용되므로 모든 필드를 선택합니다. 여기에서 요점은 필드 목록을 두 번 이상 지정해야 할 필요가 없으므로 변경 작업을 수행 할 때 오류가 발생할 가능성을 줄이는 것입니다. 결국 같은 열의 목록을 두 번 이상 지정하지 않으면 매우 어리석은 것처럼 보입니다. – Craig

+0

테이블 변수와 #temp 테이블의 차이점은 로깅, 재 컴파일 및 통계입니다. 메모리 대 디스크가 아닙니다. 'declare @a table (c int) insert into a select 1 union all select 2 sys.fn_PhysLocFormatter (%% physloc %%) from @ a'를 선택하면 파일이 표시됩니다. 행. 물론 그 페이지는 디스크에 플러시되지 않을 수도 있지만'# temp' 테이블에도 동일하게 적용됩니다. –

관련 문제