ABAP Objects: Events, Friends & Design Patterns

sender is an implicit parameter referencing the raising object.

22.1 Events

sender is an implicit parameter referencing the raising object. Static events (CLASS-EVENTS) are registered without FOR.

CLASS lcl_order DEFINITION.
  PUBLIC SECTION.
    EVENTS status_changed EXPORTING VALUE(ev_new_status) TYPE char1.
    METHODS set_status IMPORTING iv_status TYPE char1.
ENDCLASS.
CLASS lcl_order IMPLEMENTATION.
  METHOD set_status.
    RAISE EVENT status_changed EXPORTING ev_new_status = iv_status.
  ENDMETHOD.
ENDCLASS.

CLASS lcl_logger DEFINITION.
  PUBLIC SECTION.
    METHODS on_status_changed FOR EVENT status_changed OF lcl_order
      IMPORTING ev_new_status sender.
ENDCLASS.
CLASS lcl_logger IMPLEMENTATION.
  METHOD on_status_changed.
    WRITE: / 'Status changed to', ev_new_status.
  ENDMETHOD.
ENDCLASS.

START-OF-SELECTION.
  DATA(lo_order)  = NEW lcl_order( ).
  DATA(lo_logger) = NEW lcl_logger( ).
  SET HANDLER lo_logger->on_status_changed FOR lo_order.     " or FOR ALL INSTANCES
  lo_order->set_status( 'C' ).
  SET HANDLER lo_logger->on_status_changed FOR lo_order ACTIVATION abap_false.  " deregister

22.2 Friends

lcl_auditor (and its subclasses) may access private and protected components of lcl_vault. Friendship is one-directional and not inherited by the granting class's subclasses. Commonly used to let test classes access internals of a global class: in the test include write CLASS zcl_order_service DEFINITION LOCAL FRIENDS ltc_order_service.

CLASS lcl_vault DEFINITION FRIENDS lcl_auditor.
  PRIVATE SECTION.
    DATA mv_secret TYPE string VALUE `42`.
ENDCLASS.

22.3 Singleton

(A singleton lives per internal session — i.e. per program execution, not system-wide.)

CLASS zcl_config DEFINITION PUBLIC FINAL CREATE PRIVATE.
  PUBLIC SECTION.
    CLASS-METHODS get_instance RETURNING VALUE(ro_instance) TYPE REF TO zcl_config.
    METHODS get_value IMPORTING iv_key TYPE string RETURNING VALUE(rv_value) TYPE string.
  PRIVATE SECTION.
    CLASS-DATA go_instance TYPE REF TO zcl_config.
    DATA mt_values TYPE HASHED TABLE OF zconfig WITH UNIQUE KEY param.
    METHODS constructor.
ENDCLASS.

CLASS zcl_config IMPLEMENTATION.
  METHOD get_instance.
    IF go_instance IS NOT BOUND.
      go_instance = NEW #( ).
    ENDIF.
    ro_instance = go_instance.
  ENDMETHOD.
  METHOD constructor.
    SELECT * FROM zconfig INTO TABLE @mt_values.
  ENDMETHOD.
  METHOD get_value.
    rv_value = VALUE #( mt_values[ param = iv_key ]-value OPTIONAL ).
  ENDMETHOD.
ENDCLASS.

22.4 Factory

Other patterns used in ABAP: strategy (interface + injected implementation), observer (events), decorator, MVC (Web Dynpro / dialog), dependency injection for testability (constructor injection or injector friend classes, §37), builder, template method (abstract class with hook methods).

INTERFACE zif_payment.
  METHODS pay IMPORTING iv_amount TYPE p RETURNING VALUE(rv_ok) TYPE abap_bool.
ENDINTERFACE.

CLASS zcl_payment_factory DEFINITION PUBLIC FINAL CREATE PRIVATE.
  PUBLIC SECTION.
    CLASS-METHODS create
      IMPORTING iv_method     TYPE string
      RETURNING VALUE(ro_pay) TYPE REF TO zif_payment
      RAISING   zcx_unknown_method.
ENDCLASS.

CLASS zcl_payment_factory IMPLEMENTATION.
  METHOD create.
    ro_pay = SWITCH #( iv_method
      WHEN `CARD`    THEN NEW zcl_card_payment( )
      WHEN `INVOICE` THEN NEW zcl_invoice_payment( )
      ELSE THROW zcx_unknown_method( ) ).
  ENDMETHOD.
ENDCLASS.

22.5 Persistent object references and shared objects (brief)

Shared objects (SHMA, area classes CL_SHM_AREA) keep objects in shared memory across sessions for read-mostly caches.

Object Services (persistent classes, CL_OS_*) are legacy ORM; RAP replaced them in modern development.