[ABAP] OADate (Ole Automation Date) in Zeitstempel (timestamp) umrechnen

* https://stackoverflow.com/questions/43519005/how-to-convert-java-date-to-oadate-or-vice-versa
* https://msdn.microsoft.com/de-de/library/system.datetime.tooadate(v=vs.110).aspx

* Zeitstempel im OADate-Format
DATA: lv_oadate TYPE decfloat34 VALUE '43013.765983796296296000'. " 05.10.2017 18:23:01
*DATA: lv_oadate TYPE decfloat34 VALUE '42909.777881944444444000'. " 23.06.2017 18:40:09
*DATA: lv_oadate TYPE decfloat34 VALUE '42370.000717592592592593'. " 01.01.2016 00:01:02
* Basisdatum für OADate ist der 30.12.1899
DATA: lv_basedate TYPE d VALUE '18991230'.

DATA: lv_oadays TYPE i.
DATA: lv_oatime TYPE decfloat34.
DATA: lv_hour TYPE decfloat34.
DATA: lv_min TYPE decfloat34.
DATA: lv_sec TYPE decfloat34.

DATA: lv_d TYPE d.
DATA: lv_t TYPE t.
DATA: lv_datetime TYPE timestamp.

* Vorkommateil: Tage seit Basisdatum
lv_oadays = trunc( lv_oadate ).
* Nachkommateil: Tageszeit
lv_oatime = lv_oadate - CONV decfloat34( lv_oadays ).
* Nachkommateil: Stunden
lv_hour = lv_oatime * 24.
* Nachkommateil: Minuten
lv_min = ( lv_hour - trunc( lv_hour ) ) * 60.
* Nachkommateil: Sekunden
lv_sec = round( val = ( ( lv_min - trunc( lv_min ) ) * 60 ) dec = 0 ).

* Datum: Basisdatum + Tage des Vorkommateils
lv_d = lv_basedate + lv_oadays.
* Uhrzeit
lv_t = |{ CONV string( trunc( lv_hour ) ) WIDTH = 2 ALPHA = IN }{ CONV string( trunc( lv_min ) ) WIDTH = 2 ALPHA = IN }{ CONV string( trunc( lv_sec ) ) WIDTH = 2 ALPHA = IN }|.

* Datum und Uhrzeit in einem Zeitstempelobjekt zusammenfassen
CONVERT DATE lv_d TIME lv_t INTO TIME STAMP lv_datetime TIME ZONE 'UTC'.

WRITE: / '     OADate:', lv_oadate.
WRITE: / 'Zeitstempel:', lv_datetime TIME ZONE 'UTC'.

[ABAP] Zeitstempel (timestamp) in OADate (Ole Automation Date) umrechnen

* https://stackoverflow.com/questions/43519005/how-to-convert-java-date-to-oadate-or-vice-versa
* https://msdn.microsoft.com/de-de/library/system.datetime.tooadate(v=vs.110).aspx

* Zeitstempel mit Datum und Uhrzeit
*DATA: lv_datetime TYPE timestamp VALUE '20171005182301'. " 43013.765983796296296000
*DATA: lv_datetime TYPE timestamp VALUE '20170623184009'. " 42909.777881944444444000
DATA: lv_datetime TYPE timestamp VALUE '20160101000102'. " 42370.000717592592592593
* Basisdatum für OADate ist der 31.12.1899
DATA: lv_ts_base TYPE timestamp VALUE '18991231000000'.

DATA: lv_d TYPE d.
DATA: lv_t TYPE t.

DATA: lv_oadays TYPE i.

DATA: lv_hour TYPE decfloat34.
DATA: lv_min TYPE decfloat34.
DATA: lv_sec TYPE decfloat34.

DATA: lv_oadate TYPE decfloat34.

* Timestamp in Date und Time aufsplitten
CONVERT TIME STAMP lv_datetime TIME ZONE 'UTC' INTO DATE lv_d TIME lv_t.

* Zeitdifferenz zwischen Zeitstempel und Basisdatum in Sekunden
DATA(lv_diff_sec) = cl_abap_tstmp=>subtract( tstmp1 = lv_datetime
                                             tstmp2 = lv_ts_base ).

* Vorkommateil: Zeitdifferenz zwischen Zeitstempel und Basisdatum in Tagen
lv_oadays = lv_diff_sec / 86400.
* Nachkommateil: Stunden
lv_hour = CONV decfloat34( lv_t+0(2) ) / 24.
* Nachkommateil: Minuten
lv_min = CONV decfloat34( lv_t+2(2) ) / 1440.
* Nachkommateil: Sekunden
lv_sec = CONV decfloat34( lv_t+4(2) ) / 86400.

* OADate zusammenrechnen: Vorkommateil + Nachkommateil
lv_oadate = lv_oadays + lv_hour + lv_min + lv_sec.

WRITE: / 'Zeitstempel:', lv_datetime TIME ZONE 'UTC'.
WRITE: / '     OADate:', lv_oadate.

[ABAP] UTC-Zeit (TIMESTAMP) in Datum (d) und Uhrzeit (t) splitten

DATA: lv_date TYPE d.
DATA: lv_time TYPE t.
DATA: lv_utc TYPE timestamp.

GET TIME STAMP FIELD lv_utc.

* Zeitzohne bleibt UTC, Timestamp wird also ohne Umrechnung der Zone gesplittet
CONVERT TIME STAMP lv_utc TIME ZONE 'UTC' INTO DATE lv_date TIME lv_time.

WRITE: / |UTC: { lv_utc TIMESTAMP = USER }|.
WRITE: / |UTC-Datum: { lv_date DATE = USER }|.
WRITE: / |UTC-Zeit: { lv_time TIME = USER }|.

[ABAP] Timestamp in Systemdatum (d) und Systemzeit (t) umrechnen

DATA: lv_ts TYPE timestamp.
DATA: lv_date TYPE d.
DATA: lv_time TYPE t.

* Timestamp nach Systemdatum (d) und Systemzeit (t)
GET TIME STAMP FIELD lv_ts.

* TIME ZONE sy-zonlo - lokale Timezone
* TIME ZONE 'UTC'    - UTC-Zeit
CONVERT TIME STAMP lv_ts TIME ZONE sy-zonlo INTO DATE lv_date TIME lv_time.

WRITE: / lv_date, lv_time.

* Systemdatum (d) und Systemzeit (t) nach Timestamp
lv_date = sy-datum.
lv_time = sy-uzeit.

* TIME ZONE sy-zonlo - lokale Timezone
* TIME ZONE 'UTC'    - UTC-Zeit
CONVERT DATE lv_date TIME lv_time INTO TIME STAMP lv_ts TIME ZONE sy-zonlo.

WRITE: / lv_ts TIME ZONE sy-zonlo.