EXECUTE IMMEDIATE FROM¶
EXECUTE IMMEDIATE FROM은 스테이지의 파일에 지정된 SQL 문을 실행합니다. 이 파일에는 SQL 문 또는 Snowflake Scripting 블록 이 포함될 수 있습니다. 이러한 문은 구문상 올바른 SQL 문이어야 합니다.
EXECUTE IMMEDIATE FROM 명령을 사용하여 Snowflake 세션의 파일에 있는 문을 실행할 수 있습니다.
이 기능은 Snowflake 오브젝트 및 코드의 배포와 관리를 제어하는 메커니즘을 제공합니다. 예를 들어 저장된 스크립트를 실행하여 모든 계정에 대한 표준 Snowflake 환경을 만들 수 있습니다. 구성 스크립트에는 모든 새 계정에 대한 사용자, 역할, 데이터베이스, 스키마를 생성하는 문이 포함될 수 있습니다.
Jinja2 템플릿¶
EXECUTE IMMEDIATE FROM은 Jinja2 템플릿 언어를 사용하여 템플릿 파일을 실행할 수도 있습니다. 템플릿에는 변수와 식이 포함될 수 있으며, 이를 통해 루프, 조건문, 변수 대체, 매크로 등을 사용할 수 있습니다. 템플릿은 다른 템플릿을 포함할 수도 있고 스테이지에 위치한 다른 파일에 정의된 매크로를 가져올 수도 있습니다.
템플릿 언어에 대한 자세한 내용은 Jinja2 설명서 를 참조하십시오.
실행할 템플릿 파일은 다음과 같아야 합니다.
- 구문적으로 유효한 Jinja2 템플릿. 
- 스테이지 또는 Git 리포지토리 복제본 에 있습니다. 
- 구문적으로 유효한 SQL 문을 렌더링할 수 있음. 
템플릿을 사용하면 환경 변수를 사용하여 보다 유연한 제어 구조와 매개 변수화가 가능합니다. 예를 들어, 템플릿을 사용하면 스크립트에 정의된 오브젝트의 배포 대상을 동적으로 선택할 수 있습니다. 템플릿을 사용하여 SQL 스크립트를 렌더링하려면 템플릿 지시문 을 사용하거나 하나 이상의 템플릿 변수가 있는 USING 절 을 추가합니다.
템플릿 지시문¶
두 가지 템플릿 지시문 중 하나를 사용할 수 있습니다.
권장 지시문은 유효한 SQL 구문을 사용합니다.
--!jinja
선택적으로, 대체 지침을 사용할 수 있습니다.
#!jinja
참고
지시문 앞에는 바이트 순서 표시와 최대 10개의 공백 문자(줄 바꿈, 탭, 공백)만 올 수 있습니다. 같은 줄에 있는 지시어 뒤에 오는 모든 문자는 무시됩니다.
템플릿에서 스테이징된 파일의 내용 사용하기¶
템플릿은 SnowflakeFile API 를 통해 직접 또는 Jinja2의 include, import 및 inheritance 기능을 통해 다른 스테이징된 파일을 로딩할 수 있습니다.
파일은 절대 경로로 참조할 수 있습니다.
{% include "@my_stage/path/to/my_template" %}
{% import "@my_stage/path/to/my_template" as my_template %}
{% extends "@my_stage/path/to/my_template" %}
{{ SnowflakeFile.open("@my_stage/path/to/my_template", 'r', require_scoped_url = False).read() }}
포함, 가져오기 및 확장은 상대 경로도 지원하며 SnowflakeFile API 는 범위가 지정된 Snowflake 파일 URLs 을 지원합니다.
{% include "my_template" %}
{% import "../my_template" as my_template %}
{% extends "/path/to/my_template" %}
- 참고 항목:
구문¶
EXECUTE IMMEDIATE
  FROM { absoluteFilePath | relativeFilePath }
  [ USING ( <key> => <value> [ , <key> => <value> [ , ... ] ]  )  ]
  [ DRY_RUN = { TRUE | FALSE } ]
여기서
absoluteFilePath ::= @[ <namespace>. ]<stage_name>/<path>/<filename>relativeFilePath ::= '[ / | ./ | ../ ]<path>/<filename>'
필수 매개 변수¶
절대 파일 경로(absoluteFilePath)¶
- namespace
- database_name.schema_name또는- schema_name형식의 내부 또는 외부 스테이지가 있는 데이터베이스 및/또는 스키마입니다. 데이터베이스와 스키마가 사용자 세션에 대해 현재 사용 중인 경우, 네임스페이스는 선택 사항 입니다. 그렇지 않은 경우, 필수입니다.
- stage_name
- 내부 또는 외부 스테이지의 이름입니다. 
- path
- 스테이지에 있는 파일의 경로이며 대/소문자를 구분합니다. 
- filename
- 실행할 파일의 이름입니다. 구문상 정확하고 유효한 SQL 문을 포함해야 합니다. 각 문은 세미콜론으로 구분해야 합니다. 
상대 파일 경로(relativeFilePath)¶
- path
- 스테이지에 있는 파일의 상대 경로이며 대/소문자를 구분합니다. 상대 경로는 스테이지 파일 시스템의 루트를 나타내는 선행 - /, 현재 디렉터리(상위 파일이 있는 디렉터리)를 가리키는- ./, 상위 디렉터리를 가리키는- ../와 같이 확립된 규칙을 지원합니다. 자세한 내용은 사용법 노트 섹션을 참조하십시오.
- filename
- 실행할 파일의 이름입니다. 구문상 정확하고 유효한 SQL 문을 포함해야 합니다. 각 문은 세미콜론으로 구분해야 합니다. 
선택적 매개 변수¶
- USING ( <key> => <value> [ , <key> => <value> [ , ... ] ] )
- 
템플릿 확장을 매개 변수화하는 데 사용할 수 있는 하나 이상의 키-값 페어를 전달할 수 있습니다. 키-값 페어는 쉼표로 구분된 목록을 구성해야 합니다. USING 절이 있는 경우, 파일은 SQL 스크립트로 실행되기 전에 먼저 Jinja2 템플릿으로 렌더링 됩니다. 여기서 - key은 템플릿 변수의 이름입니다. 템플릿 변수 이름은 선택적으로 큰따옴표(- ")로 묶을 수 있습니다.
- value는 템플릿의 변수에 할당할 값입니다. 문자열 값은- '또는- $$로 묶어야 합니다. 해당 예제는 템플릿 사용법 노트 를 참조하십시오.
 
- DRY_RUN = { TRUE | FALSE }
- 
렌더링된 파일 을 SQL 스크립트로 실행하지 않고 미리 볼지 여부를 지정합니다. - TRUE는 SQL 문을 실행하지 않고 렌더링된 파일 내용을 반환합니다.
- FALSE템플릿에서 SQL 문을 렌더링하고 해당 문을 실행합니다.
 기본값: FALSE
반환¶
EXECUTE IMMEDIATE FROM은 다음을 반환합니다.
- 모든 문이 성공적으로 실행된 경우 파일에 있는 마지막 문의 결과입니다. 
- 파일의 문이 실패한 경우에 나타나는 오류 메시지입니다. - 파일의 문에 오류가 있으면 EXECUTE IMMEDIATE FROM 명령이 실패하고 실패한 문의 오류 메시지를 반환합니다. - 참고 - EXECUTE IMMEDIATE FROM 명령이 실패하고 오류 메시지를 반환하는 경우 파일에서 실패한 문 이전의 문은 모두 성공적으로 완료된 것입니다. 
액세스 제어 요구 사항¶
- EXECUTE IMMEDIATE FROM 명령을 실행하는 데 사용되는 역할 에는 파일이 있는 스테이지에 대한 USAGE(외부 스테이지) 또는 READ(내부 스테이지) 권한이 있어야 합니다. 
- 파일을 실행하는 데 사용되는 역할은 권한이 있는 파일에 있는 문만 실행할 수 있습니다. 예를 들어 파일에 CREATE TABLE 문이 있는 경우 역할에는 계정에서 테이블을 생성하는 데 필요한 권한 이 있어야 하며, 그렇지 않으면 문이 실패합니다. 
스키마의 모든 오브젝트에 대해 작업을 수행하려면 상위 데이터베이스 및 스키마에 대한 USAGE 권한. 스키마에 대한 모든 권한이 부여된 역할은 스키마를 확인할 수 있습니다. 예를 들어, 스키마에 대해 CREATE 권한을 부여받은 역할은 해당 스키마에 대한 USAGE 권한을 함께 부여받지 않더라도 해당 스키마에 대한 오브젝트를 생성할 수 있습니다.
지정된 권한 세트로 사용자 지정 역할을 만드는 방법에 대한 지침은 사용자 지정 역할 만들기 섹션을 참조하십시오.
보안 오브젝트 에 대해 SQL 작업을 수행하기 위한 역할과 권한 부여에 대한 일반적인 정보는 액세스 제어의 개요 섹션을 참조하십시오.
사용법 노트¶
- 실행할 파일의 SQL 문에는 EXECUTE IMMEDIATE FROM 문이 포함될 수 있습니다. 
- 절대 파일 경로를 작은따옴표( - ') 또는- $$로 묶는 것은 선택 사항입니다.
- 실행할 파일의 크기가 10MB보다 크면 안 됩니다. 
- 실행할 파일은 UTF-8 로 인코딩해야 합니다. 
- 실행할 파일은 압축을 풀어야 합니다. PUT 명령을 사용하여 파일을 내부 스테이지에 업로드하는 경우 AUTO_COMPRESS 매개 변수 를 FALSE로 명시적으로 설정해야 합니다. - 예를 들어 - my_file.sql을- my_stage에 업로드하십시오.- PUT file://~/sql/scripts/my_file.sql @my_stage/scripts/ AUTO_COMPRESS=FALSE; 
- 디렉터리의 모든 파일 실행은 지원되지 않습니다. 예를 들어, - EXECUTE IMMEDIATE FROM @stage_name/scripts/는 오류를 발생시킵니다.
템플릿 사용법 노트¶
- 템플릿의 변수 이름은 대/소문자를 구분합니다. 
- 템플릿 변수 이름은 선택적으로 큰따옴표로 묶을 수 있습니다. 예약 키워드 를 변수 이름으로 사용하는 경우 변수 이름을 묶는 것은 유용할 수 있습니다. 
- USING 절에서 지원되는 매개 변수 유형은 다음과 같습니다. - 문자열. - '또는- $$로 묶어야 합니다. 예:- USING (a => 'a', b => $$b$$).
- 숫자(소수 및 정수). 예: - USING (a => 1, b => -1.23).
- 부울. 예: - USING (a => TRUE, b => FALSE).
- NULL. 예: - USING (a => NULL).- 참고 - Jinja2 템플릿 엔진은 NULL 값을 Python NoneType 타입으로 해석합니다. 
- 세션 변수. 예: - USING (a => $var). 지원되는 데이터 타입의 값이 있는 세션 변수만 허용됩니다.
- 바인드 변수. 예: - USING (a => :var). 지원되는 데이터 타입의 값이 있는 바인드 변수만 허용됩니다. 바인드 변수를 사용하면 저장 프로시저 인자를 템플릿에 전달할 수 있습니다.
 
- Snowflake Git 리포지토리 또는 Snowflake Native Apps에 있는 파일은 템플릿에서 액세스할 수 없습니다. 
- 템플릿 렌더링의 최대 결과 크기는 100,000바이트입니다. 
- 템플릿은 Jinja2 버전 3.1.4 템플릿 엔진을 사용하여 렌더링됩니다. 
EXECUTE IMMEDIATE FROM 오류 문제 해결하기¶
이 섹션에는 EXECUTE IMMEDIATE FROM 문으로 인해 발생하는 몇 가지 일반적인 오류와 이를 해결하는 방법이 수록되어 있습니다.
파일 오류¶
| 오류 | 001501 (02000): File '<directory_name>' not found in stage '<stage_name>'.
 | 
|---|---|
| 원인 | 이 오류의 원인은 여러 가지가 있습니다. 
 | 
| 해결책 | 파일 이름을 확인하고 파일이 존재하는지 확인하십시오. 디렉터리의 모든 파일을 실행할 수는 없습니다. | 
| 오류 | 001503 (42601): Relative file references like '<filename.sql>' cannot be used in top-level EXECUTE IMMEDIATE calls.
 | 
|---|---|
| 원인 | 파일 실행 외부의 상대 파일 경로를 사용하여 문이 실행되었습니다. | 
| 해결책 | 상대 파일 경로는 파일의 EXECUTE IMMEDIATE FROM 문에서만 사용할 수 있습니다. 파일의 절대 파일 경로 를 사용하십시오. 자세한 내용은 사용법 노트 섹션을 참조하십시오. | 
| 오류 | 001003 (42000): SQL compilation error: syntax error line <n> at position <m> unexpected '<string>'.
 | 
|---|---|
| 원인 | 파일에 SQL 구문 오류가 있습니다. | 
| 해결책 | 파일의 구문 오류를 수정하고 파일을 스테이지에 다시 업로드하십시오. | 
스테이지 오류¶
| 오류 | 002003 (02000): SQL compilation error: Stage '<stage_name>' does not exist or not authorized.
 | 
|---|---|
| 원인 | 스테이지가 존재하지 않거나 스테이지에 대한 액세스 권한이 없습니다. | 
| 해결책 | 
 | 
액세스 제어 오류¶
| 오류 | 003001 (42501): Uncaught exception of type 'STATEMENT_ERROR' in file <file_name> on line <n> at position <m>:
SQL access control error: Insufficient privileges to operate on schema '<schema_name>'
 | 
|---|---|
| 원인 | 문을 실행하는 데 사용된 역할에는 파일의 문 중 일부 또는 전체를 실행하는 데 필요한 권한이 없습니다. | 
| 해결책 | 적절한 권한이 있는 역할을 사용하여 파일의 문을 실행하십시오. 자세한 내용은 액세스 제어 요구 사항 섹션을 참조하십시오. | 
참고 항목: 스테이지 오류.
템플릿 오류¶
| 오류 | 001003 (42000): SQL compilation error:
syntax error line [n] at position [m] unexpected '{'.
 | 
|---|---|
| 원인 | 파일에 템플릿 구조체(예:  | 
| 해결책 | 템플릿 지시문 을 추가하거나 USING 절 을 사용하여 문을 다시 실행하고 템플릿 변수를 하나 이상 지정합니다. | 
| 오류 | 000005 (XX000): Python Interpreter Error:
jinja2.exceptions.UndefinedError: '<key>' is undefined
in template processing
 | 
|---|---|
| 원인 | 템플릿에 사용된 변수가 USING 절에 지정되지 않은 상태로 유지되면 오류가 발생합니다. | 
| 해결책 | 템플릿의 변수 이름과 개수를 확인하고 모든 템플릿 변수에 대한 값을 포함하도록 USING 절을 업데이트합니다. | 
| 오류 | 001510 (42601): Unable to use value of template variable '<key>'
 | 
|---|---|
| 원인 | 변수  | 
| 해결책 | 템플릿 변수 값에 대해 지원되는 매개 변수 유형을 사용하고 있는지 확인합니다. 자세한 내용은 템플릿 사용법 노트 섹션을 참조하십시오. | 
| 오류 | 001518 (42601): Size of expanded template exceeds limit of 100,000 bytes.
 | 
|---|---|
| 원인 | 렌더링된 템플릿의 크기가 현재 제한을 초과합니다. | 
| 해결책 | 템플릿이 설정된 파일을 여러 개의 작은 템플릿으로 분할하고 이를 순차적으로 실행하는 새 스크립트를 추가하는 동시에, 템플릿 변수를 중첩된 스크립트에 전달합니다. | 
예¶
기본 예제¶
이 예에서는 my_stage 스테이지에 있는 create-inventory.sql 파일을 실행합니다.
- 다음 문으로 - create-inventory.sql이라는 파일을 만듭니다.- CREATE OR REPLACE TABLE my_inventory( sku VARCHAR, price NUMBER ); EXECUTE IMMEDIATE FROM './insert-inventory.sql'; SELECT sku, price FROM my_inventory ORDER BY price DESC; 
- 다음 문으로 - insert-inventory.sql이라는 파일을 만듭니다.- INSERT INTO my_inventory VALUES ('XYZ12345', 10.00), ('XYZ81974', 50.00), ('XYZ34985', 30.00), ('XYZ15324', 15.00); 
- 내부 스테이지 - my_stage를 만듭니다.- CREATE STAGE my_stage; 
- PUT 명령을 사용하여 두 로컬 파일을 모두 스테이지에 업로드합니다. - PUT file://~/sql/scripts/create-inventory.sql @my_stage/scripts/ AUTO_COMPRESS=FALSE; PUT file://~/sql/scripts/insert-inventory.sql @my_stage/scripts/ AUTO_COMPRESS=FALSE; 
- my_stage에 있는- create-inventory.sql스크립트를 실행합니다.- EXECUTE IMMEDIATE FROM @my_stage/scripts/create-inventory.sql; - 반환 결과: - +----------+-------+ | SKU | PRICE | |----------+-------| | XYZ81974 | 50 | | XYZ34985 | 30 | | XYZ15324 | 15 | | XYZ12345 | 10 | +----------+-------+ 
간단한 템플릿 예제¶
- 두 개의 변수와 템플릿 지시문을 사용하여 템플릿 파일 - setup.sql을 생성합니다.- --!jinja CREATE SCHEMA {{env}}; CREATE TABLE RAW (COL OBJECT) DATA_RETENTION_TIME_IN_DAYS = {{retention_time}}; 
- 스테이지 만들기 — 이미 파일을 업로드할 수 있는 스테이지가 있는 경우 선택 사항 입니다. - 예를 들어, Snowflake에서 내부 스테이지를 생성합니다. - CREATE STAGE my_stage; 
- 파일을 스테이지에 복사합니다. - 예를 들어, 로컬 환경에서 PUT 명령을 사용하여 - setup.sql파일을- my_stage스테이지로 업로드합니다.- PUT file://path/to/setup.sql @my_stage/scripts/ AUTO_COMPRESS=FALSE; 
- setup.sql파일을 실행합니다.- EXECUTE IMMEDIATE FROM @my_stage/scripts/setup.sql USING (env=>'dev', retention_time=>0); 
매크로, 조건부, 루프 및 가져오기가 포함된 템플릿 예제¶
- 매크로 정의가 포함된 템플릿 파일을 만듭니다. - 예를 들어 로컬 환경에서 - macros.jinja파일을 만듭니다.- {%- macro get_environments(deployment_type) -%} {%- if deployment_type == 'prod' -%} {{ "prod1,prod2" }} {%- else -%} {{ "dev,qa,staging" }} {%- endif -%} {%- endmacro -%} 
- 템플릿 파일을 생성하고 파일 상단에 템플릿 지시문( - --!jinja2)을 추가합니다.- 템플릿 지시어 뒤에 - import문을 추가하여 이전 단계에서 생성한 파일에 정의된 매크로를 가져옵니다. 예를 들어 로컬 환경에서- setup-env.sql파일을 만듭니다.- --!jinja2 {% from "macros.jinja" import get_environments %} {%- set environments = get_environments(DEPLOYMENT_TYPE).split(",") -%} {%- for environment in environments -%} CREATE DATABASE {{ environment }}_db; USE DATABASE {{ environment }}_db; CREATE TABLE {{ environment }}_orders ( id NUMBER, item VARCHAR, quantity NUMBER); CREATE TABLE {{ environment }}_customers ( id NUMBER, name VARCHAR); {% endfor %} 
- 스테이지 만들기 — 이미 파일을 업로드할 수 있는 스테이지가 있는 경우 선택 사항 입니다. - 예를 들어, Snowflake에서 내부 스테이지를 생성합니다. - CREATE STAGE my_stage; 
- 파일을 스테이지에 복사합니다. - 예를 들어, 로컬 환경에서 PUT 명령을 사용하여 - setup-env.sql및- macros.jinja파일을- my_stage스테이지에 업로드합니다.- PUT file://path/to/setup-env.sql @my_stage/scripts/ AUTO_COMPRESS=FALSE; PUT file://path/to/macros.jinja @my_stage/scripts/ AUTO_COMPRESS=FALSE; 
- 템플릿에서 렌더링된 SQL 문을 미리 보고 Jinja2 코드에 문제가 있는지 확인하십시오. - EXECUTE IMMEDIATE FROM @my_stage/scripts/setup-env.sql USING (DEPLOYMENT_TYPE => 'prod') DRY_RUN = TRUE; - 반환 결과: - +----------------------------------+ | rendered file contents | |----------------------------------| | --!jinja2 | | CREATE DATABASE prod1_db; | | USE DATABASE prod1_db; | | CREATE TABLE prod1_orders ( | | id NUMBER, | | item VARCHAR, | | quantity NUMBER); | | CREATE TABLE prod1_customers ( | | id NUMBER, | | name VARCHAR); | | CREATE DATABASE prod2_db; | | USE DATABASE prod2_db; | | CREATE TABLE prod2_orders ( | | id NUMBER, | | item VARCHAR, | | quantity NUMBER); | | CREATE TABLE prod2_customers ( | | id NUMBER, | | name VARCHAR); | | | +----------------------------------+ 
- setup-env.sql파일을 실행합니다.- EXECUTE IMMEDIATE FROM @my_stage/scripts/setup-env.sql USING (DEPLOYMENT_TYPE => 'prod'); 
