I have two broad questions:
Q1. Are executing the lines of code in Oracle SQL Developer and executing the same code in sqlplus command prompt same things?
(reason I ask this that I heard that not all the sqlplus commands are executable in SQL Developer. If answer to above question is yes then please then few useful links will help).
Q2. I am spooling the results of a sql query to a .csv file, but the thing is that columns names are truncated according the maximum length of the values in that column.
My code is:
set colsep ","
spool C:\Oracle\sample.csv
select * from acct_clas_rule;
spool off;
Output of above code is (middle column is having null values)
ABCD_,ABCD_,ABC
-----,-----,---
AB , ,WSD
ABCD , ,WSD
ABCD , ,WSD
SG , ,WSD
KD , ,WSD
WD , ,LKJ
KLHGF, ,LKO
WSDFG, ,LOK
WSDF , ,LKO
WS , ,GH
In above output, columns names have been truncated. I want full names of the columns to be displayed. Can anyone help?
I have seen the question in this link, but I didn't understand how to apply the answers provided there as there was no particular example cited. I am new to these things so I couldn't understand.
Original names of my columns (from left to right in above table) are :
ABCD_DFGT_SDF, ABCD_EDF_GH, ABCD_DFRE
PS -
1. I am using Oracle SQL developer to run sqlplus commands. I think because of which few of my commands are not working (like set underline, set linesize etc.).Please let me know if this is the case. I actually want remove those underlines beneath the columns names.
2. Also let me know that whether you answer is applicable to Oracle SQL Developer or sqlplus.
Thank You
There are a couple of things you can do, in addition to #JChomel's approach - that will work in either SQL Develoepr or SQL*Plus, while these suggestions are specific to SQL Developer.
Let's start with a dummy query based on a CTE to get something like your situation:
set colsep ","
with acct_clas_rule (abdc_1, abcd_2, abcd_3) as (
select cast('AB' as varchar2(5)), cast(null as varchar2(5)), cast('WSD' as varchar2(4)) from dual
union all select 'ABCD', null, 'WSD' from dual
-- ...
union all select 'WS', null, 'GH' from dual
)
select * from acct_clas_rule;
When run as a script in SQL Developer (from the document+arrow icon, or F5) the output is:
ABDC_,ABCD_,ABCD
-----,-----,----
AB , ,WSD
ABCD , ,WSD
WS , ,GH
If you change the query to include the SQL Developer-specific formatting hint /*csv*/ then you get the output you want:
select /*csv*/ * from acct_clas_rule;
"ABDC_1","ABCD_2","ABCD_3"
"AB","","WSD"
"ABCD","","WSD"
"WS","","GH"
except that the strings are all enclosed in double-quotes, which might not be what you really want. (It depends what you're doing with the spooled file and whether any of your string values contain commas, which would confuse Excel for instance).
With more recent versions of SQL Developer you can get exactly the same result without modifying the query using the sqlformat option:
set sqlformat csv
select * from acct_clas_rule;
but again you get the double-quotes. You could change the double-quotes to different enclosure characters, but that probably doesn't help.
A different approach is to use the built-in export tools instead of spool. If you run the query as a statement (green 'play button' icon, or control-enter) then rather than appearing in the Script Output panel, a new Query Result panel will open next to that, showing the results as a grid.
If you right-click on the results you'll get a contextual menu, and choosing Export... from that will give you a wizard to export the results in a format of your choice, including CSV:
You can leave the left and right enclosures as double-quotes to get the same results as the options above, except that null values use the word 'null' instead of an empty string:
"ABDC_1","ABCD_2","ABCD_3"
"AB",null,"WSD"
"ABCD",null,"WSD"
"WS",null,"GH
or you can change them, or remove them by choosing 'none', which gives you:
ABDC_1,ABCD_2,ABCD_3
AB,null,WSD
ABCD,null,WSD
WS,null,G
#thatjeffsmith has commented on how to change the null-replacement text for the /*csv*/ approach. For export it looks like having the word 'null' might have been a bug in 17.2.0; in 17.3.1 that does not appear, and instead you see:
ABDC_1,ABCD_2,ABCD_3
AB,,WSD
ABCD,,WSD
WS,,GH
or enclosed empty strings ("") if you leave the enclosures set.
Q1: TI'm not an expert of SQL Developer. There might be a mode like "command line" or something where you could get similar result, but unsure.
Q2: You have to set the right option to sqlplus: here is a trick I know of (it will also remove the --- --- --- that will cause other issue):
SET HEADING OFF`, to avoid column name to be printed
Union all the column names at the beginning of your script:
set colsep ","
spool C:\Oracle\sample.csv
select 'ABCD_DFGT_SDF', 'ABCD_EDF_GH', 'ABCD_DFRE' from dual
UNION ALL
select * from acct_clas_rule;
spool off;
use the sql plus set command -----> set underline off
I am still working on my first solo Oracle ApEx(Application Express) application, so I am sure that this will be old hat for some of you. I tried to look up what I want to do, but I am not sure what to even look up. If there is already a thread that answers this, then I apologize for duplication, but I have searched here for about two hours trying to figure this out.
I am open minded to a solution since I have not already built anything for this part of the application yet, so I am not locked into one set way. If there is a better way, please let me know.
I want to obtain a comma separated (or semi-colon, or colon separated) list from the user. I then want to take that data and write it to a table with each value in its own row.
Example of input:
X12345678, X22345678, X32345678 (and so on)
The numbers that are input will then be looked up on a different table because we use non-identifying PIDM numbers (Anyone that has used Ellucian's Banner will understand). This select statement is crazy simple to retrieve this number:
Select spriden_pidm
from spriden
where spriden_change_ind is null
and spriden_id = :P5_STU_ID
Then, it will be stored in a table thusly:
Example of data storage:
ID | Semester | Creating User | Created Date | Data Origin
012345678 | 201640 | JDOE1 | sysdate | ApEx : 130
022345678 | 201640 | JDOE1 | sysdate | ApEx : 130
And so forth.
Question 1: I am presuming that a loop will be the best way to accomplish this using regular expressions. Would that be a correct presumption?
Question 2: Does ApEx already have something built in that would process this better and/or faster?
ApEx version 5.0, Oracle 12c
APEX_UTIL.string_to_table
and use the comma for the second parameter
As mentioned, since we were working against the clock on a deployment, we ended up writing a loop similar to what the APEX_UTIL.string_to_table (Thanks Rob van Wijk) accomplishes:
declare
v_id varchar2(4000) := :P5_NEW_IDS;
begin
for i in 1..regexp_count( v_id, ',' ) + 1 loop
insert into zresadddrop.zsrintl(zsrintl_pidm,
zsrintl_term_code_eff,
zsrintl_created_by,
zsrintl_created_date,
zsrintl_data_origin)
select distinct spriden_pidm
, :P5_Term_Code
, :app_user
, sysdate
, 'ApEx: '||:app_id
from spriden
where spriden_change_ind is null
and spriden_id = trim(zgeneral.get_token(v_id,i));
end loop;
commit;
end;
In an attempt to more easily view the output in SQLPlus, I fiddled with window-size properties and font(tiniest font).
But this is what I get :
It is exactly the same, just much less readable.
I just want to run the query :
select * from user_tables where rownum < 10 ;
Without the messy unreadable lines (currently I can't tell apart the data from table headings)
With the help of one useful SQL*Plus option and one additional helper option it is possible. Put
set linesize 32767
set trimout on
before your select.
Enjoy.
I need to work with a SQL result set in order to do some processing for each column (medians, standard deviations, several control statements included)
The SQL is dynamic so I don't know the number of columns, rows.
First I tried to use temporary tables, views, etc to store the results, however I did not manage to overcome the 30 character limit of Oracle columns when using the below sql:
create table (or view or global temporary table) as select * from (
SELECT
DMTTBF_MAT_MATURATO_BILL_POS.MAT_V_COD_ANNOMESE,
SUM(DMTTBF_MAT_MATURATO_BILL_POS.MAT_N_NUM_EVENTI_CHZ +DMTTBF_MAT_MATURATO_BILL_POS. MAT_N_NUM_EVENTI) <-- exceeds the 30 character limit
FROM DMTTBF_MAT_MATURATO_BILL_POS
WHERE DMTTBF_MAT_MATURATO_BILL_POS.MAT_V_COD_ANNOMESE >= '201301'
GROUP BY DMTTBF_MAT_MATURATO_BILL_POS.MAT_V_COD_ANNOMESE
)
Second choice was to use some PL/SQL types to store the entire table information, so I could call it like in other programming languages (e.g. a matrix result[i][j]) but I could not find anything similar.
Third variant, using files for reading and writing: i did not try it yet; i'm still expecting a more elegant pl/sql solution
It's possible that I have the wrong approach here so any advice is more than welcome.
UPDATE: Modifying the input SQL is not an option. The program has to accept any select statement.
Note that you can alias both tables and fields. Using a table alias keeps references to it from producing walls of text in the query. Using one for a field gives it a new name in the output.
SELECT A.LONG_FIELD_NAME_HERE AS SHORTNAME
FROM REALLY_LONG_TABLE_NAME_HERE A
The auto naming adds _1 and _2 etc to differentiate the same column name coming from different table references. This often puts a field already borderline over the limit. Giving the fields names yourself bypasses this.
You can put the alias also in dynamic SQL:
sqlstr := 'create table (or view or global temporary table) as select * from (
SELECT
DMTTBF_MAT_MATURATO_BILL_POS.MAT_V_COD_ANNOMESE,
SUM(DMTTBF_MAT_MATURATO_BILL_POS.MAT_N_NUM_EVENTI_CHZ + DMTTBF_MAT_MATURATO_BILL_POS.MAT_N_NUM_EVENTI) AS '||SUBSTR('SUM(DMTTBF_MAT_MATURATO_BILL_POS.MAT_N_NUM_EVENTI_CHZ +DMTTBF_MAT_MATURATO_BILL_POS.MAT_N_NUM_EVENTI)', 1, 30)
||' FROM DMTTBF_MAT_MATURATO_BILL_POS
WHERE DMTTBF_MAT_MATURATO_BILL_POS.MAT_V_COD_ANNOMESE >= ''201301''
GROUP BY DMTTBF_MAT_MATURATO_BILL_POS.MAT_V_COD_ANNOMESE
)'
I am working on a rather large SQL script to be used with Oracle, but I'm running into an issue. First, let me outline how the script operates.
Declare variables`CUSTOMERID NUMBER;``SERVERID NUMBER;`
Create a customer if it doesn't exist
`SELECT ID INTO CUSTOMERID FROM CUSTOMER WHERE NAME = 'The Customer I just Inserted';`
Create the server if it doesn't exist, using the `CUSTOMERID` value to relate the server to the customer.
`SELECT ID INTO SERVERID WHERE HOSTNAME = 'the.server.i.just.created';`
For each service belonging to this server, insert the service using the `SERVERID` value to relate the service to the server.
Go to 2
Now this process seems to work well for just one customer with 15 servers, each having 6 services. But as soon as the next customer is introduced, I receive prompts for variable substitution. The way I'm using the variables on my insert is pretty straightforward:
INSERT INTO SERVERS(CUSTOMER_ID, HOSTNAME)
SELECT CUSTOMERID, 'the.server.i.just.created' FROM DUAL
WHERE NOT EXISTS (
SELECT *
FROM SERVERS
WHERE HOSTNAME = 'the.server.i.just.created'
);
I have also attempted using the DECLARE ... BEGIN ... END; method, but I receive the same general results. Some examples I've seen suggest to use the :CUSTOMERID style variables, but those don't seem to work at all, where they are ending up with null values, which shouldn't be happening given the previous queries.
What I am needing help with is in understanding how to achieve this. I have very limited access to the production environment, so anything I do needs to be kept basic (e.g., no new functions, types, or procedures).
I actually stumbled across the answer after beating my head on the desk repeatedly.
Basically, what was happening was some of the customer names had ampersands in them, and the word immediately following the ampersand was attempting to bind as a variable. The solution was to SET DEFINE OFF; and all was well after that.
Thank you all for your time and consideration.
You can avoid some of the requerying using a RETURNING clause. For example:
SQL> var v number
SQL> print v
v
---------
SQL> insert into demo1 (col1) values (12345) returning col1 into :v;
1 row inserted
SQL> print v
v
---------
12345
This tends to be cleaner and more controllable in PL/SQL than in in a series of standalone statements called from a script.