ALV Reports
ABAP Developmentadvanced

ALV Reports Part 9: Editable ALV with CL_GUI_ALV_GRID

Key takeaway

Build an editable grid: edit flags in the field catalog, register edit event, check changed data, the DATA CHANGED event with ER DATA CHANGED for validation, and saving changes safely with locks and a single COMMIT.

Explanation

📌 KEY POINTS
✅ Editable ALV uses CL_GUI_ALV_GRID: set edit = 'X' in the field catalog (or layout edit = 'X' for all columns).

✅ go_grid->register_edit_event( cl_gui_alv_grid=>mc_evt_modified ) and check_changed_data( ) move user input into the internal table.

✅ Validate in the DATA_CHANGED event: er_data_changed->add_protocol_entry( ) shows errors per cell.

⚠️ Editing a table directly is not enough — lock (ENQUEUE), validate, save via the correct API/update and COMMIT once.

━━━━━━━━━━━━━━━━━━━━
▶ WHERE WE ARE

Parts 3 and 8 displayed and processed data. Now users change values directly in the grid — often used for mass maintenance of custom tables or planning values.

━━━━━━━━━━━━━━━━━━━━
▶ 1. WHICH ALV CAN BE EDITED

  • CL_GUI_ALV_GRID — yes, standard way.
  • REUSE_ALV_GRID_DISPLAY — edit via fieldcat edit = 'X' works in a limited way (changes only after callbacks); avoid for serious editing.
  • CL_SALV_TABLE — not intended for editing.

━━━━━━━━━━━━━━━━━━━━
▶ 2. MAKING COLUMNS EDITABLE

  • Field catalog: edit = 'X' on editable columns; keep key columns read-only.
  • Optional per-cell control: a style table (lvc_t_styl) with cl_gui_alv_grid=>mc_style_disabled for rows that must not change; layout stylefname.
  • Checkbox columns: checkbox = 'X' plus edit = 'X'.

━━━━━━━━━━━━━━━━━━━━
▶ 3. GETTING THE DATA BACK

  • register_edit_event( mc_evt_modified ) — raises DATA_CHANGED when the user leaves a changed cell; mc_evt_enter reacts only on Enter.
  • Before saving: go_grid->check_changed_data( ) transfers pending input and triggers validation.\n\n━━━━━━━━━━━━━━━━━━━━\n▶ 4. VALIDATION WITH DATA_CHANGED\nHandler FOR EVENT data_changed OF cl_gui_alv_grid IMPORTING er_data_changed.
  • Loop at er_data_changed->mt_good_cells (row_id, fieldname, value).
  • Wrong value → er_data_changed->add_protocol_entry( i_msgid … i_fieldname … i_row_id … ). The ALV shows an error log and marks the cell.

━━━━━━━━━━━━━━━━━━━━
▶ 5. SAVING SAFELY

  • Lock the entries (ENQUEUE_EZ…) when entering edit mode, or at least before saving.
  • Compare with the original data to find changed rows only.
  • Update the database (for custom tables: MODIFY ztab FROM TABLE; for SAP data: BAPI), then COMMIT WORK once; handle errors with ROLLBACK.
  • Record who changed what if the data is business-relevant (change documents or a log table).

━━━━━━━━━━━━━━━━━━━━
▶ STEP BY STEP

  1. Create custom table ZFLIGHT_PRICE (carrid, connid, fldate, price, currency) or use a copy.
  2. Run the code example: edit prices, enter a negative value and see the error protocol.
  3. Save and check the table in SE16N.

✅ CHECKPOINT: you can build an editable ALV that validates input and saves it safely.

Code example

ABAP Code
REPORT zalv_editable. DATA: gt_out       TYPE STANDARD TABLE OF zflight_price,   " custom table copy      gt_orig      TYPE STANDARD TABLE OF zflight_price,      go_container TYPE REF TO cl_gui_custom_container,      go_grid      TYPE REF TO cl_gui_alv_grid,      gt_fcat      TYPE lvc_t_fcat,      gs_layout    TYPE lvc_s_layo,      gv_ok_code   TYPE sy-ucomm,      gv_error     TYPE abap_bool. * ===== Event handler for validation =====CLASS lcl_handler DEFINITION.  PUBLIC SECTION.    METHODS on_data_changed FOR EVENT data_changed OF cl_gui_alv_grid      IMPORTING er_data_changed.ENDCLASS. CLASS lcl_handler IMPLEMENTATION.  METHOD on_data_changed.    DATA: ls_cell  TYPE lvc_s_modi,          lv_price TYPE s_price.    gv_error = abap_false.    LOOP AT er_data_changed->mt_good_cells INTO ls_cell WHERE fieldname = 'PRICE'.      er_data_changed->get_cell_value( EXPORTING i_row_id = ls_cell-row_id                                                 i_fieldname = 'PRICE'                                       IMPORTING e_value = lv_price ).      IF lv_price <= 0.        er_data_changed->add_protocol_entry(          i_msgid = '0K' i_msgty = 'E' i_msgno = '000'          i_msgv1 = 'Price must be greater than zero'          i_fieldname = 'PRICE' i_row_id = ls_cell-row_id ).        gv_error = abap_true.      ENDIF.    ENDLOOP.  ENDMETHOD.ENDCLASS. DATA go_handler TYPE REF TO lcl_handler. START-OF-SELECTION.  SELECT * FROM zflight_price INTO TABLE gt_out WHERE carrid = 'LH'.  gt_orig = gt_out.                                    " keep original for comparison  CALL SCREEN 100.                                     " custom control CC_ALV, status with SAVE/BACK MODULE status_0100 OUTPUT.  SET PF-STATUS 'STATUS_100'.  IF go_grid IS INITIAL.    CREATE OBJECT go_container EXPORTING container_name = 'CC_ALV'.    CREATE OBJECT go_grid EXPORTING i_parent = go_container.     CALL FUNCTION 'LVC_FIELDCATALOG_MERGE'      EXPORTING i_structure_name = 'ZFLIGHT_PRICE'      CHANGING  ct_fieldcat      = gt_fcat.    PERFORM set_edit_columns.     CREATE OBJECT go_handler.    SET HANDLER go_handler->on_data_changed FOR go_grid.    go_grid->register_edit_event( cl_gui_alv_grid=>mc_evt_modified ).  " react on cell change     gs_layout-cwidth_opt = 'X'.    go_grid->set_table_for_first_display( EXPORTING is_layout = gs_layout                                          CHANGING it_outtab = gt_out it_fieldcatalog = gt_fcat ).  ENDIF.ENDMODULE. MODULE user_command_0100 INPUT.  CASE gv_ok_code.    WHEN 'SAVE'.      go_grid->check_changed_data( ).                  " pull pending input + validate      IF gv_error = abap_true.        MESSAGE 'Correct the errors before saving' TYPE 'S' DISPLAY LIKE 'E'.      ELSE.        PERFORM save_changes.      ENDIF.    WHEN 'BACK' OR 'EXIT'.      LEAVE TO SCREEN 0.  ENDCASE.  CLEAR gv_ok_code.ENDMODULE. FORM set_edit_columns.  FIELD-SYMBOLS <ls_fcat> TYPE lvc_s_fcat.  LOOP AT gt_fcat ASSIGNING <ls_fcat>.    CASE <ls_fcat>-fieldname.      WHEN 'PRICE'.        <ls_fcat>-edit = 'X'.                          " only price is editable      WHEN 'MANDT'.        <ls_fcat>-tech = 'X'.    ENDCASE.  ENDLOOP.ENDFORM. FORM save_changes.  DATA lt_changed TYPE STANDARD TABLE OF zflight_price.  DATA ls_out TYPE zflight_price.  LOOP AT gt_out INTO ls_out.    READ TABLE gt_orig TRANSPORTING NO FIELDS WITH KEY table_line = ls_out.  " whole row identical = unchanged    IF sy-subrc <> 0.      APPEND ls_out TO lt_changed.    ENDIF.  ENDLOOP.  IF lt_changed IS INITIAL.    MESSAGE 'No changes' TYPE 'S'.    RETURN.  ENDIF.* Real code: ENQUEUE lock object for the entries before this point  MODIFY zflight_price FROM TABLE lt_changed.  IF sy-subrc = 0.    COMMIT WORK.    gt_orig = gt_out.    MESSAGE 'Changes saved' TYPE 'S'.  ELSE.    ROLLBACK WORK.    MESSAGE 'Save failed' TYPE 'E'.  ENDIF.ENDFORM.

Real project scenario

A pricing team maintained 3,000 freight rates in a custom table through SM30, one screen at a time. An editable ALV allowed mass changes with Excel-like editing and immediate validation of negative or zero rates.
Two planners once changed the same rates at the same time; the second save overwrote the first. The team added an ENQUEUE on the carrier range when entering edit mode and a change log table with user and timestamp, which satisfied the auditors as well.

Common mistakes

  • Saving without check_changed_data (last edited cell is lost).
  • Not registering the edit event, so DATA_CHANGED never fires.
  • Key columns editable.
  • No locks — concurrent users overwrite each other.
  • Writing SAP standard tables directly instead of using BAPIs.

Best practices

  • Use CL_GUI_ALV_GRID for editing.
  • Validate in DATA_CHANGED with protocol entries.
  • Save only changed rows, with locks and one COMMIT.
  • Keep keys read-only; use styles for row-level protection.
  • Log business-relevant changes.

Interview angle

Questions: "How do you make an ALV editable?", "How do you validate user input in an editable ALV?", "What does check_changed_data do?"
Strong answer: CL_GUI_ALV_GRID with edit = 'X' in the field catalog, register_edit_event (mc_evt_modified/enter), DATA_CHANGED handler with er_data_changed (mt_good_cells, get_cell_value, add_protocol_entry); check_changed_data transfers pending input before save; lock, save changed rows, COMMIT once; SALV is not for editing.

Practice this lesson

Quick check

1. How should an editable ALV decide what to save?

2. Editable cells require:

3. To make cells editable in ALV you should use…

Interview questions

1. Business asks for editable ALV that posts to backend. How do you design it?

Answer it in your own words first, then compare.

2. An editable ALV for approvals updates every displayed row on save, even unchanged ones, and occasionally overwrites another user's change. How do you fix the save logic?

Answer it in your own words first, then compare.

Practice more with Interview AI →

Reference-verified: the steps are checked against official SAP documentation and tutorials, and object and field names in the sample code are checked for consistency. The code has not been compiled or run on an SAP system by ERPClimb. Syntax marked release-dependent varies by SAP release, so check it in your own system.

More lessons in this topic

Interview questions on this topic

Related SAP topics