Getting TNS :Connect timeout occurred in Oracle - sql

I have the below function and I am quite frequently getting the below errors when front end ( ADF ) calls this function to get count.
Different errors comes at different times.
I think sometimes the listener is down so it might occur but other errors ?It happens when user from front end click on the link and that link in turn calls this database function.
I'm not able to find the issue in the function :-(
1) error "-12170 : ORA-12170: TNS:Connect timeout occurred"
2) error "-12571 : ORA-12571: TNS:packet writer failure"
3) error "-12541 : ORA-12541: TNS:no listener
4) error "-12514 : ORA-12514: TNS:listener does not currently know of service requested in connect descriptor
5) error "-3113 : ORA-03113: end-of-file on communication channel
ORA-02063: preceding line from DBLINK"
6) error "-2051 : ORA-02051: another session or branch in same transaction failed or finalized
ORA-02063: preceding line from DBLINK"
FUNCTION GET_A (p_in IN VARCHAR2) RETURN NUMBER
AS
PRAGMA AUTONOMOUS_TRANSACTION;
PRE_COUNT NUMBER := NULL;
BEGIN
SELECT GET_B#DBLINK (p_in,NULL)INTO PRE_COUNT FROM dual;
COMMIT;
-- dbms_lock.sleep(2);
DBMS_SESSION.CLOSE_DATABASE_LINK('DBLINK');
COMMIT;
RETURN PRE_COUNT;
EXCEPTION
WHEN OTHERS
THEN
ROLLBACK;
LOG_ERR ( p_cd => SQLCODE,p_msg => SQLERRM);
RETURN -1;
END GET_A;

Related

error when creating a new pre-rendering process (automaic row fetch)

so i had a problem with my page and i after i compared it with other similar pages i noticed it's missing a pre-rendering -> after header -> process which basically reloads data automatically with the item value that i sent from the previous page. the process is called automatic row fetch [lefacy].
i tried to create it for that page but it always show an error when i try to load it.
any tips what i might be missing
and i get this error message
ORA-06550: line 1, column 22: PL/SQL: ORA-00936: missing expression
Contact your application administrator. Details about this incident are available via debug id "353666".
Technical Info (only visible for developers)
error_statement:
begin begin select into from "CONTRAT" where "ID_CONTRAT" = :p_rowid; end;
end;
Your select clause is incomplete. You should inform something on select and into.
example:
declare
v_name varchar2(50);
begin
select NAME
into v_name
from EMPLOYEE;
end;

Postgres Raise all Exception in the end of file execution

DO $$
BEGIN
-- Check to make sure that event starts after users created
IF EXISTS (
SELECT users.id
FROM event
INNER JOIN users ON event.user_id::INT = users.id
WHERE event.start > users.created
)
THEN
RAISE NOTICE 'SUCCESSFUL %', now();
ELSE
RAISE EXCEPTION 'ERROR on % - All Event start timestamps must be created after users are created',now();
END IF;
END $$;
This exception is to check for timestamps and works well. But I want to add a similar condition and at-least 3 more exception conditions. I want to now return the exceptions at the end. I do-not want process to stop if first check fails. I want all the failed tests to be raised all at once in the end. How do I do that ? I read about stacked diagnostics bu dontt know if its the right approach or should I just use IF-else if ?
It is in the nature of an exception to interrupt processing, so you cannot simply use exceptions for that.
You could collect all exceptions in a (temporary?) table and communicate them to the client in the end, or concatenate them to a single large exception.
You could also emit the individual messages as NOTICE and throw an exception at the end.

SQL Developer DBMS_OUTPUT without 'PL/SQL procedure successfully completed.'

In SQL Developer, when running some PL/SQL, when the procedure is completed, the message 'PL/SQL procedure successfully completed.' is returned.
The PL/SQL that is run may return error messages to the user if the operation could not be completed for any reason through DBMS_OUTPUT.PUT_LINE, however, the user will also see 'PL/SQL procedure successfully completed.', which could be misleading (especially if the Script Output window is small enough that the DBMS_OUTPUT is not visible).
Is there any way to have the DBMS_OUTPUT return what it should whilst also having the script not return 'PL/SQL procedure successfully completed.'?
If not, are there any alternatives in SQL Developer that I may be unaware of to provide instant personalised feedback to the user?
declare
testex exception;
begin
if 1=1 then
raise testex;
end if;
exception when testex then
dbms_output.put_line('Error msg');
end;
Below code works in my end. Did you try to run your code like below?
Copied text from a website to explain the SET FEEDBACK OFF command.
Source link: https://docs.oracle.com/cd/B19306_01/server.102/b14357/ch12040.htm
SET FEED[BACK] {6 | n | ON | OFF} -
Displays the number of records returned by a script when a script selects at least n records.
ON or OFF turns this display on or off. Turning feedback ON sets n to 1. Setting feedback to zero is equivalent to turning it OFF.
SET FEEDBACK OFF also turns off the statement confirmation messages such as 'Table created' and 'PL/SQL procedure successfully completed' that are displayed after successful SQL or PL/SQL statements.
Add a RAISE statement in the error handler to re-raise the exception so that any outer handler can deal with it:
declare
testex exception;
begin
if 1=1 then
raise testex;
end if;
exception when testex then
dbms_output.put_line('Error msg');
RAISE; -- re-raise the exception to an outer handler
end;
Best of luck.
You have coded it explicitly to complete successfully in the event of a testex exception. The code says: if this happens, then print a message and end. If you want it to actually fail then it needs to raise an exception.
I would just use something like this:
begin
if 1=1 then
raise_application_error(-20000, 'Bananas are not available on a Tuesday');
end if;
end;
/
begin
*
ERROR at line 1:
ORA-20000: Bananas are not available on a Tuesday
ORA-06512: at line 3
This will cause an actual error, rather than just printing out a message that happens to talk about an error, allowing you to control deployments and build scripts etc.
It will also roll back any uncommitted transactions within the block, which your current approach does not, and it will show the actual line number.

PL/SQL Rollback Transaction with multiple package calls

I am new to Oracle PL/SQL and am trying to adjust from SQL Server with C# to a Oracle custom web application using PL/SQL for multiple layers of the application.
I currectly am having issues with rolling back a transaction. Since I am using to writing reusable code, I have written my PL/SQL code using packages and methods within those classes. My update procedure first completes validation and if validated successfully, calls a succession of various package methods to complete the save. Unfortunately, my rollback in the EXCEPTION portion of the update procedure does not rollback everything when the Rollback function is called. I'm at a loss as to why it is doing this. My basic code (although not exact due to legal issues) is as follows:
PROCEDURE SaveApplicationData(
variableName IN VARCHAR2 DEFAULT NULL,
--...
seq_id OUT INT )
AS
BEGIN
SET TRANSACTION NAME 'Transaction Name';
--Save initial program record
SaveNewRecord(variableName, seq_id);
IF (seq_id != 0) THEN
--If saved successfully, seq_id represents record ID
package_class.secondarySaveMethod(variableName, seq_id);
second_package_class.anotherSaveMethod(variableName, seq_id);
END IF;
COMMIT;
htp.p('Sequence ID: ' || seq_id);
htp.p('Saved the record"' || programName || '" successfully!');
EXCEPTION
WHEN OTHERS THEN
utilityPackage.rollbacktransaction;
END SaveApplicationData;
The utilityPackage.rollbacktransaction includes a ROLLBACK as well as the custom error exception handling package used by our organization.
Essentially, it will roll back the section that causes the error, but as soon as it rolls the section back, it continues with the rest of the transaction (and does not roll back previously executed blocks of code).
Please let me know if this does not make sense - and thank you in advance for your help!
Coming from a SQL Server environment before Oracle I can understand the confusion. Oracle does not use a BEGIN TRANSACTION. Instead, a transaction is implicitly started for you.
Thus, I believe in your case SET TRANSACTION NAME is not what you are looking to do, see
SET TRANSACTION.
I recommend removing the rollback code from your package and placing it in C#. It should be the responsibility of the caller to commit. Use a transaction in C# to guarantee the the transaction is committed upon successful execution of the package(s).
Ideally, your package structure should look more like this.
declare
ex_custom EXCEPTION;
PRAGMA EXCEPTION_INIT( ex_custom, -20001 );
begin
--Save initial program record
SaveNewRecord(variableName, seq_id);
IF (seq_id != 0) THEN
--If saved successfully, seq_id represents record ID
package_class.secondarySaveMethod(variableName, seq_id);
second_package_class.anotherSaveMethod(variableName, seq_id);
ELSE
-- seq_id invalid throw an exception
RAISE_APPLICATION_ERROR(-20001,'Custom error')
END IF;
htp.p('Sequence ID: ' || seq_id);
htp.p('Saved the record"' || programName || '" successfully!');
EXCEPTION
WHEN ex_custom THEN
-- if needed we log it
utility.log_exception;
-- Raise it for the client to handle
raise;
END SaveApplicationData;

Should I use the Too Many Rows Error as my exception clause in my Oracle Update statement?

I have a series of update statements that I need to use in my Oracle package. It's rare but there may be an occasional and unavoidable user error that would result in one of the update statements throwing a "Single row sub-query returns one or more rows" Error.
I've been looking into exception handling for oracle PL/SQl and I'm a bit stuck on how and what to use to catch this exception so the package doesn't crash.
I know of the pre-built "Too Many Rows" exception clause that exists but everything I read seems to say it is used for improper insert statements.
Can I use this as my exception? Or do I need to build my own exception clause. I've never built one myself before and have only a rough idea on where to put everything needed for it.
The following code is basically how the updates are set up in this particular procedure
but for the sake of brevity I'm only using a bare bones example of how it looks.
INSERT INTO TempTable... --(Initial insert statement)
UPDATE TempTable t SET t.Row_one = (SELECT (Statement_One))
WHERE T.Row_One is NULL
UPDATE TempTable t SET t.Row_one = (SELECT (Statement_Two))
WHERE T.Row_One is NULL
UPDATE TempTable t SET t.Row_one = (SELECT (Statement_Three))
WHERE T.Row_One is NULL
-- Does the exception clause start here?
EXCEPTION
WHEN TOO_MANY_ROWS THEN
(What do I tell the Procedure to do here, what am I able to tell it to do?)
--end of updates that need the exception handling
-- more insert statements into other tables based on data from the preceding Temp Table
END;
Will this work or do I need to build a custom exception?
Thanks in advance.
First, the TOO_MANY_ROWS exception will not catch the case where your select statements return multiple rows. The TOO_MANY_ROWS exception is for ORA-01422 when you issue a SELECT .. INTO statement that returns more than one row. The exception you'll encounter in your case is ORA-01427, Single row subquery returns more than one row.
If you want to handle this specific error in your procedure, use the EXCEPTION_INIT pragma to associate an exception name with the error:
too_many_values EXCEPTION;
PRAGMA EXCEPTION_INIT(too_many_values, -1427);
Then you can reference this name in your exception handler:
EXCEPTION
WHEN TOO_MANY_VALUES THEN
{perform your handler here}
What you put in the handler depends on what your procedure does. Many times you'll want to return some sort of error code/message to your caller:
PROCEDURE my_proc(p_one VARCHAR2, p_err OUT VARCHAR2) IS
too_many_values EXCEPTION;
PRAGMA EXCEPTION_INIT(too_many_values, -1427);
BEGIN
...
EXCEPTION
WHEN TOO_MANY_VALUES THEN
p_err := 'More than one value available to assign in the update';
RAISE; -- re-raise the exception for the caller
WHEN OTHERS THEN
p_err := SQLERRM; -- return the oracle message for the unexpected error
RAISE;
END;
Another approach is to skip the specific exception handlers and return generic oracle messages in the WHEN OTHERS handler:
EXCEPTION
WHEN OTHERS THEN
p_err := SQLERRM;
END;
The advantage with the first approach is you can customize your messages to be more end-user friendly when the output from the process is fed directly back to the user. The advantage with the latter approach is there is less coding involved. Error handling is an important and often skimped on aspect of any application.
The documentation from Oracle is here.
EDIT:
If this is a package, and you want to avoid passing a long chain of error variables through a series of procedure calls, you could declare an error variable with package scope, set it when the error is encountered, and RAISE the error again.
PACKAGE BODY my_pkg is
g_err VARCHAR2(256);
PROCEDURE procx(... , p_err OUT VARCHAR2) IS...
...
proc_y(p1);
EXCEPTION
WHEN OTHERS THEN
p_err := NVL(g_err, SQLERRM);
END;
PROCEDURE proc_y(p1 VARCHAR2) IS
...
proc_z(p2);
END;
PROCEDURE proc_z(p2 VARCHAR2) IS
too_many_values EXCEPTION;
PRAGMA EXCEPTION_INIT(too_many_values, -1427);
BEGIN
....
EXCEPTION
WHEN TOO_MANY_VALUES THEN
g_err := 'More than one value available to assign in the update';
RAISE; -- re-raise the exception for the caller
END;
When the exception is raised in proc_z, it is handled and then raised again. It propagates back through proc_y (no handler there) and then gets returned to the user in proc_x. Errors not set in the global g_err get the generic Oracle error message. This avoids having to pass the initial error parameter throughout the package.