blob: c877b876403337b7ec87693c23629b84a09bfcb2 [file]
ij> --
-- Licensed to the Apache Software Foundation (ASF) under one or more
-- contributor license agreements. See the NOTICE file distributed with
-- this work for additional information regarding copyright ownership.
-- The ASF licenses this file to You under the Apache License, Version 2.0
-- (the "License"); you may not use this file except in compliance with
-- the License. You may obtain a copy of the License at
--
-- http://www.apache.org/licenses/LICENSE-2.0
--
-- Unless required by applicable law or agreed to in writing, software
-- distributed under the License is distributed on an "AS IS" BASIS,
-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-- See the License for the specific language governing permissions and
-- limitations under the License.
--
--
-- this test is for basic update functionality
--
-- create the table
create table t1 (int_col int, smallint_col smallint, char_30_col char(30),
varchar_50_col varchar(50));
0 rows inserted/updated/deleted
ij> create table t2 (int_col int, smallint_col smallint, char_30_col char(30),
varchar_50_col varchar(50));
0 rows inserted/updated/deleted
ij> -- populate t1
insert into t1 values (1, 2, 'char_30_col', 'varchar_50_col');
1 row inserted/updated/deleted
ij> insert into t1 values (null, null, null, null);
1 row inserted/updated/deleted
ij> insert into t2 select * from t1;
2 rows inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
1 |2 |char_30_col |varchar_50_col
NULL |NULL |NULL |NULL
ij> -- update with constants
update t1 set int_col = 3, smallint_col = 4, char_30_col = 'CHAR_30_COL',
varchar_50_col = 'VARCHAR_50_COL';
2 rows inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
3 |4 |CHAR_30_COL |VARCHAR_50_COL
3 |4 |CHAR_30_COL |VARCHAR_50_COL
ij> update t1 set varchar_50_col = null, char_30_col = null, smallint_col = null,
int_col = null;
2 rows inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
NULL |NULL |NULL |NULL
NULL |NULL |NULL |NULL
ij> update t1 set smallint_col = 6, int_col = 5, varchar_50_col = 'varchar_50_col',
char_30_col = 'char_30_col';
2 rows inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
5 |6 |char_30_col |varchar_50_col
5 |6 |char_30_col |varchar_50_col
ij> -- update columns with column values
update t1 set smallint_col = int_col, int_col = smallint_col,
varchar_50_col = char_30_col, char_30_col = varchar_50_col;
2 rows inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
6 |5 |varchar_50_col |char_30_col
6 |5 |varchar_50_col |char_30_col
ij> update t1 set int_col = int_col, smallint_col = smallint_col,
char_30_col = char_30_col, varchar_50_col = varchar_50_col;
2 rows inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
6 |5 |varchar_50_col |char_30_col
6 |5 |varchar_50_col |char_30_col
ij> -- Negative test - column in SET clause twice
update t1 set int_col = 1, int_col = 2;
ERROR 42X16: Column name 'INT_COL' appears multiple times in the SET clause of an UPDATE statement.
ij> -- Negative test - non-existent column in SET clause
update t1 set notacolumn = int_col + 1;
ERROR 42X14: 'NOTACOLUMN' is not a column in table or VTI 'APP.T1'.
ij> -- target table in source - deferred update
--
-- first, populate table
delete from t1;
2 rows inserted/updated/deleted
ij> insert into t1 values (1, 1, 'one', 'one');
1 row inserted/updated/deleted
ij> insert into t1 values (2, 2, 'two', 'two');
1 row inserted/updated/deleted
ij> delete from t2;
2 rows inserted/updated/deleted
ij> insert into t2 select * from t1;
2 rows inserted/updated/deleted
ij> autocommit off;
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
1 |1 |one |one
2 |2 |two |two
ij> update t1 set int_col =
(select t1.int_col
from t1, t2
where t1.int_col = t2.int_col and t1.int_col = 1);
2 rows inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
1 |1 |one |one
1 |2 |two |two
ij> rollback;
ij> update t1 set int_col =
(select
(select int_col
from t1
where int_col = 2)
from t2
where int_col = 1);
2 rows inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
2 |1 |one |one
2 |2 |two |two
ij> rollback;
ij> update t1 set int_col =
(select 1
from t2
where int_col = 2
and 1 in
(select int_col
from t1)
);
2 rows inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
1 |1 |one |one
1 |2 |two |two
ij> rollback;
ij> update t1 set int_col =
(select int_col
from
(select int_col
from t1) a
where int_col = 2);
2 rows inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
2 |1 |one |one
2 |2 |two |two
ij> rollback;
ij> update t1 set int_col =
(select int_col
from t2
where int_col = 37
union
select int_col
from t1
where int_col = 2);
2 rows inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
2 |1 |one |one
2 |2 |two |two
ij> rollback;
ij> update t1 set int_col =
(select int_col
from t2
where int_col = 37
union
select int_col
from
(select int_col
from t1
where int_col = 2) a
);
2 rows inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
2 |1 |one |one
2 |2 |two |two
ij> rollback;
ij> -- single-row deferred update
update t1 set int_col =
(select int_col
from t1
where int_col = 1)
where int_col = 2;
1 row inserted/updated/deleted
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
1 |1 |one |one
1 |2 |two |two
ij> rollback;
ij> -- zero-row deferred update - degenerate case
update t1 set int_col =
(select int_col
from t1
where int_col = 1)
where int_col = 37;
0 rows inserted/updated/deleted
WARNING 02000: No row was found for FETCH, UPDATE or DELETE; or the result of a query is an empty table.
ij> select * from t1;
INT_COL |SMALL&|CHAR_30_COL |VARCHAR_50_COL
----------------------------------------------------------------------------------------------------
1 |1 |one |one
2 |2 |two |two
ij> rollback;
ij> autocommit on;
ij> -- drop the table
drop table t1;
0 rows inserted/updated/deleted
ij> drop table t2;
0 rows inserted/updated/deleted
ij> -- Show whether update is statement atomic or not
create table s (s smallint, i int);
0 rows inserted/updated/deleted
ij> insert into s values (1, 1);
1 row inserted/updated/deleted
ij> insert into s values (1, 65337);
1 row inserted/updated/deleted
ij> insert into s values (1, 1);
1 row inserted/updated/deleted
ij> select * from s;
S |I
------------------
1 |1
1 |65337
1 |1
ij> -- this should fail and no rows should change
update s set s=s+i;
ERROR 22003: The resulting value is outside the range for the data type SMALLINT.
ij> -- this select should have the same results as the previous one.
select * from s;
S |I
------------------
1 |1
1 |65337
1 |1
ij> -- Show that the table name can be used on the set column
update s set s.s=3;
3 rows inserted/updated/deleted
ij> -- and that it must match the target table
update s set t.s=4;
ERROR 42X55: Table name 'T' should be the same as 'S'.
ij> select * from s;
S |I
------------------
3 |1
3 |65337
3 |1
ij> -- do some partial updates
create table t1 (c1 char(250), c2 varchar(100), c3 varchar(100));
0 rows inserted/updated/deleted
ij> insert into t1 values ('a', 'b', 'c');
1 row inserted/updated/deleted
ij> insert into t1 values ('a', 'b', 'c');
1 row inserted/updated/deleted
ij> insert into t1 values ('a', 'b', 'c');
1 row inserted/updated/deleted
ij> insert into t1 values ('a', 'b', 'c');
1 row inserted/updated/deleted
ij> update t1 set c1 = '1st';
4 rows inserted/updated/deleted
ij> select cast(c1 as char(5)), cast(c2 as char(5)), cast(c3 as char(5)) from t1;
1 |2 |3
-----------------
1st |b |c
1st |b |c
1st |b |c
1st |b |c
ij> update t1 set c2 = '2nd';
4 rows inserted/updated/deleted
ij> select cast(c1 as char(5)), cast(c2 as char(5)), cast(c3 as char(5)) from t1;
1 |2 |3
-----------------
1st |2nd |c
1st |2nd |c
1st |2nd |c
1st |2nd |c
ij> update t1 set c3 = '3rd';
4 rows inserted/updated/deleted
ij> select cast(c1 as char(5)), cast(c2 as char(5)), cast(c3 as char(5)) from t1;
1 |2 |3
-----------------
1st |2nd |3rd
1st |2nd |3rd
1st |2nd |3rd
1st |2nd |3rd
ij> update t1 set c3 = '4th', c2 = '4th';
4 rows inserted/updated/deleted
ij> select cast(c1 as char(5)), cast(c2 as char(5)), cast(c3 as char(5)) from t1;
1 |2 |3
-----------------
1st |4th |4th
1st |4th |4th
1st |4th |4th
1st |4th |4th
ij> update t1 set c1 = '5th', c3 = '5th';
4 rows inserted/updated/deleted
ij> select cast(c1 as char(5)), cast(c2 as char(5)), cast(c3 as char(5)) from t1;
1 |2 |3
-----------------
5th |4th |5th
5th |4th |5th
5th |4th |5th
5th |4th |5th
ij> update t1 set c2 = 'expandingxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
4 rows inserted/updated/deleted
ij> select cast(c1 as char(5)), cast(c2 as char(5)), cast(c3 as char(5)) from t1;
1 |2 |3
-----------------
5th |expan|5th
WARNING 01004: Data truncation
5th |expan|5th
WARNING 01004: Data truncation
5th |expan|5th
WARNING 01004: Data truncation
5th |expan|5th
WARNING 01004: Data truncation
ij> update t1 set c3 = 'expandingxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
4 rows inserted/updated/deleted
ij> select cast(c1 as char(5)), cast(c2 as char(5)), cast(c3 as char(5)) from t1;
1 |2 |3
-----------------
5th |expan|expan
WARNING 01004: Data truncation
WARNING 01004: Data truncation
5th |expan|expan
WARNING 01004: Data truncation
WARNING 01004: Data truncation
5th |expan|expan
WARNING 01004: Data truncation
WARNING 01004: Data truncation
5th |expan|expan
WARNING 01004: Data truncation
WARNING 01004: Data truncation
ij> update t1 set c2 = 'shrink';
4 rows inserted/updated/deleted
ij> update t1 set c3 = 'shrink';
4 rows inserted/updated/deleted
ij> select cast(c1 as char(5)), cast(c2 as char(5)), cast(c3 as char(5)) from t1;
1 |2 |3
-----------------
5th |shrin|shrin
WARNING 01004: Data truncation
WARNING 01004: Data truncation
5th |shrin|shrin
WARNING 01004: Data truncation
WARNING 01004: Data truncation
5th |shrin|shrin
WARNING 01004: Data truncation
WARNING 01004: Data truncation
5th |shrin|shrin
WARNING 01004: Data truncation
WARNING 01004: Data truncation
ij> update t1 set c2 = 'expandingxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx',
c3 = 'expandingxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';
4 rows inserted/updated/deleted
ij> select cast(c1 as char(5)), cast(c2 as char(5)), cast(c3 as char(5)) from t1;
1 |2 |3
-----------------
5th |expan|expan
WARNING 01004: Data truncation
WARNING 01004: Data truncation
5th |expan|expan
WARNING 01004: Data truncation
WARNING 01004: Data truncation
5th |expan|expan
WARNING 01004: Data truncation
WARNING 01004: Data truncation
5th |expan|expan
WARNING 01004: Data truncation
WARNING 01004: Data truncation
ij> drop table t1;
0 rows inserted/updated/deleted
ij> create table t1 (c1 int, c2 int, c3 int, c4 int, c5 int, c6 int, c7 int, c8 int, c9 int);
0 rows inserted/updated/deleted
ij> insert into t1 values (1,2,3,4,5,6,7,8,9);
1 row inserted/updated/deleted
ij> update t1 set c3 = 33, c5 = 55, c6 = 666, c8 = 88;
1 row inserted/updated/deleted
ij> select * from t1;
C1 |C2 |C3 |C4 |C5 |C6 |C7 |C8 |C9
-----------------------------------------------------------------------------------------------------------
1 |2 |33 |4 |55 |666 |7 |88 |9
ij> update t1 set c9 = 99;
1 row inserted/updated/deleted
ij> select * from t1;
C1 |C2 |C3 |C4 |C5 |C6 |C7 |C8 |C9
-----------------------------------------------------------------------------------------------------------
1 |2 |33 |4 |55 |666 |7 |88 |99
ij> drop table t1;
0 rows inserted/updated/deleted
ij> --
-- here we test extra state lying around in the
-- deleteResultSet on a prepared statement that
-- is executed multiple times. if we don't
-- get a nasty error then we are ok
--
create table x (x int, y int);
0 rows inserted/updated/deleted
ij> create index ix on x(x);
0 rows inserted/updated/deleted
ij> create index iy on x(y);
0 rows inserted/updated/deleted
ij> insert into x values (1,1),(2,2),(3,3);
3 rows inserted/updated/deleted
ij> autocommit off;
ij> prepare p as 'update x set x = x where x = ? and y = ?';
ij> execute p using 'values (1,1)';
1 row inserted/updated/deleted
ij> execute p using 'values (2,2)';
1 row inserted/updated/deleted
ij> commit;
ij> -- test extra state in update
get cursor c1 as 'select * from x for update of x';
ij> prepare p1 as 'update x set x = x where current of c1';
ij> execute p1;
ERROR 24000: Invalid cursor state - no current row.
ij> next c1;
X |Y
-----------------------
1 |1
ij> execute p1;
1 row inserted/updated/deleted
ij> next c1;
X |Y
-----------------------
2 |2
ij> next c1;
X |Y
-----------------------
3 |3
ij> execute p1;
1 row inserted/updated/deleted
ij> close c1;
ij> execute p1;
ERROR 42X30: Cursor 'C1' not found. Verify that autocommit is off.
ij> -- clean up
autocommit on;
ij> drop table x;
0 rows inserted/updated/deleted
ij> -- bug 4318, possible deadlock if table first has IX, then X table lock; make
-- sure you don't have IX table lock and X table lock at the same time
create table tab1 (c1 int not null primary key, c2 int);
0 rows inserted/updated/deleted
ij> insert into tab1 values (1, 8);
1 row inserted/updated/deleted
ij> autocommit off;
ij> -- default read committed isolation level
update tab1 set c2 = c2 + 3 where c1 = 1;
1 row inserted/updated/deleted
ij> select type, mode from syscs_diag.lock_table where CAST(tablename AS VARCHAR(128)) = 'TAB1' order by type;
TYPE |MODE
----------
ROW |X
TABLE|IX
ij> rollback;
ij> -- serializable isolation level
set current isolation to SERIALIZABLE;
0 rows inserted/updated/deleted
ij> update tab1 set c2 = c2 + 3 where c1 = 1;
1 row inserted/updated/deleted
ij> select type, mode from syscs_diag.lock_table where CAST(tablename AS VARCHAR(128)) = 'TAB1' order by type;
TYPE |MODE
----------
ROW |X
TABLE|IX
ij> rollback;
ij> autocommit on;
ij> drop table tab1;
0 rows inserted/updated/deleted
ij> --------------------------------------------
--
-- Test upgrade piece of the fix for bug171.
--
--------------------------------------------
create table bug171_employee( empl_id int, bonus int );
0 rows inserted/updated/deleted
ij> create table bug171_bonuses( empl_id int, bonus int );
0 rows inserted/updated/deleted
ij> insert into bug171_employee( empl_id, bonus ) values ( 1, 0 ), ( 2, 0 ), ( 3, 0 );
3 rows inserted/updated/deleted
ij> insert into bug171_bonuses( empl_id, bonus )
values
( 1, 100 ), ( 1, 100 ), ( 1, 100 ),
( 2, 200 ), ( 2, 200 ), ( 2, 200 ),
( 3, 300 ), ( 3, 300 ), ( 3, 300 );
9 rows inserted/updated/deleted
ij> select * from bug171_employee;
EMPL_ID |BONUS
-----------------------
1 |0
2 |0
3 |0
ij> select * from bug171_bonuses;
EMPL_ID |BONUS
-----------------------
1 |100
1 |100
1 |100
2 |200
2 |200
2 |200
3 |300
3 |300
3 |300
ij> --
-- The problem query. could not use correlation names in update.
--
update bug171_employee e
set e.bonus =
(
select sum( b.bonus ) from bug171_bonuses b
where b.empl_id = e.empl_id
);
3 rows inserted/updated/deleted
ij> select * from bug171_employee;
EMPL_ID |BONUS
-----------------------
1 |300
2 |600
3 |900
ij> -- positioned update with correlation names
autocommit off;
ij> get cursor bug171_c1 as
'select * from bug171_employee where empl_id = 1 for update';
ij> next bug171_c1;
EMPL_ID |BONUS
-----------------------
1 |300
ij> update bug171_employee e
set e.bonus =
(
select 2 * sum( b.bonus ) from bug171_bonuses b
where b.empl_id = e.empl_id
)
where current of bug171_c1;
1 row inserted/updated/deleted
ij> close bug171_c1;
ij> select * from bug171_employee;
EMPL_ID |BONUS
-----------------------
1 |600
2 |600
3 |900
ij> autocommit on;
ij> --
-- Cleanup
--
drop table bug171_employee;
0 rows inserted/updated/deleted
ij> drop table bug171_bonuses;
0 rows inserted/updated/deleted
ij> --
-- DERBY-1329: Correlated subquery in UPDATE ... SET ... WHERE CURRENT OF
--
CREATE TABLE BASICTABLE1(ID INTEGER, C3 CHAR(10));
0 rows inserted/updated/deleted
ij> CREATE TABLE BASICTABLE2(IID INTEGER, CC3 CHAR(10));
0 rows inserted/updated/deleted
ij> insert into BASICTABLE1 (C3, ID) values ('abc', 1);
1 row inserted/updated/deleted
ij> insert into BASICTABLE2 (CC3, IID) values ('def', 1);
1 row inserted/updated/deleted
ij> -- Check data.
select * from BASICTABLE1;
ID |C3
----------------------
1 |abc
ij> select * from BASICTABLE2;
IID |CC3
----------------------
1 |def
ij> autocommit off;
ij> get cursor c1 as 'select c3, id from basictable1 for update';
ij> next c1;
C3 |ID
----------------------
abc |1
ij> -- Before fix for DERBY-1329 the following statement would fail with
-- an ASSERT failure or an IndexOutOfBoundsException; after the fix
-- the statement should succeed and the update as well.
update BASICTABLE1 set C3 = (SELECT CC3 FROM BASICTABLE2
WHERE BASICTABLE1.ID=BASICTABLE2.IID) where current of c1;
1 row inserted/updated/deleted
ij> -- Check data; BASICTABLE1 should have been updated.
select * from BASICTABLE1;
ID |C3
----------------------
1 |def
ij> select * from BASICTABLE2;
IID |CC3
----------------------
1 |def
ij> -- Cleanup.
rollback;
ij> drop table BASICTABLE1;
0 rows inserted/updated/deleted
ij> drop table BASICTABLE2;
0 rows inserted/updated/deleted
ij> -- tests for DERBY-1043
CREATE TABLE DERBY10431 (ID SMALLINT GENERATED ALWAYS AS IDENTITY, A_COL VARCHAR(15) NOT NULL PRIMARY KEY);
0 rows inserted/updated/deleted
ij> CREATE TABLE DERBY10432 (TYPE VARCHAR(15) NOT NULL, A_COL VARCHAR(15) NOT NULL, AMOUNT SMALLINT NOT NULL DEFAULT 0);
0 rows inserted/updated/deleted
ij> INSERT INTO DERBY10431(A_COL) VALUES ('apples');
1 row inserted/updated/deleted
ij> INSERT INTO DERBY10432 VALUES ('tree fruit','apples',1);
1 row inserted/updated/deleted
ij> SELECT * FROM DERBY10431;
ID |A_COL
----------------------
1 |apples
ij> SELECT * FROM DERBY10432;
TYPE |A_COL |AMOUNT
--------------------------------------
tree fruit |apples |1
ij> -- after fix for DERBY-1043 this update should cause an exception
UPDATE DERBY10432 SET DERBY10432.A_COL = DERBY10431.A_COL WHERE A_COL = 'apples';
ERROR 42X04: Column 'DERBY10431.A_COL' is either not in any table in the FROM list or appears within a join specification and is outside the scope of the join specification or appears in a HAVING clause and is not in the GROUP BY list. If this is a CREATE or ALTER TABLE statement then 'DERBY10431.A_COL' is not a column in the target table.
ij> DROP TABLE DERBY10431;
0 rows inserted/updated/deleted
ij> DROP TABLE DERBY10432;
0 rows inserted/updated/deleted
ij>