目录
一、创建CDS+BOPF暴露给Fiori
1.1 创建CDS VIEW抽取层VIEW
1.2 创建CDS 转换层VIEW( transfer)
1.3 创建CDS 输出层 VIEW(Consumption)
二、BOPF相关开发测试
2.1 BOPF里面ACTION的实现
2.2 BOPF里面Validations的实现
三、Fiori测试
BOPF是业务对象处理框架(Business Object Processing Framework,以下简称BOPF),SAP有很多标准的BOPF,本例主要是使用CDS创建自开发的BOPF
整体的CDS结构一般做三层,类似于BW,分别是抽取层(View),转换层(Basic),输出层(Consumption),分别对Basis层和Consumption层搭建BOPF框架,Consumption层暴露给Fiori使用
【前期准备】
@AbapCatalog.sqlViewName: 'ZDDL_P_FLY'
@AbapCatalog.compiler.compareFilter: true
@AbapCatalog.preserveKey: true
@AccessControl.authorizationCheck: #NOT_REQUIRED
@EndUserText.label: '航班信息抽取层 basis'
define view ZZ_P_FLY as select from spfli {
key spfli.carrid ,
key spfli.connid ,
spfli.countryfr ,
spfli.cityfrom ,
spfli.airpfrom ,
spfli.countryto ,
spfli.cityto ,
spfli.airpto ,
spfli.fltime ,
spfli.deptime ,
spfli.arrtime ,
spfli.distance ,
spfli.distid ,
spfli.fltype ,
spfli.period
}
CDS转换层也是主要的逻辑处理部分,抽取层基本不对数据处理,为转换层搭建BOPF框架,激活之后就会产生对应的BOPF(T-code:BOBX) ,之后对BOPF这块详解
@AbapCatalog.sqlViewName: 'ZDDL_I_FLY'
@AbapCatalog.compiler.compareFilter: true
@AbapCatalog.preserveKey: true
@AccessControl.authorizationCheck: #NOT_REQUIRED
@EndUserText.label: '航班信息转换层 transfer'
@ObjectModel:{
modelCategory: #BUSINESS_OBJECT,
compositionRoot: true,
representativeKey: ['carrid','connid'],
semanticKey: ['carrid','connid'],
transactionalProcessingEnabled: true,
writeActivePersistence: 'SPFLI',
// enable crud
createEnabled: true,
updateEnabled: true,
deleteEnabled: true
}
define view ZZ_I_FLY as select from ZZ_P_FLY {
key carrid ,
key connid ,
countryfr ,
cityfrom ,
airpfrom ,
countryto ,
cityto
}
CDS 输出层 VIEW指消费层,同样要搭建BOPF框架,但不会产生BOPF对象,这一层主要是把CDS发布成ODATA服务暴露给Fiori调用
@AbapCatalog.sqlViewName: 'ZDDL_C_FLY'
@AbapCatalog.compiler.compareFilter: true
@AbapCatalog.preserveKey: true
@AccessControl.authorizationCheck: #NOT_REQUIRED
@EndUserText.label: '航班信息输出层 consumption'
@ObjectModel:{
semanticKey: ['carrid','connid'],
transactionalProcessingDelegated: true,
// enable crud
createEnabled: true,
updateEnabled: true,
deleteEnabled: true
}
@UI.headerInfo: {typeName: 'fly', typeNamePlural: 'fly', title: {value: 'carrid'}}
@OData.publish: true
define view ZZ_C_FLY as select from ZZ_I_FLY {
@UI: {
lineItem: [{ type: #FOR_ACTION, position: 1,
dataAction: 'BOPF:SET_CITY',
label: 'Set CITY_TO' }],
identification: [{type: #FOR_ACTION,
position: 1,
dataAction: 'BOPF:SET_CITY',
label: 'Set CITY_TO' }]
}
key carrid ,
@UI: {
lineItem: [{ position: 20}],
identification: [{position: 20}],
fieldGroup: [{qualifier: 'Basic'}]
}
key connid ,
@UI: {
lineItem: [{ position: 30}],
identification: [{position: 30}],
fieldGroup: [{qualifier: 'Basic'}]
}
countryfr ,
@UI: {
lineItem: [{ position: 40}],
identification: [{position: 40}],
fieldGroup: [{qualifier: 'Basic'}]
}
cityfrom ,
@UI: {
lineItem: [{ position: 50}],
identification: [{position: 50}],
fieldGroup: [{qualifier: 'Imsg'}]
}
airpfrom ,
@UI: {
lineItem: [{ position: 60}],
identification: [{position: 60}],
fieldGroup: [{qualifier: 'Imsg'}]
}
countryto ,
@UI: {
lineItem: [{ position: 70}],
identification: [{position: 70}],
fieldGroup: [{qualifier: 'Imsg'}]
}
//@ObjectModel.readOnly: true
cityto
}
以上CDS+BOPF的框架就完成了,接下来是找转换层生成的BOPF(TCODE:BOBF/BOBX)
method /BOBF/IF_FRW_ACTION~EXECUTE.
data(lt_DATA) = value ZTZIFLY( ).
DATA: ls_msg TYPE symsg,
lv_dummy_msg TYPE string.
"Read UI clicked sale order
io_read->retrieve(
exporting
iv_node = is_ctx-node_key " BO Node Name
it_key = it_key " BO Key
importing
et_data = lt_DATA ). " Data Return Structure
"Assuming single instance for a action
LOOP AT lt_DATA assigning field-symbol().
-CITYTO = 'BOPFCIT'.
"Now update the BO instance
io_modify->update(
exporting
iv_node = is_ctx-node_key " Node
iv_key = -key " Key
iv_root_key = -root_key " NodeID
is_data = ref #( -node_data ) " Data
it_changed_fields = value #(
( ZIF_Z_I_FLY_C=>sc_node_attribute-ZZ_I_FLY-CITYTO ) )
).
ENDLOOP.
IF -CARRID = 'AA'.
* MESSAGE S000(zyk_cm_bus_plan) WITH 'THIS IS ANOTHER!' INTO lv_dummy_msg.
* MOVE-CORRESPONDING sy TO ls_msg.
* eo_message->add_message(
* EXPORTING
* is_msg = ls_msg " Structure of Message Variables
* iv_node = is_ctx-node_key " Node Name
* iv_key = -key " Key
** iv_lifetime = /bobf/cm_frw=>co_lifetime_state
* ).
* APPEND VALUE #( key = -key ) TO et_failed_key .
ENDIF.
IF eo_message IS BOUND .
eo_message = /bobf/cl_frw_factory=>GET_MESSAGE( ) .
ENDIF.
endmethod.
使用(tcode:BOBT)测试ACTION
Validations和action类似需要创建实施类,Trigger Action勾选Action就会触发校验