URI 파일 이름

URI 파일 이름 (Uniform Resource Identifiers)

SQLite에서 데이터베이스 파일을 지정할 때 file: URI 형식을 사용하는 방법을 다루는 문서예요. SQLite는 URI 쿼리 매개변수를 이용해 데이터베이스 연결의 세부 동작을 제어할 수 있어요.

출처: URI Filenames In SQLite (sqlite.org)

본문

1. SQLite의 URI 파일 이름

3.7.7 버전(2011-06-23)부터 sqlite3_open(), sqlite3_open16(), sqlite3_open_v2() 인터페이스와 ATTACH 명령에 전달하는 데이터베이스 파일 인자는 일반 파일 이름으로 지정하거나 URI(Uniform Resource Identifier)로 지정할 수 있어요. URI 파일 이름을 사용하면 URI의 쿼리 매개변수로 새로 생성되는 데이터베이스 연결의 세부 동작을 제어할 수 있는 장점이 있어요. 예를 들어 vfs= 쿼리 매개변수로 대체 VFS를 지정할 수 있고, mode=ro 쿼리 매개변수로 데이터베이스를 읽기 전용으로 열 수도 있어요.

2. 하위 호환성 (Backwards Compatibility)

기존 응용 프로그램과의 완전한 하위 호환성을 유지하기 위해 URI 파일 이름 기능은 기본적으로 비활성화되어 있어요. URI 파일 이름은 컴파일 타임 옵션인 SQLITE_USE_URI=1 또는 SQLITE_USE_URI=0으로 활성화/비활성화할 수 있어요. URI 파일 이름의 컴파일 타임 설정은 시작 시점에 sqlite3_config(SQLITE_CONFIG_URI,1) 또는 sqlite3_config(SQLITE_CONFIG_URI,0) 설정 호출로 바꿀 수 있어요. 컴파일 타임이나 시작 시점 설정과 관계없이, sqlite3_open_v2(N,P,F,V)의 F 매개변수로 전달되는 비트 집합에 SQLITE_OPEN_URI 비트를 포함하면 개별 데이터베이스 연결에 대해 URI 파일 이름을 활성화할 수 있어요.

데이터베이스 연결이 처음 열릴 때 URI 파일 이름을 인식하도록 되어 있다면 ATTACH 문에서도 URI 파일 이름을 인식해요. 마찬가지로 연결이 처음 열릴 때 URI 파일 이름을 인식하지 않도록 되어 있다면 ATTACH에서도 인식하지 않아요.

SQLite는 URI 설정과 관계없이 file:로 시작하지 않는 파일 이름은 항상 일반 파일 이름으로 해석해요. 그리고 실제 파일이 file:로 시작하는 경우는 매우 드물기 때문에, 대부분의 응용 프로그램은 현재 URI 파일 이름을 사용하지 않더라도 URI 처리를 활성화해도 안전해요.

3. URI 형식

RFC 3986에 따르면 URI는 scheme(스킴), authority(권한), path(경로), query string(쿼리 문자열), fragment(프래그먼트)로 이루어져 있어요. 스킴은 항상 필요하고, authority 또는 path 중 하나도 항상 필요해요. 쿼리 문자열과 프래그먼트는 선택 사항이에요.

SQLite는 데이터베이스 파일을 식별하기 위해 file: URI 구문을 사용해요. SQLite는 Firefox, Chrome, Safari, Internet Explorer, Opera 같은 인기 웹 브라우저와, Windows의 "cmd start""powershell start", macOS의 "open", Linux의 "xdg-open" 같은 명령줄 프로그램과 정확히 같은 방식으로 file: URI를 해석하려고 노력해요. URI 구문 분석 규칙을 간단히 요약하면 다음과 같아요.

  • URI의 스킴은 반드시 file:이어야 해요. 다른 스킴이면 입력을 일반 파일 이름으로 취급해요.
  • authority는 생략하거나 비어 있거나 localhost일 수 있어요. 그 외의 authority는 오류가 나요. 예외적으로, SQLite가 SQLITE_ALLOW_URI_AUTHORITY로 컴파일되었다면 "localhost"가 아닌 authority 값은 UNC 파일 이름으로 기본 운영체제에 그대로 전달돼요.
  • authority가 있으면 path는 선택 사항이에요. authority가 생략되면 path가 필수예요.
  • 쿼리 문자열은 선택 사항이에요. 쿼리 문자열이 있으면 모든 쿼리 매개변수가 기본 VFS의 xOpen 메서드로 전달돼요.
  • fragment는 선택 사항이에요. 있으면 무시돼요.

path, 쿼리 문자열, fragment에는 "%HH" 형식(**H**는 16진수 숫자)의 이스케이프 시퀀스가 0개 이상 들어갈 수 있어요.

잘 구성되지 않은(well-formed) URI가 아닌 파일 이름은 일반 파일 이름으로 해석돼요.

URI는 UTF8 텍스트로 처리돼요. sqlite3_open16()의 파일 이름 인자는 처리 전에 UTF16 네이티브 바이트 순서에서 UTF8로 변환돼요.

3.1. URI 경로 (The URI Path)

URI의 path 구성 요소는 열려는 SQLite 데이터베이스인 디스크 파일을 지정해요. path 구성 요소가 생략되면 데이터베이스는 임시 파일에 저장되고, 데이터베이스 연결이 닫힐 때 자동으로 삭제돼요. authority 부분이 있으면 path는 항상 절대 경로예요. authority 부분이 생략되면 path가 "/" 문자(ASCII 코드 0x2f)로 시작할 때는 절대 경로이고, 그 외에는 상대 경로예요. Windows에서 절대 경로가 "/X:/"로 시작하고 X가 단일 ASCII 알파벳 문자("a""z" 또는 "A""Z")라면, "X:"는 파일이 들어 있는 볼륨의 드라이브 문자로 해석되지 최상위 디렉터리로는 해석되지 않아요.

일반 파일 이름은 보통 아래 단계를 거쳐 동등한 URI로 변환할 수 있어요. 단, 드라이브 문자가 있는 Windows 상대 경로는 바로 URI로 변환할 수 없고, 먼저 절대 경로로 바꿔야 해요.

  1. 모든 "?" 문자를 "%3f"로 변환해요.
  2. 모든 "#" 문자를 "%23"로 변환해요.
  3. Windows에서만 모든 "\" 문자를 "/"로 변환해요.
  4. 두 개 이상 연속된 "/" 문자를 단일 "/" 문자로 변환해요.
  5. Windows에서만 파일 이름이 드라이브 문자로 시작하면 앞에 "/" 문자 하나를 붙여요.
  6. "file:" 스킴을 앞에 붙여요.

3.2. 쿼리 문자열 (Query String)

URI 파일 이름 뒤에는 선택적으로 쿼리 문자열이 올 수 있어요. 쿼리 문자열은 첫 번째 "?" 문자 뒤에 오는 텍스트로, "#"로 시작하는 선택적 fragment는 제외해요. 쿼리 문자열은 key/value 쌍으로 나뉘어요. 보통 이 key/value 쌍을 "쿼리 매개변수"라고 불러요. key/value 쌍은 단일 "&" 문자로 구분되고, key가 먼저 오고 단일 "=" 문자로 value와 구분돼요. key와 value 모두 %HH 이스케이프 시퀀스를 포함할 수 있어요.

쿼리 매개변수의 텍스트는 VFS의 xOpen 메서드의 파일 이름 인자에 덧붙여져요. 쿼리 매개변수의 %HH 이스케이프 시퀀스는 xOpen 파일 이름에 덧붙여지기 전에 해석돼요. 단일 0바이트가 xOpen 파일 이름 인자와 첫 번째 쿼리 매개변수의 key를 구분하고, 각 key와 value, 그리고 이전 value와 다음 key를 구분해요. xOpen 파일 이름에 덧붙여지는 쿼리 매개변수 목록은 길이가 0인 key 하나로 끝나요. 쿼리 매개변수의 value는 빈 문자열일 수 있다는 점에 주의하세요.

3.3. 인식되는 쿼리 매개변수 (Recognized Query Parameters)

일부 쿼리 매개변수는 SQLite 코어가 해석해서 새 연결의 특성을 바꾸는 데 사용해요. 모든 쿼리 매개변수는 SQLite 코어가 먼저 읽고 해석하더라도 항상 VFS의 xOpen 메서드로 전달돼요.

아래 쿼리 매개변수는 3.15.0 버전(2016-10-14) 기준으로 SQLite가 인식해요. 앞으로 새 쿼리 매개변수가 추가될 수 있어요.

cache=shared
cache=private

cache 쿼리 매개변수는 새 데이터베이스를 shared cache 모드로 열지, 개인 캐시(private cache)로 열지를 결정해요.

immutable=1

immutable 쿼리 매개변수는 불리언 값으로, 기본 데이터베이스 파일이 읽기 전용 매체에 있어서 수정할 수 없음을 SQLite에 알려줘요. 심지어 다른 권한을 가진 프로세스조차 수정할 수 없음을 나타내요. SQLite는 immutable 데이터베이스 파일을 항상 읽기 전용으로 열고, 모든 파일 잠금과 변경 감지를 건너뛰어요. 이 쿼리 매개변수(또는 xDeviceCharacteristics의 SQLITE_IOCAP_IMMUTABLE 비트)가 데이터베이스 파일이 immutable이라고 주장했는데 파일이 실제로 변경되면, SQLite는 잘못된 쿼리 결과를 반환하거나 SQLITE_CORRUPT 오류를 낼 수 있어요.

mode=ro
mode=rw
mode=rwc
mode=memory

mode 쿼리 매개변수는 새 데이터베이스를 읽기 전용으로 열지, 읽기-쓰기로 열지, 없으면 생성하며 읽기-쓰기로 열지, 아니면 디스크와 전혀 상호작용하지 않는 순수 인메모리 데이터베이스로 할지를 각각 결정해요.

modeof=filename

unix 시스템에서 sqlite3_open_v2() 중에 새 데이터베이스 파일을 만들 때, SQLite는 새 데이터베이스 파일의 권한을 기존 파일 "filename"의 권한과 일치하도록 설정하려고 해요.

nolock=1

nolock 쿼리 매개변수는 불리언 값으로, true일 때 VFS의 xLock, xUnlock, xCheckReservedLock 메서드에 대한 모든 호출을 비활성화해요. 예를 들어 파일 잠금을 지원하지 않는 파일 시스템의 파일에 접근할 때 nolock 쿼리 매개변수를 사용할 수 있어요. 주의: 두 개 이상의 데이터베이스 연결이 같은 SQLite 데이터베이스와 상호작용하려 할 때 그중 하나 이상이 "nolock"을 활성화했다면 데이터베이스 손상(corruption)이 발생할 수 있어요. "nolock" 쿼리 매개변수는 응용 프로그램이 데이터베이스에 대한 쓰기가 직렬화됨을 보장할 수 있을 때만 사용해야 해요.

psow=0
psow=1

psow 쿼리 매개변수는 열리는 데이터베이스 파일의 powersafe overwrite 속성을 재정의해요. psow 쿼리 매개변수는 기본 windows와 unix VFS에서는 동작하지만, 다른 독점적이거나 비표준 VFS에서는 아무 효과가 없을 수 있어요.

vfs=NAME

vfs 쿼리 매개변수는 데이터베이스 연결을 _NAME_이라는 VFS로 열게 해요. _NAME_이 SQLite에 내장되거나 sqlite3_vfs_register()로 이전에 등록된 VFS의 이름이 아니면 열기 시도는 실패해요.

더 알아보기 (Learn more)