Champs système dans ABAP Cloud : Alternatives à SY-*

Catégorie
ABAP Cloud
Publié
Auteur
Johannes

Les champs SY classiques (variables système) font partie intégrante du développement ABAP depuis des décennies. Dans ABAP Cloud, cependant, beaucoup de ces champs ne sont pas disponibles ou ne sont pas recommandés. Cet article présente toutes les alternatives importantes pour un code compatible Cloud.

Pourquoi les champs SY sont problématiques dans ABAP Cloud

Dans ABAP Cloud (Tier 1 / Level A), des règles strictes s’appliquent à l’utilisation des APIs :

  • Pas de dépendances implicites : Les champs SY sont des variables globales avec un état implicite
  • Pas de valeurs spécifiques à la session : Les applications Cloud sont sans état
  • Testabilité : Les champs SY sont difficiles à mocker
  • Découplage : Les APIs Released offrent des interfaces propres
┌─────────────────────────────────────────────────────────────┐
│ ABAP classique ABAP Cloud │
│ ─────────────────────────────────────────────────────────── │
│ SY-UNAME → CL_ABAP_CONTEXT_INFO │
│ SY-DATUM / SY-UZEIT → CL_ABAP_CONTEXT_INFO │
│ SY-LANGU → CL_ABAP_CONTEXT_INFO │
│ SY-SUBRC → Toujours disponible (exception !) │
│ SY-TABIX → Toujours disponible (exception !) │
│ SY-DBCNT → Toujours disponible (exception !) │
└─────────────────────────────────────────────────────────────┘

Aperçu : Champs SY et leurs alternatives

Champ SYDescriptionAlternative ABAP Cloud
SY-UNAMENom d’utilisateur techniqueCL_ABAP_CONTEXT_INFO=>GET_USER_TECHNICAL_NAME( )
SY-DATUMDate systèmeCL_ABAP_CONTEXT_INFO=>GET_SYSTEM_DATE( )
SY-UZEITHeure systèmeCL_ABAP_CONTEXT_INFO=>GET_SYSTEM_TIME( )
SY-ZONLOFuseau horaire utilisateurCL_ABAP_CONTEXT_INFO=>GET_USER_TIME_ZONE( )
SY-LANGULangue de connexionCL_ABAP_CONTEXT_INFO=>GET_USER_LANGUAGE_ABAP_FORMAT( )
SY-MANDTMandantCL_ABAP_CONTEXT_INFO=>GET_CLIENT( )
SY-SYSIDID systèmeCL_ABAP_CONTEXT_INFO=>GET_SYSTEM_ID( )
SY-SUBRCCode retourToujours disponible
SY-TABIXIndex de tableToujours disponible
SY-DBCNTNombre de lignes DBToujours disponible
SY-INDEXIndex de boucleToujours disponible
SY-TFILLLignes de tableLINES( itab ) recommandé
SY-MSGIDClasse de messageToujours disponible
SY-MSGNONuméro de messageToujours disponible
SY-MSGTYType de messageToujours disponible

La classe centrale : CL_ABAP_CONTEXT_INFO

La classe CL_ABAP_CONTEXT_INFO est l’API Released la plus importante pour les informations de contexte dans ABAP Cloud. Elle remplace la plupart des champs SY liés à l’utilisateur et au système.

Aperçu des méthodes

CLASS cl_abap_context_info DEFINITION.
PUBLIC SECTION.
CLASS-METHODS:
" Informations utilisateur
get_user_technical_name RETURNING VALUE(result) TYPE syuname,
get_user_alias RETURNING VALUE(result) TYPE string,
get_user_description RETURNING VALUE(result) TYPE string,
get_user_formatted_name RETURNING VALUE(result) TYPE string,
" Date et heure
get_system_date RETURNING VALUE(result) TYPE d,
get_system_time RETURNING VALUE(result) TYPE t,
get_system_timestamp RETURNING VALUE(result) TYPE utclong,
get_user_time_zone RETURNING VALUE(result) TYPE timezone,
" Langue
get_user_language_abap_format
RETURNING VALUE(result) TYPE sy-langu,
get_user_language_iso_format
RETURNING VALUE(result) TYPE laiso,
" Système
get_system_id RETURNING VALUE(result) TYPE sy-sysid,
get_client RETURNING VALUE(result) TYPE sy-mandt,
get_system_url RETURNING VALUE(result) TYPE string.
ENDCLASS.

Exemple pratique : Informations utilisateur et système

CLASS zcl_context_demo DEFINITION
PUBLIC FINAL
CREATE PUBLIC.
PUBLIC SECTION.
TYPES: BEGIN OF ty_user_context,
user_name TYPE string,
user_alias TYPE string,
system_date TYPE d,
system_time TYPE t,
timestamp TYPE utclong,
time_zone TYPE timezone,
language TYPE sy-langu,
system_id TYPE sy-sysid,
client TYPE sy-mandt,
END OF ty_user_context.
METHODS get_current_context
RETURNING VALUE(rs_context) TYPE ty_user_context.
ENDCLASS.
CLASS zcl_context_demo IMPLEMENTATION.
METHOD get_current_context.
" ABAP Cloud : API Released pour les informations de contexte
rs_context = VALUE #(
user_name = cl_abap_context_info=>get_user_technical_name( )
user_alias = cl_abap_context_info=>get_user_alias( )
system_date = cl_abap_context_info=>get_system_date( )
system_time = cl_abap_context_info=>get_system_time( )
timestamp = cl_abap_context_info=>get_system_timestamp( )
time_zone = cl_abap_context_info=>get_user_time_zone( )
language = cl_abap_context_info=>get_user_language_abap_format( )
system_id = cl_abap_context_info=>get_system_id( )
client = cl_abap_context_info=>get_client( )
).
ENDMETHOD.
ENDCLASS.

Catégorie 1 : Informations utilisateur

SY-UNAME → CL_ABAP_CONTEXT_INFO

" ABAP classique (non compatible Cloud)
DATA(lv_user) = sy-uname.
" ABAP Cloud
DATA(lv_user) = cl_abap_context_info=>get_user_technical_name( ).
" Alias utilisateur (ex. adresse email)
DATA(lv_alias) = cl_abap_context_info=>get_user_alias( ).
" Nom formaté (ex. "Jean Dupont")
DATA(lv_formatted) = cl_abap_context_info=>get_user_formatted_name( ).

Cas d’utilisation : Journalisation d’audit

METHOD log_user_action.
DATA(lv_user) = cl_abap_context_info=>get_user_technical_name( ).
DATA(lv_timestamp) = cl_abap_context_info=>get_system_timestamp( ).
INSERT INTO ztab_audit_log VALUES @(
VALUE #(
log_uuid = cl_system_uuid=>create_uuid_x16_static( )
user_name = lv_user
action = iv_action
entity_id = iv_entity_id
timestamp = lv_timestamp
)
).
ENDMETHOD.

Catégorie 2 : Date et heure

SY-DATUM, SY-UZEIT → CL_ABAP_CONTEXT_INFO

" ABAP classique
DATA(lv_date) = sy-datum.
DATA(lv_time) = sy-uzeit.
" ABAP Cloud : Date et heure
DATA(lv_date) = cl_abap_context_info=>get_system_date( ).
DATA(lv_time) = cl_abap_context_info=>get_system_time( ).
" ABAP Cloud : Horodatage UTC (recommandé pour la base de données)
DATA(lv_timestamp) = cl_abap_context_info=>get_system_timestamp( ).

Fuseau horaire et heure locale

" Obtenir le fuseau horaire utilisateur
DATA(lv_timezone) = cl_abap_context_info=>get_user_time_zone( ).
" Convertir l'horodatage en heure locale
DATA: lv_local_date TYPE d,
lv_local_time TYPE t.
CONVERT TIME STAMP cl_abap_context_info=>get_system_timestamp( )
TIME ZONE lv_timezone
INTO DATE lv_local_date TIME lv_local_time.

Cas d’utilisation : Définir la date de réservation

METHOD set_booking_dates.
" ABAP Cloud : Heure actuelle comme horodatage UTC
DATA(lv_now) = cl_abap_context_info=>get_system_timestamp( ).
" Utiliser dans une détermination RAP
MODIFY ENTITIES OF zi_booking IN LOCAL MODE
ENTITY Booking
UPDATE FIELDS ( CreatedAt LastChangedAt )
WITH VALUE #( FOR key IN keys
( %tky = key-%tky
CreatedAt = lv_now
LastChangedAt = lv_now ) ).
ENDMETHOD.

Catégorie 3 : Langue et localisation

SY-LANGU → CL_ABAP_CONTEXT_INFO

" ABAP classique
DATA(lv_langu) = sy-langu.
" ABAP Cloud : Format ABAP (D, E, F, ...)
DATA(lv_langu) = cl_abap_context_info=>get_user_language_abap_format( ).
" ABAP Cloud : Format ISO (DE, EN, FR, ...)
DATA(lv_langu_iso) = cl_abap_context_info=>get_user_language_iso_format( ).

Cas d’utilisation : Textes multilingues

METHOD get_status_text.
DATA(lv_langu) = cl_abap_context_info=>get_user_language_abap_format( ).
SELECT SINGLE text
FROM ztab_status_text
WHERE status = @iv_status
AND langu = @lv_langu
INTO @rv_text.
IF sy-subrc <> 0.
" Repli sur l'anglais
SELECT SINGLE text
FROM ztab_status_text
WHERE status = @iv_status
AND langu = 'E"
INTO @rv_text.
ENDIF.
ENDMETHOD.

Catégorie 4 : Informations système

SY-MANDT, SY-SYSID → CL_ABAP_CONTEXT_INFO

" ABAP classique
DATA(lv_client) = sy-mandt.
DATA(lv_sysid) = sy-sysid.
" ABAP Cloud
DATA(lv_client) = cl_abap_context_info=>get_client( ).
DATA(lv_sysid) = cl_abap_context_info=>get_system_id( ).
" URL système (pour les liens dans les emails, etc.)
DATA(lv_url) = cl_abap_context_info=>get_system_url( ).

Catégorie 5 : Champs SY toujours disponibles

Certains champs SY sont également disponibles dans ABAP Cloud car ils sont nécessaires pour les constructions de langage fondamentales :

SY-SUBRC (Code retour)

" SY-SUBRC est également disponible dans ABAP Cloud
SELECT SINGLE * FROM ztab_customer WHERE id = @lv_id INTO @ls_customer.
IF sy-subrc = 0.
" Client trouvé
ENDIF.
READ TABLE lt_customers WITH KEY id = lv_id INTO ls_customer.
IF sy-subrc <> 0.
" Non trouvé
ENDIF.

SY-TABIX (Index de table)

" SY-TABIX est également disponible dans ABAP Cloud
LOOP AT lt_items INTO DATA(ls_item).
ls_item-position = sy-tabix.
MODIFY lt_items FROM ls_item.
ENDLOOP.
" Alternative avec déclaration inline
LOOP AT lt_items INTO DATA(ls_item2) USING KEY primary_key.
DATA(lv_index) = sy-tabix.
ENDLOOP.

SY-DBCNT (Compteur base de données)

" SY-DBCNT est également disponible dans ABAP Cloud
DELETE FROM ztab_old_data WHERE created_at < @lv_cutoff_date.
DATA(lv_deleted_rows) = sy-dbcnt.
UPDATE ztab_status SET status = 'ARCHIVED' WHERE status = 'OLD'.
DATA(lv_updated_rows) = sy-dbcnt.

SY-INDEX (Index de boucle DO)

" SY-INDEX est également disponible dans ABAP Cloud
DO 5 TIMES.
APPEND VALUE #( attempt = sy-index ) TO lt_retries.
ENDDO.

Cas particulier : Champs de message

Les champs SY pour les messages (SY-MSGID, SY-MSGNO, SY-MSGTY, SY-MSGV1-4) sont disponibles dans ABAP Cloud, mais RAP utilise son propre système de messages :

" Dans RAP : Utiliser IF_ABAP_BEHV_MESSAGE
APPEND VALUE #(
%tky = ls_booking-%tky
%msg = new_message_with_text(
severity = if_abap_behv_message=>severity-error
text = |Statut invalide : { ls_booking-Status }| )
) TO reported-booking.
" Ou avec une classe de message
APPEND VALUE #(
%tky = ls_booking-%tky
%msg = new_message(
id = 'ZBOOKING_MSG"
number = '001"
severity = if_abap_behv_message=>severity-error
v1 = ls_booking-Status )
) TO reported-booking.

Génération d’UUID

Pour la génération d’UUID, il existe également une API Released :

" ABAP classique (fonctionne mais pas optimal)
DATA: lv_uuid TYPE sysuuid_x16.
TRY.
lv_uuid = cl_system_uuid=>create_uuid_x16_static( ).
CATCH cx_uuid_error.
ENDTRY.
" ABAP Cloud : Même API mais import explicite
DATA(lv_uuid) = cl_system_uuid=>create_uuid_x16_static( ).
" Pour le format string
DATA(lv_uuid_string) = cl_system_uuid=>create_uuid_c36_static( ).

Comparaison : Classique vs Cloud

TâcheABAP classiqueABAP Cloud
Nom d’utilisateursy-unamecl_abap_context_info=>get_user_technical_name( )
Date actuellesy-datumcl_abap_context_info=>get_system_date( )
Heure actuellesy-uzeitcl_abap_context_info=>get_system_time( )
Horodatage UTCGET TIME STAMPcl_abap_context_info=>get_system_timestamp( )
Languesy-langucl_abap_context_info=>get_user_language_abap_format( )
Fuseau horairesy-zonlocl_abap_context_info=>get_user_time_zone( )
Mandantsy-mandtcl_abap_context_info=>get_client( )
ID systèmesy-sysidcl_abap_context_info=>get_system_id( )
UUIDcl_system_uuid=>...cl_system_uuid=>create_uuid_x16_static( )

Bonnes pratiques

À faire

  • Utilisez CL_ABAP_CONTEXT_INFO pour toutes les infos utilisateur/système
  • Utilisez UTCLONG pour les horodatages en base de données
  • Stockez le fuseau horaire séparément si l’heure locale est pertinente
  • Utilisez SY-SUBRC et SY-TABIX - ils sont compatibles Cloud

À éviter

  • Pas de SY-UNAME pour le code Cloud (erreur ATC)
  • Pas de SY-DATUM/SY-UZEIT pour le code Cloud
  • Pas de champs SY dans les tests unitaires - utilisez l’injection de dépendances
  • Ne pas vérifier SY-BATCH - Le Cloud est toujours en ligne

Conclusion

La migration des champs SY vers les APIs ABAP Cloud est simple :

  1. Infos utilisateur/système : CL_ABAP_CONTEXT_INFO est le remplacement central
  2. Date/heure : Également CL_ABAP_CONTEXT_INFO avec UTCLONG pour la DB
  3. SY-SUBRC/TABIX/DBCNT : Restent disponibles - pas de migration nécessaire
  4. UUID : CL_SYSTEM_UUID est déjà une API Released

L’ATC vérifie automatiquement les champs SY non compatibles Cloud et indique les alternatives.

Pour la migration pratique du code existant, voir l’article suivant Migration des champs système - Migration pratique. Plus d’informations sur les APIs compatibles Cloud dans Concept de niveaux Clean Core.