J'essaie d'ajouter de nouveaux connecteurs à un modèle EA à l'aide de Python. Malheureusement, lorsque mon script s'exécute, il n'ajoute pas le connecteur. Le même script écrit en Javascript, via la console EA Javascript, est capable d'ajouter le connecteur.

Ce qui est étrange, c'est que le script Python n'échoue pas. Il se comporte comme s'il avait ajouté le connecteur. Si je rafraîchis les éléments connectés, il semble que le connecteur soit là. Je peux même obtenir un ConnectorID à partir de la console Python.

PYTHON:

from win32com.client import Dispatch
import os

ea = Dispatch("EA.App")
rep = ea.Repository
path = os.path.normpath("C:/temp/eaFile.eap")

e1 = rep.GetElementByID(121228)
e2 = rep.GetElementByID(120663)
newCon = e1.Connectors.AddNew("","Association")
newCon.ClientID = e1.ElementID
newCon.SupplierID = e2.ElementID
newCon.Update()

JAVASCRIPT:

e1 = Repository.GetElementByID(121228);
e2 = Repository.GetElementByID(120663);
newCon = e1.Connectors.AddNew("", "Association");
newCon.ClientID = e1.ElementID;
newCon.SupplierID = e2.ElementID;
newCon.Update();

Je m'attends à ce que le connecteur soit visible sous forme de lien sur l'élément dans Enterprise Architect - je ne le trouve pas lorsqu'il est exécuté à partir de Python, je le trouve lorsqu'il est exécuté à partir de Javascript.

1
Nickdom1 8 nov. 2019 à 03:20

2 réponses

Meilleure réponse

Enfin compris. Le problème principal était que je manquais la ligne suivante après avoir défini mon chemin:

rep.OpenFile(path)

À cause de cela, il ne se connecterait pas. Doit avoir perdu cette ligne lors du dépannage de ce script.

Je pense qu'un problème secondaire était que ma console Python était toujours ouverte depuis les sessions précédentes, et j'avais plusieurs modèles EA ouverts, donc il y avait une certaine bizarrerie dans la façon dont EA se comportait avec la connexion au modèle souhaité (comme je l'ai dit, je recevais commentaires dans le script comme si j'étais connecté).

Je pense que le plus gros cadeau ici est qu'EA aime recharger le projet chaque fois que j'exécute avec succès un script python contre le référentiel, fermant toutes les fenêtres ouvertes de l'application (probablement pour prendre en compte les modifications). Si EA ne jette pas votre travail, vous faites quelque chose de mal!

1
Nickdom1 8 nov. 2019 à 15:32

Pour une raison étrange, vous devez appeler la mise à jour sans accolades.

e1 = rep.getelementbyguid("{B2F19D81-1475-41f2-BABD-AA66E11FAE10}")
e2 = rep.getelementbyguid("{86DFDB7C-0838-47eb-8402-384701170C34}")
con = e1.connectors.addnew("", "Dependency")
con.supplierId = e2.elementId
con.update

Travaillé pour moi. Je n'ai jamais cherché à savoir pourquoi, je suis juste habitué à la méthode EA ...

N.B. Le connecteur a déjà clientId défini, vous n'avez donc pas besoin de cette affectation.


Voici un extrait de ma classe wrapper

import win32com.client
from singleton import Singleton
import errorlogger
import eacodes
import xml.etree.ElementTree as ET
import re
import os

@Singleton
class Repository:
    def __init__(self):
        try:
            app = win32com.client.GetActiveObject("EA.App")
            self.eaRep = app.Repository
            models = self.eaRep.models
            done = True
        except Exception as e:
            print (e)
            done = False
        if not done:
            logger = errorlogger.ErrorLogger.Instance()
            logger._fatal("Can not find a running EA instance")

        self.base = self.eaRep.connectionstring
        if os.path.exists(self.base):
            path, self.base = os.path.splitext(self.base.lower())
        else:
            self.base = "server"
        self.wildcard = "%" if self.base == ".eap" else "*"

    def query(self, sql):
        root = ET.fromstring(self.eaRep.SQLQuery (sql))
        data = root.getchildren()
        if len(data) == 0: return []
        ds = data[0][0]
        rows = []
        for row in ds:
            cols = []
            for col in row.getchildren(): cols.append(col.text)
            rows.append(cols)
        return rows

Il est coupé de l'ensemble et manque des parties, mais vous pouvez le prendre comme début. Singleton peut être trouvé quelque part ici sur SO (IIRC). Usage:

rep = Repository.Instance()
e = rep.getElementByGuid("{B2F19D81-1475-41f2-BABD-AA66E11FAE10}")
print e.name
for row in rep.query("SELECT name FROM t_object"):
    print row[0]
2
qwerty_so 9 nov. 2019 à 10:14