적용 대상:SQL Server
Azure SQL Database
Azure SQL Managed Instance
Microsoft Fabric의 SQL 데이터베이스
같은 범위에서 ID 열에 삽입된 마지막 ID 값을 반환합니다. 범위는 저장 프로시저, 트리거, 함수 또는 일괄 처리와 같은 모듈입니다. 따라서 두 문이 같은 저장 프로시저, 함수 또는 일괄 처리에 있으면 같은 범위에 있는 것입니다.
구문
SCOPE_IDENTITY()
반환 형식
numeric(38,0)
설명
SCOPE_IDENTITY, IDENT_CURRENT 및 @@IDENTITY는 ID 열에 삽입된 값을 반환하기 때문에 비슷한 함수입니다.
IDENT_CURRENT는 범위와 세션으로 제한되는 것이 아니라 지정된 테이블로 제한됩니다. IDENT_CURRENT는 임의 세션 및 범위에 있는 특정 테이블에 생성된 값을 반환합니다. 자세한 내용은 IDENT_CURRENT(Transact-SQL)를 참조하세요.
SCOPE_IDENTITY 및 @@IDENTITY는 현재 세션의 테이블에서 생성된 마지막 ID 값을 반환합니다. 그러나 SCOPE_IDENTITY는 현재 범위 내에 삽입된 값을 반환합니다. @@IDENTITY는 특정 범위로 제한되지 않습니다.
예를 들어 두 개의 테이블 T1과 T2가 있고 T1에 INSERT 트리거가 정의되어 있다고 가정합니다. T1에 행이 삽입될 때 트리거가 발생하고 T2에서 행을 삽입합니다. 이 시나리오에서는 T1에서의 삽입과 트리거에 의한 T2에서의 삽입이라는 두 범위를 보여 줍니다.
T1과 T2에 모두 ID 열이 있고 @@IDENTITY 및 SCOPE_IDENTITY가 T1에서 INSERT 문 끝에 다른 값을 반환한다고 가정해 봅니다. @@IDENTITY는 현재 세션의 범위에서 삽입된 마지막 ID 열 값을 반환합니다. 이 값은 T2에 삽입된 값입니다. SCOPE_IDENTITY()는 T1에 삽입된 IDENTITY 값을 반환합니다. 이 값은 같은 범위에서 발생한 마지막 삽입 값입니다. 범위에서 ID 열에 INSERT 문이 발생하기 전에 SCOPE_IDENTITY() 함수가 호출되면 이 함수는 Null 값을 반환합니다.
문 및 트랜잭션이 실패해도 테이블의 현재 ID가 변경되고 ID 열 값 간에 간격이 생성될 수 있습니다. 테이블에 값을 삽입하려고 시도한 트랜잭션이 커밋되지 않아도 ID 값은 롤백되지 않습니다. 예를 들어 IGNORE_DUP_KEY 위반으로 인해 INSERT 문이 실패해도 테이블의 현재 ID 값은 계속 증가합니다.
예제
A. 트리거에 @@IDENTITY 및 SCOPE_IDENTITY 사용
다음 예에서는 두 개의 테이블 TZ 및 TY를 만들고 TZ에서 INSERT 트리거를 만듭니다.
TZ 테이블에 행이 삽입될 때 트리거(Ztrig)가 발생하고 TY에서 행을 삽입합니다.
USE tempdb;
GO
CREATE TABLE TZ (
Z_id INT IDENTITY(1,1)PRIMARY KEY,
Z_name VARCHAR(20) NOT NULL);
INSERT TZ
VALUES ('Lisa'),('Mike'),('Carla');
SELECT * FROM TZ;
결과 집합: 테이블 TZ를 보여주는 방법입니다.
Z_id Z_name
-------------
1 Lisa
2 Mike
3 Carla
CREATE TABLE TY (
Y_id INT IDENTITY(100,5)PRIMARY KEY,
Y_name VARCHAR(20) NULL);
INSERT TY (Y_name)
VALUES ('boathouse'), ('rocks'), ('elevator');
SELECT * FROM TY;
결과 집합: TY를 보여주는 방법입니다.
Y_id Y_name
---------------
100 boathouse
105 rocks
110 elevator
행이 테이블 TZ에 삽입될 때 행을 테이블 TY에 행을 삽입하는 트리거를 작성합니다.
CREATE TRIGGER Ztrig
ON TZ
FOR INSERT AS
BEGIN
INSERT TY VALUES ('')
END;
트리거를 시작하고 @@IDENTITY 및 SCOPE_IDENTITY 함수로 사용자가 어떤 ID 값을 얻게 할지 결정합니다.
INSERT TZ VALUES ('Rosalie');
SELECT SCOPE_IDENTITY() AS [SCOPE_IDENTITY];
GO
SELECT @@IDENTITY AS [@@IDENTITY];
GO
결과 집합은 다음과 같습니다.
/*SCOPE_IDENTITY returns the last identity value in the same scope. This was the insert on table TZ.*/`
SCOPE_IDENTITY
4
/*@@IDENTITY returns the last identity value inserted to TY by the trigger.
This fired because of an earlier insert on TZ.*/
@@IDENTITY
115
B. 복제에 @@IDENTITY 및 SCOPE_IDENTITY() 사용
다음 예에서는 병합 복제용으로 게시된 데이터베이스에서 삽입을 위해 @@IDENTITY 및 SCOPE_IDENTITY()를 사용하는 방법을 보여 줍니다. 이 예의 두 테이블은 모두 AdventureWorks2025 예제 데이터베이스에 있습니다. Person.ContactType은 게시되지 않았고 Sales.Customer는 게시되었습니다. 병합 복제는 게시된 테이블에 트리거를 추가합니다. 따라서 @@IDENTITY는 사용자 테이블에 대한 삽입 대신 복제 시스템 테이블에 대한 삽입에서 값을 반환할 수 있습니다.
Person.ContactType 테이블의 최대 ID 값은 20입니다. 테이블에 행을 삽입하면 @@IDENTITY 및 SCOPE_IDENTITY()에서 동일한 값을 반환합니다.
USE AdventureWorks2022;
GO
INSERT INTO Person.ContactType ([Name]) VALUES ('Assistant to the Manager');
GO
SELECT SCOPE_IDENTITY() AS [SCOPE_IDENTITY];
GO
SELECT @@IDENTITY AS [@@IDENTITY];
GO
결과 집합은 다음과 같습니다.
SCOPE_IDENTITY
21
@@IDENTITY
21
Sales.Customer 테이블의 최대 ID 값은 29483입니다. 테이블에 행을 삽입하면 @@IDENTITY 및 SCOPE_IDENTITY()에서 서로 다른 값을 반환합니다.
SCOPE_IDENTITY()는 사용자 테이블에 대한 삽입에서 값을 반환하는 반면 @@IDENTITY는 복제 시스템 테이블에 대한 삽입에서 값을 반환합니다. 삽입된 ID 값에 액세스해야 하는 애플리케이션에 대해 SCOPE_IDENTITY()를 사용합니다.
INSERT INTO Sales.Customer ([TerritoryID],[PersonID]) VALUES (8,NULL);
GO
SELECT SCOPE_IDENTITY() AS [SCOPE_IDENTITY];
GO
SELECT @@IDENTITY AS [@@IDENTITY];
GO
결과 집합은 다음과 같습니다.
SCOPE_IDENTITY
29484
@@IDENTITY
89