将空值传递给 OData V2 Edm.Time 属性
Pass an empty value to an OData V2 Edm.Time property
我有一个变量类型 time 但有时这个变量没有任何东西。
当它是初始值时,它不应该是 "000000"
,我想要一个没有任何东西的空值(没有零)。让我用代码解释我的问题:
IF lwa_hora IS INITIAL.
CLEAR lwa_hora.
ls_entity-hora = lwa_hora. " Result: 000000 but I don't want any zero
ELSE.
ls_entity-hora = lwa_hora. " Result: 000000
ENDIF.
我试过 CLEAR
但没有任何反应。
我需要这个是因为在 JavaScript 前端客户端逻辑中,我需要 OData 属性 包含虚假值(例如 null
或空字符串 ""
).
但它始终具有值 "000000"
,即 而不是 空字符串。是否可以在后端做一些事情来“清除”变量?
abap (t
) 中的时间数据类型是值类型。它在内部实现为一个整数,计算自午夜以来的秒数。自午夜起 0 秒是一个有效值,因此它不能有空值。
但是,ABAP 允许您创建对任何值类型的引用:
hora TYPE REF TO t.
这意味着 hora
将是对 TYPE t
变量的引用。最初,此引用将是未绑定的,这在概念上与其他编程语言中的空引用非常相似。您可以通过以下方式检查:
IF ls_entity-hora IS BOUND.
...
IF ls_entity-hora IS NOT BOUND.
您可以使用 GET REFERENCE OF lwa_hora INTO ls_entity-hora
分配时间值。但是现在您有一个对现有变量的引用。改变lwa_hora
的值,ls_entity-hora
的值也会改变。那可能并不总是你想要的。所以最好在内存中新建一条数据供我们引用指向:
CREATE DATA ls_entity-hora.
现在 ls_entity-hora
不再是未绑定的(或者“空”,如果你想这样称呼它的话),它指向一个新的时间值 000000
。如果你想读取或更改这个引用指向的这个无名数据的值,那么你可以使用取消引用运算符 ->*
:
ls_entity-hora->* = lwa_hora.
如果您有意将引用设置为未绑定(或“将引用设置为空”),您可以通过清除引用来实现:
CLEAR ls_entity-hora.
顺便说一下:在过去十年中,用 d
和 t
类型的两个独立变量表示时间点已经过时了。当前针对这种情况的最佳做法是使用类型为 TIMESTAMP
(如果需要秒级精度)或 TIMESTAMPL
(如果需要微秒级精度)的单个变量。 00000000000000
的时间戳显然是非法值,因此可以用来表示时间点的缺失。这种类型通常还可以更轻松地与 SAPUI5 前端进行通信(就像您的情况一样),因为许多用于制作 oData 服务的技术都提供 Javascript Date
和 ABAP [=26= 之间的自动转换].
堆分配时间的另一种方法是在它旁边存储一个布尔值,指示它是否已设置:
TYPES:
BEGIN OF optional_time,
time TYPE t,
is_null TYPE abap_bool,
END OF optional_time.
DATA(no_time) = VALUE optional_time( is_null = abap_true ).
" Setting to null:
DATA(some_time) = no_time.
" Setting to some time:
some_time = VALUE #( time = '12:30' ).
IF some_time = no_time.
" ...
ENDIF.
这种事情在前端处理可能比在后端处理更好。
如果对应的 属性 可为空,则 SAP Gateway 在 OData 响应中将 ABAP Date/time 初始值序列化为 NULL。您需要确保此 属性 设置为 TRUE
,就像此示例中的
你也可以在运行时设置这个属性
TRY .
lo_action = model->get_entity_type( iv_entity_name = 'Z_REPORTType').
lo_property = lo_action->get_property( iv_property_name = 'Requested_Date').
lo_property->set_nullable( iv_nullable = abap_true ).
CATCH /iwbep/cx_mgw_busi_exception /iwbep/cx_mgw_med_exception /iwbep/cx_mgw_tech_exception INTO DATA(lo_exception).
ENDTRY.
我有一个变量类型 time 但有时这个变量没有任何东西。
当它是初始值时,它不应该是 "000000"
,我想要一个没有任何东西的空值(没有零)。让我用代码解释我的问题:
IF lwa_hora IS INITIAL.
CLEAR lwa_hora.
ls_entity-hora = lwa_hora. " Result: 000000 but I don't want any zero
ELSE.
ls_entity-hora = lwa_hora. " Result: 000000
ENDIF.
我试过 CLEAR
但没有任何反应。
我需要这个是因为在 JavaScript 前端客户端逻辑中,我需要 OData 属性 包含虚假值(例如 null
或空字符串 ""
).
但它始终具有值 "000000"
,即 而不是 空字符串。是否可以在后端做一些事情来“清除”变量?
abap (t
) 中的时间数据类型是值类型。它在内部实现为一个整数,计算自午夜以来的秒数。自午夜起 0 秒是一个有效值,因此它不能有空值。
但是,ABAP 允许您创建对任何值类型的引用:
hora TYPE REF TO t.
这意味着 hora
将是对 TYPE t
变量的引用。最初,此引用将是未绑定的,这在概念上与其他编程语言中的空引用非常相似。您可以通过以下方式检查:
IF ls_entity-hora IS BOUND.
...
IF ls_entity-hora IS NOT BOUND.
您可以使用 GET REFERENCE OF lwa_hora INTO ls_entity-hora
分配时间值。但是现在您有一个对现有变量的引用。改变lwa_hora
的值,ls_entity-hora
的值也会改变。那可能并不总是你想要的。所以最好在内存中新建一条数据供我们引用指向:
CREATE DATA ls_entity-hora.
现在 ls_entity-hora
不再是未绑定的(或者“空”,如果你想这样称呼它的话),它指向一个新的时间值 000000
。如果你想读取或更改这个引用指向的这个无名数据的值,那么你可以使用取消引用运算符 ->*
:
ls_entity-hora->* = lwa_hora.
如果您有意将引用设置为未绑定(或“将引用设置为空”),您可以通过清除引用来实现:
CLEAR ls_entity-hora.
顺便说一下:在过去十年中,用 d
和 t
类型的两个独立变量表示时间点已经过时了。当前针对这种情况的最佳做法是使用类型为 TIMESTAMP
(如果需要秒级精度)或 TIMESTAMPL
(如果需要微秒级精度)的单个变量。 00000000000000
的时间戳显然是非法值,因此可以用来表示时间点的缺失。这种类型通常还可以更轻松地与 SAPUI5 前端进行通信(就像您的情况一样),因为许多用于制作 oData 服务的技术都提供 Javascript Date
和 ABAP [=26= 之间的自动转换].
堆分配时间的另一种方法是在它旁边存储一个布尔值,指示它是否已设置:
TYPES:
BEGIN OF optional_time,
time TYPE t,
is_null TYPE abap_bool,
END OF optional_time.
DATA(no_time) = VALUE optional_time( is_null = abap_true ).
" Setting to null:
DATA(some_time) = no_time.
" Setting to some time:
some_time = VALUE #( time = '12:30' ).
IF some_time = no_time.
" ...
ENDIF.
这种事情在前端处理可能比在后端处理更好。
如果对应的 属性 可为空,则 SAP Gateway 在 OData 响应中将 ABAP Date/time 初始值序列化为 NULL。您需要确保此 属性 设置为 TRUE
,就像此示例中的
你也可以在运行时设置这个属性
TRY .
lo_action = model->get_entity_type( iv_entity_name = 'Z_REPORTType').
lo_property = lo_action->get_property( iv_property_name = 'Requested_Date').
lo_property->set_nullable( iv_nullable = abap_true ).
CATCH /iwbep/cx_mgw_busi_exception /iwbep/cx_mgw_med_exception /iwbep/cx_mgw_tech_exception INTO DATA(lo_exception).
ENDTRY.