Back to the sqlplus prompt - sql

I'm a beginner in PL/SQL, I'm trying some sql script but sometimes I have an error in my script and the prompt doesn't appear; I remain in input mode.
How can I retrieve the prompt without shutting down the terminal?
(p.s.: I used sql plus for oracle 11g under Ubuntu OS)

From the documentation
SQL*Plus treats PL/SQL subprograms in the same manner as SQL commands, except that a semicolon (;) or a blank line does not terminate and execute a block. Terminate PL/SQL subprograms by entering a period (.) by itself on a new line. You can also terminate and execute a PL/SQL subprogram by entering a slash (/) by itself on a new line.
If you're entering a PL/SQL block and getting numbered prompts, enter a period (.) on its own and you'll drop back to the SQL> prompt.
SQL> declare
2
3
4
5 .
SQL>
The code you entered will still be in the buffer and you can run it with /, or edit it in your configured text editor with edit. (You can set that with define _editor = "/usr/bin/vim", for example).

Related

Oracle debug session exits instantly for trigger

I am trying to debug a compound trigger. I compiled it for debug,and put breakpoints on the trigger and hit "debug". Then it prompts me a window for a PL/SQL block. I entered my sql statement, and hit "OK".
The debug session just ends instantly
I got following message in the Debugging Message window:
Connecting to the database EFTS.
Executing PL/SQL: CALL DBMS_DEBUG_JDWP.CONNECT_TCP( '127.0.0.1', '6503' )
Debugger accepted connection from database on port 6503.
Executing PL/SQL: CALL DBMS_DEBUG_JDWP.DISCONNECT()
Process exited.
Disconnecting from the database EFTS.
Debugger disconnected from database.
Strangely, the debugger works for stored procedures. I am able to trace through the procedures line by line. However, for TRIGGER, it just ended instantly.
Trigger Declaration:
create or replace TRIGGER
MySchema.T_EVNTS_UPSERT
FOR INSERT OR UPDATE ON MySchema.MyTable
COMPOUND TRIGGER
SQLDeveloper Version: the latest
Oracle Version: 12c
Make sure you have changed this setting
It should say instead 'Step Into'
Also ensure the lines of pl/sql with breakpoints are executable lines of code, otherwise they'll be ignored.

SQLplus expected symbol

hello I'm new to SQL I'm attempting to create a database and am having an issue running this code in cmd sqlplus
execute 'CREATE BIGFILE TABLESPACE "COMPANY_DATA" DATAFILE 'c:\software\COMPANY_data_tablespace' SIZE 1G AUTOEXTEND ON NEXT 1024M MAXSIZE UNLIMITED LOGGING EXTENT MANAGEMENT LOCAL SEGMENT SPACE MANAGEMENT AUTO;'
I am receiving this error
Error at line 1:
ORA-06550: line 1, column7:
PLS-00103: encountered the symbol execute 'CREATE BIGFILE TABLESPACE "MG_DATA" DATAFILE when expecting the following:
(begin case declare exit for goto if loop mod null pargma
raise return select update while with <an identifier>
<adouble-quoted delimited-identifier><a bind variable><<
continue close current delete fetch lock insert open rollback
savepoint set SQL execute commit forall merge pipe purge
I'm not sure what I missing in the syntax I know this is a noobie question but kinda stumped thanks
Your syntax error is caused by the fact that you enclose the entire CREATE statement in single quotes, but the statement itself has embedded single quotes. So the parser sees the first quote, and terminates that string when it sees the next. And that occurs when you hit the file name. You'd need to escape the embedded quotes.
Or much better, as #GMB said, just submit the CREATE statement directly. Why did you think you needed quote it and submit it with EXECUTE in the first place?

How this CREATE statement is parsed by sqlplus?

I saw some CREATE statements I never thought could be parsed by SQLPLUS:
plus#PDB1> #create
2 or
3 replace procedure p as
4 begin
5 null;
6 end;
7 /
Procedure created.
plus#PDB1> #create
2 table t3(x int);
Table created.
So how the pound signs (#) were parsed here ? I cannot find any documentation for this. If there is a documentation to it, point me there.
This is the SQLPREFIX character. The manual describes it:
While you are entering a SQL command or PL/SQL block, you can enter a SQL*Plus command on a separate line, prefixed by the SQL*Plus prefix character. SQL*Plus will execute the command immediately without affecting the SQL command or PL/SQL block that you are entering.
An example use case of running a SQL*PlusĀ® command inside a SQL command:
SQL> SELECT *
# show release
release 1102000200
FROM dual;
D
-
X
While you would usually use this to run something immediately inside a larger command, since you can use it anywhere, you can actually use it on its own too.
SQL> # SELECT * FROM dual;
D
-
X

Ignoring SQLPLUS commands in JDBC

I have a .sql file that contains below statements:
SET LINESIZE 2000
WHENEVER SQLERROR EXIT 1 ROLLBACK
WHENEVER OSERROR EXIT 1 ROLLBACK
SET PAGESIZE 0
SET HEADING ON
SET FEEDBACK OFF
SET VERIFY OFF
INSERT INTO TABLE_A
--get some value from TABLE B that will be added in Table A....
COMMIT;
EXIT;
When I run this SQL in my SQL Editor (TOAD/SQL Navigator etc.) , it works fine. I see some messages though when SQLNavigator execute this command:
SQL*Plus command ignored.
Processing ...
WHENEVER SQLERROR EXIT 1 ROLLBACK
SQL*Plus command ignored.
Processing ...
WHENEVER OSERROR EXIT 1 ROLLBACK
SQL*Plus command ignored.
Processing ...
SET PAGESIZE 0
When I run this SQL through JDBC, i get an exception:
Caused by: java.sql.SQLException: ORA-00922: missing or invalid option
at oracle.jdbc.driver.DatabaseError.throwSqlException(DatabaseError.java:112)
at oracle.jdbc.driver.T4CTTIoer.processError(T4CTTIoer.java:331)
at oracle.jdbc.driver.T4CTTIoer.processError(T4CTTIoer.java:288)
at oracle.jdbc.driver.T4C8Oall.receive(T4C8Oall.java:743)
at oracle.jdbc.driver.T4CPreparedStatement.doOall8(T4CPreparedStatement.java:216)
at oracle.jdbc.driver.T4CPreparedStatement.executeForRows(T4CPreparedStatement.java:955)
at oracle.jdbc.driver.OracleStatement.doExecuteWithTimeout(OracleStatement.java:1168)
at oracle.jdbc.driver.OraclePreparedStatement.executeInternal(OraclePreparedStatement.java:3285)
at oracle.jdbc.driver.OraclePreparedStatement.executeUpdate(OraclePreparedStatement.java:3368)
I'm assuming this error is because JDBC is not able to understand SQLPlus statements and failing. Is there a way I can tell JDBC to ignore those statements and just run the main SQL? Or to resolve this I just need to modify the SQL file by removing the SQLPlus statements?
You'll need to remove the SQL*Plus commands from the file.
JDBC is intended to be a database-agnostic interface so it is designed to work the same with a variety of different database engines. SQL*Plus commands are designed to work just with SQL*Plus connecting to an Oracle database (though other tools that support Oracle databases will often support a subset of SQL*Plus commands as well). It wouldn't make sense for JDBC to know about what constitutes a SQL*Plus command so it has no way to figure out what is a SQL*Plus command or to filter them out.
Beyond that, simply removing the SQL*Plus commands will change the semantics of the script. The WHENEVER SQLERROR and WHENEVER OSEROR commands instruct SQL*Plus to issue a rollback in the event of an error (which it sounds like your script generates). You'd need to code that logic into your JDBC application if you want to match the behavior.
When you run these statements through TOAD, etc. they usually parse the text either by a delimiter (e.g. semi-column) or by line feed and run the statements separately. However, when you send the whole text to JDBC, it's probably trying to run it all at once, hence the error. You may have to parse the statements and separate them properly before sending to JDBC.

When do I need to use a semicolon vs a slash in Oracle SQL?

We have been having some debate this week at my company as to how we should write our SQL scripts.
Background:
Our database is Oracle 10g (upgrading to 11 soon). Our DBA team uses SQLPlus in order to deploy our scripts to production.
Now, we had a deploy recently that failed because it had used both a semicolon and a forward slash (/). The semicolon was at the end of each statement and the slash was between statements.
alter table foo.bar drop constraint bar1;
/
alter table foo.can drop constraint can1;
/
There were some triggers being added later on in the script, some views created as well as some stored procedures. Having both the ; and the / caused each statement to run twice causing errors (especially on the inserts, which needed to be unique).
In SQL Developer this does not happen, in TOAD this does not happen. If you run certain commands they will not work without the / in them.
In PL/SQL if you have a subprogram (DECLARE, BEGIN, END) the semicolon used will be considered as part of the subprogram, so you have to use the slash.
So my question is this: If your database is Oracle, what is the proper way to write your SQL script? Since you know that your DB is Oracle should you always use the /?
I know this is an old thread, but I just stumbled upon it and I feel this has not been explained completely.
There is a huge difference in SQL*Plus between the meaning of a / and a ; because they work differently.
The ; ends a SQL statement, whereas the / executes whatever is in the current "buffer". So when you use a ; and a / the statement is actually executed twice.
You can easily see that using a / after running a statement:
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
In this case one actually notices the error.
But assuming there is a SQL script like this:
drop table foo;
/
And this is run from within SQL*Plus then this will be very confusing:
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
The / is mainly required in order to run statements that have embedded ; like CREATE PROCEDURE,CREATE FUNCTION,CREATE PACKAGE statements and for any BEGIN...END blocks.
I wanted to clarify some more use between the ; and the /
In SQLPLUS:
; means "terminate the current statement, execute it and store it to the SQLPLUS buffer"
<newline> after a D.M.L. (SELECT, UPDATE, INSERT,...) statement or some types of D.D.L (Creating Tables and Views) statements (that contain no ;), it means, store the statement to the buffer but do not run it.
/ after entering a statement into the buffer (with a blank <newline>) means "run the D.M.L. or D.D.L. or PL/SQL in the buffer.
RUN or R is a sqlsplus command to show/output the SQL in the buffer and run it. It will not terminate a SQL Statement.
/ during the entering of a D.M.L. or D.D.L. or PL/SQL means "terminate the current statement, execute it and store it to the SQLPLUS buffer"
NOTE: Because ; are used for PL/SQL to end a statement ; cannot be used by SQLPLUS to mean "terminate the current statement, execute it and store it to the SQLPLUS buffer" because we want the whole PL/SQL block to be completely in the buffer, then execute it. PL/SQL blocks must end with:
END;
/
It's a matter of preference, but I prefer to see scripts that consistently use the slash - this way all "units" of work (creating a PL/SQL object, running a PL/SQL anonymous block, and executing a DML statement) can be picked out more easily by eye.
Also, if you eventually move to something like Ant for deployment it will simplify the definition of targets to have a consistent statement delimiter.
Almost all Oracle deployments are done through SQL*Plus (that weird little command line tool that your DBA uses). And in SQL*Plus a lone slash basically means "re-execute last SQL or PL/SQL command that I just executed".
See
http://ss64.com/ora/syntax-sqlplus.html
Rule of thumb would be to use slash with things that do BEGIN .. END or where you can use CREATE OR REPLACE.
For inserts that need to be unique use
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>)
From my understanding, all the SQL statement don't need forward slash as they will run automatically at the end of semicolons, including DDL, DML, DCL and TCL statements.
For other PL/SQL blocks, including Procedures, Functions, Packages and Triggers, because they are multiple line programs, Oracle need a way to know when to run the block, so we have to write a forward slash at the end of each block to let Oracle run it.
I only use the forward slash once at the end of each script, to tell sqlplus that there is not more lines of code. In the middle of a script, I do not use a slash.
use semicolon in sql script files to separate sql statements that tell client software (SQL*Plus, SQL Developer) what are the single statements to be executed.
use slash in sql script files to separate pl/sql blocks that tell client software (SQL*Plus, SQL Developer) what are the single pl/sql blocks to be executed.
use slash in SQL*Plus command line when you want to execute buffered statement (yes it is a single sql statement without the semicolon or pl/sql block without the slash).
Use slash after statements that end with "end;", otherwise do not use it.
Before creating the object type in Oracle, dummy types are created to reference other types that have not yet been defined. Slash is used to executing the most recent type definition changes, or to replace the existing type in the SQL buffer with the replaced type.
References:
https://docs.oracle.com/cd/E18283_01/server.112/e16604/ch_twelve004.htm