Anmelden

View Full Version : Variablenname in Variable



Seiten : 1 [2]

Fuerchau
02-12-14, 16:46
War von Eleganz die Rede?
Habe ich da was überlesen:D?

holgerscherer
02-12-14, 16:48
Du musst das Journal nachprogrammieren? Ich denke, hier liegt Dein Problem ;-)
Warum benutzt Du nicht das vom System?

-h

holgerscherer
02-12-14, 16:50
Die Nummer hatte ich auch mal gemacht zwecks dynamischer Analyse von Dateien und Spiegelung auf eine andere Kiste. War zu V4-Zeiten. Da hat das Blech irgendwann die Weisse Rauchfahne gewunken.

Aber elegant? Das ist was anderes. Vielleicht dynamisch generierter SQL-Code, der dann via RUNSQLSTM aufgerufen wird? :)

-h

maro78
03-12-14, 06:40
Ich habe das seiner Zeit ohne Pointer und Masochismus einfach mit einem SQL-RPGLE gelöst.

Ob das elegant ist - keine Ahnung. War aber zielführend, nicht teuer, und hatte funktioniert :cool:

Für jedes Feld der zu untersuchenden Datei ...

SELECT CAST(COLUMN_TEXT AS CHARACTER (50) ccsid 273),
SYSTEM_COLUMN_NAME,
SYSTEM_TABLE_NAME
FROM QSYS2/SYSCOLUMNS
WHERE
SYSTEM_TABLE_NAME = 'DeineTabelle' AND
SYSTEM_TABLE_SCHEMA = 'DeineLib'



... ein SQL-Vergleich auf Feldunterschiede durchführen


SELECT

CASE WHEN
%trim(p$Datei1) + '.' +
%trim(p$Feld) + ' <> ' +
%trim(p$Datei2) + '.' +
%trim(p$Feld) + ' THEN ' +
p$Feld
ELSE ' ' END
... n mal für jedes Feld ...

FROM p$Datei1
LEFT OUTER JOIN p$Datei2 ON ...
WHERE ...


... anschließend Fetch into dieses SQL in eine interne DS (hier sqlsatz)


d sqlsatz ds
d sq001 70
d sq002 70
...
d sq250 70

d sqlsatzx ds
d sqxxx 70 dim(250)

...
c+ FETCH NEXT FROM xyz into :sqlsatz
...
c move sqlsatz sqlsatzx


Die Felder mit Datenänderung stehen dann als Feldname jeweils in einem Element von sqxxx.
Also alles lesen wo sqxxx(p$Counter) <> *blanks ist und ggf. für die Subfileanzeige mit SQL die Vorher/Nachher Werte dieses speziellen Feldes ermitteln.

andreaspr@aon.at
03-12-14, 08:06
Es gibt auch die Möglichkeit des DESCRIPTOR.
Da kannst du völlig dynamisch dein SQL zusammenbasteln und einlesen.
Das Einlesen einzelner Werte würde wie folgt aussehen:

...
if vresult_ind >= 0;

Select;
When vtype = '1';
// Character
exec Sql GET DESCRIPTOR 'mydesc' VALUE :i :sp2 = DATA;

When vtype = '4';
// Integer
exec Sql GET DESCRIPTOR 'mydesc' VALUE :i :sp1 = DATA;
endsl;

endif;

Damit brauchst du die Spalten nicht alle Definieren, du musst halt nur aufpassen dass du für jedes Feld eine passende Variable zur Verfügung hast.

lg Andreas

Fuerchau
03-12-14, 08:19
Ich denke nicht dass die SQL-Vorschläge hier helfen, da das After/Bevor-Image wohl nicht als Einzelsatz in einer Tabelle sondern als Gesamtpuffer von einem Trigger irgendwo gespeichert ist.

Hier müsste ich ein neues Konzept erstellen und somit eine neue Tabelle (auf Basis der alten + Identity-Bezug mit B/A-Kennzeichnung) erstellen und ein feldbezogenes After/Bevor-Image per Trigger schreiben.
Dann kann ich per dynamischem SQL die Felder vergleichen und für eine Subfile-Ausgabe auch mittels CHAR(NumFeld) einfach aufbereiten.

Fuerchau
03-12-14, 08:43
Um überhaupt mit Descriptoren zu arbeiten musst du diese auch erstellen, automatisch steht da nichts zur Verfügung.
Beispiele stehen im Handbuch SQL-Programming.

Im wesentlichen sind dies:
Allocate descriptor ...
Describe xxx using descriptor ...
fetch ... into descriptor ...

Dann kannst du auch per "Get Descriptor ... DATA" den Inhalt (sowie Attribute usw.) auslesen.
Benötigt wird hierfür aber ein dynamischer SQL auf Feldebene!

andreaspr@aon.at
03-12-14, 09:10
... ums noch genauer zu beschreiben:
var = 'select ...'
prepare s1 from :var
decalare c1 cursor for s1
allocate descriptor 'xxx' ...
describe s1 using descriptor 'xxx'
open c1
fetch c1 into sql descriptor 'xxx'
// anzahl der spalten abrufen
get descriptor 'xxx' :count = count
dann in einer Schleife für jede Spalte (i = Spaltennummer):
get descriptor 'xxx' value :i :type=type, ...
und dann wie oben von mir schon beschrieben mit
get descriptor 'xxx' value :i :vdata = data

Fuerchau
03-12-14, 09:25
Manchmal frage ich mich, warum immer alles so kompliziert sein muss.
Mit einer dynamischen SQLDA bekomme ich auch alle Informationen sowie beim Fetch auch gleich die Inhalte. Durch Typanpassung kann ich immer ein CHAR/VARCHAR-Feld als Ziel angeben.
Ich muss nur halt die SQLDA per %alloc() anlegen, im Array der SQLItem's je Variable einen %alloc() für einen Speicherbeireich durchführen.
Wenn ich dann fertig bin, kann ich alles per %free() wieder freigeben.

Descriptoren machen eigentlich nur bei Sprachen Sinn, die keine dynamische SQLDA unterstützen.

Mit V4R3 habe ich einen SQLCPY entwickelt (in meinem Download zum Test verfügbar), der genau nach diesem Verfahren arbeitet.

harkne
04-12-14, 08:35
Hallo zusammen. Vielen Dank für die vielen Tipps. Ansage von Cheffe war es jetzt ganz einfach mit viel Schreibarbeit die einzelnen Felder abzufragen und auch brav Konstant in die Subfile mit dem Wert zu schreiben und nichts kompliziertes zu programmieren ;-).

Ich werde mir aber bei Zeit die Möglichkeiten mal näher anschauen.
Vielen Dank nochmal an alle

@holgerscherer Die Auwahlmöglichkeiten um sich die Daten anzeigen zu lassen sind so umfangreich, dass will man nicht wirklich über das Journal selektieren.

PS: Pointer. Damit kann mir niemand drohen, das Zeugs werde ich nie kapieren und werde es deshalb auch nie verwenden müssen. Ich bin einfacher Softwareentwickler ;-)