why i get component must be declared in plsql? - oracle

I want to access a function that exists from another schema called cmp.
the call works fine with script :
select * from (cmp.INTERFACES.get_famille_par_cin('WB23476','F00000011324'))
but with the following script it causes an error: PLS-00302: Component 'INTERFACES' must be declared
set SERVEROUTPUT on
declare
tbl typ_familles:=typ_familles();
begin
tbl:=cmp.INTERFACES.get_famille_par_cin('WB23476','F00000011324');
thx for your help !

Related

Not recognizing the record type parameter of a stored procedure

I am trying to test a newly created stored procedure in Oracle.
I added the stored procedure to the package and successfully compiled it. The input parameter is a record type.
This is the script:
SET serveroutput on;
DECLARE
p_trlr_rec trailer%ROWTYPE;
BEGIN
/* Call procedure within package, identifying schema if necessary */
TMS_SL_SQL_TRAILER.PR_UPDATE_DUE_INFO(p_trlr_rec);
END;
I get the error:
PLS-00306: wrong number or types of arguments in call to 'PR_UPDATE_DUE_INFO'
In the package file, the parameter is defined like this:
PROCEDURE PR_UPDATE_DUE_INFO
(p_rec IN OUT rectype_trailer);
PROCEDURE PR_UPDATE_DUE_INFO
(p_rec IN OUT rectype_trailer);
I also tried adding the TYPE definition:
PROCEDURE PR_UPDATE_DUE_INFO
(p_rec IN OUT rectype_trailer);
but I get the same error.
Why won't the script recognize the record definition?
Well the script is recognizing your record definitions, both of them. The calling routine is passing a parameter of type "trailer%ROWTYPE" but your procedure is expecting a type of "rectype_trailer" Even if "rectype_trailer" is defined elsewhere they are not the same; thus the error is wrong type of argument.
You need to change one of them to match the other. Assuming the rowtype definition is correct you need to change the procedure definition to
PROCEDURE PR_UPDATE_DUE_INFO
(p_rec IN OUT trailer%ROWTYPE);
In short the calling parameter definition must exactly match the called procedure definition.
PROCEDURE PR_UPDATE_DUE_INFO
(p_rec IN OUT rectype_trailer);
So for this to compile you must have declared that record type somewhere, hopefully in the specification of the package TMS_SL_SQL_TRAILER. So you simply need to reference that declaration in the calling code:
DECLARE
p_trlr_rec TMS_SL_SQL_TRAILER.rectype_trailer;
BEGIN
/* Call procedure within package, identifying schema if necessary */
TMS_SL_SQL_TRAILER.PR_UPDATE_DUE_INFO(p_trlr_rec);
END;
Oracle PL/SQL strictly enforces data typing. Two different types with identical structures are two different types and the compiler regards them as incompatible. So the compiler hurls when it tries to parse your calling code even if TMS_SL_SQL_TRAILER.rectype_trailer is declared as being of trailer%ROWTYPE.

Variable not being replaced (learning Dynamic PL/SQL)

The below code returns error ORA-00942: table or view does not exist, I think may be because PL/SQL runtime engine(or something I don't know what) is trying to treat table_in as a Table but why would it do so, I have already table_in declared as variable.
The ex26011601 table exists with values in the same schema.
set serveroutput on
declare
function tabcount (table_in in varchar2)
return pls_integer
is
l_return pls_integer;
begin
select count(*) into l_return from table_in;
return l_return;
end;
begin
dbms_output.put_line(tabcount('ex26011601'));
end;
I understand EXECUTE IMMEDIATE would solve the purpose. What I am trying to get is why is it necessary and whats wrong with current statement that 'table_in' could not be treated as variable even after being declared in the scope. Or what is the reason why a variable is not expected there?
I understand EXECUTE IMMEDIATE would solve the purpose. What I am
trying to get is why is it necessary and whats wrong with current
statement that 'table_in' could not be treated as variable even after
being declared in the scope.
As per oracle documentation : Static SQL
A PL/SQL static SQL statement can have a PL/SQL identifier wherever its SQL counterpart can have a placeholder for a bind variable. The PL/SQL identifier must identify either a variable or a formal parameter.To use PL/SQL identifiers for table names, column names, and so on, use the EXECUTE IMMEDIATE statement
In PL/SQL, you need dynamic SQL to run when :
SQL whose text is unknown at compile time
For example, a SELECT statement that includes an identifier that is unknown at compile time (such as a table name) or a WHERE clause in
which the number of sub clauses is unknown at compile time.
SQL that is not supported as static SQL
Dynamic SQL
Yes, as you said oracle pl/sql syntax does not allowing that, pass table name by variable. As you also said you can do it only by dynamic sql and execute immediate:
execute immediate 'select count(*) from ' || table_in
into l_return;

Create and execute an Oracle Stored Procedure for a select query in SQL Developer

I am using Oracle SQL Developer with Oracle 11g.
I face a strange issue creating a simple stored procedure for a Select query that doesn't need any input parameters as such. It just selects from a user defined function from the "dual" table.
These are the issues I face:
I am not able to create a procedure with no input parameters (because I don't need to use any parameter value in the select!). But the syntax does not allow me to have zero parameters, it demands a REF_CURSOR out parameter. Is the REF_CURSOR a compulsory thing in SQL Developer procedures? Is it anything to do with procedures involving a Select query?
The select query demands an INTO clause (a variable to copy the query result) in SQL developer. Is it mandatory?
Even if I used an INTO clause, I can't figure out the syntax to declare a temporary variable to copy the query result into this variable. So that I can use this out variable in my program snippet.
This is my procedure block:
Create or Replace PROCEDURE Getmarketdetails
AS
DECLARE temp varchar;
BEGIN
SELECT *
INTO temp from dual;
END Getmarketdetails;
I get these errors on compiling the procedure:
PLS-00103: Encountered the symbol "DECLARE" when expecting one of
the following: begin function pragma procedure subtype type
current cursor delete exists prior external language The
symbol "begin" was substituted for "DECLARE" to continue.
PLS-00103: Encountered the symbol "end-of-file" when expecting one of the following: ( begin case declare end exception exit for goto if loop mod null pragma raise return select update while with << continue close current delete fetch lock insert open rollback savepoint set sql execute commit forall merge pipe purge .
All I need is the perfect script syntax to create the stored procedure for this and also execute it using the exec command. And some clarifications to questions raised above. Appreciate if someone can oblige ! :)
Your syntax is incorrect - you need to declare a length for your varchar and you don't need the declare.
Create or Replace PROCEDURE Getmarketdetails
AS
temp varchar(100);
BEGIN
SELECT *
INTO temp from dual;
END Getmarketdetails;
Create or Replace PROCEDURE Getmarketdetails
AS
temp varchar2(20);
BEGIN
SELECT 'stack overflow' INTO temp from dual;
Dbms_output.put_line(temp);
END Getmarketdetails;
Some modification done in your procedure. Don't write declare and mention variables as per your need.

existing state of package has been invalidated

I am facing this error.
I have two Schema Schema A and Schema B
Schema B contains a table my_table in which values are being Inserted.
There is also a triggger my_trigger written for my_table in schemaB for each row
CREATE OR REPLACE TRIGGER schemaB.my_trigger
ON schemaA.my_table
FOR EACH ROW
BEGIN
IF INSERTING THEN
schemaA.my_package.my_procedure (:NEW.field_A,NEW.field_B, :NEW.field_C);
END IF;
EXCEPTION
WHEN OTHERS THEN
Insert into my_log(DBMS_UTILITY.format_error_stack,sysdate);
END my_trigger;
/ AFTER INSERT
This trigger written on my_table of schemaB is calling a procedure which is present in Schema A.
However when the trigger is being fired I am getting the below error in my logs
ERROR: ORA-04061: existing state of package "schemaA.my_package" has been invalidated
ORA-04065: not executed, altered or dropped package "schemaA.my_package"
ORA-06508: PL/SQL: could not find program unit being called: "schemaA.my_package"
ORA-06512: at "schemaB.my_trigger", line 17 10/1/2015 6:38:07 PM
Also the procedure in schemaA is declared as PRAGMA_AUTONOMOUS_TRANSACTION
Is this some grants issue as i checked all the grants has been given, I have checked dependencies of the both trigger and procedure
and all seems to valid. Can you kindly help?
I have tried using Pragma serially_reusable in the calling package but still giving me same error
Many thanks
Possible issues you can have is:
The package/procedure you are calling is invalid
check this query whether you have an entry of your package or objects used in your package in this all_objects view
select * from all_objects where status = 'INVALID' and owner = 'SCHEMA_NAME';
Check your package is having global variables? if yes then check if those variable is not being changed by any other session
run below script to compile all the objects in your schema
begin
dbms_utility.compile_schema('SCHEMA_NAME',false);
end;
Last option if none of the above works then remove all the procedures/function from your package, add new function and try to run your function from the trigger. check if this works then your package is in special lock. after adding a new function it's state will be valid again and then you can add all your actual funcs/procs and remove the newly added one.

Execute Oracle Stored Proc

I have an oracle stored proc with signiture: (part of package: Contractor)
PROCEDURE usp_sel_contractors(g_contractors OUT sel_contractor);
I am trying to execute it like:
execute Contractor.usp_sel_contractors;
I'm used to MSSqlServer. This seems like it should be strait forward.
I keep getting error:
Invalid Sql Statement
Thanks!
Assuming sel_contractor is a ref cursor type, you could do this in SQL Plus:
var rc refcursor
exec usp_sel_contractors(:rc)
print rc
I'm not sure why you'd be getting that specific error message, but the obvious problem is that the procedure has a parameter and you're not passing one. Since it's an OUT parameter you would need to pass a variable of the appropriate type which will be populated by the procedure.
For example:
DECLARE
my_contractors sel_contractor;
BEGIN
usp_sel_contractors( my_contractors );
// Do something with the contents of my_contractors here
END;
/

Resources