이 문서는 지원되지 않는 버전의 PostgreSQL을위한 것입니다.
당신은에 대해 같은 페이지를 보려고 할 수 있습니다토토 커뮤니티 PostgreSQL : 문서 : 17 : 41.5. 기본 진술버전 또는 위에 나열된 다른 지원 버전 중 하나입니다.

38.5. 범퍼카 토토 진술

이 섹션과 다음 섹션에서는 모든 것을 설명합니다. 명시 적으로 이해되는 진술 유형pl/pgsql. 하나로 인식되지 않은 것 이 진술 유형은 SQL 명령으로 추정되며 에 설명 된대로 실행하려면 기본 데이터베이스 엔진으로 전송됩니다.섹션 38.5.2and섹션 38.5.3.

38.5.1. 과제

값의 할당pl/pgsql가변 또는 행/레코드 필드는입니다 as :

변수: =표현;

위에서 설명한 바와 같이, 그러한 진술의 표현은 다음과 같습니다. SQL을 통해 평가select기본 데이터베이스 엔진으로 전송 된 명령. 표현은해야합니다 단일 값을 산출하십시오.

표현식의 결과 데이터 유형이 일치하지 않으면 변수의 데이터 유형이거나 변수는 특정입니다 크기/정밀도 (예 :char (20)), 결과 값은에 의해 암시 적으로 변환됩니다.pl/pgsql결과를 사용한 통역사 유형의 출력 기능 및 변수 유형의 입력 기능. 이로 인해 런타임 오류가 발생할 수 있습니다 문자열 형태의 입력 함수에 의해 생성 된 결과 값은 입력 기능에 허용되지 않습니다.

예 :

세금 : = 하위 토탈 * 0.06;
my_record.user_id : = 20;

38.5.2. 범퍼카 토토 실행 결과없이

예를 들어 행을 반환하지 않는 SQL 명령의 경우삽입a반환절, 범퍼카 토토을 실행할 수 있습니다 A 내에서PL/PGSQL함수 범퍼카 토토을 작성하면.

anyPL/PGSQL변수 이름 명령 텍스트에 나타나는 것은 매개 변수로 대체됩니다. 기호, 그리고 변수의 현재 값이 제공됩니다. 실행 시간에 매개 변수 값으로 이것은 똑같습니다 표현에 대해 앞에서 설명한 처리; 자세한 내용은 참조섹션 38.10.1. 예를 들어, 글을 쓰면 :

선언
    핵심 텍스트;
    델타 정수;
시작하다
    ...
    myTab set val = val + delta where id = key; 업데이트

기본 SQL 엔진에서 보이는 명령 텍스트가 보입니다. 좋다:

MyTab Set Val = Val + $ 1 여기서 id = $ 2; 업데이트

일반적으로 이것에 대해 생각할 필요는 없지만 구문 오류를 이해해야 할 때 알아두면 도움이됩니다. 메시지.

주의

pl/pgsql의지 중 하나와 일치하는 식별자를 대체하십시오 함수의 선언 된 변수; 충분히 밝지 않습니다 그것이 당신이 의미하는지 여부를 아는 것입니다! 따라서, 그것은입니다 어떤 것과 동일한 변수 이름을 사용하는 것이 나쁜 생각 필요한 테이블, 열 또는 기능 이름 함수 내 명령에서 참조. 자세한 내용 토론 참조섹션 38.10.1.

이러한 방식으로 SQL 명령을 실행할 때pl/pgsql범퍼카 토토을 한 번만 계획하십시오 후속 처형에 대한 계획을 재사용합니다. 데이터베이스 연결. 이것의 의미는 논의된다 세부 사항섹션 38.10.2.

때로는 표현식 또는를 평가하는 것이 유용합니다select쿼리하지만 결과를 버리고, 예를 들어 부작용이있는 함수를 호출 할 때 유용한 결과 값이 없습니다.pl/pgsql, 사용공연진술 :

공연쿼리;

이것은 실행쿼리및 결과를 버립니다. 쓰기쿼리SQL을 작성하는 것과 같은 방식select범퍼카 토토이지만 교체하십시오 초기 키워드selectwith공연. pl/pgsql변수가 대체됩니다 결과를 반환하지 않는 명령과 마찬가지로 쿼리로 계획은 같은 방식으로 캐시됩니다. 또한 특수 변수발견16241_16344섹션 38.5.5).

참고 :그 글쓰기를 기대할 수 있습니다select직접이를 달성 할 것입니다 결과이지만 현재로서는 유일한 수용 방법은입니다.공연. 할 수있는 SQL 명령 와 같은 반환 행select, Will 가없는 한 오류로 거부됩니다.in다음에 논의 된 절 부분.

예 :

create_mv를 수행합니다 ( 'CS_SESSION_PAGE_REQUESTS_MV', MY_QUERY);

38.5.3. 쿼리 실행 단일 줄 결과

단일 행을 산출하는 SQL 명령의 결과 (아마도 여러 열의)) 레코드 변수에 할당 할 수 있습니다. 행 형 변수 또는 스칼라 변수 목록. 이것은 이에 의해 수행됩니다 기본 SQL 명령 작성 및 추가in절. 예를 들어,

selectselect_expressions[에엄격한]대상에서 ...;
삽입 ... 반환표현[에엄격한]대상;
업데이트 ... 반환표현[에엄격한]대상;
삭제 ... 반환표현[에엄격한]대상;

여기서대상레코드가 될 수 있습니다 변수, 행 변수 또는 쉼표로 구분 된 간단한 목록 변수 및 레코드/행 필드.pl/pgsql변수가 대체됩니다 쿼리의 나머지 부분으로, 계획은 행을 반환하지 않는 명령에 대해 위에서 설명했습니다. 이것 Worksselect, 삽입/업데이트/삭제with반환및 유틸리티 명령 반환 행 설정 결과 (예 :설명). 을 제외하고into절, SQL 명령은 그것과 동일합니다 외부에 쓰여질 것입니다pl/pgsql.

팁 :이 해석에 대한 주목selectwithinis 와는 상당히 다릅니다PostgreSQL'S Regement선택명령, 여기서inTarget은 새로 생성 된 테이블입니다. 당신이 A에서 테이블을 만들고 싶습니다.select내부의 결과pl/pgsql함수, 구문 사용테이블 작성 ... 선택.

행 또는 가변 목록이 대상으로 사용되는 경우 쿼리의 결과 열은 대상의 구조와 정확히 일치해야합니다. 번호 및 데이터 유형 또는 런타임 오류가 발생합니다. 언제 a 레코드 변수는 대상이며 자동으로 구성됩니다 쿼리 결과 열의 행 유형에 자체.

thein절은 거의 나타날 수 있습니다 SQL 명령의 어느 곳에서나. 관습 적으로 그것은 쓰여졌습니다 직전 또는 바로 직전select_expressionsinselect범퍼카 토토 또는 범퍼카 토토의 끝에 다른 범퍼카 토토 유형. 당신이 이것을 따르는 것이 좋습니다 대회의 경우pl/pgsql파서는 앞으로 더 엄격 해집니다 버전.

if엄격한에 지정되어 있지 않습니다.in조항,대상첫 번째 행으로 설정됩니다 쿼리로 반환하거나 쿼리가 반환 된 경우 Nulls로 반환 줄. ("첫 번째 줄"IS 사용하지 않는 한 잘 정의되지 않았습니다주문 에 의해.) 첫 번째 행 후 결과 행은 폐기됩니다. 스페셜을 확인할 수 있습니다발견변수 (참조섹션 38.5.5) 행이 반환되었는지 여부를 결정하려면 :

empname = myName에서 EMP에서 MyRec에 * 선택을 선택하십시오.
찾을 수없는 경우
    예외 '직원 % 찾을 수 없음', MyName;
끝 If;

엄격한옵션이 지정되어 있습니다. 쿼리는 정확히 하나의 행을 반환해야합니다. 그렇지 않으면 런타임 오류가 보고되면, 어느 쪽이든no_data_found(no 줄) 또는TOO_MANY_ROWS(하나 이상 열). 잡으려면 예외 블록을 사용할 수 있습니다. 예를 들면 오류 :

시작
    Empname = myName에서 Emp에서 Strict Myrec으로 * 선택하십시오.
    예외
        그렇다면 no_data_found 일 때
            예외 '직원 % 찾을 수 없음', MyName;
        언제 너무 _many_rows
            예외를 제기하는 '직원 % 고유하지 않음', MyName;
끝;

범퍼카 토토의 성공적인 실행엄격한항상 설정발견to true.

for삽입/업데이트/삭제with반환, pl/pgsql그 이상에 대한 오류를보고합니다 반환 된 줄 하나,엄격한IS 지정되지 않았습니다. 와 같은 옵션이 없기 때문입니다.주문 by어느 것을 결정 해야하는지 영향을받는 행을 반환해야합니다.

참고 :the엄격한옵션 Oracle PL/SQL의 동작과 일치선택및 관련 진술.

여러 결과를 처리 해야하는 경우를 처리하려면 SQL 쿼리의 행, 참조섹션 38.6.4.

38.5.4. 동적 실행 범퍼카 토토

종종 내부에서 동적 범퍼카 토토을 생성하고 싶을 것입니다 당신의pl/pgsql기능, 그 기능 다른 테이블이나 다른 범퍼카 토토 데이터 유형이 실행 될 때마다.PL/PGSQL의 정상적인 계획을 캐시하려는 시도 범퍼카 토토 용 (섹션 38.10.2)는 그러한 시나리오에서 작동하지 않습니다. 이것을 처리합니다 일종의 문제,execute진술 제공됩니다 :

executeCommand-string[[로엄격한]대상 ] [사용표현[, ...]];

여기서Command-stringis 문자열을 산출하는 표현 (유형텍스트) 실행 할 명령을 포함합니다. 그만큼 선택 과목대상는 기록입니다 변수, 행 변수 또는 쉼표로 구분 된 간단한 목록 변수 및 레코드/행 필드. 명령이 저장됩니다. 선택 사항사용삽입 할 공급 값 명령에.

대체 없음pl/pgsql변수는 계산 된 명령 문자열에서 수행됩니다. 필요한 모든 변수 값은 명령 문자열에 삽입해야합니다. 건설; 또는 아래에 설명 된대로 매개 변수를 사용할 수 있습니다.

또한,execute. 대신, 범퍼카 토토은입니다 진술이 실행될 때마다 준비됩니다. 따라서 범퍼카 토토 문자열은 함수 내에서 동적으로 생성 될 수 있습니다 다른 테이블과 열에서 동작을 수행합니다.

thein조항은 위치를 지정합니다 SQL 명령의 결과를 반환하는 행의 결과를 할당해야합니다. 만약에 행 또는 가변 목록이 제공되며 정확히 일치해야합니다. 쿼리 결과 구조 (레코드 변수가 중고, 결과 구조와 일치하도록 구성됩니다. 자동으로). 여러 행이 반환되면 첫 번째 행만이 반환됩니다 에 할당됩니다.in변수. 행이 반환되지 않으면 NULL이에 할당됩니다.in변수. 그렇지 않은 경우in조항이 지정되어 있으며 쿼리 결과가 있습니다 폐기.

인 경우엄격한옵션이 제공됩니다 쿼리가 정확히 하나를 생성하지 않는 한 오류 가보고됩니다 열.

명령 문자열은 매개 변수 값을 사용할 수 있습니다 명령에서에 참조$ 1, $ 2등.이 기호는 값을 나타냅니다 에 제공됨사용절. 이것 방법은 종종 데이터 값을 텍스트로 명령 문자열 : 런타임 오버 헤드를 피합니다 값을 텍스트와 뒤로 변환하면 훨씬 적습니다. 필요하지 않기 때문에 SQL 주입 공격이 발생하기 쉽습니다. 인용 또는 탈출. 예는 다음과 같습니다.

실행 'inserted_by = $ 1이고 삽입 된 mytable에서 count (*)를 선택하십시오. <= $ 2'
   c
   Checked_user 사용, Checked_date;

매개 변수 기호는 데이터 값에만 사용할 수 있습니다. - 동적으로 결정된 테이블 또는 열을 사용하려면 이름, 명령 문자열에 텍스트로 삽입해야합니다. 예를 들어, 이전 쿼리를 동적으로 선택된 테이블, 당신은 이것을 할 수 있습니다 :

execute 'count (*)에서'
    || tabname :: regclass
    || 'inserted_by = $ 1이고 삽입 된 <= $ 2'
   c
   Checked_user 사용, Checked_date;

anexecute단순한 상수 범퍼카 토토 문자열 및 일부사용위의 첫 번째 예에서와 같이 매개 변수는 기능적입니다 명령을 직접 작성하는 것과 동일합니다pl/pgsql및 교체 허용pl/pgsql변수가 발생합니다 자동으로. 중요한 차이점은execute각각에 대한 명령을 다시 계획합니다 실행, 현재와 관련된 계획 생성 매개 변수 값; 반면pl/pgsql일반적으로 일반 계획을 만듭니다 재사용을 위해 캐시합니다. 최고의 계획 인 상황에서 매개 변수 값에 크게 의존합니다.execute훨씬 더 빠를 수 있습니다. 언제 계획은 매개 변수 값에 민감하지 않으며, 다시 계획은 폐기물이 되십시오.

선택현재는 없습니다 지원execute; 대신에, 평원 실행select범퍼카 토토 및 지정in의 일부로execute자체.

참고 :thepl/pgsql execute진술은와 관련이 없습니다토토 : 문서 : 8.4 : executeSQL 에 의해 뒷받침되는 진술PostgreSQL서버. 서버의execute명령문을 사용할 수 없습니다 직접PL/PGSQL기능 (필요하지 않음).

예 38-1. 동적으로 값을 인용합니다 쿼리

동적 명령으로 작업 할 때 종종 단일 따옴표의 탈출을 처리합니다. 권장 방법 기능 본문에서 고정 텍스트를 인용하는 것은 달러 인용입니다. (달러 인용문을 사용하지 않는 레거시 코드가있는 경우 개요를 참조하십시오섹션 38.11.1, 번역 할 때 약간의 노력을 절약 할 수 있습니다 더 합리적인 체계에 대한 코드.)

동적 값에 삽입해야합니다 구성된 쿼리는 신중한 처리가 필요합니다 자체에는 인용 문자가 포함되어 있습니다. 예제 (이것은 가정합니다 당신이 기능을 위해 달러 인용문을 사용하고 있다는 전체, 따라서 견적 마크를 두 배로 늘릴 필요는 없습니다) :

실행 'TBL 세트 업데이트'
        || quote_ident (colname)
        || '='
        || quote_literal (newValue)
        || 'key ='
        || quote_literal (keyvalue);

이 예제는의 사용을 보여줍니다.QUOTE_INDENquote_literal함수 ( 참조섹션 9.4). 안전을 위해 열 또는 테이블 식별자를 포함하는 표현식이 있어야합니다 통과QUOTE_INDEN동적 쿼리에 삽입하기 전에. 포함 된 표현 구성된 문자열이어야하는 값 명령을 통과해야합니다quote_literal. 이러한 기능은 두 배로 동봉 된 입력 텍스트를 반환하기위한 적절한 단계 또는 모든 내장 된 특별한 인용문 캐릭터가 제대로 탈출했습니다.

왜냐하면quote_literalIS 레이블엄격한, 항상 Null 인수로 호출되면 Null을 반환하십시오. 위에서 예, ifNewValue또는KeyValue전체 동적 쿼리 인 null이었다 문자열은 무효가되어의 오류로 이어집니다.execute. 사용 하여이 문제를 피할 수 있습니다 그만큼QUOTE_NULLABLE함수, 와 동일하게 작동합니다.quote_literal널 인수는 문자열을 반환합니다NULL. 예를 들어,

실행 'TBL 세트 업데이트'
        || quote_ident (colname)
        || '='
        || quote_nullable (newValue)
        || 'key ='
        || quote_nullable (keyvalue);

당신이 null 일 수있는 값을 다루고 있다면, 당신 일반적으로 사용해야QUOTE_NULLABLE대신quote_literal.

항상 그렇듯이 널 값을 보장하기 위해주의를 기울여야합니다. 쿼리에서는 의도하지 않은 결과를 제공하지 않습니다. 예를 들어어디

'여기서 key ='|| quote_nullable (keyvalue)

if 성공하지 못할 것입니다.KeyValueIS 평등 연산자 사용의 결과이기 때문에 NULL=널 피연산자가있는 것은 항상입니다 널. NULL이 일반적인 키 가치처럼 일하기를 원한다면 위를 다시 작성해야합니다.

'키가'||와 구별되지 않는 경우 quote_nullable (keyvalue)

(현재,||=, 그렇지 않으면 그렇게하지 마십시오. 보다PostgreSQL : 문서 : 8.4 : 비교 토토 핫더 많은 것 Nulls 및에 대한 정보IS 별개의.)

달러 견적은 고정 인용에만 유용합니다. 텍스트. 이것을 쓰려고하는 것은 매우 나쁜 생각 일 것입니다 예제 :

실행 'TBL 세트 업데이트'
        || quote_ident (colname)
        || '= $$'
        || NewValue
        || '$$ key ='
        || quote_literal (keyvalue);

이면 끊어지기 때문에NewValue포함 된$$. 같은 반대는 어떤 것도 적용됩니다 당신이 선택할 수있는 다른 달러 인용 분리기. 안전하게 미리 알려지지 않은 견적 텍스트, 당신필수usequote_literal, QUOTE_NULLABLE또는quote_ident, 적절하게.

동적 범퍼카 토토의 훨씬 더 큰 예와execute예 38-7, a를 구축하고 실행합니다.생성 기능새 함수를 정의하도록 범퍼카 토토.

38.5.5. 결과를 얻습니다 상태

명령의 효과를 결정하는 몇 가지 방법이 있습니다. 첫 번째 방법은를 사용하는 것입니다.진단양식이있는 범퍼카 토토 :

진단 받기변수=항목[ , ... ];

이 범퍼카 토토은 시스템 상태 표시기를 검색 할 수 있습니다. 각항목는 핵심 단어입니다 지정된 상태에 할당 할 상태 값 식별 변수 (수신하기에 적합한 데이터 유형이어야합니다. 그것). 현재 사용 가능한 상태 항목은row_count, 마지막SQL범퍼카 토토으로 전송SQL엔진 및result_oid, 삽입 된 마지막 행의 OID 가장 최근SQL범퍼카 토토. 참고result_oid만 유용합니다 후삽입테이블에 범퍼카 토토 Oids 포함.

예 :

진단 받기 integer_var = row_count;

명령의 효과를 결정하는 두 번째 방법은 다음과 같습니다. 이름이 지정된 특수 변수를 확인하려면발견, 유형의부울. 발견시작합니다 각각의 거짓pl/pgsql함수 호출. 다음 유형의 각 유형에 의해 설정됩니다. 진술 :

  • a선택성명서 세트발견행이 할당 된 경우 True 행이 반환되지 않으면 false.

  • aPerform범퍼카 토토문 세트발견그것이 생산하는 경우 (및 소실) 하나 이상의 행, 행이없는 경우 거짓 생산.

  • 업데이트, 삽입삭제진술 세트발견true if at 최소 한 행에 영향을 받고 행이 영향을받지 않으면 거짓입니다.

  • aFetch진술 세트발견행을 반환하는 경우 True, 행이 반환되지 않으면 false.

  • a움직임범퍼카 토토문 세트발견성공적으로도 커서를 재배치하고, 그렇지 않으면 거짓.

  • afor성명서 세트발견한 번 이상 반복하면 참이되면, 그렇지 않으면 거짓. 이것은의 네 가지 변형에 적용됩니다.forStatement (Integerfor루프, 레코드 세트for루프, 동적 레코드 세트for루프 및 커서for루프).발견이런 식으로 설정됩니다.for루프 출구; 루프 실행 내부에서발견for문, 변경 될 수 있지만 루프 내 다른 진술의 실행에 의해 몸.

  • areturn queryand반환 쿼리 실행진술 세트발견쿼리가 반환되는 경우 최소 1 행, 행이 반환되지 않으면 거짓.

발견는 로컬 변수입니다 각pl/pgsql함수; 어느 그것에 대한 변경은 현재 함수에만 영향을 미칩니다.

38.5.6. 전혀 아무것도하지 않는다

때때로 아무것도하지 않는 자리 표시 자 진술 유용한. 예를 들어, 하나의 팔이 /then/else 체인이 의도적으로 비어 있습니다. 이를 위해 사용하십시오 그만큼NULL진술 :

null;

예를 들어, 다음 두 조각의 코드 조각입니다 동등한:

시작
        Y : = x / 0;
    예외
        Division_by_zero가있을 때
            널;  - 오류를 무시하십시오
    끝;
시작
        Y : = x / 0;
    예외
        Division_By_Zero 일 때 - 오류를 무시하십시오
    끝;

바람직한 맛의 문제입니다.

참고 :Oracle의 PL/SQL에서 빈 명령문 목록 허용되지 않습니다.NULL진술은필수그러한 상황 이로.pl/pgsql허용 당신은 그냥 아무것도 쓰지 않고 대신.