Prima di tutto è necessario sapere che SAP non è un database e OpenSQL è sempre tradotto nel dialetto SQL del database sottostante. Se il database sottostante non supporta WITH
o WITH RECURSIVE
e da quello che vedo dal seguente article non tutti i database lo fanno, quindi aggiungerlo a OpenSQL non avrebbe senso in molti casi non ci sarebbe nulla da mappare a .
Quindi la prima soluzione sarebbe come proposto, scrivendo una funzione/metodo/subroutine ricorsiva separata o se si desidera veramente utilizzare la funzionalità di database sottostante è possibile utilizzare l'interfaccia ADBC
. Se hai familiarità con JDBC
allora il concetto non dovrebbe essere nuovo per te. Se lo fai per scopi produttivi, dovresti assicurarti che ci sia una probabilità minima o nulla di una migrazione del database in futuro.
La soluzione con ADBC
che funziona per me su un sistema SAP con un database Oracle sottostante.
REPORT Z_ADBC_TEST.
CLASS lcl_test DEFINITION.
PUBLIC SECTION.
CLASS-METHODS:
main.
ENDCLASS.
CLASS lcl_test IMPLEMENTATION.
METHOD main.
DATA lo_sql_connection TYPE REF TO cl_sql_connection.
DATA lo_sql_statement TYPE REF TO cl_sql_statement.
DATA lo_sql_result_set TYPE REF TO cl_sql_result_set.
TYPES BEGIN OF lt_result_struct,
n TYPE i,
fact TYPE i,
END OF lt_result_struct.
DATA lt_result TYPE TABLE OF t_result_struct WITH DEFAULT KEY.
DATA lr_ref_to_data TYPE REF TO data.
FIELD-SYMBOLS <fs_result> LIKE LINE OF lt_result.
lo_sql_connection = cl_sql_connection=>get_connection().
lo_sql_statement = lo_sql_connection->create_statement().
GET REFERENCE OF lt_result INTO lr_ref_to_data.
lo_sql_result_set = lo_sql_statement->execute_query(
`WITH temp(n, fact) ` &&
`AS (SELECT 0,1 FROM dual UNION ALL ` &&
`SELECT n+1,(n+1)*fact FROM temp ` &&
`WHERE n < 9) ` &&
`SELECT * FROM temp`
).
lo_sql_result_set->set_param_table(lr_ref_to_data).
WHILE lo_sql_result_set->next_package() > 0.
LOOP AT lt_result ASSIGNING <fs_result>.
WRITE:/<fs_result>-n, <fs_result>-fact.
ENDLOOP.
ENDWHILE.
ENDMETHOD.
ENDCLASS.
END-OF-SELECTION.
lcl_test=>main().
Non vedo nessun altro modo di scoprire tutti i discendenti che selezionando ricorsivamente i bambini - esattamente quello a cui hai pensato. Laddove questo era un problema di prestazioni, in alcuni casi abbiamo introdotto una colonna 'master_id', contenente l'id di livello superiore dell'elemento e un indice secondario sul database per esso, – rplantiko
Non penso che sia troppo ampio, specialmente dato che il commento di @ rplantiko è quasi una risposta completa. –