SAP ABAP实用技巧介绍系列之 关于View framework处理Before save event的讨论
作者:互联网
Created by Jerry Wang, last modified on Jul 17, 2014
点击New Entries后,
[外链图片转存失败(img-0Co1I8jG-1562209890702)(https://user-images.githubusercontent.com/5669954/27263153-2feebfbc-5464-11e7-9fde-fddcec97a122.png)]
输入会触发validation 逻辑的entry:
Maintenance view生成的function module 会被call到,
[外链图片转存失败(img-oChB4GCP-1562209890703)(https://user-images.githubusercontent.com/5669954/27263156-2fffdfb8-5464-11e7-9fe1-9c6ca54576c0.png)]
在里面会call 到screen 0001的PAI Module:
<status>-upd_flag会决定是否真正实行database update。如果其值为false,end user点击Save button后,将不会触发真正的database 更新,在UI上会得到Data already saved的信息。
F8之后,会发现<STATUS>-UPD_FLAG已经在某处被clear了,在CHECK_UPD重新判断是否该填充: 判断的逻辑是TOTAL internal table里是否有action不为space的entry。 如下图,row 3即为在UI上通过点击New Entries后输入的entry,action为N ( New ) 因此此种情况下update flag置为X: 然后进入SAVE相应的逻辑:
[外链图片转存失败(img-4ag8eF0p-1562209890705)(https://user-images.githubusercontent.com/5669954/27263161-300ae3ea-5464-11e7-9ad1-286bab9eaeb6.png)]
这里能发现如果status update flag为false,则直接在UI上显示Data already saved的提示信息:[外链图片转存失败(img-v16b1coT-1562209890705)(https://user-images.githubusercontent.com/5669954/27263162-30166440-5464-11e7-8c0c-c7fb5aba688b.png)]
这里能call 到developer在before save event上实现的callback:
[外链图片转存失败(img-1aNJBvzR-1562209890705)(https://user-images.githubusercontent.com/5669954/27263163-301a0186-5464-11e7-9bce-781cec75c7d7.png)]
Table参数EXTRACT包含了New Entries screen上Table control里的值( 包含end user输入的entry和其他空行)
空行一共20条,是在下面这个代码里生成的:
通过实验,只要将新建entry的action由N改为L,即能实现即使UI报错之后,该entry仍然处于可编辑状态的效果:
[外链图片转存失败(img-gAWZBjkj-1562209890706)(https://user-images.githubusercontent.com/5669954/27263135-2fa82124-5464-11e7-99df-47771a231a31.png)]
效果如下:
此时将Product type改为03,期望的效果是 03 - CRMM_PR_TAX能够成功保存:
此时第二次进入<status>-update的判断逻辑:
total internal table里的entry,蓝色的是直接invalid的输入,红色是纠正后的输入, 因此我们发现我们在UI上将product type由02改为03之后,之前02 对应的entry仍然存储在total里没有被框架删除,因此需要我们手动在BEFORE SAVE的module里完成这个删除动作。
因此在before save的处理逻辑里将invalid entry手动删除:
之所以用flag si_pend_delete控制,是为了避免在第一次新建entry时,错误地那些action = N的entry也删掉。
然后,有时候会发现view framework并不能将用户修改了invalid entry之后第二次重新输入的值写入到total table里,例如user 将product type修正为05之后,点save button: 从callstack能清楚发现开始执行save 操作:
[外链图片转存失败(img-EgKcbAPQ-1562209890710)(https://user-images.githubusercontent.com/5669954/27263140-2fbf9ebc-5464-11e7-80b9-9b03e72a6204.png)]
然而,在before save的callback里,并不包含最新输入的05 entry:
相反,这个05 entry包含在extract internal table里,因此需要developer在before save subroutine里手动做一个merge:
merge代码如下:
如果直接在第一次before save callback执行体内删除invalid entry( line 50), 会导致即使第二次纠正了invalid entry(例如product type从02改正为03)后点击save button,由于<status>-update判断为space,此时将不会有database update,而是直接报"Data already saved"的信息。
在同时输入多行且部分行valid,部分行不valid时,上述solution将很难正确处理所有可能的情况。
例如:
此时row 3应该删除,因为其不valid,但是 row 5和 row 7应该保留,因为是新输入的entry:
目前的实现这种粗暴的删除所有action为N的做法不能区分出invalid record和新输入的record
前两行检查通过,此时我将第三行entry改成 04-401-CRMM_PR_TAX:
然后选中第二行,点delete button:
然后再点save:
然而最后存储到数据库的结果如下:
标签:实用技巧,githubusercontent,img,framework,user,entry,save,5464 来源: https://blog.csdn.net/i042416/article/details/94601046