The following is a procedure that uses 2 parameters: customer_code
and pay_amount
. The procedure works as expected, however when I enter wrong cus_code
I get this error instead of my custom checking:
ORA-01403: no data found
ORA-06512: at "XXXXX.CUST_PAY", line 19
ORA-06512: at line 2
The procedure:
CREATE OR REPLACE PROCEDURE cust_pay (temp_ccode IN NUMBER, pay_amount IN NUMBER)AS
BEGIN
DECLARE
Value_check NUMBER;
cbalance NUMBER;
BEGIN
SELECT Count(cus_code)
INTO value_check
FROM customer
WHERE cus_code = temp_ccode;
IF value_check IS NULL THEN
Dbms_Output.put_line('the value was not FOUND');
ELSE
UPDATE customer
SET cus_balance = cus_balance - pay_amount
WHERE cus_code = temp_ccode;
SELECT cus_balance
INTO cbalance
FROM customer
WHERE cus_code = temp_ccode;
IF cbalance < 0 THEN
Dbms_Output.put_line('The client owes us ' || cbalance);
ELSE
Dbms_Output.put_line('Customer new balance is ' || cbalance);
END IF;
END IF;
END;
END;
What did I do wrong? I guess I need to check the value before I SELECT
, right?
Best Answer
If you use a
count()
aggregate on a resultset that has no rows, you'll get zero, not a null.If a
SELECT
doesn't find anything, an exception is raised (NO_DATA_FOUND
), and you need to catch that exception in anEXCEPTIONS
block.In your case the second select is raising the exception - since zero is not null, your first
if
branch will not be taken. (update
doesn't raise an exception if it doesn't update anything.)Your procedure is generally too complicate already though. You can declare variables in the procedure "header" directly, remove both selects - all the info you want can be gotten from a single
update
.(This assumes that
cust_code
is unique.)If the update didn't do anything,
sql%rowcount
will be zero, which tells you whether that customer exists or not (equivalent to your firstselect
). The update itself is unchanged from your code except that thereturning ... into
avoids the need for your third select and grabs the updated value directly into a local variable.