ABAP OO + MVC + ALV

Getting started ... Alles für einen gelungenen Start.
4 Beiträge • Seite 1 von 1
4 Beiträge Seite 1 von 1

ABAP OO + MVC + ALV

Beitrag von TimTo (ForumUser / 5 / 4 / 0 ) »
Hallo!

ich frage mich momentan wie man das MVC Pattern in ABAP OO umsetzt falls man mit editierbaren ALVs und einem Report arbeitet.

Aktuell besteht mein Programm aus den folgenden Elementen:

- Report
- Presenter (globale Klasse)
- Controller (globale Klasse)
- Persistence (globale Klasse)

Report
Auf einem Selektionsbild nehme ich Eingaben entgegen anhand derer später Daten (editierbar) in einem ALV angezeigt werden sollen.
Im PAI-Modul reagiere ich auf Userinteraktionen (z.B. Button-Klicks oder Änderungen von Daten im ALV)

Presenter
Beinhaltet Attribute und Methoden die direkt mit der ALV-Anzeige zu tun haben (Ausgabetabelle, ref auf ALV & Container, Methoden für ALV-Refresh...)

Controller
Dient als Vermittler zwischen den anderen Klassen. Ich instanziiere z.B. in meinem Report ein Controller-Objekt, welches wiederum die Instanziierung der Presenter- und Persistence-Klasse auslöst.
Im PAI-Modul des Reports rufe ich Methoden des Controllers auf die dann die entsprechenden Methoden der Presenter-/Persistence-Klasse aufrufen.

Persistence
Hier findet die gesamte Interaktion mit der Datenbank statt.
Beim START-OF-SELECTION Ereignis des Reports rufe ich z.B. eine Methode des Controllers auf, die wiederum eine Methode der Persistence-Klasse aufruft, welche die entsprechenden Daten von der DB lädt und diese in einer internen Tabelle speichert (ich reiche die Eingaben im Selektionsbild über den Controller bis zur Persistence-Klasse durch die dann das SELECT auf die db auslöst).


Kurzes Beispiel:
Fall 1: User möchte ein neues Objekt/einen neuen Datensatz erzeugen und dem ALV anfügen.
Der Ablauf wäre bei mir folgendermaßen:
- User klickt auf Button
- Im PAI-Modul des Reports wird anhand des ok_code eine Controller-Methode aufgerufen: ZCL_CONTROLLER->erzeuge_objekt( ).

Innerhalb der erzeuge_objekt( ) Methode passiert folgendes:
- Es wird eine Methode der Persistence-Klasse aufgerufen, die nach bestimmten Vorgaben ein Objekt erzeugt und dieses als Return-Parameter zurückgibt.
- Es wird eine Methode der Presenter-Klasse aufgerufen, in der das erzeugte Objekt der Ausgabetabelle des ALV angefügt wird (Insert in Ausgabetabelle innerhalb Presenter-Klasse). Innerhalb dieser Methode wird wiederum eine Controller-Methode aufgerufen, die die "Synchronisierung" zwischen Ausgabetabelle der Presenter-Klasse und der Tabelle der Persistence-Klasse auslöst (Ausgabetabelle vom Presenter holen und Interne Tabelle in Persistence-Klasse überschreiben).
- Anschließend wird eine Methode der Presenter-Klasse aufgerufen, die die Anzeige des ALV aktualisiert.



Meine Frage:
Ist mein Vorgehen so korrekt?
Mich stört vor allem die doppelte Datenhaltung.. also Ausgabetabelle für das ALV in der Presenter-Klasse und der Tabelle der DB-Daten in der Persistence-Klasse. Wie könnte ich das elegant umgehen?
Wo gehört z.B. Validierungslogik bei Überprüfung geänderter Daten hin? (also User editiert Felder im ALV - aktuell mache ich das in der Presenter-Klasse).
Ansonsten bin ich für jede Anregung zur Verbesserung meines Vorgehens dankbar!

edit:
Was mich außerdem verwirrt: Was gehört bei einer entsprechenden Architektur alles in die PAI & PBO Module?

gesponsert
Stellenangebote auf ABAPforum.com schalten
kostenfrei für Ausbildungsberufe und Werksstudenten


Re: ABAP OO + MVC + ALV

Beitrag von ralf.wenzel (Top Expert / 3776 / 176 / 262 ) »
Also, MVC mit PAI & PBO ist nicht so ganz trivial, insbesondere musst du unterscheiden zwischen einem Button auf dem Dynpro und einem Button im ALV. Der ALV arbeitet mit Handlern, wie man es sich im OO-Umfeld vorstellt, das PAI wird einfach prozedural durchlaufen, egal welche Aktion du durchführst. Im Coding selbst unterscheidest du dann zwischen den Aktionen.

Wenn du im Dynpro selbst keine Buttons brauchst, sondern dich nur im ALV bewegst, braucht das PAI fast nichts zu machen, es gibt halt Standardbuttons wie F3 etc., auf die man reagieren muss. Das mache ich normalerweise auch mit Events, die ausgelöst werden, weil das den geringsten Bruch zwischen OO und prozeduraler Programmierung erzeugt.

Die Zeilen eines ALV kannst du nicht als Objekt ansprechen, hier hat die SAP irgendwo aufgehört, in OO zu denken ;) Aber natürlich kann man jede Zeile als Objekt verwalten, das habe ich schon so gemacht. Aber im ALV selbst ist dann Ende mit Objekt.

Die doppelte Datenhaltung ist eigentlich keine, weil sie technisch unterschiedliche Daten enthalten. Das wird dann klar, wenn du dich vom Konzept der Datenbank löst (dann sind nämlich die Strukturen in der Persistenz nicht mehr zwingend gleich den Strukturen im Presenter, auch wenn sie logisch dieseleben Daten enthalten). Im SAP-Umfeld ist es so, dass man das gern vermengt. Ich habe Objekte gesehen, die (obwohl es eine Persistenz-Schicht gibt) die DB-Strukturen als Attribute verwenden. Das ist praktisch, solange man mit dieser DB arbeitet und verwirrend, wenn man das mal nicht mehr tut.

Guck dir mal das Konzept der OO-Transaktionen an. Wir schreiben hier gerade ein ganzes Modul ohne einen einzigen Report.....

Ralf

Folgende Benutzer bedankten sich beim Autor ralf.wenzel für den Beitrag:
TimTo


Re: ABAP OO + MVC + ALV

Beitrag von TimTo (ForumUser / 5 / 4 / 0 ) »
ralf.wenzel hat geschrieben:Also, MVC mit PAI & PBO ist nicht so ganz trivial...
Das beruhigt mich schonmal.. letztendlich kann man also sagen, dass das MVC-Pattern in Kombination mit einem Report nicht zu 100% umsetzbar ist?
ralf.wenzel hat geschrieben: Wenn du im Dynpro selbst keine Buttons brauchst...
Bei mir ist genau das Gegenteil der Fall. Alle Userinteraktionen geschehen (bisher) über Buttons in der Dynpro-Toolbar und werden im PAI-Modul behandelt. Lediglich bei der Änderung des ALV, also wenn der User Daten in editierbare Zellen einträgt/sie ändert behandle ich (momentan noch im Presenter?) das data_changed Ereignis. Innerhalb der Handler-Methode rufe ich dann Validierungsmethoden (die sich ebenfalls im Presenter befinden..) auf.
ralf.wenzel hat geschrieben: Die Zeilen eines ALV kannst du nicht als Objekt ansprechen, hier hat die SAP irgendwo aufgehört, in OO zu denken ;) Aber natürlich kann man jede Zeile als Objekt verwalten, das habe ich schon so gemacht. Aber im ALV selbst ist dann Ende mit Objekt.
Das stimmt, ich rede hier auch lediglich von Objekten da ich von der Denkweise her nichts anderes kenne.. ich arbeite in dem Programm lediglich mit Tabellen - Datensätze werden nicht durch Objekte repräsentiert.
ralf.wenzel hat geschrieben: Die doppelte Datenhaltung ist eigentlich keine, weil sie technisch unterschiedliche Daten enthalten...
Also kommt man um das hin- und herschieben der Daten nicht rum? Ich hatte erst überlegt die Ausgabetabelle einfach in der Persistence-Klasse (öffentlich) zu halten, aber das kommt mir irgendwie auch nicht richtig vor..
ralf.wenzel hat geschrieben: Guck dir mal das Konzept der OO-Transaktionen an. Wir schreiben hier gerade ein ganzes Modul ohne einen einzigen Report.....
Meinst du die Object Services (Persistenzdienst, Transaktiondienst)?
Das lustige ist, in der Uni habe ich ABAP anhand von Webdynpro gelernt.. hier haben wir auch ausschließlich Object Services inkl. aufwändigem Sperrsystem verwendet (MVC war hierbei natürlich kein Problem - klassische Dynpro-Programmierung wurde leider nur angeschnitten).
Leider musste ich feststellen, dass diese Sachen in der Realität (teilweise) als unnötiger Overhead angesehen werden (was ich bei kleineren Anwendungen die teilweise nur von einem User genutzt werden auch durchaus verstehen kann).


Vielleicht noch kurz zum Hintergrund:
Ich habe die Aufgabe einen uralt-Report mit einigen tausend Zeilen prozeduralem Code objektorientiert umzusetzen. Der Report ist in zahlreiche Includes und Unterprogrammen strukturiert, die es nun sauber auf Klassen aufzuteilen gilt..
Funktionsbausteine, Validierungslogik etc. möchte ich natürlich nicht neu schreiben und versuche deshalb so viel wie möglich zu übernehmen, ohne dass ich den Code des Reports in eine einzige Klasse mit tausenden von Methoden auslagere.. ich bin mir nur noch nicht vollständig schlüssig wie :)

Gruß,
Tim

Re: ABAP OO + MVC + ALV

Beitrag von ralf.wenzel (Top Expert / 3776 / 176 / 262 ) »
TimTo hat geschrieben:Das beruhigt mich schonmal.. letztendlich kann man also sagen, dass das MVC-Pattern in Kombination mit einem Report nicht zu 100% umsetzbar ist?

Nein, der Report ist eigentlich ein Störfaktor im MVC-Pattern.
TimTo hat geschrieben:Bei mir ist genau das Gegenteil der Fall. Alle Userinteraktionen geschehen (bisher) über Buttons in der Dynpro-Toolbar und werden im PAI-Modul behandelt. Lediglich bei der Änderung des ALV, also wenn der User Daten in editierbare Zellen einträgt/sie ändert behandle ich (momentan noch im Presenter?) das data_changed Ereignis. Innerhalb der Handler-Methode rufe ich dann Validierungsmethoden (die sich ebenfalls im Presenter befinden..) auf.
Das ist das Problem, du hast Dynpro-Aktionen und ALV-Aktionen. Und die Behandlung unterscheidet sich grundlegend, darum mache ich das so (wie ich schon schrieb), dass ich so programmiere, dass es im Dynpro dem ALV-Mechanismus möglichst ähnlich ist. Ich raise z. B. ein Event (wobei es dann das Problem gibt, dass Leute das nicht verstehen und wieder rausprogrammieren), was dazu führt, dass man im Dynpro ein OO-ähnliches Verhalten bekommt. Nicht, weil OO-ähnliches Verhalten besser ist, sondern um möglichst wenig Stilbruch zu bekommen.
TimTo hat geschrieben:Das stimmt, ich rede hier auch lediglich von Objekten da ich von der Denkweise her nichts anderes kenne.. ich arbeite in dem Programm lediglich mit Tabellen - Datensätze werden nicht durch Objekte repräsentiert.
Das kommt drauf an, wie du das umsetzt. Du kannst natürlich eine Klasse haben, deren Objekte für je einen Datensatz stehen. Damit kannst du arbeiten. Aber am Ende übergibst du dem ALV eine Tabelle mit Datensätzen, das ist richtig.
TimTo hat geschrieben:Also kommt man um das hin- und herschieben der Daten nicht rum? Ich hatte erst überlegt die Ausgabetabelle einfach in der Persistence-Klasse (öffentlich) zu halten, aber das kommt mir irgendwie auch nicht richtig vor.
Was soll die Ausgabetabelle in der Persistenzklasse? Ausgabe ist Ausgabe und Persistenz ist Persistenz. Und öffentliche Attribute verletzten das Konzept der Kapselung, dann kannst du das Kapseln (platt gesagt) auch gleich sein lassen.

Das Hin- und herschieben von identischen Daten sieht nur so obsolet aus, weil du identische Strukturen siehst. Wenn du in deinen Objekten die Attribute mal losgelöst von der DB-Repräsentanz aufbaust, wirst du sehen, dass das technisch zwei unterschiedliche Dinge sind, auch wenn sie denselben Inhalt haben. Stell dir einfach mal vor, hinter deiner Persistenzklasse liegt keine Datenbank, sondern eine Textdatei, die alle Daten enthält.

Wenn du es richtig machst, sollte das keine Auswirkung haben auf die Objekte selbst, weil sie unabhängig von der DB-Repräsentanz funktionieren sollen. Das ist ja der Sinn der Kapselung: Die Geschäftslogik funktioniert unabhängig von dem, was die Persistenzklassen genau machen.
TimTo hat geschrieben:Das lustige ist, in der Uni habe ich ABAP anhand von Webdynpro gelernt..
Und das hast du überlebt? Respekt! :D
TimTo hat geschrieben:Leider musste ich feststellen, dass diese Sachen in der Realität (teilweise) als unnötiger Overhead angesehen werden (was ich bei kleineren Anwendungen die teilweise nur von einem User genutzt werden auch durchaus verstehen kann).
Die Frage, was unnötiger Overhead ist und was nicht, ist hier oft Thema. Da gibt es keine Wahrheiten, nur Meinungen. Ich habe neulich in einem Lokal die Hausinstallation begutachtet, weil dort immer wieder der Strom ausfiel. Eine Katastrophe, sag ich dir. Man könnte es auch "pragmatischen Ansatz" nennen, das gilt aber nur für den Bau. Wenn du dann was ändern musst, machst du es praktisch neu. Und auch hier gibt es Leute, die (in Bezug auf ABAP) sagen: Dann ist neu machen pragmatischer als ändern. Kann man so sehen, ich sehe das nicht so.

So ist es bei Software auch: So wie man Kabel nicht kreuz und quer verlegt und es Zonen in der Wand gibt, wo sie hingehören (was auf die Funktion selbst überhaupt keinen Einfluss hat), so schreibt eine UI nicht in die DB und die Geschäftslogik ist ordentlich gekapselt. Denn spätestens, wenn man UI oder DB wechselt, ist man froh darum, nicht alle Anwendungen schreiben und neu testen zu müssen. Jedes Geschäftsobjekt wird durch eine Klasse repräsentiert, was den Vorteil hat: Irgendwann hat man (fast) alle Geschäftsobjekte als OO-Repräsentanz im System und "klöppelt" die nur noch zusammen bzw. ändert die "Verklöppelung", wenn sich was ändert.

In der Wartung hat das also deutliche Vorteile, auch wenn es erstmal Arbeit ist.

Zum Thema Mehrarbeit: Der Sicherungskasten war genau NICHT beschriftet, weil der Elektriker keinen Bock oder keine Zeit hatte - was dann dazu führt, dass ich selbst rausfinden musste, welche Sicherung überhaupt was absichert (bei der Größe der Lokalität waren das STUNDEN an Arbeit). So ist das mit Dokumentationen, da hat dann keiner Zeit für, aber wenn da mal einer an die Anwendung ran muss, fängt der erstmal das Debuggen an, weil das Coding die einzige Informationsquelle ist.

Ich halte dieses Arbeiten für unprofessionell - und stecke HIER regelmäßig Prügel dafür ein, dass ich das so pauschal sage.

Und zu kleinen Programmen: Ein Kabel verlegt man auch DANN nicht quer durch die Wand, wenn "mal eben eine Lampe" angeschlossen werden muss. Das macht man grundsätzlich nach denselben Prinzipien wie den Rest auch (schon, um keinen Paradigmen-Bruch einzubauen). Das ist bestenfalls zu tolerieren, wenn es sich um eine temporäre Lösung handelt (die man - um zurück zum Beispiel zu kommen - per langem Kabel an eine Steckdose anschließen würde).

Mein Tipp: Wenn du es neu machst, mach es gleich richtig. Ja, es ist teuer, Altlasten loszuwerden, aber wenn das Endergebnis besser ist als das, was jetzt da ist, ist das in meinen Augen gerechtfertigt (wobei ich nicht der Budgetverantwortliche bin ;) ). Insbesondere wenn man über den Tellerrand guckt. Bei einem Ex-Kunden gab es ein Team, das nur ABAP-QS gemacht hat und die hatten auch einen sehr guten Überblick darüber, was es schon gibt. Und wenn die ein Coding zum zweiten Mal gesehen haben, wurde die Abnahme mit der Auflage beendet, das in einer Serviceklasse auszulagern. Die Qualität des Codings war herausragend, weil man sehr viel nicht neu erfinden musste. Jedes Problem, das einmal gelöst war, hat sich niemandem mehr gestellt, weil es eine Lösung gab, die alle verwenden konnten. Und das war nichtmal sonderlich abstrakt.

Noch ein Tipp: Schreibe Unit-Tests! Je mehr Fehler du auf maschinellem Wege findest, umso weniger Fehler findet der Anwender im produktiven Betrieb! Es wird eine Menge produziert, aber so ziemlich das einzige Produktionsgut, das nicht maschinell getestet wird, sind ABAPs (so kommt es mir zumindest manchmal vor -- jeder Schokoriegel, den du in einem Laden kaufen kannst, unterliegt strengeren Qualitätskriterien als der durchschnittliche Kunden-ABAP).

Viel Erfolg - wenn wir dir helfen können, einfach Fragen stellen!



Ralf
Bild
Ralf Wenzel Heuristika SAP-Development
25 Jahre SAP-Entwickler • 20 Jahre Freiberufler
PublikationenUngarische NotationXing

Seite 1 von 1

Vergleichbare Themen

5
Antw.
10029
Views
Kundeneigene ABAP-Muster Vorlage im ABAP-Editor anlegen
von Stentor » 19.07.2005 11:10 • Verfasst in Basis
3
Antw.
3446
Views
OLE und ABAP: Aufruf von Excel-VBA Prozeduren aus ABAP
von OnkelSAP » 26.05.2010 09:45 • Verfasst in ABAP Objects®
2
Antw.
3039
Views
ABAP Objects oder ABAP Referenz
von Gast » 23.06.2005 15:52 • Verfasst in ABAP® für Anfänger
6
Antw.
4623
Views
ABAP Workbench und ABAP Dictionary - für Einsteiger
von schnonus » 03.04.2008 10:39 • Verfasst in ABAP® für Anfänger
3
Antw.
15664
Views
ABAP 7.02 - Neues Feature - Pragmas in ABAP
von foessleitnerj » 09.01.2013 17:02 • Verfasst in Tips + Tricks & FAQs

Über diesen Beitrag


Unterstütze die Community und teile den Beitrag für mehr Leser und Austausch

Newsletter Anmeldung

Keine Beiträge verpassen! Wöchentlich versenden wir lesenwerte Beiträge aus unserer Community.
Die letzte Ausgabe findest du hier.
Details zum Versandverfahren und zu Ihren Widerrufsmöglichkeiten findest du in unserer Datenschutzerklärung.