Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / IBM DB2, WebSphere, IMS, U2, etc Новый топик    Ответить
 Срочно! Опция WITH ROW MOVEMENT в VIEW  [new]
kdima71
Member

Откуда:
Сообщений: 180
Привет всем!

Я имею DB2 UDB 8.2 for Win2000 (после FixPack 7).
Пока новичок в DB2.

Хочу сразу сделать пояснение, я использую опцию WITH ROW MOVEMENT с пониманием для каких целей она служит.

Делаю следующее:

DROP TABLE NODE_1

CREATE TABLE NODE_1 (
DOC_ID INTEGER NOT NULL,
NODE_ID INTEGER NOT NULL,
CONSTRAINT NODE1_CHK
CHECK (NODE_ID = 1)
ENFORCED
ENABLE QUERY OPTIMIZATION
)

DROP TABLE NODE_2

CREATE TABLE NODE_2 (
DOC_ID INTEGER NOT NULL,
NODE_ID INTEGER NOT NULL,
CONSTRAINT NODE2_CHK
CHECK (NODE_ID = 2)
ENFORCED
ENABLE QUERY OPTIMIZATION
)

DROP VIEW ALL_NODES_V

CREATE VIEW ALL_NODES_V AS
SELECT * FROM NODE_1
UNION ALL
SELECT * FROM NODE_2
WITH ROW MOVEMENT

Далее:

INSERT INTO ALL_NODES_V VALUES (1,1)

COMMIT

SELECT * FROM ALL_NODES_V

DOC_ID NODE_ID
----------- -----------
1 1

1 записей выбрано.

UPDATE ALL_NODES_V SET NODE_ID = 1

COMMIT

SELECT * FROM ALL_NODES_V

DOC_ID NODE_ID
----------- -----------
1 1
1 1

2 записей выбрано.


Это как понимать?
Почему DB2 добавляет новую запись после UPDATE???
Сталкивался кто-либо с такой проблемой и если какой-либо обход?
И вообще это "баг" или "причуды SQL" (по Graeme Birchall)?

Заранее благодарю за любые пояснения и извините за возможную категоричность!
18 дек 04, 18:11    [1191197]     Ответить | Цитировать Сообщить модератору
 Re: Срочно! Опция WITH ROW MOVEMENT в VIEW  [new]
gardenman
Member

Откуда: С-Петербург
Сообщений: 2347
connect to test2@

drop view VV@
drop table t1@
drop table t2@


create table t1 (
	node	integer  not null check (node=1),
	id		integer  not null,
	name	char(30),
	constraint PK primary key (node,id)
)@

create table t2 (
	node	integer  not null check (node=2),
	id		integer  not null,
	name	char(30),
	constraint PK primary key (node,id)
)@


create view VV as
select * from t1
union all
select * from t2
with row movement@

commit@

insert into VV (node,id,name) values (1,1,'111111')@
commit@
insert into VV (node,id,name) values (2,1,'222222')@
commit@
select * from VV@
select * from t1@
select * from t2@
commit@

update VV set (name)=('33333') where node=1 and id=1@
select * from VV@
select * from t1@
select * from t2@
commit@

update VV set (node,id)=(2,3) where node=1 and id=1@
select * from VV@
select * from t1@
select * from t2@
commit@

update VV set (node,id)=(2,3) where node=2 and id=3@
select * from VV@
select * from t1@
select * from t2@
commit@



connect to test2

   Информация соединения с базой данных

 Сервер баз данных           = DB2/NT 8.2.0
 ID авторизации SQL          = DB2ADMIN
 Алиас локальной базы данных = TEST2


drop view VV
DB20000I  Команда SQL выполнена успешно.

drop table t1
DB20000I  Команда SQL выполнена успешно.

drop table t2
DB20000I  Команда SQL выполнена успешно.

create table t1 ( node	integer  not null check (node=1), id		integer  not null, name	char(30), constraint PK primary key (node,id) )
DB20000I  Команда SQL выполнена успешно.

create table t2 ( node	integer  not null check (node=2), id		integer  not null, name	char(30), constraint PK primary key (node,id) )
DB20000I  Команда SQL выполнена успешно.

create view VV as select * from t1 union all select * from t2 with row movement
DB20000I  Команда SQL выполнена успешно.

commit
DB20000I  Команда SQL выполнена успешно.

insert into VV (node,id,name) values (1,1,'111111')
DB20000I  Команда SQL выполнена успешно.

commit
DB20000I  Команда SQL выполнена успешно.

insert into VV (node,id,name) values (2,1,'222222')
DB20000I  Команда SQL выполнена успешно.

commit
DB20000I  Команда SQL выполнена успешно.

select * from VV

NODE        ID          NAME                          
----------- ----------- ------------------------------
          2           1 222222                        
          1           1 111111                        

  2 записей выбрано.


select * from t1

NODE        ID          NAME                          
----------- ----------- ------------------------------
          1           1 111111                        

  1 записей выбрано.


select * from t2

NODE        ID          NAME                          
----------- ----------- ------------------------------
          2           1 222222                        

  1 записей выбрано.


commit
DB20000I  Команда SQL выполнена успешно.

update VV set (name)=('33333') where node=1 and id=1
DB20000I  Команда SQL выполнена успешно.

select * from VV

NODE        ID          NAME                          
----------- ----------- ------------------------------
          2           1 222222                        
          1           1 33333                         

  2 записей выбрано.


select * from t1

NODE        ID          NAME                          
----------- ----------- ------------------------------
          1           1 33333                         

  1 записей выбрано.


select * from t2

NODE        ID          NAME                          
----------- ----------- ------------------------------
          2           1 222222                        

  1 записей выбрано.


commit
DB20000I  Команда SQL выполнена успешно.

update VV set (node,id)=(2,3) where node=1 and id=1
DB20000I  Команда SQL выполнена успешно.

select * from VV

NODE        ID          NAME                          
----------- ----------- ------------------------------
          2           1 222222                        
          2           3 33333                         

  2 записей выбрано.


select * from t1

NODE        ID          NAME                          
----------- ----------- ------------------------------

  0 записей выбрано.


select * from t2

NODE        ID          NAME                          
----------- ----------- ------------------------------
          2           1 222222                        
          2           3 33333                         

  2 записей выбрано.


commit
DB20000I  Команда SQL выполнена успешно.

update VV set (node,id)=(2,3) where node=2 and id=3
DB21034E  Данная команда обрабатывалась как оператор SQL, поскольку она не 
является допустимой командой процессора командной строки.  При обработке SQL 
было получено сообщение:
SQL0803N  Одно или несколько значений в операторе INSERT, в операторе UPDATE 
или при обновлении внешнего ключа, вызванном оператором DELETE, недопустимы, 
поскольку первичный ключ, ограничение уникальности или индекс уникальности "1" 
запрещают повторение строк для этих столбцов в таблице "DB2ADMIN.T2".  
SQLSTATE=23505

select * from VV

NODE        ID          NAME                          
----------- ----------- ------------------------------
          2           1 222222                        
          2           3 33333                         

  2 записей выбрано.


select * from t1

NODE        ID          NAME                          
----------- ----------- ------------------------------

  0 записей выбрано.


select * from t2

NODE        ID          NAME                          
----------- ----------- ------------------------------
          2           1 222222                        
          2           3 33333                         

  2 записей выбрано.


commit
DB20000I  Команда SQL выполнена успешно.



В общем, дело наверное в специфике, каким образом записи обрабатываются в этом случае. Об этом говорит фрагмент
update VV set (node,id)=(2,3) where node=2 and id=3 - была получена ошибка
вот план запроса:


DB2 Universal Database Version 8.1, 5622-044 (c) Copyright IBM Corp. 1991, 2002
Licensed Material - Program Property of IBM
IBM DB2 Universal Database SQL Explain Tool

DB2 Universal Database Version 8.1, 5622-044 (c) Copyright IBM Corp. 1991, 2002

Licensed Material - Program Property of IBM

IBM DB2 Universal Database SQL Explain Tool



******************** DYNAMIC ***************************************



==================== STATEMENT ==========================================



	Isolation Level          = Cursor Stability
	Blocking                 = Block Unambiguous Cursors
	Query Optimization Class = 5

	Partition Parallel       = No
	Intra-Partition Parallel = No

	SQL Path                 = "SYSIBM", "SYSFUN", "SYSPROC", "DB2ADMIN"

SQL Statement:

  update VV set (node, id)=(2, 3)
  where node=2 and id=3


Section Code Page = 1251

Estimated Cost = 115,830208
Estimated Cardinality = 6,000000

Data Stream 1:
|  Not Piped
|  Data Stream 2:
|  |  Not Piped
|  |  Data Stream 3:
|  |  |  Not Piped
|  |  |  (
|  |  |  |  Access Table Name = DB2ADMIN.T2  ID = 2,11
|  |  |  |  |  Index Scan:  Name = SYSIBM.SQL041220112216530  ID = 1
|  |  |  |  |  |  Regular Index (Not Clustered)
|  |  |  |  |  |  Index Columns:
|  |  |  |  |  |  |  1: NODE (Ascending)
|  |  |  |  |  |  |  2: ID (Ascending)
|  |  |  |  |  #Columns = 1
|  |  |  |  |  Single Record
|  |  |  |  |  Fully Qualified Unique Key
|  |  |  |  |  #Key Columns = 2
|  |  |  |  |  |  Start Key: Inclusive Value
|  |  |  |  |  |  |  |  1: 2
|  |  |  |  |  |  |  |  2: 3
|  |  |  |  |  |  Stop Key: Inclusive Value
|  |  |  |  |  |  |  |  1: 2
|  |  |  |  |  |  |  |  2: 3
|  |  |  |  |  Data Prefetch: None
|  |  |  |  |  Index Prefetch: None
|  |  |  |  |  Isolation Level: Read Stability
|  |  |  |  |  Lock Intents
|  |  |  |  |  |  Table: Intent Exclusive
|  |  |  |  |  |  Row  : Exclusive
|  |  |  UNION
|  |  |  |  Access Table Name = DB2ADMIN.T1  ID = 2,10
|  |  |  |  |  Index Scan:  Name = DB2ADMIN.PK  ID = 1
|  |  |  |  |  |  Regular Index (Not Clustered)
|  |  |  |  |  |  Index Columns:
|  |  |  |  |  |  |  1: NODE (Ascending)
|  |  |  |  |  |  |  2: ID (Ascending)
|  |  |  |  |  #Columns = 1
|  |  |  |  |  Single Record
|  |  |  |  |  Fully Qualified Unique Key
|  |  |  |  |  #Key Columns = 2
|  |  |  |  |  |  Start Key: Inclusive Value
|  |  |  |  |  |  |  |  1: 1
|  |  |  |  |  |  |  |  2: 3
|  |  |  |  |  |  Stop Key: Inclusive Value
|  |  |  |  |  |  |  |  1: 1
|  |  |  |  |  |  |  |  2: 3
|  |  |  |  |  Data Prefetch: None
|  |  |  |  |  Index Prefetch: None
|  |  |  |  |  Isolation Level: Read Stability
|  |  |  |  |  Lock Intents
|  |  |  |  |  |  Table: Intent Exclusive
|  |  |  |  |  |  Row  : Update
|  |  |  |  |  Sargable Index Predicate(s)
|  |  |  |  |  |  #Predicates = 1
|  |  |  )
|  |  |  Update:  Table Name = DB2ADMIN.T1  ID = 2,10
|  |  |  |  Update Predicate(s)
|  |  |  |  |  #Predicates = 2
|  |  |  Update:  Table Name = DB2ADMIN.T2  ID = 2,11
|  |  |  |  Update Predicate(s)
|  |  |  |  |  #Predicates = 2
|  |  |  Insert Into Temp Table  ID = t1
|  |  |  |  #Columns = 4
|  |  End of Data Stream 3
|  |  Access Temp Table  ID = t1
|  |  |  #Columns = 4
|  |  |  Relation Scan
|  |  |  |  Prefetch: Eligible
|  |  Establish Row Position
|  |  |  Access Table Name = DB2ADMIN.T1  ID = 2,10
|  |  Delete:  Table Name = DB2ADMIN.T1  ID = 2,10
|  |  |  Delete Predicate(s)
|  |  |  |  #Predicates = 2
|  |  Establish Row Position
|  |  |  Access Table Name = DB2ADMIN.T2  ID = 2,11
|  |  Delete:  Table Name = DB2ADMIN.T2  ID = 2,11
|  |  |  Delete Predicate(s)
|  |  |  |  #Predicates = 2
|  |  Insert Into Temp Table  ID = t2
|  |  |  #Columns = 4
|  End of Data Stream 2
|  Access Temp Table  ID = t2
|  |  #Columns = 4
|  |  Relation Scan
|  |  |  Prefetch: Eligible
|  Insert:  Table Name = DB2ADMIN.T1  ID = 2,10
|  |  Insert Predicate(s)
|  |  |  #Predicates = 1
|  Insert Into Temp Table  ID = t3
|  |  #Columns = 4
End of Data Stream 1

Access Temp Table  ID = t3

|  #Columns = 4
|  Relation Scan
|  |  Prefetch: Eligible
Insert:  Table Name = DB2ADMIN.T2  ID = 2,11
|  Insert Predicate(s)
|  |  #Predicates = 1

End of section

Optimizer Plan:

                                                                                    INSERT 
                                                                                    (   2) 
                                                                                   /      \
                                                                               TBSCAN  Table:   
                                                                               (   3)  DB2ADMIN 
                                                                                 |     T2       
                                                                                TEMP  
                                                                               (   4) 
                                                                                 |    
                                                                               INSERT 
                                                                               (   5) 
                                                                              /      \
                                                                          TBSCAN  Table:   
                                                                          (   6)  DB2ADMIN 
                                                                            |     T1       
                                                                           TEMP  
                                                                          (   7) 
                                                                            |    
                                                                          DELETE 
                                                                          (   8) 
                                                                       /-/      \
                                                                 FETCH           Table:   
                                                                 (   9)          DB2ADMIN 
                                                              /-/      \         T2       
                                                        DELETE         Table:   
                                                        (  10)         DB2ADMIN 
                                                       /      \        T2       
                                                FETCH        Table:   
                                                (  11)       DB2ADMIN 
                                               /      \      T1       
                                           TBSCAN  Table:   
                                           (  12)  DB2ADMIN 
                                             |     T1       
                                            TEMP  
                                           (  13) 
                                             |    
                                           UPDATE 
                                           (  14) 
                                       /--/      \
                                 UPDATE           Table:   
                                 (  15)           DB2ADMIN 
                              /-/      \          T2       
                        UNION           Table:   
                        (  16)          DB2ADMIN 
                     /-/      \         T1       
               FETCH            FETCH  
               (  17)           (  19) 
              /      \            |    
       IXSCAN        Table:     IXSCAN 
       (  17)        DB2ADMIN   (  19) 
         |           T2           |    
 Index:                        Index:   
 SYSIBM                        DB2ADMIN 
 SQL041220112216530            PK       


Видно что на определенном этапе происходит удаление, а затем - вставка.
Я полагаю что так как удаление фактически еще не свершилось, то при апдейте значений ключей теми же значениями происходит конфликт.
А вообще-то поизучайте план запроса. Мне что-то влом сегодня думать.
20 дек 04, 11:28    [1192674]     Ответить | Цитировать Сообщить модератору
 Re: Срочно! Опция WITH ROW MOVEMENT в VIEW  [new]
kdima71
Member

Откуда:
Сообщений: 180
Привет всем!

Обход (workaround) проблемы, с которой я столкнулся, был успешно мною найден!!!
20 дек 04, 16:52    [1194290]     Ответить | Цитировать Сообщить модератору
 Re: Срочно! Опция WITH ROW MOVEMENT в VIEW  [new]
gardenman
Member

Откуда: С-Петербург
Сообщений: 2347
дык поделись)....
20 дек 04, 16:57    [1194306]     Ответить | Цитировать Сообщить модератору
 Re: Срочно! Опция WITH ROW MOVEMENT в VIEW  [new]
kdima71
Member

Откуда:
Сообщений: 180
Обход заключается в том, что я принудительно присваиваю NEW TRANSITION VARIABLE значение OLD TRANSITION VARIABLE, если новое значение для partition key не выходит за рамки допустимого значения (CHECK CONSTRAINT) для partition.

CREATE TRIGGER NODE_1_B_UR 
NO CASCADE BEFORE UPDATE OF NODE_ID ON NODE_1 
REFERENCING  OLD AS old  NEW AS new  
FOR EACH ROW MODE DB2SQL 
BEGIN ATOMIC
 if old.node_id = new.node_id then
  set new.node_id = old.node_id;
end if;
END@

P.S. "Мне что-то влом сегодня думать" - я думаю, что теперь я оставляю за собой право на подобные эпитеты в будущем!

С уважением, kdima71.
20 дек 04, 17:25    [1194454]     Ответить | Цитировать Сообщить модератору
 Re: Срочно! Опция WITH ROW MOVEMENT в VIEW  [new]
riman
Member

Откуда:
Сообщений: 2234
Information Center
An update to a view defined using the WITH ROW MOVEMENT
4
clause could cause a delete operation and an insert operation against
4
the underlying tables of the view. 4
For details, see the description of the CREATE VIEW statement.
21 дек 04, 07:55    [1195325]     Ответить | Цитировать Сообщить модератору
 Re: Срочно! Опция WITH ROW MOVEMENT в VIEW  [new]
riman
Member

Откуда:
Сообщений: 2234
Т.е. это именно то, что и упоминал gardenman:
gardenman
Видно что на определенном этапе происходит удаление, а затем - вставка.
Я полагаю что так как удаление фактически еще не свершилось, то при апдейте значений ключей теми же значениями происходит конфликт.
А вообще-то поизучайте план запроса. Мне что-то влом сегодня думать.
21 дек 04, 07:57    [1195328]     Ответить | Цитировать Сообщить модератору
Все форумы / IBM DB2, WebSphere, IMS, U2, etc Ответить