ODBC 드라이버의 연결 복원력
애플리케이션이 계속 연결되어 있는지 확인하기 위해 ODBC 드라이버는 유휴 연결을 복원할 수 있습니다.
Important
연결 복원력 기능은 Microsoft Azure SQL Database, Fabric SQL Database 및 SQL Server 2014 이상 서버 버전에서 지원됩니다.
이 기능은 Microsoft ODBC Driver 11 for SQL Server부터 Windows에서 사용할 수 있습니다. Linux에서는 Microsoft ODBC Driver 17 for SQL Server의 버전 17.2부터 사용할 수 있습니다.
유휴 연결 복원력에 대한 자세한 내용은 기술 문서 - 유휴 연결 복원력을 참조하세요.
재연결 동작을 제어하기 위해 ODBC Driver for SQL Server에는 다음과 같은 두 가지 옵션이 있습니다.
연결 다시 시도 횟수.
연결 다시 시도 횟수는 연결 오류가 있는 경우 다시 연결을 시도할 횟수를 제어합니다. 유효한 값은 0에서 255 사이입니다. 값이 0이면 다시 연결을 시도하지 않습니다. 기본값은 재연결 시도 한 번입니다.
다음과 같이 연결 다시 시도 횟수를 수정할 수 있습니다.
연결 다시 시도 횟수 제어로 ODBC Driver for SQL Server를 사용하는 데이터 원본을 정의하거나 수정합니다.
ConnectRetryCount
연결 문자열 키워드(keyword)를 사용합니다.•
SQL_COPT_SS_CONNECT_RETRY_COUNT
(읽기 전용) 연결 속성을 사용하여 연결 다시 시도 횟수를 검색합니다. 응용 프로그램에서 연결 복원력을 지원하지 않는 서버에 연결하는 경우SQL_COPT_SS_CONNECT_RETRY_COUNT
는 0을 반환합니다.
연결 다시 시도 간격.
연결 다시 시도 간격은 각각의 연결 다시 시도 사이의 시간(초)을 지정합니다. 유효한 값은 1-60입니다. 다시 연결하기 위한 총 시간은 연결 시간 제한(SQLSetStmtAttr의 SQL_ATTR_QUERY_TIMEOUT)을 초과할 수 없습니다. 기본값은 10초입니다.
다음과 같이 하면 연결 다시 시도 간격을 수정할 수 있습니다.
연결 다시 시도 간격 제어로 ODBC Driver for SQL Server를 사용하는 데이터 원본을 정의하거나 수정합니다.
ConnectRetryInterval
연결 문자열 키워드(keyword)를 사용합니다.•
SQL_COPT_SS_CONNECT_RETRY_INTERVAL
(읽기 전용) 연결 속성을 사용하여 연결 다시 시도 간격의 길이를 검색합니다.
응용 프로그램에서 SQL_DRIVER_COMPLETE_REQUIRED 연결을 설정하고 나중에 끊어진 연결을 통해 문을 실행하려고 할 경우 ODBC 드라이버가 대화 상자를 다시 표시하지 않습니다. 복구가 진행 중인 동안
- 복구하는 동안
SQLGetConnectAttr(SQL_COPT_SS_CONNECTION_DEAD)
에 대한 모든 호출에서SQL_CD_FALSE
가 반환되어야 합니다. - 복구 실패 시
SQLGetConnectAttr(SQL_COPT_SS_CONNECTION_DEAD)
에 대한 모든 호출에서SQL_CD_TRUE
가 반환되어야 합니다.
다음 상태 코드는 서버에서 명령을 실행하는 모든 함수에서 반환됩니다.
State(상태) | 메시지 |
---|---|
IMC01 |
The connection is broken and recovery is not possible. The client driver attempted to recover the connection one or more times and all attempts failed. Increase the value of ConnectRetryCount to increase the number of recovery attempts. |
IMC02 |
The server did not acknowledge a recovery attempt, connection recovery is not possible. |
IMC03 |
The server did not preserve the exact client TDS version requested during a recovery attempt, connection recovery is not possible. |
IMC04 |
The server did not preserve the exact server major version requested during a recovery attempt, connection recovery is not possible. |
IMC05 |
The connection is broken and recovery is not possible. The connection is marked by the server as unrecoverable. No attempt was made to restore the connection. |
IMC06 |
The connection is broken and recovery is not possible. The connection is marked by the client driver as unrecoverable. No attempt was made to restore the connection. |
예시
다음 샘플에는 두 가지 함수가 포함되어 있습니다. func1
은 Windows 기반 ODBC Driver for SQL Server를 사용하는 DSN(데이터 원본 이름)과 연결할 수 있는 방법을 보여 줍니다. DSN은 SQL Server 인증을 사용하며 사용자 ID를 지정합니다. 그런 다음 func1
은 SQL_COPT_SS_CONNECT_RETRY_COUNT
를 사용하여 연결 다시 시도 횟수를 검색합니다.
func2
는 연결 다시 시도 및 다시 시도 간격에 대한 설정을 검색하기 위해 SQLDriverConnect
, ConnectRetryCount
연결 문자열 키워드(keyword), 연결 속성을 사용합니다.
// Connection_resiliency.cpp
// compile with: odbc32.lib
#include <windows.h>
#include <stdio.h>
#include <sqlext.h>
#include <msodbcsql.h>
void func1() {
SQLHENV henv;
SQLHDBC hdbc;
SQLHSTMT hstmt;
SQLRETURN retcode;
SQLSMALLINT i = 21;
// Allocate environment handle
retcode = SQLAllocHandle(SQL_HANDLE_ENV, SQL_NULL_HANDLE, &henv);
// Set the ODBC version environment attribute
if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) {
retcode = SQLSetEnvAttr(henv, SQL_ATTR_ODBC_VERSION, (void*)SQL_OV_ODBC3, 0);
// Allocate connection handle
if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) {
retcode = SQLAllocHandle(SQL_HANDLE_DBC, henv, &hdbc);
// Set login timeout to 5 seconds
if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) {
SQLSetConnectAttr(hdbc, SQL_LOGIN_TIMEOUT, (SQLPOINTER)5, 0);
// Connect to data source
retcode = SQLConnect(hdbc, (SQLCHAR*)"MyDSN", SQL_NTS, (SQLCHAR*)"userID", SQL_NTS, (SQLCHAR*)"password_for_userID", SQL_NTS);
retcode = SQLGetConnectAttr(hdbc, SQL_COPT_SS_CONNECT_RETRY_COUNT, &i, SQL_IS_INTEGER, NULL);
// Allocate statement handle
if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) {
retcode = SQLAllocHandle(SQL_HANDLE_STMT, hdbc, &hstmt);
// Process data
if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) {
SQLFreeHandle(SQL_HANDLE_STMT, hstmt);
}
SQLDisconnect(hdbc);
}
SQLFreeHandle(SQL_HANDLE_DBC, hdbc);
}
}
SQLFreeHandle(SQL_HANDLE_ENV, henv);
}
}
void func2() {
SQLHENV henv;
SQLHDBC hdbc1;
SQLHSTMT hstmt;
SQLRETURN retcode;
SQLSMALLINT i = 21;
#define MAXBUFLEN 255
SQLCHAR ConnStrIn[MAXBUFLEN] = "DRIVER={ODBC Driver 18 for SQL Server};SERVER=server_that_supports_connection_resiliency;Encrypt=yes;UID=userID;PWD=<password>;ConnectRetryCount=2";
SQLCHAR ConnStrOut[MAXBUFLEN];
SQLSMALLINT cbConnStrOut = 0;
// Allocate environment handle
retcode = SQLAllocHandle(SQL_HANDLE_ENV, SQL_NULL_HANDLE, &henv);
// Set the ODBC version environment attribute
if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) {
retcode = SQLSetEnvAttr(henv, SQL_ATTR_ODBC_VERSION, (SQLPOINTER*)SQL_OV_ODBC3_80, SQL_IS_INTEGER);
// Allocate connection handle
if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) {
retcode = SQLAllocHandle(SQL_HANDLE_DBC, henv, &hdbc1);
// Set login timeout to 5 seconds
if (retcode == SQL_SUCCESS || retcode == SQL_SUCCESS_WITH_INFO) {
// SQLSetConnectAttr(hdbc1, SQL_LOGIN_TIMEOUT, (SQLPOINTER)5, 0);
retcode = SQLDriverConnect(hdbc1, NULL, ConnStrIn, SQL_NTS, NULL, 0, NULL, SQL_DRIVER_NOPROMPT);
}
retcode = SQLGetConnectAttr(hdbc1, SQL_COPT_SS_CONNECT_RETRY_COUNT, &i, SQL_IS_INTEGER, NULL);
retcode = SQLGetConnectAttr(hdbc1, SQL_COPT_SS_CONNECT_RETRY_INTERVAL, &i, SQL_IS_INTEGER, NULL);
}
}
}
int main() {
func1();
func2();
}