Oracle SQL에서 세미콜론과 슬래시를 언제 사용해야합니까?


179

우리는 이번 주에 회사에서 SQL 스크립트 작성 방법에 대해 토론했습니다.

배경 : 데이터베이스는 Oracle 10g입니다 (곧 11로 업그레이드). DBA 팀은 스크립트를 프로덕션에 배포하기 위해 SQLPlus를 사용합니다.

이제 세미콜론과 슬래시 ( /)를 모두 사용했기 때문에 최근 배포에 실패했습니다 . 세미콜론은 각 문장의 끝에 있었고 슬래시는 문장 사이에있었습니다.

alter table foo.bar drop constraint bar1;
/
alter table foo.can drop constraint can1;
/

스크립트에서 나중에 추가 된 트리거, 일부 뷰 및 일부 저장 프로 시저가 추가되었습니다. ;및 /문 을 모두 사용하면 각 문이 두 번 실행되어 오류가 발생했습니다 (특히 고유 한 삽입에서).

SQL Developer에서는 이런 일이 발생하지 않으며 TOAD에서는 이런 일이 발생하지 않습니다. 특정 명령을 실행하면 명령이 없으면 작동하지 않습니다 /.

PL / SQL에서 서브 프로그램 (DECLARE, BEGIN, END)이있는 경우 사용 된 세미콜론은 서브 프로그램의 일부로 간주되므로 슬래시를 사용해야합니다.

내 질문은 이것입니다 : 데이터베이스가 Oracle 인 경우 SQL 스크립트를 작성하는 올바른 방법은 무엇입니까? DB가 Oracle이라는 것을 알고 있으므로 항상 /?


1
누군가 SQLDeveloper로 데이터베이스 익스포트를 수행하는 경우 "터미네이터"라는 체크 박스가 있는데,이 옵션을 선택하면 세미콜론을 사용하여 각 명령문을 종료합니다. 이 옵션은 기본적으로 선택되어 있습니다. 세미콜론을 제거하고 중복 명령문 실행을 피하려면 선택 취소하십시오.
— Ruslans Uralovs

7
이 오래된 스레드를 무의식적으로 막기 위해 SQL 언어에는 세미콜론이 없다고 언급하겠습니다. 그것은 단지 SQL * 플러스에서 기본 종료 문자 (사용자가 설정할 수 있습니다 sqlterminator에 !당신이 좋아하는 경우)이 규칙은 다른 도구 다음되는 경향이있다. 그러나 PL / SQL 언어는 세미콜론을 필수 구문 요소로 사용합니다.
— William Robertson

답변:


31

선호의 문제이지만 슬래시를 일관되게 사용하는 스크립트를 선호합니다.이 방식으로 모든 작업 단위 (PL / SQL 객체 생성, PL / SQL 익명 블록 실행 및 DML 문 실행)가 가능합니다. 눈으로 더 쉽게 골랐습니다.

또한 결국 배포를 위해 Ant와 같은 것으로 이동하면 대상 정의를 단순화하여 일관된 명령문 구분 기호를 갖습니다.


1
이 답변은 이유를 설명하지 /않거나 ;자세한 내용은 @a_horse_with_no_name 또는 @Mr_Moneybags의 답변을 참조하십시오
— Kay

333

나는 이것이 오래된 실이라는 것을 알고 있지만 방금 넘어졌으며 이것이 완전히 설명되지 않았다고 생각합니다.

a /와 a 의 의미는 ;다르게 작동하므로 SQL * Plus에는 큰 차이가 있습니다.

;단부는 SQL 명령문의 반면, /현재에 실행하는대로 "버퍼". 당신은을 사용할 때 그래서 ; 및/ 문이 실제로 두 번 실행됩니다.

/명령문을 실행 한 후 다음 을 사용하면 쉽게 알 수 있습니다 .

SQL*Plus: Release 11.2.0.1.0 Production on Wed Apr 18 12:37:20 2012

Copyright (c) 1982, 2010, Oracle.  All rights reserved.

Connected to:
Oracle Database 11g Enterprise Edition Release 11.2.0.1.0 - Production
With the Partitioning and OLAP options

SQL> drop table foo;

Table dropped.

SQL> /
drop table foo
           *
ERROR at line 1:
ORA-00942: table or view does not exist

이 경우 실제로 오류를 알 수 있습니다.


그러나 다음과 같은 SQL 스크립트가 있다고 가정합니다.

drop table foo;
/

그리고 이것은 SQL * Plus 내에서 실행되며 매우 혼란 스럽습니다.

SQL*Plus: Release 11.2.0.1.0 Production on Wed Apr 18 12:38:05 2012

Copyright (c) 1982, 2010, Oracle.  All rights reserved.


Connected to:
Oracle Database 11g Enterprise Edition Release 11.2.0.1.0 - Production
With the Partitioning and OLAP options

SQL> @drop

Table dropped.

drop table foo
           *
ERROR at line 1:
ORA-00942: table or view does not exist

은 /주로 내장 한 문을 실행하기 위해 필요한 ;유사한 CREATE PROCEDURE문을.


2
@amis, 저는 Oracle을 처음 사용하고 같은 문제에 봉착했습니다. 이 질문은 매우 유용하지만 모든 답변은 "최상의 방법"이 아닌 "이유"에 대한 설명 또는이 문제를 해결하는 방법에 대한 설명을 제공했습니다. 따라서 내가 올바르게 이해하면 하나의 스크립트 만 가지고 모든 도구에 사용할 수있는 방법이 없습니다 ... 또는 어떤 방법을 발견합니까?
— ceinmart

5
@ceinmart : "가장 좋은 방법"은 SQL 스크립트를 실행할 하나의 도구를 정의하는 것입니다. 스크립트의 "정확성"은 해당 도구를 사용하여 검증됩니다. 프로그래밍 언어를위한 하나의 컴파일러 또는 하나의 특정 버전의 런타임 환경 (Java 7, .Net 4.0, PHP 5.x, ...)과
— 유사

1
좋은 대답입니다. 그것은 나입니까 아니면 Oracle 구피와 다른 DB와 비교할 때 구식입니까? 나는 많은 Sybase를 사용했으며 훨씬 직관적입니다.
— splashout

1
@splashout : 당신이 기본 구분 기호를 (포함 문을 실행하려면 아니라 ;) 당신은 대체 구분 지정하는 방법 찾아야
— a_horse_with_no_name

97

나는 사이에 더 많은 사용을 분명히하고 싶었다 ;./

SQLPLUS에서 :

  1. ; "현재 명령문을 종료하고 실행하여 SQLPLUS 버퍼에 저장"을 의미합니다.
  2. <newline>DML (SELECT, UPDATE, INSERT, ...) 문 또는 no를 포함하는 일부 유형의 DDL (Creating Tables and Views) 문 다음에 ;, 문을 버퍼에 저장하지만 실행하지는 않습니다.
  3. /버퍼에 명령문을 입력 한 후 (공백 포함 <newline>)는 " 버퍼 에서 DML 또는 DDL 또는 PL / SQL을 실행하는 것을 의미합니다.
  4. RUN또는 R버퍼에 SQL을 표시 / 출력하고 실행하기위한 sqlsplus 명령입니다. SQL 문을 종료하지 않습니다.
  5. / DML 또는 DDL 또는 PL / SQL을 입력하는 동안 "현재 명령문을 종료하고 실행하여 SQLPLUS 버퍼에 저장"을 의미합니다.

참고 : 때문에 ;문을 종료 PL / SQL에 사용되는은 ;우리가 전체 PL / SQL 블록이 완전히되고 싶어하기 때문에 의미 "현재 문을 종료를 실행하고 SQLPLUS 버퍼에 저장"을 SQLPLUS에서 사용할 수 없습니다 버퍼, 실행하십시오. PL / SQL 블록은 다음과 같이 끝나야합니다.

END;
/

22

거의 모든 Oracle 배포는 SQL * Plus (DBA가 사용하는 이상한 작은 명령 줄 도구)를 통해 수행됩니다. 그리고 SQL * Plus에서 슬래시는 기본적으로 "방금 실행 한 마지막 SQL 또는 PL / SQL 명령을 다시 실행"을 의미합니다.

보다

http://ss64.com/ora/syntax-sqlplus.html

경험상 BEGIN .. END또는 할 수있는 일에 슬래시를 사용하는 것이 일반적입니다 CREATE OR REPLACE.

고유하게 사용해야하는 인서트

INSERT INTO my_table ()
SELECT <values to be inserted>
FROM dual
WHERE NOT EXISTS (SELECT 
                  FROM my_table
                  WHERE <identify data that you are trying to insert>)

14

내 이해에 따르면 모든 SQL 문은 DDL, DML, DCL 및 TCL 문을 포함한 세미콜론의 끝에서 자동으로 실행되므로 슬래시가 필요하지 않습니다.

프로 시저, 함수, 패키지 및 트리거를 포함한 다른 PL / SQL 블록의 경우 여러 라인 프로그램이므로 Oracle은 블록을 실행할시기를 알 수있는 방법이 필요하므로 각 블록의 끝에 슬래시를 작성해야합니다. 오라클이 운영하게하십시오.


1

각 스크립트의 끝에서 한 번만 슬래시를 사용하여 더 많은 코드 줄이 없다는 것을 sqlplus에 알립니다. 스크립트 중간에 슬래시를 사용하지 않습니다.


따라서 마지막에 / (서브 프로그램 및 트리거와 같은)가 필요한 항목을 주문합니까? 트리거가 여러 개인 경우 어떻게합니까? 테스트를 실행했으며 각 테스트 사이에 /가 없으면 첫 번째 테스트 만 실행됩니다. 뭔가 빠졌습니까?
— amischiefr

나는 (가능하다면) 피하려고 노력하지만 (트리거 에서처럼) 할 수 없다면 oracle의 샘플 스키마를 생성하는 공식 스크립트에서 사용되는 세미콜론과 슬래시를 사용합니다 : download.oracle.com/docs /cd/B19306_01/server.102/b14198/… 삽입 문제의 경우, 테이블을 채우는 스크립트와 오브젝트를 작성하는 스크립트를 분리하려고합니다.
— Jonathan

1
죄송하지만 질문에 대한 답변은 아닙니다.
— DerMike
당사 사이트를 사용함과 동시에 당사의 쿠키 정책과 개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.