[Gelöst] CC: Tabelle in anderen Mandanten kopieren (RecRef)

3. März 2016 12:39

Freundliches Hallo.

Möchte Daten in gleiche Tabelle von anderen Mandanten kopieren.

Bekomme nen Fehler:
Fehler.PNG


Lösche erst Zieltabelle. Dann insert().

Mein Code:
Code.PNG


Sieht jemand den Fehler?

MfG
Christian
Du hast keine ausreichende Berechtigung, um die Dateianhänge dieses Beitrags anzusehen.
Zuletzt geändert von navCH am 3. März 2016 16:57, insgesamt 1-mal geändert.

Re: CC: Tabelle in anderen Mandanten kopieren (RecRef)

3. März 2016 12:52

Nutze statt eines Screenshots besser eine Kopie des Codes in code-Tags (so wie ich es gleich tue), so können die Helfer Codeausschnitte leichter kopieren und korigieren. Deine Einrückungen bleiben dabei erhalten.

Das Problem dürfte das Konstrukt um UNTIL MyRecRef2.NEXT = MyRecRef.COUNT sein. Hast du mal gedebuggt, was MyRecRef2.NEXT schrittweise zurückliefert? Passt das mit COUNT?

Ersetzte den kompletten Block ab IF MyRecRef2.ISEMPTY durch das hier:
Code:
// IF MyRecRef2.ISEMPTY THEN .... // ist aufgrund der vorherigen Codezeile immer true ...
IF MyRecRef.FIND('-') THEN BEGIN
  REPEAT
    MyRecRef2 
:= MyRecRef;
    MyRecRef2.INSERT;
  UNTIL MyRecRef.NEXT = 0;
END;


Sollte auch das nicht die Lösung sein, ist eventuell das MyRecRef2 := MyRecRef; zu "hart". Schauen wir mal ...

Re: CC: Tabelle in anderen Mandanten kopieren (RecRef)

3. März 2016 13:55

Bekomme mit deinem Code auch die gleiche Fehlermeldung
Zuletzt geändert von McClane am 3. März 2016 14:37, insgesamt 1-mal geändert.
Grund: Bitte keine kompletten Beiträge zitieren!

Re: CC: Tabelle in anderen Mandanten kopieren (RecRef)

3. März 2016 14:10

Hat es einen bestimmten Grund, dass du hier mit RecordRefs arbeitest? Verwendest du die Funktion in Wirklichkeit globaler?
Wenn nein, solltest du normale Record-Variablen verwenden, denen mittels CHANGECOMPANY den passenden Mandanten zuweisen und jeden Datensatz mittels TRANSFERFIELDS + INSERT übernehmen. Dann kann eigentlich nichts schief gehen.

Muss der Ansatz mit RecordRef bleiben, so scheint es mir, als wäre - wie gesagt - MyRecRef2 := MyRecRef zu "hart" und muss durch eine FieldRef-Schleife ersetzt werden.

Re: CC: Tabelle in anderen Mandanten kopieren (RecRef)

3. März 2016 14:16

Natalie hat geschrieben:Hat es einen bestimmten Grund, dass du hier mit RecordRefs arbeitest? Verwendest du die Funktion in Wirklichkeit globaler?


Eigentlich nicht, aber ich wüsste gern ob es mit RecordRef funktioniert.

Re: CC: Tabelle in anderen Mandanten kopieren (RecRef)

3. März 2016 14:34

Fehler.PNG


Der sagt mir die Warengruppe existiert bereits, obwohl die Zieltabelle leer ist
Du hast keine ausreichende Berechtigung, um die Dateianhänge dieses Beitrags anzusehen.

Re: CC: Tabelle in anderen Mandanten kopieren (RecRef)

3. März 2016 14:48

navCH hat geschrieben:Der sagt mir die Warengruppe existiert bereits, obwohl die Zieltabelle leer ist
Hatte ich schon verstanden.

Ich habe dir bereits gesagt, warum diese Meldung zu kommen scheint und wie du sie abstellen könntest.

Re: CC: Tabelle in anderen Mandanten kopieren (RecRef)

3. März 2016 15:23

Natalie hat geschrieben:Muss der Ansatz mit RecordRef bleiben, so scheint es mir, als wäre - wie gesagt - MyRecRef2 := MyRecRef zu "hart" und muss durch eine FieldRef-Schleife ersetzt werden.


Habe es mit FieldRef versucht und hierbei gibt es eine andere Fehlermeldung. Er sagt immer noch Warengruppe existiert, aber findet keinen Inhalt der Tabelle:
Fehler 2.PNG


Code:
Company.Name:='Ziel_Mandant';
MyRecRef2.OPEN(50014,FALSE,Company.Name);
MyRecRef2.DELETEALL;
Company.Name:='Mandant';
MyRecRef.OPEN(50014,FALSE,Company.Name);

IF MyRecRef.FINDFIRST THEN
REPEAT

    MyFieldRef3:=MyRecRef.FIELDINDEX(3);
    MyFieldRef2:=MyRecRef.FIELDINDEX(2);
    MyFieldRef1:=MyRecRef.FIELDINDEX(1);

    IF MyRecRef2.ISEMPTY THEN
    REPEAT

        MyFieldRef6:=MyRecRef2.FIELDINDEX(3);
        MyFieldRef5:=MyRecRef2.FIELDINDEX(2);
        MyFieldRef4:=MyRecRef2.FIELDINDEX(1);
        MyFieldRef6:=MyFieldRef3;
        MyFieldRef5:=MyFieldRef2;
        MyFieldRef4:=MyFieldRef1;
       
        MyRecRef2.INSERT;
    UNTIL MyRecRef2.NEXT = MyRecRef.COUNT;
UNTIL MyRecRef.NEXT(+1)=0;


MyRecRef.CLOSE;
MyRecRef2.CLOSE;


Auch hierbei die gleiche Meldung:

Code:
Company.Name:='Ziel_Mandant';
MyRecRef2.OPEN(50014,FALSE,Company.Name);
MyRecRef2.DELETEALL;
Company.Name:='Mandant';
MyRecRef.OPEN(50014,FALSE,Company.Name);

IF MyRecRef.FIND('-') THEN BEGIN
  REPEAT
    MyFieldRef3:=MyRecRef.FIELDINDEX(3);
    MyFieldRef2:=MyRecRef.FIELDINDEX(2);
    MyFieldRef1:=MyRecRef.FIELDINDEX(1);

    MyFieldRef6:=MyRecRef2.FIELDINDEX(3);
    MyFieldRef5:=MyRecRef2.FIELDINDEX(2);
    MyFieldRef4:=MyRecRef2.FIELDINDEX(1);

    MyFieldRef6:=MyFieldRef3;
    MyFieldRef5:=MyFieldRef2;
    MyFieldRef4:=MyFieldRef1;
   
    MyRecRef2.INSERT;
  UNTIL MyRecRef.NEXT = 0;
END;


MyRecRef.CLOSE;
MyRecRef2.CLOSE;
Du hast keine ausreichende Berechtigung, um die Dateianhänge dieses Beitrags anzusehen.

Re: CC: Tabelle in anderen Mandanten kopieren (RecRef)

3. März 2016 16:37

Durch die direkte Zuweisung wird die gesamte Referenz übertragen, inklusive dem Verweis auf den Mandanten.

Daher muss der FieldRef-Value übergeben werden, anstatt den FieldRef zuzuweisen:

Code:
IF SourceRecRef.FIND('-') THEN BEGIN
  REPEAT
    FOR I 
:= 1 TO SourceRecRef.FIELDCOUNT DO BEGIN
      SourceFieldRef 
:= SourceRecRef.FIELDINDEX(I);
      TargetFieldRef := TargetRecRef.FIELDINDEX(I);
      TargetFieldRef.VALUE := SourceFieldRef.VALUE;
    END;    
    TargetRecRef
.INSERT;
  UNTIL SourceRecRef.NEXT = 0;
END;

Re: CC: Tabelle in anderen Mandanten kopieren (RecRef)

3. März 2016 16:40

Hier die Lösung meines Problems. Ich hatte eine Schleife zu viel.
Die Schleife in der Ziel-Tabelle war falsch. Wusste nicht das beim Insert() der Fokus auch gleich in die neue Spalte springt.
@Timo Lässer: Ja, .Value hatte ich auch vergessen.
Danke.

Lösung:
Code:
Company.Name:='Ziel_Mandant';
MyRecRef2.OPEN(50014,FALSE,Company.Name);
MyRecRef2.DELETEALL;
COMMIT;

Company.Name:='Mandant';
MyRecRef.OPEN(50014,FALSE,Company.Name);

IF MyRecRef.FINDFIRST THEN
REPEAT

    MyFieldRef3:=MyRecRef.FIELDINDEX(3);
    MyFieldRef2:=MyRecRef.FIELDINDEX(2);
    MyFieldRef1:=MyRecRef.FIELDINDEX(1);

    MyFieldRef6:=MyRecRef2.FIELDINDEX(3);
    MyFieldRef5:=MyRecRef2.FIELDINDEX(2);
    MyFieldRef4:=MyRecRef2.FIELDINDEX(1);

    MyFieldRef6.VALUE:=MyFieldRef3.VALUE;
    MyFieldRef5.VALUE:=MyFieldRef2.VALUE;
    MyFieldRef4.VALUE:=MyFieldRef1.VALUE;
       
    MyRecRef2.INSERT;

UNTIL MyRecRef.NEXT(+1)=0;

MyRecRef2.CLOSE;
MyRecRef.CLOSE;

Re: CC: Tabelle in anderen Mandanten kopieren (RecRef)

3. März 2016 16:48

Hallo,

wie Natalie schon sagte ist RecRef2:=RecRef; zu "direkt"
Du musst wie das Timo schon geschrieben hat FieldRef.VALUE verwenden, um die Werte Feld für Feld zu übertragen.

Leider klappt das auch nicht immer generisch (BLOBs/Binaries/Flowfields usw.).
Daher sollte man das auch noch abfangen:

Code:
IF NOT (FORMAT(SourceFieldRef.TYPE) IN['Binary','BLOB']) AND (FORMAT(SourceFieldRef.CLASS) = 'Normal') THEN 
TargetFieldRef
.VALUE := SourceFieldRef.VALUE


:arrow: Wenn man das gut implementiert kann das nützlich sein um Daten von einer Tabelle von Mandant A in die eines anderen Mandant B generisch (mit den gerade angemerkten Ausnahmen) zu übertragen. :-)

mfg,
winfy

Re: [Gelöst] CC: Tabelle in anderen Mandanten kopieren (RecR

3. März 2016 17:07

Hallo,

wer das mal in NAV 2009 in Real- Life sehen möchte, und nicht immer alles neu programmieren möchte, sollte sich mal die Einrichtungsscheckliste anschauen, die macht so etwas :mrgreen:

Gruß Fiddi

Re: [Gelöst] CC: Tabelle in anderen Mandanten kopieren (RecR

3. März 2016 17:27

fiddi hat geschrieben:wer das mal in NAV 2009 in Real- Life sehen möchte, und nicht immer alles neu programmieren möchte, sollte sich mal die Einrichtungsscheckliste anschauen, die macht so
[...]
Gruß Fiddi


In der Einrichtungscheckliste gehen aber nur bestimmte Tabellen. Hier kann man im Grunde jede Tabelle z.B. 50xxx nehmen für die man die entsprechenden Berechtigungen hat.
Als Mandantenkopie ungeeignet, aber gerade bei vielen eigenen (kleinen bis ca. 100.000 Datensätze) Tabellen finde ich das sinnvoll.

mfg,
winfy

Re: [Gelöst] CC: Tabelle in anderen Mandanten kopieren (RecR

3. März 2016 17:43

Hallo,
In der Einrichtungscheckliste gehen aber nur bestimmte Tabellen


kann man aber relative problemlos erweitern.
Und ganz so einfach ist das kopieren auch nicht, denn wenn man abhängige Tabellen kopiert, muss man schon sehr genau aufpassen, in welcher Reihenfolge man kopiert :wink:

Gruß Fiddi

Re: CC: Tabelle in anderen Mandanten kopieren (RecRef)

4. März 2016 12:45

Timo Lässer hat geschrieben:Durch die direkte Zuweisung wird die gesamte Referenz übertragen, inklusive dem Verweis auf den Mandanten.

Daher muss der FieldRef-Value übergeben werden, anstatt den FieldRef zuzuweisen:

Code:
IF SourceRecRef.FIND('-') THEN BEGIN
  REPEAT
    FOR I 
:= 1 TO SourceRecRef.FIELDCOUNT DO BEGIN
      SourceFieldRef 
:= SourceRecRef.FIELDINDEX(I);
      TargetFieldRef := TargetRecRef.FIELDINDEX(I);
      TargetFieldRef.VALUE := SourceFieldRef.VALUE;
    END;    
    TargetRecRef
.INSERT;
  UNTIL SourceRecRef.NEXT = 0;
END;


Die Schleife von Timo Lässer ist für mehrere Tabellen, mit unterschiedlichen Fieldcount sehr gut geeignet!

Re: [Gelöst] CC: Tabelle in anderen Mandanten kopieren (RecR

4. März 2016 14:18

fiddi hat geschrieben:Und ganz so einfach ist das kopieren auch nicht, denn wenn man abhängige Tabellen kopiert, muss man schon sehr genau aufpassen, in welcher Reihenfolge man kopiert :wink:


Ja es gibt da ein paar Fallstricke.
Es setzt natürlich voraus, dass man weiß was man macht und damit ist das nicht ganz ungefährlich. :wink:
Ich finde es aber dennoch sehr nützlich.

mfg,
winfy

Re: [Gelöst] CC: Tabelle in anderen Mandanten kopieren (RecR

4. März 2016 23:00

Hallo,
navCH hat geschrieben:Die Schleife von Timo Lässer ist für mehrere Tabellen, mit unterschiedlichen Fieldcount sehr gut geeignet!

Das ist ganz und gar nicht der Fall. :shock:
Die Schleife erfordert ein genaues 1:1 Abbild der beiden Tabellen (wg. gemeinsamer Index I), ansonsten werden unterschiedliche Felder zugewiesen. Ob das funktioniert, ist Zufall, auf alle Fälle aber falsch.

Außerdem fehlt in Timos Schleife noch die Abfrage, ob es sich um spezielles Feld handelt, das man nicht kopieren kann (siehe winfy);

Code:
SourceRecRef.OPEN(DATABASE::Customer,FALSE,'Company A');
TargetRecRef.OPEN(DATABASE::Customer,FALSE,'Company B');
IF SourceRecRef.FIND('-') THEN BEGIN
  REPEAT
    FOR I := 1 TO SourceRecRef.FIELDCOUNT DO BEGIN
      SourceFieldRef := SourceRecRef.FIELDINDEX(I);
      IF NOT (FORMAT(SourceFieldRef.TYPE) IN['Binary','BLOB']) AND (FORMAT(SourceFieldRef.CLASS) = 'Normal') THEN BEGIN
         TargetFieldRef := TargetRecRef.FIELDINDEX(I);
         TargetFieldRef.VALUE := SourceFieldRef.VALUE;
      END;
    END;   
    TargetRecRef.INSERT;
  UNTIL SourceRecRef.NEXT = 0;
END;


Gruß Fiddi