一般来说,多表视图在Form是不可以直接更新的。但是视图有其方便性(就是可以串出很多需要的栏位,不需要在Form的Post-query或者其他触发器中特别写代码赋值),
所以很多时候我们需要Form可以实现从视图直接更新数据。
总结了一下,令Form可以直接修改View的数据的办法有2个:
1 增加ON-DELETE/LOCK/UPDATE/INSERT语句,增加相应的代码即可。重要的核心流程维护Form必须用这种办法。
但是这种写法有一个地方很麻烦,就是要写大量的pkg代码支持更删改(虽然代码可以自动生成)。
所以,对于非核心流程维护数据的Form,要实现更改数据,有一个算是比较简单的办法:
适合那种只是要更新某些特定栏位的写法
a.增加3个触发器:ON-LOCK/UPDATE/INSERT,代码写null。
这时候,View的栏位都可以随意更改了,只是不会自动Update到数据库里面。
b当您修改的View的栏位要反应到数据库,在更改的时候,更新数据库栏位即可:
If Nvl(:XYG_CONTACT_TO_MDS.TRANSFER_WIP_FLAG,'N') <> 'Y' Then
--全协—先将User看到的栏位设为全协:
:XYG_CONTACT_TO_MDS.TRANSFER_WIP_FLAG := 'T';
--接着修改数据库。
Update XYG_QB_CONTRACT_LINES_ALL xl
Set TRANSFER_WIP_FLAG = 'T'
,OUTSIDE_PROCESS_FLAG = :XYG_CONTACT_TO_MDS.OUTSIDE_PROCESS_FLAG
,OUTSIDE_PROCESS_ID = :XYG_CONTACT_TO_MDS.OUTSIDE_PROCESS_ID
Where xl.Line_id=:XYG_CONTACT_TO_MDS.LINE_ID;
standard.commit;--只是后台commit到数据库,并不是Form的commit。
End If;
2 另外一种办法:如果是数据源是一张多表视图,但只更新数据到一张表,这种情况比较好处理。
a.先将数据块的Query表与 DML 目标表分别设置
b.然后将非DML 表的字段设置 Query only设置“是” 。这点是必须要注意的!重复:非DML表的字段(例如Rowid等)的QUERY_ONLY必须设为是,否则改的时候会报错误。
c.应的View的数据库必须将Item:TABLE ID的Primary Key属性设为Y才行。
经过严格的测试,发现这种应该是对单表—View的一个比较完善的非常简单的做法。
对于QUERY_ONLY=N(非基表栏位)的时候,这个记录的UPDATE属性设为Y,这时候也可以修改这个栏位!
当2个Form同时修改1笔记录的时候:
1个Form已经修改了,没保存;另外一个Form修改的时候,会不断自动尝试,点取消的时候会提示nowait锁有错
当另外一个Form已经修改了,保存了;另外一个Form试图修改的时候,会提示记录已经被别人更新了。