I have looked at asktom, and thatjeffsmith, and on this site, but I still unclear. It is confusing b/c in other tools I have used it is very simple.
I have a script that creates a small table from the data in my database (Oracle), I want to include syntax at the end of the script that exports the table I just created to my computer as a csv file. I would prefer to have this at the end of the script as opposed to a stored procedure or anything like that, b/c I have to frequently change where I save the csv files, and I'd just prefer to do it that way.
Something like:
SELECT /*csv*/ *
FROM table_name
EXPORT/OUTPUT/SAVE TO filepath.csv
I can do this with R, SPSS, STATA, SAS, in a line or two. Something like that is what I am looking for. I think I might need to specify format, quotes, header, or delimiter, but am not sure given the csv modifier in the SELECT statement. I feel like this is day 2 stuff but for some reason I cannot find a simple answer.
Thank you in advance.
Create a package like below
CREATE OR REPLACE PACKAGE APPS.csv AS
PROCEDURE generate (p_dir IN VARCHAR2,
p_file IN VARCHAR2,
p_query IN VARCHAR2);
PROCEDURE generate_rc (p_dir IN VARCHAR2,
p_file IN VARCHAR2,
p_refcursor IN OUT SYS_REFCURSOR);
PROCEDURE set_separator (p_sep IN VARCHAR2);
END csv;
/
CREATE OR REPLACE PACKAGE BODY APPS.csv AS
g_sep VARCHAR2(5) := ',';
-- Prototype for hidden procedure.
PROCEDURE generate_all (p_dir IN VARCHAR2,
p_file IN VARCHAR2,
p_query IN VARCHAR2,
p_refcursor IN OUT SYS_REFCURSOR);
-- Stub to generate a CSV from a query.
PROCEDURE generate (p_dir IN VARCHAR2,
p_file IN VARCHAR2,
p_query IN VARCHAR2) AS
l_cursor SYS_REFCURSOR;
BEGIN
generate_all (p_dir => p_dir,
p_file => p_file,
p_query => p_query,
p_refcursor => l_cursor);
END generate;
-- Stub to generate a CVS from a REF CURSOR.
PROCEDURE generate_rc (p_dir IN VARCHAR2,
p_file IN VARCHAR2,
p_refcursor IN OUT SYS_REFCURSOR) AS
BEGIN
generate_all (p_dir => p_dir,
p_file => p_file,
p_query => NULL,
p_refcursor => p_refcursor);
END generate_rc;
-- Do the actual work.
PROCEDURE generate_all (p_dir IN VARCHAR2,
p_file IN VARCHAR2,
p_query IN VARCHAR2,
p_refcursor IN OUT SYS_REFCURSOR) AS
l_cursor PLS_INTEGER;
l_rows PLS_INTEGER;
l_col_cnt PLS_INTEGER;
l_desc_tab DBMS_SQL.desc_tab;
l_buffer VARCHAR2(32767);
l_file UTL_FILE.file_type;
BEGIN
IF p_query IS NOT NULL THEN
l_cursor := DBMS_SQL.open_cursor;
DBMS_SQL.parse(l_cursor, p_query, DBMS_SQL.native);
ELSIF p_refcursor%ISOPEN THEN
l_cursor := DBMS_SQL.to_cursor_number(p_refcursor);
ELSE
RAISE_APPLICATION_ERROR(-20000, 'You must specify a query or a REF CURSOR.');
END IF;
DBMS_SQL.describe_columns (l_cursor, l_col_cnt, l_desc_tab);
FOR i IN 1 .. l_col_cnt LOOP
DBMS_SQL.define_column(l_cursor, i, l_buffer, 32767 );
END LOOP;
IF p_query IS NOT NULL THEN
l_rows := DBMS_SQL.execute(l_cursor);
END IF;
l_file := UTL_FILE.fopen(p_dir, p_file, 'w', 32767);
-- Output the column names.
FOR i IN 1 .. l_col_cnt LOOP
IF i > 1 THEN
UTL_FILE.put(l_file, g_sep);
END IF;
UTL_FILE.put(l_file, l_desc_tab(i).col_name);
END LOOP;
UTL_FILE.new_line(l_file);
-- Output the data.
LOOP
EXIT WHEN DBMS_SQL.fetch_rows(l_cursor) = 0;
FOR i IN 1 .. l_col_cnt LOOP
IF i > 1 THEN
UTL_FILE.put(l_file, g_sep);
END IF;
DBMS_SQL.COLUMN_VALUE(l_cursor, i, l_buffer);
UTL_FILE.put(l_file, l_buffer);
END LOOP;
UTL_FILE.new_line(l_file);
END LOOP;
UTL_FILE.fclose(l_file);
DBMS_SQL.close_cursor(l_cursor);
EXCEPTION
WHEN OTHERS THEN
IF UTL_FILE.is_open(l_file) THEN
UTL_FILE.fclose(l_file);
END IF;
IF DBMS_SQL.is_open(l_cursor) THEN
DBMS_SQL.close_cursor(l_cursor);
END IF;
DBMS_OUTPUT.put_line('ERROR: ' || DBMS_UTILITY.format_error_backtrace);
RAISE;
END generate_all;
-- Alter separator from default.
PROCEDURE set_separator (p_sep IN VARCHAR2) AS
BEGIN
g_sep := p_sep;
END set_separator;
END csv;
/
CREATE A DIRECTORY IN DATABASE LIKE THIS
CREATE OR REPLACE DIRECTORY EXTRACT_DIR AS 'c:\oracle\extract';
GRANT READ, WRITE ON DIRECTORY EXTRACT_DIR TO SCOTT;
GRANT EXECUTE ON UTL_FILE TO SCOTT;
EXEC csv.generate('EXTRACT_DIR', 'emp.csv', p_query => 'SELECT * FROM emp');
Hope this help to Extract a table data into csv at desired location
This is as close as I could get to answering my own question.
SET FEEDBACK OFF
SELECT /*csv*/
var1, var2, var3...varX
FROM
tablename;
Run as script (F5) in Oracle, it will produce script output in csv format, without producing any notes or documentation inside output. From there, click small disk icon, save as 'all files' and add .csv extension to end of filename.
...I'm pretty surprised there isn't a 2-3 line snippet of syntax that outputs the result of a query or script as formatX in locationY. But I guess there isn't.
Thank you to those who posted comments.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.