I am writing a trigger for an Oracle DB to send an email then update a column for that record acknowledging that the email has been sent. I was advised to create a cursor to fetch each row, then gather the info for the email, send the email, update the record, then repeat in a loop. The code below is what I have so far.
CREATE OR REPLACE TRIGGER "SEND_EMAIL"
After INSERT OR UPDATE OF ISSUE_ADDED_TO_ALM ON DB_TABLE FOR EACH ROW
DECLARE
l_table DB_TABLE%rowtype;
l_body varchar2(4000);
l_to_address varchar2(2000);
l_from varchar2(200);
l_name varchar2(100);
l_summary varchar2(1000);
l_description varchar2(4000);
l_ALM_ID varchar2(100);
l_subject varchar2(400);
l_added_to_alm varchar2(200);
l_SID varchar2(200);
CURSOR cur_ADDED_TO_ALM IS
select * FROM DB_TABLE where ISSUE_ADDED_TO_ALM = '1' and EMAIL_NOTIFICATION = '0';
BEGIN
OPEN cur_ADDED_TO_ALM;
LOOP
Fetch cur_ADDED_TO_ALM into l_table;
Exit when cur_ADDED_TO_ALM%NOTFOUND;
l_from := 'Data Quality IMS Team';
select ISSUE_REQUESTER into l_SID from DB_TABLE;
select emp_email_name,concat(concat(emp_first_name,' '),emp_last_name) into l_to_address, l_name from telephone_book where emp_id = l_SID;
select ISSUE_SUMMARY,ISSUE_DESCRIPTION,ALM_ISSUE_ID into l_summary, l_description, l_ALM_ID from DB_TABLE where ISSUE_ADDED_TO_ALM = '1' and EMAIL_NOTIFICATION = '0';
l_subject := l_ALM_ID + 'Request has been created.';
l_body := '<style type="text/css">
p{font-family: Calibri, Arial, Helvetica, sans-serif;
font-size:12pt;
margin-left:30px;
}
</style>';
l_body := l_body || '<p>Your request has been created.</p>';
l_body := l_body || '<p>Data Quality Center received the following request:</p>';
l_body := l_body || '<p>Request ID: '|| l_ALM_ID ||'</p>';
l_body := l_body || '<p>Request Title: '|| l_summary||'</p>';
l_body := l_body || '<p>Request Description: '|| l_description||'</p>';
HTMLDB_MAIL.SEND(
P_TO => l_to_address,
P_FROM => l_from,
P_BODY => l_body,
P_BODY_HTML => l_body,
P_SUBJ => l_subject);
wwv_flow_mail.push_queue(
P_SMTP_HOSTNAME => 'mail.sever_name.net',
P_SMTP_PORTNO => '5'
);
END LOOP;
update DB_TABLE set EMAIL_NOTIFICATION = '1' where ALM_ISSUE_ID = l_ALM_ID
IF cur_ADDED_TO_ALM%ISOPEN then
CLOSE cur_ADDED_TO_ALM;
END IF;
end;
I get the following error:
ORA-04091: table server.DB_Table is mutating, trigger/function may not see it ORA-06512: at “server.SEND_EMAIL”, line 15 ORA-06512: at “server.SEND_EMAIL”, line 18 ORA-04088: error during execution of trigger ‘server.SEND_EMAIL’

I offer these solutions.
UPDATEthe table upon which the trigger is activating. You should instead set the value using:new.EMAIL_NOTIFICATION := 1;SELECTthe table upon which the trigger is activating. This logically doesn’t make sense. That’s the reason you’re getting a “mutating table” error. The table is changing (mutatiing) and you want to read it, which would produce ambiguous results. DO NOT GO AROUND THIS WITH AN AUTONOMOUS TRANSACTION. Someone somewhere is going to give you this suggestion. That would be digging yourself even deeper into a hole.Overall, this is a terrible idea. For a purpose such as this you really don’t want to do it this way. Think about it, the user does an insert or update and must wait until the database sends all the necessary emails. If there are any exceptions raised in the trigger the transaction fails and you have to roll back.
Better plans