Transaction longue partagée (parallel)
De Wiki1000
Les transactions longues peuvent être partagées sous réserve de ne pas exécuter de BatchLongTran à l'intérieur du code parallélisé.
En effet l'exécution d'un batch doit être synchronisé avec le code métier pour éviter de mettre à jour des objets dans un état incohérent.
A défaut le scénario suivant peut se produire :
Dans ce scénario :
- Le code crée un objet puis le modifie en plusieurs étapes avant d'appeler BatchLongTran.
- L'exécution du batch par l'exécution parallèle (worker2) met à jour un objet en cours de création (worker1) dans un état incohérent.
Le comportement des patterns de code vis à vis des transactions longues est le suivant :
ForEachP with long(BatchSize) transaction
- Ce pattern exécute BatchLongTran à l'intérieur de sa boucle, vous n'avez pas besoin d'appeler explicitement BatchLongTran.
WithP long(BatchSize) transaction
- Ce pattern n'appelle pas BatchLongTran et vous devez appeler explicitement BatchLongTran à l'extérieur du code parallélisé.
Tip :
|
Une transaction longue partagée :
procedure doProcessList(ls:ClassCList); var inst:ClassC; begin foreach inst in ls do inst.unBool := True; end; function TestForEachParallelLongTran:Integer; var inst:ClassC; list:ClassCList; cursor:ClassCCursor; count:Integer; begin List := ClassC.CreateList; Cursor := ClassC.CreateCursorWhere('','',true,[]); foreachP inst in cursor index count with long transaction do begin List.AddRef(inst); if cursor.LOI or (List.Count=100) then begin parallel doProcessList(List); List.Clear; end; end; Result := 1+count; end;
Tip : Notez l'utilisation de LOI pour tester la fin du curseur dans la boucle du foreach |