2013-04-05 4 views
1

웹 응용 프로그램. C#, SQL 2k8교착 상태 대 로깅

실제 동적 SQL이 실행되기 전에 많은 일들이 진행되고 원하는 레코드가 반환됩니다.

최근에 트랜잭션 커밋과 전체 앱 (교착 상태 문제)에 대해 몇 가지 코드를 추가하고 전체 9 야드를 롤백하고 다시 시도해보십시오.

큰 플러스이지만, 정말 필요했습니다.

하지만 목록에 가능한 모든 문제를 디버깅하기 위해

, 나는 (옛 기록을 주 단지 지난 몇 저장하지 않습니다) 로그 테이블에 동적 SQL 문자열

을 저장했다 문제는 다음과 같습니다. 현재 목록이 손상된 경우 로그가 없습니다. 때문에 롤백 물건 ...

내 최고의 아이디어는 지금까지 두 번 목록을 호출했다 :

  1. 는 "확인"- 모드, 동적 SQL을 만들 로그 TBL에 저장됩니다, 하지만

  2. "목록"EXEC하지 않을 것이다 - 모드 중 하나를 것입니다 :

도 2a. 동적 SQL을

또는

2B를 다시 계산. "check-mode

둘 중 하나 또는 2b 중 하나 인 동적 SQL을 동적으로 재사용하는 것은 목록 저장 프로 시저 중 가장 비싼 부분이 동적 SQL의 실제 실행이기 때문에 성능상의 문제가 없어야합니다. "- 모드는 기본적인 문자열 연결입니다

교착 상태 재시 부분은도 좋다 번째 DB 호출을 할 것입니다 여전히

나는이 생각에 가장 행복한 사람이 아니다 궁금 .!.. 이것을 달성하는 더 좋은 방법이 있다면.

+0

전체 재시도 논리가 하나의 거대한 트랜잭션에 있습니까? 아니면 다시 시도 할 때마다 새 트랜잭션을 시작합니까? – mellamokb

+0

마다 재시도가 새로운 트랜잭션입니다. – Ash

답변

1

트랜잭션 도중 데이터를 저장하기 위해 TRY CATCH 블록과 함께 (테이블) 변수를 사용할 수 있습니다. 변수는 롤백 후 보관됩니다.

BEGIN TRY 
    BEGIN TRAN 

    DECLARE @SQL NVARCHAR(MAX) 
    SET @SQL = 'SELECT 1' 

    RAISERROR('A',16,1) 

    EXEC (@SQL) 

    COMMIT 

END TRY 
BEGIN CATCH 
    ROLLBACK 
    SELECT @SQL --WRITE TO LOG TABLE 

END CATCH 

을 그리고 당신의 트랜잭션이 SP의 외부에있는 경우 - (일반적으로 좋은 생각입니다) C# 코드에서, 당신은 할 수 있습니다 당신의 번역이 내부 저장 프로 시저를하는 경우

, 즉,이 같은 것을 볼 수 있습니다 일어난 액추얼 오류와 함께 RAISERROR로 앱에 변수를 다시 보냅니다. 다음과 같은 내용 :

BEGIN TRY 

    DECLARE @SQL NVARCHAR(MAX) 
    SET @SQL = 'SELECT 1' 

    RAISERROR('A',16,1) 

    EXEC (@SQL) 

END TRY 
BEGIN CATCH 

    DECLARE @ErrorMessage NVARCHAR(4000) 
    DECLARE @ErrorSeverity INT 
    DECLARE @ErrorState INT 

    SELECT 
     @ErrorMessage = 'Error: ' + ERROR_MESSAGE() + '; SQL: ' + @SQL, 
     @ErrorSeverity = ERROR_SEVERITY(), 
     @ErrorState = ERROR_STATE() 

    RAISERROR (@ErrorMessage,@ErrorSeverity,@ErrorState) 

END CATCH 
+0

사실 SQL이 (다소) 죽었으므로 SQL에서 트랜잭션을 생성하지 않습니다. 트랜잭션과 재시도 부분은 모두 C#입니다. 스토어드 프로 시저의 모든 작업을 수행합니다. – Ash

+0

@Swoosh OK, 제가 말했듯이 그것은 더 좋은 아이디어입니다.SP의 TRY/CATCH 블록을 사용하여 오류를 처리하고 생성 된 동적 SQL과 함께 C#으로 다시 전송할 수 있습니다 (C#에서 로깅을 수행). 또한, 두 개의 SP에 대한 귀하의 아이디어에는 아무런 문제가 없습니다. 2b 아이디어가 정확히 있어야합니다. 하나의 SP는 동적 SQL을 준비하고 로깅하고, 다른 하나는이를 실행합니다. –