1 # -*- coding: utf-8 -*-
2 # CONFIGURATION MANAGEMENT OF EDF VERSION
3 # ======================================================================
4 # COPYRIGHT (C) 1991 - 2002 EDF R&D WWW.CODE-ASTER.ORG
5 # THIS PROGRAM IS FREE SOFTWARE; YOU CAN REDISTRIBUTE IT AND/OR MODIFY
6 # IT UNDER THE TERMS OF THE GNU GENERAL PUBLIC LICENSE AS PUBLISHED BY
7 # THE FREE SOFTWARE FOUNDATION; EITHER VERSION 2 OF THE LICENSE, OR
8 # (AT YOUR OPTION) ANY LATER VERSION.
10 # THIS PROGRAM IS DISTRIBUTED IN THE HOPE THAT IT WILL BE USEFUL, BUT
11 # WITHOUT ANY WARRANTY; WITHOUT EVEN THE IMPLIED WARRANTY OF
12 # MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. SEE THE GNU
13 # GENERAL PUBLIC LICENSE FOR MORE DETAILS.
15 # YOU SHOULD HAVE RECEIVED A COPY OF THE GNU GENERAL PUBLIC LICENSE
16 # ALONG WITH THIS PROGRAM; IF NOT, WRITE TO EDF R&D CODE_ASTER,
17 # 1 AVENUE DU GENERAL DE GAULLE, 92141 CLAMART CEDEX, FRANCE.
20 # ======================================================================
22 Ce module contient le plugin generateur de fichier au format
27 import types,string,re
29 from Noyau import N_CR
30 from Noyau.N_utils import repr_float
33 from Extensions.parametre import ITEM_PARAMETRE
34 from Formatage import Formatage
35 from Extensions.param2 import Formula
39 Retourne les informations nécessaires pour le chargeur de plugins
41 Ces informations sont retournées dans un dictionnaire
46 # La factory pour créer une instance du plugin
47 'factory' : PythonGenerator,
51 class PythonGenerator:
53 Ce generateur parcourt un objet de type JDC et produit
54 un fichier au format python
56 L'acquisition et le parcours sont réalisés par la méthode
57 generator.gener(objet_jdc,format)
59 L'écriture du fichier au format ini par appel de la méthode
60 generator.writefile(nom_fichier)
62 Ses caractéristiques principales sont exposées dans des attributs
64 - extensions : qui donne une liste d'extensions de fichier préconisées
67 # Les extensions de fichier préconisées
70 def __init__(self,cr=None):
71 # Si l'objet compte-rendu n'est pas fourni, on utilise le compte-rendu standard
75 self.cr=N_CR.CR(debut='CR generateur format python pour python',
76 fin='fin CR format python pour python')
77 # Le texte au format python est stocké dans l'attribut text
81 def writefile(self,filename):
86 def gener(self,obj,format='brut'):
88 Retourne une représentation du JDC obj sous une
89 forme qui est paramétrée par format.
90 Si format vaut 'brut', retourne une liste de listes de ...
91 Si format vaut 'standard', retourne un texte obtenu par concaténation de la liste
92 Si format vaut 'beautifie', retourne le meme texte beautifié
94 self.appli=obj.get_jdc_root().appli
96 liste= self.generator(obj)
99 elif format == 'standard':
100 self.text=string.join(liste)
101 elif format == 'beautifie':
102 jdc_formate = Formatage(liste,mode='.py')
103 self.text=jdc_formate.formate_jdc()
105 raise "Format pas implémenté : "+format
108 def generator(self,obj):
110 Cette methode joue un role d'aiguillage en fonction du type de obj
111 On pourrait utiliser les méthodes accept et visitxxx à la
112 place (dépend des gouts !!!)
114 # ATTENTION a l'ordre des tests : il peut avoir de l'importance (héritage)
115 if isinstance(obj,Accas.PROC_ETAPE):
116 return self.generPROC_ETAPE(obj)
117 # Attention doit etre placé avant MACRO (raison : héritage)
118 elif isinstance(obj,Accas.FORM_ETAPE):
119 return self.generFORM_ETAPE(obj)
120 elif isinstance(obj,Accas.MACRO_ETAPE):
121 return self.generMACRO_ETAPE(obj)
122 elif isinstance(obj,Accas.ETAPE):
123 return self.generETAPE(obj)
124 elif isinstance(obj,Accas.MCFACT):
125 return self.generMCFACT(obj)
126 elif isinstance(obj,Accas.MCList):
127 return self.generMCList(obj)
128 elif isinstance(obj,Accas.MCBLOC):
129 return self.generMCBLOC(obj)
130 elif isinstance(obj,Accas.MCSIMP):
131 return self.generMCSIMP(obj)
132 elif isinstance(obj,Accas.ASSD):
133 return self.generASSD(obj)
134 elif isinstance(obj,Accas.ETAPE_NIVEAU):
135 return self.generETAPE_NIVEAU(obj)
136 elif isinstance(obj,Accas.COMMENTAIRE):
137 return self.generCOMMENTAIRE(obj)
138 # Attention doit etre placé avant PARAMETRE (raison : héritage)
139 elif isinstance(obj,Accas.PARAMETRE_EVAL):
140 return self.generPARAMETRE_EVAL(obj)
141 elif isinstance(obj,Accas.PARAMETRE):
142 return self.generPARAMETRE(obj)
143 elif isinstance(obj,Accas.EVAL):
144 return self.generEVAL(obj)
145 elif isinstance(obj,Accas.COMMANDE_COMM):
146 return self.generCOMMANDE_COMM(obj)
147 elif isinstance(obj,Accas.JDC):
148 return self.generJDC(obj)
149 elif isinstance(obj,Accas.MCNUPLET):
150 return self.generMCNUPLET(obj)
151 elif isinstance(obj,ITEM_PARAMETRE):
152 return self.generITEM_PARAMETRE(obj)
153 elif isinstance(obj,Formula):
154 return self.generFormula(obj)
156 raise "Type d'objet non prévu",obj
158 def generJDC(self,obj):
160 Cette méthode convertit un objet JDC en une liste de chaines de
161 caractères à la syntaxe python
164 if obj.definition.l_niveaux == ():
165 # Il n'y a pas de niveaux
166 for etape in obj.etapes:
167 l.append(self.generator(etape))
170 for etape_niveau in obj.etapes_niveaux:
171 l.extend(self.generator(etape_niveau))
173 # Si au moins une étape, on ajoute le retour chariot sur la dernière étape
174 if type(l[-1])==types.ListType:
175 l[-1][-1] = l[-1][-1]+'\n'
176 elif type(l[-1])==types.StringType:
180 def generMCNUPLET(self,obj):
182 Méthode générant une représentation de self permettant son ecriture
183 dans le format python
187 for v in obj.mc_liste:
188 text = re.sub(".*=","",self.generator(v))
193 def generCOMMANDE_COMM(self,obj):
195 Cette méthode convertit un COMMANDE_COMM
196 en une liste de chaines de caractères à la syntaxe python
198 l_lignes = string.split(obj.valeur,'\n')
200 for ligne in l_lignes:
201 txt = txt + '##'+ligne+'\n'
204 def generEVAL(self,obj):
206 Cette méthode convertit un EVAL
207 en une liste de chaines de caractères à la syntaxe python
209 return 'EVAL("""'+ obj.valeur +'""")'
211 def generCOMMENTAIRE(self,obj):
213 Cette méthode convertit un COMMENTAIRE
214 en une liste de chaines de caractères à la syntaxe python
216 # modification pour répondre à la demande de C. Durand, d'éviter
217 # l'ajout systématique d'un dièse, à la suite du commentaire
218 # Dans la chaine de caracteres obj.valeur, on supprime le dernier
220 sans_saut = re.sub("\n$","",obj.valeur)
221 l_lignes = string.split(sans_saut,'\n')
223 for ligne in l_lignes:
224 txt = txt + '#'+ligne+'\n'
226 # suppression du dernier saut de ligne
227 txt = re.sub("\n$","",txt)
230 def generPARAMETRE_EVAL(self,obj):
232 Cette méthode convertit un PARAMETRE_EVAL
233 en une liste de chaines de caractères à la syntaxe python
235 if obj.valeur == None:
236 return obj.nom + ' = None ;\n'
238 return obj.nom + ' = '+ self.generator(obj.valeur) +';\n'
240 def generITEM_PARAMETRE(self,obj):
243 def generFormula(self,obj):
246 def generPARAMETRE(self,obj):
248 Cette méthode convertit un PARAMETRE
249 en une liste de chaines de caractères à la syntaxe python
251 return repr(obj) + ";\n"
253 def generETAPE_NIVEAU(self,obj):
255 Cette méthode convertit une étape niveau
256 en une liste de chaines de caractères à la syntaxe python
259 if obj.etapes_niveaux == []:
260 for etape in obj.etapes:
261 l.append(self.generator(etape))
263 for etape_niveau in obj.etapes_niveaux:
264 l.extend(self.generator(etape_niveau))
267 def generETAPE(self,obj):
269 Cette méthode convertit une étape
270 en une liste de chaines de caractères à la syntaxe python
273 sdname= self.generator(obj.sd)
277 label=sdname + '='+obj.definition.nom+'('
279 if obj.reuse != None :
280 str = 'reuse ='+ self.generator(obj.reuse) + ','
282 for v in obj.mc_liste:
283 if isinstance(v,Accas.MCBLOC) :
284 liste=self.generator(v)
287 elif isinstance(v,Accas.MCSIMP) :
288 text=self.generator(v)
289 l.append(v.nom+'='+text)
292 liste=self.generator(v)
293 liste[0]=v.nom+'='+liste[0]
301 def generFORM_ETAPE(self,obj):
303 Méthode particulière pour les objets de type FORMULE
307 if nom == '' : nom = 'sansnom'
308 l.append(nom + ' = FORMULE(')
309 for v in obj.mc_liste:
310 text=self.generator(v)
311 l.append(v.nom+'='+text)
315 def generMACRO_ETAPE(self,obj):
317 Cette méthode convertit une macro-étape
318 en une liste de chaines de caractères à la syntaxe python
324 sdname= self.generator(obj.sd)+'='
328 label = sdname + obj.definition.nom+'('
330 if obj.reuse != None:
331 # XXX faut il la virgule ou pas ????
332 str = "reuse =" + self.generator(obj.reuse) + ','
334 for v in obj.mc_liste:
335 if isinstance(v,Accas.MCBLOC) :
336 liste=self.generator(v)
339 elif isinstance(v,Accas.MCSIMP) :
340 text=self.generator(v)
341 l.append(v.nom+'='+text)
344 liste=self.generator(v)
345 liste[0]=v.nom+'='+liste[0]
354 def generPROC_ETAPE(self,obj):
356 Cette méthode convertit une PROC étape
357 en une liste de chaines de caractères à la syntaxe python
360 label=obj.definition.nom+'('
362 for v in obj.mc_liste:
363 if isinstance(v,Accas.MCBLOC) :
364 liste=self.generator(v)
367 elif isinstance(v,Accas.MCSIMP) :
368 text=self.generator(v)
369 l.append(v.nom+'='+text)
372 liste=self.generator(v)
373 liste[0]=v.nom+'='+liste[0]
382 def generASSD(self,obj):
384 Convertit un objet dérivé d'ASSD en une chaine de caractères à la
387 return obj.get_name()
389 def generMCFACT(self,obj):
391 Convertit un objet MCFACT en une liste de chaines de caractères à la
396 for v in obj.mc_liste:
397 if not isinstance(v,Accas.MCSIMP) and not isinstance (v,Accas.MCBLOC) :
398 # on est en présence d'une entite composée : on récupère une liste
399 liste=self.generator(v)
400 liste[0]=v.nom+'='+liste[0]
402 elif isinstance(v,Accas.MCBLOC):
403 liste=self.generator(v)
407 # on est en présence d'un MCSIMP : on récupère une string
408 text =self.generator(v)
409 l.append(v.nom+'='+text)
410 # il faut être plus subtil dans l'ajout de la virgule en différenciant
411 # le cas où elle est obligatoire (si self a des frères cadets
412 # dans self.parent) ou non
413 # (cas où self est seul ou le benjamin de self.parent)
417 def generMCList(self,obj):
419 Convertit un objet MCList en une liste de chaines de caractères à la
422 if len(obj.data) > 1:
424 for mcfact in obj.data: l.append(self.generator(mcfact))
427 l= self.generator(obj.data[0])
430 def generMCBLOC(self,obj):
432 Convertit un objet MCBLOC en une liste de chaines de caractères à la
436 for v in obj.mc_liste:
437 if isinstance(v,Accas.MCBLOC) :
438 liste=self.generator(v)
441 elif isinstance(v,Accas.MCFACT):
442 liste=self.generator(v)
443 elif isinstance(v,Accas.MCList):
444 liste=self.generator(v)
445 liste[0]=v.nom+'='+liste[0]
446 # PN essai de correction bug identation
447 if (hasattr(v,'data')) :
448 if (isinstance(v.data[0],Accas.MCFACT) and (len(v.data) == 1)):
457 data=self.generator(v)
458 if type(data) == types.ListType:
459 data[0]=v.nom+'='+data[0]
465 def format_item(self,valeur,etape):
466 if type(valeur) == types.InstanceType :
467 if valeur.__class__.__name__ == 'CO' or hasattr(etape,'sdprods') and valeur in etape.sdprods :
468 s = "CO('"+ self.generator(valeur) +"')"
469 elif isinstance(valeur,Accas.PARAMETRE):
470 # il ne faut pas prendre la string que retourne gener
471 # mais seulement le nom dans le cas d'un paramètre
474 s = self.generator(valeur)
475 elif type(valeur) == types.FloatType :
476 # Pour un flottant on utilise str
477 # ou la notation scientifique
480 clefobj=obj.GetNomConcept()
481 if self.appli.dict_reels.has_key(clefobj):
482 if self.appli.dict_reels[clefobj].has_key(valeur):
483 s=self.appli.dict_reels[clefobj][valeur]
486 elif type(valeur) == types.StringType :
487 if valeur.find('\n') == -1:
488 # pas de retour chariot, on utilise repr
490 elif valeur.find('"""') == -1:
491 # retour chariot mais pas de triple ", on formatte
496 # Pour les autres types on utilise repr
501 def generMCSIMP(self,obj) :
503 Convertit un objet MCSIMP en une liste de chaines de caractères à la
506 if type(obj.valeur) in (types.TupleType,types.ListType) :
508 for val in obj.valeur :
509 s =s +self.format_item(val,obj.etape) + ','
510 if len(obj.valeur) > 1:
512 if obj.nbrColonnes() :
513 s=self.formatColonnes(obj.nbrColonnes(),s)
515 s=self.format_item(obj.valeur,obj.etape) + ','
519 def formatColonnes(self,nbrColonnes,text):
522 liste=text.split(",")
525 while ( indice < len(liste) -2 ) :
526 for l in range(nbrColonnes) :
527 textformat=textformat+liste[indice]+","
529 textformat=textformat+"\n"
530 textformat=textformat+"),"