I have a table with 4 columns and am passing the inputs of these 4 columns with old and new values to update them as shown below.
_________________________________________
Create table (column1 IN VARCHAR2,
column2 IN VARCHAR2,
column3 IN VARCHAR2,
column4 IN VARCHAR2,
)
insert into table values ('as','af','gh','kl');
insert into table values ('ss','sf','sh','sl');
insert into table values ('s1','ssf','sfh','sasfl');
procedure test1( oldcolumn1 IN VARCHAR2,
oldcolumn2 IN VARCHAR2,
oldcolumn3 IN VARCHAR2,
oldcolumn4 IN VARCHAR2,
newcolumn1 IN VARCHAR2,
newcolumn2 IN VARCHAR2,
newcolumn3 IN VARCHAR2,
newcolumn4 IN VARCHAR2)
________________________________________
Requirement here is to update these 4 columns with the new values where the actual column values areequal to oldcolumn inputs.But there is no guarantee that user may pass all 4 column values everttime.
If they pass oldcoulumn1 value in that case need to update only the column1.
If they pass oldcolumn4 values in that case need to update only the column4.
if they pass olculmn1 and oldcolumn5 then need to update column1 and column5.
Can you please suggest a way how to write update statements in such case?
Sounds like you need some dynamic SQL!
Check whether each input value is null. If it has a value, add it to the update string.
Make sure you're using bind variables when you build up the update statement!
For example:
create table t
(
column1 varchar2(10), column2 varchar2(10),
column3 varchar2(10), column4 varchar2(10)
);
insert into t values
( 'as','af','gh','kl'
) ;
insert into t values
( 'ss','sf','sh','sl'
) ;
insert into t values
( 's1','ssf','sfh','sasfl'
) ;
create or replace procedure test1
(
oldcolumn1 in varchar2, oldcolumn2 in varchar2,
oldcolumn3 in varchar2, oldcolumn4 in varchar2,
newcolumn1 in varchar2, newcolumn2 in varchar2,
newcolumn3 in varchar2, newcolumn4 in varchar2
)
as
update_sql varchar2(4000) := 'update t';
where_clause varchar2(4000) := 'where 1=1';
set_clause varchar2(4000) := 'set ';
cur binary_integer;
dummy int;
no_input exception;
begin
if coalesce ( oldcolumn1, oldcolumn2, oldcolumn3, oldcolumn4) is null then
raise no_input;
end if;
if oldcolumn1 is not null then
set_clause := set_clause || 'column1 = :new1,';
where_clause := where_clause || ' and column1 = :old1';
end if;
if oldcolumn2 is not null then
set_clause := set_clause || 'column2 = :new2,';
where_clause := where_clause || ' and column2 = :old2';
end if;
set_clause := substr(set_clause, 1, length(set_clause)-1);
update_sql := update_sql || ' ' || set_clause || ' ' || where_clause;
cur := dbms_sql.open_cursor;
dbms_sql.parse(cur, update_sql, dbms_sql.native);
if oldcolumn1 is not null then
dbms_sql.bind_variable(cur, 'old1', oldcolumn1);
dbms_sql.bind_variable(cur, 'new1', newcolumn1);
end if;
if oldcolumn2 is not null then
dbms_sql.bind_variable(cur, 'old2', oldcolumn2);
dbms_sql.bind_variable(cur, 'new2', newcolumn2);
end if;
dummy := dbms_sql.execute(cur);
dbms_sql.close_cursor(cur);
end;
/
select * from t;
COLUMN1 COLUMN2 COLUMN3 COLUMN4
---------- ---------- ---------- ----------
as af gh kl
ss sf sh sl
s1 ssf sfh sasfl
exec test1('as', null, null, null, 'c', null, null, null);
select * from t;
COLUMN1 COLUMN2 COLUMN3 COLUMN4
---------- ---------- ---------- ----------
c af gh kl
ss sf sh sl
s1 ssf sfh sasfl
exec test1(null, 'af', null, null, null, 'd', null, null);
select * from t;
COLUMN1 COLUMN2 COLUMN3 COLUMN4
---------- ---------- ---------- ----------
c d gh kl
ss sf sh sl
s1 ssf sfh sasfl
exec test1('ss', 'ssf', null, null, 'e', 'f', null, null);
select * from t;
COLUMN1 COLUMN2 COLUMN3 COLUMN4
---------- ---------- ---------- ----------
c d gh kl
ss sf sh sl
s1 ssf sfh sasfl