Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to use a variable for a table name when running a For Loop within an Oracle pl/sql email send

I am unable to complile this section of Oracle code as the compiler reports "PL/SQL: ORA-00942: table or view does not exist"

The Oracle table exists but this procedure must pass a table name to the For Loop procedure based on the "Order_ID" parameter. I am working within the Schema where the table exists so I am not addressing a schema name.

Example: TEMP_TBL_123 exists in the database and by passing the order_ID of 123 I am attempting to use variable TMP_TBL_NM to hold the table name "TEMP_TBL_123".

.................................................

CREATE OR REPLACE PROCEDURE EMAIL_DEPT_BLAST_TEST (SUBJECT VARCHAR2,MAIL_FROM VARCHAR2, MAIL_TO VARCHAR2,
                                               L_MESSAGE VARCHAR2, L_MESSAGE2 VARCHAR2, ORDER_ID NUMBER)
IS
MAIL_HOST VARCHAR2(30):='XX.XX.XX.XX';
MAIL_CONN UTL_SMTP.CONNECTION;
TMP_TBL_NM VARCHAR2(30);

BEGIN

TMP_TBL_NM := 'TEMP_TBL_' || ORDER_ID;

MAIL_CONN := UTL_SMTP.OPEN_CONNECTION(MAIL_HOST, 25);
UTL_SMTP.HELO(MAIL_CONN, MAIL_HOST);
UTL_SMTP.MAIL(MAIL_CONN,'[email protected]');
UTL_SMTP.RCPT(MAIL_CONN, MAIL_TO);
UTL_SMTP.OPEN_DATA(MAIL_CONN);
UTL_SMTP.WRITE_DATA(MAIL_CONN, 'Date: '||to_char(trunc(SYSDATE))||utl_tcp.crlf);
UTL_SMTP.WRITE_DATA(MAIL_CONN, 'From: '|| mail_from ||utl_tcp.crlf);
UTL_SMTP.WRITE_DATA(MAIL_CONN, 'To: '|| mail_to || utl_tcp.crlf);
UTL_SMTP.WRITE_DATA(MAIL_CONN, 'Subject: '||subject||utl_tcp.crlf);
UTL_SMTP.WRITE_DATA(MAIL_CONN, UTL_TCP.CRLF);
UTL_SMTP.WRITE_DATA(MAIL_CONN, ''|| L_MESSAGE || UTL_TCP.CRLF);
UTL_SMTP.WRITE_DATA(MAIL_CONN, UTL_TCP.CRLF);

UTL_SMTP.WRITE_DATA(MAIL_CONN, 'Order details:' || UTL_TCP.crlf);
UTL_SMTP.WRITE_DATA(MAIL_CONN, 'Quantity - Location ID - Address' || UTL_TCP.crlf);

BEGIN
    FOR I IN (SELECT LOCATION_ID, TRIM(TO_CHAR(COUNT(*),'9,999')) AS QUANTITY FROM TMP_TBL_NM GROUP BY LOCATION_ID)
    LOOP 
    UTL_SMTP.WRITE_DATA(MAIL_CONN, I.QUANTITY  || ' - ');
    UTL_SMTP.WRITE_DATA(MAIL_CONN, I.LOCATION_ID || ' ');
    UTL_SMTP.WRITE_DATA(MAIL_CONN,UTL_TCP.CRLF);
    END LOOP;
END;

UTL_SMTP.WRITE_DATA(MAIL_CONN, L_MESSAGE2 || UTL_TCP.CRLF);  

UTL_SMTP.WRITE_DATA(MAIL_CONN,UTL_TCP.CRLF);
UTL_SMTP.CLOSE_DATA(MAIL_CONN);
UTL_SMTP.QUIT(MAIL_CONN);

END SCT_CNTS_EMAIL_DEPT_BLAST_TEST;
like image 846
user1536113 Avatar asked Jul 18 '12 21:07

user1536113


People also ask

How do I pass a value from one cursor to another cursor in Oracle PL SQL?

It is possible to reference another cursor within the first one: declare cursor c1 is select distinct Assigned from table_name; cursor c2(p_Assigned in varchar2) is select id, Assigned from table_name where Assigned = p_Assigned; begin for r1 in c1 loop dbms_output.

What is difference between Varray and nested table in Oracle?

Differences Between Varrays And Nested Tables A Varray which is stored in a database maintains its subscripts and sequence. It is always maintained as a single object. Whereas, the nested tables are used when the count of the number of elements is not restricted.

Which function will you use to transfer a PL SQL table log to a database table?

To transfer a PL/SQL table log a database log table function “PROCEDURE ps2db” is used.

What is index by Pls_integer in Oracle?

INDEX BY PLS_INTEGER; Declare an associative array of numbers, indexed by string: TYPE numbers_aat IS TABLE OF NUMBER. INDEX BY VARCHAR2(100);


1 Answers

I didn't have much luck making John's example work. Here's something that does:

DECLARE
    C SYS_REFCURSOR;
    stmt VARCHAR2(1000); 
    tmp_tbl_nm  VARCHAR2(64) := 'USER_TABLES';
    the_name    VARCHAR2(64);
BEGIN
    stmt := 'SELECT table_name  FROM ' || TMP_TBL_NM || ' ORDER BY 1';
    OPEN C FOR stmt;
    LOOP
      FETCH C INTO the_name;
      EXIT WHEN C%NOTFOUND;
      dbms_output.put_line(the_name);
    END LOOP;
END;
/
CONTINENT
COUNTRY
COUNTRYINFOIMPORT
COUNTRY_LANGUAGE
GEONAME
LANGUAGE

PL/SQL procedure successfully completed.

SQL>

I don't think you can return a cursor with an EXECUTE IMMEDIATE statement. This documentation page, second paragraph, seems to indicate not. At any rate, you don't need it, just use the OPEN - FOR syntax.

like image 108
DCookie Avatar answered Oct 27 '22 05:10

DCookie