itsource

저장 프로시저에서 출력 파라미터 크기를 정의하려면 어떻게 해야 합니까?

mycopycode 2023. 8. 20. 10:48
반응형

저장 프로시저에서 출력 파라미터 크기를 정의하려면 어떻게 해야 합니까?

저장 프로시저에서 출력 파라미터 크기를 정의하려면 어떻게 해야 합니까?

그럴수는 없어요.물론 저장 프로시저에서 OUT 매개변수에 입력하는 데이터의 양을 제어할 수 있습니다.데이터를 저장할 크기의 로컬 변수를 생성한 다음 해당 변수의 값을 OUT 매개 변수에 할당할 수 있습니다.

호출 프로그램은 OUT 파라미터를 수신하는 변수의 크기를 결정합니다.

다음은 하위 유형을 선언하고 사용하는 간단한 패키지입니다.

SQL> create or replace package my_pkg as
  2      subtype limited_string is varchar2(10);
  3      procedure pad_string (p_in_str varchar
  4                          , p_length number
  5                          , p_out_str out limited_string);
  6  end my_pkg;
  7  /

Package created.

SQL> create or replace package body my_pkg as
  2      procedure pad_string
  3          (p_in_str varchar
  4              , p_length number
  5              , p_out_str out limited_string)
  6      as
  7      begin
  8          p_out_str := rpad(p_in_str, p_length, 'A');
  9      end  pad_string;
 10  end my_pkg;
 11  /

Package body created.

SQL>

하지만, 우리가 PAD_를 부른다면,STRING()은 출력 문자열이 하위 유형의 정밀도를 초과하는 방식으로 계속 성공적으로 완료됩니다.귀찮아요!

SQL> var out_str varchar2(128)
SQL>
SQL> exec my_pkg.pad_string('PAD THIS!', 12, :out_str)

PL/SQL procedure successfully completed.

SQL>
SQL> select length(:out_str) from dual
  2  /

LENGTH(:OUT_STR)
----------------
              12

SQL>

이것은 귀찮지만 PL/SQL이 작동하는 방식이기 때문에 우리는 그것을 감수해야 합니다.

상황을 해결하는 방법은 기본적으로 DBC 원칙을 적용하고 매개 변수를 검증하는 것입니다.따라서 다음과 같은 입력에 대해 비즈니스 규칙을 주장할 수 있습니다.

SQL> create or replace package body my_pkg as
  2      procedure pad_string
  3          (p_in_str varchar
  4              , p_length number
  5              , p_out_str out limited_string)
  6      as
  7      begin
  8          if length(p_in_str) + p_length > 10 then
  9              raise_application_error(
 10                      -20000
 11                      , 'Returned string cannot be longer than 10 characters!');
 12          end if;
 13          p_out_str := rpad(p_in_str, p_length, 'A');
 14      end  pad_string;
 15  end my_pkg;
 16  /

Package body created.

SQL>
SQL> exec my_pkg.pad_string('PAD THIS!', 12, :out_str)
BEGIN my_pkg.pad_string('PAD THIS!', 12, :out_str); END;

*
ERROR at line 1:
ORA-20000: Returned string cannot be longer than 10 characters!
ORA-06512: at "APC.MY_PKG", line 9
ORA-06512: at line 1


SQL>

또는 다음과 같은 출력에 대해 비즈니스 규칙을 주장할 수 있습니다.

SQL> create or replace package body my_pkg as
  2      procedure pad_string
  3          (p_in_str varchar
  4              , p_length number
  5              , p_out_str out limited_string)
  6      as
  7          l_str limited_string;
  8      begin
  9          l_str := rpad(p_in_str, p_length, 'A');
 10          p_out_str := l_str;
 11      end  pad_string;
 12  end my_pkg;
 13  /

Package body created.

SQL>
SQL> exec my_pkg.pad_string('PAD THIS!', 12, :out_str)
BEGIN my_pkg.pad_string('PAD THIS!', 12, :out_str); END;

*
ERROR at line 1:
ORA-06502: PL/SQL: numeric or value error: character string buffer too small
ORA-06512: at "APC.MY_PKG", line 9
ORA-06512: at line 1

SQL>

대부분의 시나리오에서 두 가지를 모두 수행해야 합니다.이것은 인터페이스를 구축하는 예의바른 방법입니다. 왜냐하면 다른 루틴은 그들이 말한 가치를 되돌려 줄 것이라는 확신을 가지고 우리의 절차를 호출할 수 있기 때문입니다.

패키지 헤더에 하위 유형을 사용하고 본문에 체크를 입력할 수 있습니다.

CREATE OR REPLACE PACKAGE my_test
AS
   SUBTYPE   my_out   IS   VARCHAR2( 10 ); 

   PROCEDURE do_something( pv_variable IN OUT my_out );
END;
/

CREATE OR REPLACE PACKAGE BODY my_test
AS 
   PROCEDURE do_something( pv_variable IN OUT my_out )
   IS
      lv_variable   my_out;
   BEGIN
      -- Work on a local copy of the variable in question
      lv_variable := 'abcdefghijklmnopqrstuvwxyz';

      pv_variable := lv_variable;
   END do_something;

END;
/

그러면 이걸 실행할 때

DECLARE
   lv_variable VARCHAR2(30);
BEGIN
   my_test.do_something( lv_variable );
   DBMS_OUTPUT.PUT_LINE( '['||lv_variable||']');
END;
/

오류가 발생할 수 있습니다.

ORA-06502: PL/SQL: numeric or value error: character string buffer too small

아웃 파라미터를 사용하는 정신에 반하는 것처럼 보이지만 토니의 의견 이후에는 호출된 코드 내에서 데이터를 제어할 수 있는 유일한 방법이 이것이었습니다.

언급URL : https://stackoverflow.com/questions/3184338/how-can-we-define-output-parameter-size-in-stored-procedure

반응형