Nous avons eu un débat cette semaine dans mon entreprise sur la manière dont nous devrions écrire nos scripts SQL.
Contexte: Notre base de données est Oracle 10g (mise à niveau vers 11 bientôt). Notre équipe de DBA utilise SQLPlus afin de déployer nos scripts en production.
Nous avons récemment eu un déploiement qui a échoué car il utilisait à la fois un point-virgule et une barre oblique (/
). Le point-virgule était à la fin de chaque déclaration et la barre oblique était entre les déclarations.
alter table foo.bar drop constraint bar1;
/
alter table foo.can drop constraint can1;
/
Certains déclencheurs ont été ajoutés ultérieurement dans le script, des vues créées ainsi que des procédures stockées. Avoir à la fois le ;
Et le /
A provoqué l'exécution de chaque instruction deux fois, provoquant des erreurs (en particulier sur les insertions, qui devaient être uniques).
Cela ne se produit pas dans SQL Developer, cela ne se produit pas dans TOAD. Si vous exécutez certaines commandes, elles ne fonctionneront pas sans le /
.
En PL/SQL, si vous avez un sous-programme (DECLARE, BEGIN, END), le point-virgule utilisé sera considéré comme faisant partie du sous-programme, vous devez donc utiliser la barre oblique.
Ma question est donc la suivante: si votre base de données est Oracle, quelle est la bonne façon d’écrire votre script SQL? Puisque vous savez que votre base de données est Oracle, devriez-vous toujours utiliser le /
?
C'est une question de préférence, mais je préfère voir des scripts qui utilisent systématiquement le slash - de cette façon, toutes les "unités" de travail (création d'un objet PL/SQL, exécution d'un bloc anonyme PL/SQL et exécution d'une instruction DML) peuvent être utilisées. pris plus facilement à l'œil.
De plus, si vous passez finalement à quelque chose comme Ant pour le déploiement, cela simplifiera la définition des cibles pour avoir un délimiteur d'instruction cohérent.
Je sais que c'est un vieux fil, mais je suis tombé dessus et je sens que cela n'a pas été expliqué complètement.
Il y a une énorme différence dans SQL * Plus entre le sens d'un /
et un ;
parce qu'ils travaillent différemment.
Le ;
termine une instruction SQL alors que le /
exécute tout ce qui se trouve dans le "tampon" actuel. Alors, quand vous utilisez un ;
et a /
la déclaration est en réalité exécutée deux fois.
Vous pouvez facilement voir cela en utilisant un /
après avoir exécuté une déclaration:
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
Dans ce cas, on remarque réellement l'erreur.
Mais supposons qu’il existe un script SQL comme celui-ci:
drop table foo;
/
Et ceci est exécuté à partir de SQL * Plus, ce sera très déroutant:
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
Le /
est principalement nécessaire pour exécuter des instructions ayant incorporé ;
comme un CREATE PROCEDURE
déclaration.
Je voulais clarifier un peu plus d'utilisation entre le ;
et le /
Dans SQLPLUS:
;
signifie "termine l’instruction en cours, l’exécute et la stocke dans le tampon SQLPLUS"<newline>
après un D.M.L. (SELECT, UPDATE, INSERT, ...) ou certains types d’instructions D.D.L (Création de tables et de vues) (ne contenant pas de ;
), cela signifie stocker l’instruction dans la mémoire tampon, mais ne l’exécutez pas./
après avoir entré une instruction dans le tampon (avec un blanc <newline>
) signifie "exécuter le fichier D.M.L. ou D.DL. ou PL/SQL dans le tampon.RUN
ou R
est une commande sqlsplus permettant d'afficher/de générer le code SQL dans le tampon et de l'exécuter. Cela ne terminera pas une instruction SQL./
lors de l’entrée d’un D.M.L. ou D.D.L. ou PL/SQL signifie "mettre fin à l'instruction en cours, l'exécuter et la stocker dans le tampon SQLPLUS"NOTE: Parce que ;
sont utilisés pour que PL/SQL termine une instruction ;
_ ne peut pas être utilisé par SQLPLUS pour signifier "termine l'instruction courante, l'exécute et le stocke dans le tampon SQLPLUS" car nous voulons que l'ensemble du bloc PL/SQL soit complètement dans le tampon, puis exécutons-le. Les blocs PL/SQL doivent se terminer par:
END;
/
Presque tous les déploiements Oracle sont effectués via SQL * Plus (cet étrange petit outil de ligne de commande utilisé par votre administrateur de base de données). Et dans SQL * Plus, une barre oblique signifie essentiellement "ré-exécuter la dernière commande SQL ou PL/SQL que je viens d'exécuter".
Voir
La règle de base serait d'utiliser slash avec des choses qui font BEGIN .. END
ou où vous pouvez utiliser CREATE OR REPLACE
.
Pour les plaquettes qui doivent être à usage unique
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>)
À ma connaissance, toutes les instructions SQL n'ont pas besoin de barre oblique, car elles s'exécutent automatiquement à la fin des points-virgules, y compris les instructions DDL, DML, DCL et TCL.
Pour les autres blocs PL/SQL, y compris les procédures, les fonctions, les packages et les déclencheurs, comme il s’agit de programmes multi-lignes, Oracle a besoin d’un moyen de savoir quand exécuter le bloc. Nous devons donc écrire une barre oblique à la fin de chaque bloc pour: laisser Oracle l'exécuter.
J'utilise uniquement la barre oblique une fois à la fin de chaque script pour indiquer à sqlplus qu'il n'y a plus de lignes de code. Au milieu d'un script, je n'utilise pas de barre oblique.