::NPTEAM:: Network Programer Team

검색 :
RSS 구독 : 글 / 댓글 / 트랙백 / 글+트랙백

MS-SQL 2005의 TRY _ CATCH를 써보자

2009/09/10 13:43, 글쓴이 TTF
CREATE PROCEDURE NormalInsert(
	@Context nvarchar(100)
)
AS
BEGIN
	SET NOCOUNT ON

	DECLARE @StartTime    DATETIME
	SET @StartTime = GETDATE()

	DECLARE @LoopCount INT
	SET @LoopCount = 10000

	WHILE( @LoopCount > 0 )
	BEGIN
		BEGIN TRANSACTION
			INSERT SendBox(Context) values (@Context)
			IF( @@Error <> 0 or @@RowCount = 0)
			BEGIN
				ROLLBACK TRANSACTION
				RAISERROR('Error when processing INSERT statement or Task Table.',15,1)
				RETURN -100
			END

		COMMIT TRANSACTION

		SET @LoopCount = @LoopCount - 1
	END

	PRINT 'Elapsed Time : ' + convert( varchar(128), GETDATE() - @StartTime, 114 )

	RETURN
END
GO

Normal Insert 사용시
Elapsed Time : 00:00:02:653
Elapsed Time : 00:00:02:593
Elapsed Time : 00:00:02:560
Elapsed Time : 00:00:02:737
Elapsed Time : 00:00:02:593
CREATE PROCEDURE TryInsert(
	@Context nvarchar(100)
)
AS
BEGIN
	SET NOCOUNT ON

	DECLARE @StartTime    DATETIME
	SET @StartTime = GETDATE()

	DECLARE @LoopCount INT
	SET @LoopCount = 10000

	WHILE( @LoopCount > 0 )
	BEGIN
		BEGIN TRY
			BEGIN TRANSACTION
				INSERT SendBox(Context) values (@Context)
			COMMIT TRANSACTION
		END TRY

		BEGIN CATCH
			ROLLBACK TRANSACTION

			BEGIN
				RAISERROR('Error when processing INSERT statement or Task Table.',15,1)
				RETURN -100
			END
		END CATCH

		SET @LoopCount = @LoopCount - 1
	END

	PRINT 'Elapsed Time : ' + convert( varchar(128), GETDATE() - @StartTime, 114 )

	RETURN
END
GO

Try Insert 사용시
Elapsed Time : 00:00:02:860
Elapsed Time : 00:00:02:810
Elapsed Time : 00:00:03:063
Elapsed Time : 00:00:02:640
Elapsed Time : 00:00:02:767
2009/09/10 13:43 2009/09/10 13:43

맨 위로

[MS-SQL] BAK 파일을 새로운 DATABASE로 복원하기(attach_db_from_backup)

2008/10/11 00:24, 글쓴이 TTF

MDF 파일만 있을 경우에는 sp_attach_single_file_db 프로시저를 이용해서 아주 간편하고 쉽게 DB를 복원할 수 있다.

그러나 Backup(BAK) 파일의 경우에는 복원하는데 약간 불편함을 감수해야 한다.

아래의 프로시저를 이용하면 이러한 불편함을 약간이나마 해소할 수 있다.


IF EXISTS (SELECT * FROM dbo.sysobjects WHERE id = object_id(N'[dbo].[_Attach_DB_From_Backup]') AND OBJECTPROPERTY(id, N'IsProcedure') = 1)
DROP procedure [dbo].[_Attach_DB_From_Backup]
GO
  
SET QUOTED_IDENTIFIER ON 
GO
SET ANSI_NULLS ON 
GO
  
  
CREATE PROCEDURE [dbo]._Attach_DB_From_Backup
  @strRestoreDBName varchar(128),
  @strBackupFilePath  varchar(255)
AS
  
-- master DB 체크
IF DB_NAME() <> 'master'
BEGIN
  RAISERROR( 'current database name was not "master". You should be change "master" database', 16, 1 )
  RETURN
END
  
-- 생성할 DB가 존재하는지 체크
IF EXISTS (SELECT * FROM  master..sysdatabases WHERE name = @strRestoreDBName )
BEGIN
  RAISERROR( 'It was already existed database name. Try to execute procedure another DB name', 16, 1 )
  RETURN
END
  
-- 실행 시간 측정
declare @StartTime datetime
SET @StartTime = GetDate()
  
-- 동적 실행 쿼리로 쓰일 변수
declare @strQuery nvarchar(2048)
  
-- DB 생성
SET @strQuery = 'CREATE DATABASE ' + @strRestoreDBName
EXEC sp_executesql @strQuery
  
  
-- 임시 테이블 생성 - (Backup 파일에서 정보 추출)
CREATE TABLE #FileListInfo
(
  LogicalName nvarchar(128)  NULL,
  PhysicalName  nvarchar(260) NULL,
  Type    char(1)   NULL,
  FileGroupName nvarchar(128)  NULL,
  [Size]    numeric(20,0) NULL,
  [MaxSize] numeric(20,0)  NULL
  [FileID]    bigint    NULL,
  [CreateLSN]    numeric(25,0)  NULL,
  [DropLSN]    numeric(25,0)  NULL,
  [UniqueID]    uniqueidentifier NULL,
  [ReadOnlyLSN]   numeric(25,0)  NULL,
  [ReadWriteLSN]   numeric(25,0)  NULL,
  [BackupSizeInBytes]  bigint    NULL,
  [SourceBlockSize]  int     NULL,
  [FileGroupID]   int     NULL,
  [LogGroupGUID]   uniqueidentifier NULL,
  [DifferentialBaseLSN] numeric(25,0)  NULL,
  [DifferentialBaseGUID] uniqueidentifier NULL,
  [IsReadOnly]   bit     NULL,
  [IsPresent]    bit     NULL
)
  
-- 임시 테이블 생성 - (생성된 DB에서 정보(MDF, LDF 파일 경로) 추출)
CREATE TABLE #CreatedDBInfo
(
  name    nvarchar(128) NULL,
  filename  nvarchar(260) NULL
)
  
-- Backup 파일로 부터 정보 추출 -> #FileListInfo
SET @strQuery = N'RESTORE FILELISTONLY FROM DISK = ''' + @strBackupFilePath + ''''
INSERT INTO #FileListInfo EXEC sp_executesql @strQuery
  
-- 생성된 DB에서 정보 추출 -> #CreatedDBInfo
SET @strQuery = 'select name, filename from ' + @strRestoreDBName + '.[dbo].sysfiles'
INSERT INTO #CreatedDBInfo EXEC sp_executesql @strQuery
  
  
-- Backup 파일로 부터 LogicalName(Data, Log)를 가져온다.
declare @LogicalName_Data nvarchar(128)
declare @LogicalName_Log  nvarchar(128)
  
SELECT @LogicalName_Data = LogicalName FROM #FileListInfo where Type = 'D'
IF( @@error <> 0 OR @@rowcount = 0 OR @LogicalName_Data IS NULL )
begin
  RAISERROR( 'LogicalName for Data is not exist', 16, 1 )
  DROP TABLE #FileListInfo
  DROP TABLE #CreatedDBInfo
  
  SET @strQuery = 'DROP DATABASE ' + @strRestoreDBName
  EXEC sp_executesql @strQuery
  RETURN
end
SELECT @LogicalName_Log  = LogicalName FROM #FileListInfo where Type = 'L'
IF( @@error <> 0 OR @@rowcount = 0 OR @LogicalName_Log IS NULL )
begin
  RAISERROR( 'LogicalName for Log is not exist', 16, 1 )
  DROP TABLE #FileListInfo
  DROP TABLE #CreatedDBInfo
  
  SET @strQuery = 'DROP DATABASE ' + @strRestoreDBName
  EXEC sp_executesql @strQuery
  RETURN
end
  
  
-- 생성된 DB에서 MDF, LDF 파일 경로를 가져온다.
declare @strFileName_Data nvarchar(260)
declare @strFileName_Log  nvarchar(260)
  
  
SELECT @strFileName_Data = filename FROM #CreatedDBInfo where filename like '%MDF%'
IF( @@error <> 0 OR @@rowcount = 0 OR @strFileName_Data IS NULL )
begin
  RAISERROR( '#CreatedDBInfo has not MDF file path', 16, 1 )
  DROP TABLE #FileListInfo
  DROP TABLE #CreatedDBInfo
  
  SET @strQuery = 'DROP DATABASE ' + @strRestoreDBName
  EXEC sp_executesql @strQuery
  RETURN
end
SELECT @strFileName_Log  = filename FROM #CreatedDBInfo where filename like '%LDF%'
IF( @@error <> 0 OR @@rowcount = 0 OR @strFileName_Log IS NULL )
begin
  RAISERROR( '#CreatedDBInfo has not LDF file path', 16, 1 )
  DROP TABLE #FileListInfo
  DROP TABLE #CreatedDBInfo
  
  SET @strQuery = 'DROP DATABASE ' + @strRestoreDBName
  EXEC sp_executesql @strQuery
  RETURN
end
  
-- Backup 파일로 부터 DB를 복원 한다.
SET @strQuery = 'RESTORE DATABASE ' + RTRIM(@strRestoreDBName) + ' FROM DISK = ''' + RTRIM(@strBackupFilePath)
    + ''' WiTH REPLACE, MOVE ''' + RTRIM(@LogicalName_Data) + ''' TO ''' + RTRIM(@strFileName_Data) + ''', '
    + ' MOVE ''' + RTRIM(@LogicalName_Log) + ''' TO ''' + RTRIM(@strFileName_Log) + ''''
  
EXEC sp_executesql @strQuery
  
-- 임시 테이블 Drop
DROP TABLE #FileListInfo
DROP TABLE #CreatedDBInfo
  
SELECT 'Elapsed time : ' + convert( varchar(128), GetDate() - @StartTime, 114 )
  
SET NOCOUNT OFF
  
GO
SET QUOTED_IDENTIFIER OFF 
GO
SET ANSI_NULLS ON 
GO 

참조 사이트
http://www.planet-source-code.com/vb/scripts/ShowCode.asp?txtCodeId=1247&lngWId=5
http://www.sqlteam.com/forums/topic.asp?TOPIC_ID=36961

2008/10/11 00:24 2008/10/11 00:24

맨 위로

[MS-SQL] 테이블 목록 변수에 넣기, 컬럼 목록 변수에 넣기

2008/02/23 01:58, 글쓴이 TTF
 
-- 전체 테이블 목록 변수에 넣기
declare @TableNames varchar(8000)
 
SELECT top 10 @TableNames = coalesce(@TableNames,'') + name + ', '
FROM sysobjects
WHERE xtype = 'U'
 
SELECT LEFT(  @TableNames, LEN(@TableNames) - 1 ) AS TableNames
 
 
--테이블의 컬럼 목록 변수에 넣기
declare @ColumnNames varchar(8000)
declare @TableName varchar(128)
SET   @TableName  = '_TTFID'
 
SELECT top 10 @ColumnNames = coalesce( @ColumnNames, '' ) + name  + ', '
FROM syscolumns
WHERE id = ( SELECT id FROM sysobjects
       WHERE name =  @TableName )
ORDER BY colid
 
SELECT @TableName AS TableName, LEFT( @ColumnNames, LEN( @ColumnNames ) - 1 ) AS ColumnNames
 
2008/02/23 01:58 2008/02/23 01:58

맨 위로

[MS-SQL] INT_MAX를 select 문으로 계산하기

2008/02/19 01:17, 글쓴이 TTF
우리는 프로그래밍 할때 숫자를 BYTE 단위로 나누어서 쓰는 것을 즐겨 사용하곤 했었습니다.
int _tmain(int argc, _TCHAR* argv[])
{
  int nValue = 65535;
 
  int nLowValue = LOBYTE( nValue );
  int nHighValue = HIBYTE( nValue );
 
  cout << "nLowValue : " << nLowValue << endl;
  cout << "nHighValue : " << nHighValue << endl;
 
  return 0;
}

C++ 코딩에서는 위와 같이 매크로를 이용해서 BYTE 단위로 쪼개기도 하고,
int _tmain(int argc, _TCHAR* argv[])
{
  int nValue = 65535;
 
  int nLowValue = nValue & 0xFF;
  int nHighValue = (nValue >> 8) & 0xFF;
 
  cout << "nLowValue : " << nLowValue << endl;
  cout << "nHighValue : " << nHighValue << endl;
 
  return 0;
}

위와 같이 쉬프트 연산자와 & | 연산자를 이용하기도 하였습니다.

그러나 DB의 select 문에서는 위와 같은 방식을 사용할 수 없습니다.
SELECT (256 * 256)

위의 결과는 65535가 정상적으로 출력됩니다. 그럼 문제가 되는 구문을 살펴 보겠습니다.

SELECT (256 * 256 * 256 * 256)

이 구문은 논리적으로 오류가 없어 보입니다. 적어도 C++ 관점에서 본다면 그렇지요.

하지만, 문제점이 있습니다. DB는 기본적으로 select에 대한 계산식은 명시적으로 지정하지 않으면 int 연산으로 casting 하게 됩니다.

따라서 이와 같은 메시지가 나오게 되었습니다.  
서버: 메시지 8115, 수준 16, 상태 2, 줄 1
expression을() 데이터 형식 int()로 변환하는 중 산술 오버플로 오류가 발생했습니다.

그렇다면 어떻게 해결하면 될까요? 답은 간단합니다.
SELECT cast(256 AS bigint) * cast(256 AS bigint) * cast(256 AS bigint) * cast(256 AS bigint)

오버플로우가 발생하지 않도록 더 큰 자료형인 bigint로 캐스팅해서 연산해주면 됩니다.

저런 문제점이 발생한 배경은 bigint 자료형을 HILONG, LOLONG으로 나누고 싶었는데, 256을 4번 곱한 값으로 나누기 연산을 수행했을때, 위와 같은 문제점이 발생하였습니다.

이 문제에 대한 해결책을 알려주신 최선호(약올라)님에게 감사의 말씀을 드립니다.

-- 4번 곱하기가 눈에 거슬리시는 분들을 위한 팁
SELECT power( cast(256 AS bigint), 4)
 
2008/02/19 01:17 2008/02/19 01:17

맨 위로

[MS-SQL]CURSOR 사용시 진행 상황을 표시하자

2008/01/31 00:35, 글쓴이 TTF

IF EXISTS (SELECT * FROM dbo.sysobjects WHERE id = object_id(N'[_Object]') AND OBJECTPROPERTY(id, N'IsUserTable') = 1)
DROP TABLE [_Object]
GO
 
CREATE TABLE [dbo]._Object
(
  ID  int,
  Context varchar(128),
  Date  datetime
)
 
declare @ID     int
declare @Context  varchar(128)
 
SET @ID = 0
 
WHILE( @ID < 10000 )
BEGIN
  SET @ID = @ID + 1
  SET @Context = 'Context' + convert( varchar(10), @ID )
 
  INSERT INTO [dbo].[_Object] (ID, Context, Date) VALUES ( @ID, @Context, GETDATE() )
END
 
SELECT * FROM _Object

위와 같이 _Object 테이블을 먼저 만들면, 다음과 같은 결과가 나옵니다.

그럼 위의 Context 컬럼의 숫자를 10000부터 꺼꾸로 빼는 과정을 Cursor를 이용해서 만들겠습니다.
DECLARE cursor_Obj CURSOR FAST_FORWARD
FOR SELECT ID, Context FROM _Object
 
DECLARE @ID  int
DECLARE @Context varchar(128)
OPEN cursor_Obj
 
FETCH NEXT FROM cursor_Obj INTO @ID, @Context
WHILE (@@fetch_status = 0)
BEGIN
  UPDATE _Object SET Context = 'Context' + convert(varchar(10), 10001 - @ID)
  WHERE ID = @ID
 
  FETCH NEXT FROM cursor_Obj INTO @ID, @Context
END
 
CLOSE cursor_Obj
DEALLOCATE cursor_Obj
GO

ID 컬럼에 인덱스가 걸려있지 않아서 매우 느리고 답답합니다.
느린 실행 예제를 만들기 위한 것이므로 조금만 참아주세요. ㅎㅎ

자, 이제 언제 끝날지 모르는 Cursor 작업에 진행률 표시를 넣어봅시다.
SET NOCOUNT ON
 
---------------------------- 진행 상황 표시 관련 변수 선언 ----------------------------
DECLARE @ProcessRowCount  INT
DECLARE @ProcessCurCount  INT
DECLARE @ProcessPercentage  INT
DECLARE @ProcessPrevPercentage  INT
DECLARE @StartTime    DATETIME
DECLARE @ProcessRatio  INT
 
SET @ProcessRowCount = 0
SET @ProcessCurCount = 0
SET @ProcessPercentage = 0
SET @ProcessPrevPercentage = 0
SET @StartTime = GETDATE()
 
SET @ProcessRatio    = 10 -- Ratio 값 범위(2 - 100) : 값 1 미지원
 
SELECT  @ProcessRowCount = count('') FROM _Object WITH(NOLOCK)
---------------------------------------------------------------------------------------
 
DECLARE cursor_Obj CURSOR FAST_FORWARD
FOR SELECT ID, Context FROM _Object WITH(NOLOCK)
 
DECLARE @ID  int
DECLARE @Context varchar(128)
 
OPEN cursor_Obj
 
FETCH NEXT FROM cursor_Obj INTO @ID, @Context
WHILE (@@fetch_status = 0)
BEGIN
  ---------------------------- 진행 상황 표시 관련 변수 선언 ----------------------------
  SET @ProcessCurCount = @ProcessCurCount + 1
  SET @ProcessPercentage = (@ProcessCurCount * 100 / @ProcessRowCount)
 
  IF ( (@ProcessPercentage % @ProcessRatio) = 0 )
  BEGIN
    IF ( (@ProcessPrevPercentage % @ProcessRatio) <> (@ProcessPercentage % @ProcessRatio) )
    BEGIN
      PRINT 'Elapsed Time : ' + convert( varchar(128), GETDATE() - @StartTime, 114 )
      + ',    Processing...' + convert( varchar(4), @ProcessPercentage ) + '%'
    END
  END
 
  SET @ProcessPrevPercentage = @ProcessPercentage
  ---------------------------------------------------------------------------------------
 
  UPDATE _Object SET Context = 'Context' + convert(varchar(10), 10001 - @ID)
  WHERE ID = @ID
 
  FETCH NEXT FROM cursor_Obj INTO @ID, @Context
END
 
CLOSE cursor_Obj
DEALLOCATE cursor_Obj
GO

위와같이 쿼리를 작성하였으나... "어라! 결과 진행 상황이 안나오고 나중에 한번에 출력되는데?"

이런 의문점이 생기는 것이 당연하다.
의문점이 생기지 않았다면, 위의 쿼리를 다시 실행하고 오세요!!

해결방법 : CTRL+T 텍스트 모드로 결과 출력
이렇게 변경 후 실행하면 실시간으로 진행상황을 알 수 있다.

쿼리를 실행하면 다음과 같은 결과를 얻을 수 있다.
2008/01/31 00:35 2008/01/31 00:35

맨 위로

[MS-SQL] like 사용시 주의할 점

2007/12/19 00:58, 글쓴이 TTF

select * from ... where 절에서 가장 많이 쓰이는 연산자 중의 하나는 바로 "LIKE" 문일 것이다.

Like 문을 이용해서 '%문자열%' 원하는 문자열이 포함되어 있는 컬럼을 쉽고 간편하게 검색할 수 있다.

그러나!! 우리가 많이 쓰는 Like 문에도 헛점이 있다.

위와 같은 테이블이 있을 경우에 다음과 같은 test5에 해당하는 문장을 선택하기 위하여 다음의 쿼리를 질의 하였다.
SELECT * FROM _TTFID
WHERE Context LIKE '%test5%'

결과는 우리가 예상한데로 다음과 같이 출력되었다.

이쯤 되면, "어라? 제대로 잘되는데 뭐가 문제라는 거야?" 라고 반문하시는 분들도 계실것이고, 다음의 문제점을 미리 예측하신 분들도 계실것 입니다.

자 그럼 문제의 쿼리로 넘어가 볼까요?
SELECT * FROM _TTFID
WHERE Context LIKE '[test5%'

분명히 LIKE 문 다음에 '[test5' 이후에 일치하는 모든 결과를 보여줘!! 라고 질의했습니다.
결과는 다음과 같습니다.

엥? 결과가 하나도 안나오네 -_-; 뭐지? 뭘 잘못한거지? 이렇게 당황하셨다면 SQL 도움말에서 like문을 찾아보세요.

와일드카드 문자설명예제
%문자가 0개 이상인 문자열WHERE title LIKE '%computer%'는 책 제목에 'computer' 단어가 있는 모든 책 제목을 찾습니다.
_ (밑줄)단일 문자WHERE au_fname LIKE '_ean'은 ean으로 끝나는 모든 4문자 이름을 찾습니다(Dean, Sean 등).
[ ]지정된 범위([a-f]) 또는 집합([abcdef])에 있는 단일 문자WHERE au_lname LIKE '[C-P]arsen'은 arsen으로 끝나고 C와 P 사이의 단일 문자로 시작하는 저자의 성을 찾습니다. 예를 들면, Carsen, Larsen, Karsen 등입니다.
[^]지정된 범위([^a-f]) 또는 집합([^abcdef])에 없는 단일 문자WHERE au_lname LIKE 'de[^l]%'은 de로 시작하고 그 다음에 오는 문자가 l이 아닌 저자의 성을 모두 찾습니다.


와일드 카드 문자를 주목해서 보시면 눈치 빠르신 분들은 아! 저거였구나! 하실 것 입니다.
문제는 바로 "[" 문자가 와일드카드 문자였다는 것입니다.

만약 질의문을 다음과 같이 했다면 문제가 없었겠지만, 우리는 like 연산자를 이용하여 질의를 하였습니다.
SELECT * FROM _TTFID
WHERE Context = '[test5]'

LIKE 연산자가 대괄호로 시작되는 첫번째 문장을 지정된 범위 또는 집합을 선택하는 와일드카드로 인식했던 것이었습니다.

따라서 DB 내용 입력시 첫번째 문자열은 되도록  특수기호를 피하여 입력하는 것이 좋겠습니다. ^^

그래도 "나는 Like 문으로 꼭 '['로 시작하는 context를 검색하고 말테야!"라고 혈서로 맹세하시는 분들을 위해서 다음의 방법을 알려드립니다.
SELECT * FROM _TTFID
WHERE Context LIKE '[[]test5%'

[ 와일드카드 문자 ] <- 이와 같이 와일드카드 문자를 대괄호로 양쪽에서 감싸주시면 해결됩니다.
2007/12/19 00:58 2007/12/19 00:58

맨 위로

[MSDB] MDF 파일로 DB 생성하기

2007/10/04 20:40, 글쓴이 TTF
MS_SQL 2000은 MDF 파일과 LDF 파일로 나뉘어진다.

MDF는 Main Data 파일을...
LDF는 트랜잭션 및 로그를 저장한다.


1. MDF와 LDF 가 있을 경우에는
sp_attach_db 'DB명', 'MDF 파일 경로', 'LDF 파일 경로'


2. MDF만 있을 경우에는
sp_attach_single_file_db 'DB명', 'MDF 파일 경로'


위와 같은 방법으로 복구할 수 있다.
2007/10/04 20:40 2007/10/04 20:40

맨 위로

수 많은 SP에서 특정 SP찾아내기

2007/07/29 21:17, 글쓴이 TTF

특정문자가 포함된 Store Procedure 또는 특정 이름으로 된 Store Procedure를 찾을 때 유용한 SQL문입니다.

SELECT  A.NAME
FROM SYSOBJECTS A, SYSCOMMENTS B
WHERE  A.ID = B.ID
AND A.NAME LIKE @SP_NAME+ '%'
AND B.TEXT LIKE '%' + @DS_TEXT + '%'

이 SQL을 사용자정의함수로 만들어 놓고 사용하시면, 수많은 SP 중에서 특정 명령어 또는 문자가 포함된 SP를 주욱 찾을 수가 있겠지요. ^^

특히 시스템 유지보수를 할 때 매우 유용하게 쓰인 답니다.

 
2007/07/29 21:17 2007/07/29 21:17

맨 위로

DTS 백업하기

2007/07/29 21:09, 글쓴이 TTF

DTS(MSDB) 백업 및 복구

기본적으로 DTS로 작업을 하고 나면 데이터는 MSDB에 들어 갑니다.

이것은 작업 스케줄이나 복제등의 정보가 들어가는것과 마찬가지로 DTS MSDB에 저장하게 됩니다.

DTS 작업을 하고 나면 스크립트를 저장하는 것이 아니고 MSDB를 백업을 해야만 합니다.

하지만, MSDB는 시스템 데이터베이스이기 때문에 삭제도 함부로 복구도 안 됩니다.
(
뭐 하겠다고 하면 뭔 방법이 없지는 않겠지요)

따라서 MSDB Backup 해서 복구하는 단계를 한번 적어옵니다...

[SQL QUERY]

1. DB 무결성 검사

dbcc checkdb(msdb)

2. MSDB Backup

backup database msdb to disk='c:\msdb.bak' with init

3. 현재 MSDB를 사용하고 있는 사용자가 있는지 확인

sp_who2

4. MSDB를 사용하고 있는 사용자/프로세스가 있을경우 죽임

kill 51

5. master DB 위치에서

use master

go

6. MSDB 옵션을 단일사용자로 변환

sp_dboption 'msdb', 'single user','true'


7. 복구 시작

restore database msdb from disk='c:\msdb.bak' with recovery

8. MSDB 옵션을 다중사용자로 환원

sp_dboption 'msdb', 'single user','false'

9. EM에서 들어가 DTS가 제대로 위치하고 있는지 확인한다.



source server linked server 잡은 후
insert into sysdtspackages
select * from kimms.msdb.dbo.sysdtspackages

-- 7.0 의 dts -> 2000 dts 로 옮기는 과정
insert into sysdtspackages
select * ,0 from lily.msdb.dbo.sysdtspackages
이렇게 복사해도 되고 아니면 가라 msdb 만들어 놓고 저것만
넣어놓고 써도 되고 뭐 쉽게 다 됩니다. ^^
2007/07/29 21:09 2007/07/29 21:09

맨 위로