--- /dev/null
+# -*- coding: utf-8 -*-\r
+# Copyright (C) 2008-2018 EDF R&D\r
+#\r
+# This file is part of SALOME ADAO module\r
+#\r
+# This library is free software; you can redistribute it and/or\r
+# modify it under the terms of the GNU Lesser General Public\r
+# License as published by the Free Software Foundation; either\r
+# version 2.1 of the License.\r
+#\r
+# This library is distributed in the hope that it will be useful,\r
+# but WITHOUT ANY WARRANTY; without even the implied warranty of\r
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU\r
+# Lesser General Public License for more details.\r
+#\r
+# You should have received a copy of the GNU Lesser General Public\r
+# License along with this library; if not, write to the Free Software\r
+# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA\r
+#\r
+# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com\r
+import os\r
+from Accas import OPER, BLOC, FACT, SIMP, ASSD, JDC_CATA, VerifTypeTuple, Matrice, UserASSD\r
+from Extensions.i18n import tr\r
+import types\r
+monFichier = os.path.abspath(__file__)\r
+\r
+JdC = JDC_CATA(\r
+ code='Morgane',\r
+ fr = "Modèle physique d'une vallée",\r
+)\r
+VERSION_CATALOGUE = 'V_0'\r
+\r
+class vallee(ASSD) : pass\r
+class usine(UserASSD) : pass\r
+class reservoir(UserASSD) : pass\r
+\r
+unitesChute=['hm3','m3']\r
+\r
+Vallee=OPER(nom="Vallee", sd_prod=vallee,\r
+ fr="Elément défini pour éventuellement contenir la définition des vallées de manière autonome. Les contraintes sont définies au niveau de l'élément et doivent donc être répétées si le type est utilisé ailleurs",\r
+ Reservoirs=FACT(statut='o', \r
+ Reservoir = FACT ( statut ='o', max='**', \r
+ NomReservoir = SIMP(statut='o', typ=(reservoir,'createObject'),), \r
+ TypeReservoir = SIMP(statut='o', typ= 'TXM', into = ['Lac', 'Eclusee',]), \r
+ Volume = SIMP(statut='o', typ= 'R', defaut=0, val_min=0,),\r
+ Surface = SIMP(statut='o', typ= 'R'),\r
+ CotesVolume = FACT(statut='f',\r
+ fr="Si, quelque part dans l'étude (usine ou réservoir), il y a des cotes (ie on travaille en mètres), il faut les cotes volumes car le coeur de calcul travaille en volume",\r
+ CoteVolume = FACT (statut='o', max='**',\r
+ Cote = SIMP(statut='o', typ='R', defaut=0, val_min=0),\r
+ Volume = SIMP(statut='o', typ='R', defaut=0, val_min=0),\r
+ Surface = SIMP(statut='o', typ='R', defaut=0, val_min=0),\r
+ ),\r
+ ),\r
+ ),\r
+ ), # Reservoirs\r
+\r
+ Usines = FACT(statut ='o', \r
+ fr="Attention, l'ordre des usines a une importance", \r
+ Usine = FACT ( statut ='o', max='**', \r
+ fr="Les usines sont des turbines, des pompes ou des non énergétiques. Leur description dépend de ce type",\r
+ NomDUsine = SIMP(statut='o', typ=(usine,'createObject'),), \r
+ TypeDUsine = SIMP(statut='o', typ= 'TXM', into = ['Turbine', 'Pompe', 'NonEnergetique']), \r
+ b_TypeDUsine_Turbine = BLOC( condition = 'TypeDUsine == "Turbine"', \r
+ CaracteristiquesTurbine=FACT( statut='o', \r
+ fr="Caractéristiques spécifiques aux turbines", DebitMaxPhysique = SIMP(typ='I', statut='o',defaut=100000, val_min=0), \r
+ TypeDeDeversement = SIMP(typ= 'TXM', into = ['CapaciteFixe', 'NonAutorise', 'DebitMaxGestion']),\r
+ b_Turbine_CapaciteFixe = BLOC( condition = 'TypeDeDeversement == "CapaciteFixe"', \r
+ Capacite = SIMP(typ='I', defaut=0, val_min=0),\r
+ ), \r
+ HauteurChute = SIMP(typ='R', defaut=0, statut='o', val_min=0),\r
+ Puissance = SIMP(typ='R', defaut=0,statut='o', val_min=0),\r
+ Debit = SIMP(typ='R', defaut=0, statut='o', val_min=0),\r
+ BandePrimaire = SIMP(typ='R', defaut=0 , statut='o', val_min=0),\r
+ BandeSecondaire = SIMP(typ='R', defaut=0, statut='o', val_min=0),\r
+ ),\r
+ ), # fin Turbine\r
+ b_TypeDUsine_Pompe = BLOC( condition = 'TypeDUsine == "Pompe"',\r
+ fr="Caractéristiques spécifiques aux pompes",\r
+ CaracteristiquesPompe=FACT( statut='o',\r
+ DebitMaxPhysique = SIMP(typ='I', statut='o',defaut=-100000, val_max=0),\r
+ HauteurChute = SIMP(typ='R', defaut=0, statut='o', val_min=0),\r
+ Puissance = SIMP(typ='R', defaut=0, statut='o', val_min=0),\r
+ Debit = SIMP(typ='R', defaut=0, statut='o', val_min=0),\r
+ ),\r
+ ), # fin Pompe\r
+ b_TypeDUsine_NonEnergetique = BLOC( condition = 'TypeDUsine == "NonEnergetique"',\r
+ CaracteristiquesNonEnergetique=FACT( statut='o',\r
+ DebitMaxPhysique = SIMP(typ='I', statut='o', defaut=100000, val_min=0),\r
+ ),\r
+ ),\r
+ b_TypeDUsine = BLOC( condition = 'TypeDUsine != None',\r
+ DelaiAval = SIMP(typ='I', statut='o',defaut=0, val_min=0),\r
+ UniteHauteurChute = SIMP(typ="TXM", statut='o', into=unitesChute, defaut="hm3"),\r
+ Interpolation = SIMP(typ="TXM", statut='o', into=["EnVolume", "EnCote"], defaut="EnCote"),\r
+ ReservoirAmont = SIMP(typ=reservoir,statut='o'),\r
+ b_DelaiAval_NonNul = BLOC( condition = "DelaiAval != 0",\r
+ ReservoirAval = SIMP(typ=reservoir,statut='o'),\r
+ ),\r
+ ), # fin bloc commun\r
+ ), # fin Usine\r
+ \r
+ ), # Usines\r
+)\r
+++ /dev/null
-# -*- coding: utf-8 -*-\r
-# Copyright (C) 2008-2018 EDF R&D\r
-#\r
-# This file is part of SALOME ADAO module\r
-#\r
-# This library is free software; you can redistribute it and/or\r
-# modify it under the terms of the GNU Lesser General Public\r
-# License as published by the Free Software Foundation; either\r
-# version 2.1 of the License.\r
-#\r
-# This library is distributed in the hope that it will be useful,\r
-# but WITHOUT ANY WARRANTY; without even the implied warranty of\r
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU\r
-# Lesser General Public License for more details.\r
-#\r
-# You should have received a copy of the GNU Lesser General Public\r
-# License along with this library; if not, write to the Free Software\r
-# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA\r
-#\r
-# See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com\r
-import os\r
-from Accas import OPER, BLOC, FACT, SIMP, ASSD, JDC_CATA, VerifTypeTuple, Matrice, UserASSD\r
-from Extensions.i18n import tr\r
-import types\r
-monFichier = os.path.abspath(__file__)\r
-\r
-JdC = JDC_CATA(\r
- code='Morgane',\r
- fr = "Modèle physique d'une vallée",\r
-)\r
-VERSION_CATALOGUE = 'V_0'\r
-\r
-class vallee(ASSD) : pass\r
-class usine(UserASSD) : pass\r
-class reservoir(UserASSD) : pass\r
-\r
-unitesChute=['hm3','m3']\r
-\r
-Vallee=OPER(nom="Vallee", sd_prod=vallee,\r
- fr="Elément défini pour éventuellement contenir la définition des vallées de manière autonome. Les contraintes sont définies au niveau de l'élément et doivent donc être répétées si le type est utilisé ailleurs",\r
- Reservoirs=FACT(statut='o', \r
- Reservoir = FACT ( statut ='o', max='**', \r
- NomReservoir = SIMP(statut='o', typ=(reservoir,'createObject'),), \r
- TypeReservoir = SIMP(statut='o', typ= 'TXM', into = ['Lac', 'Eclusee',]), \r
- Volume = SIMP(statut='o', typ= 'R', defaut=0, val_min=0,),\r
- Surface = SIMP(statut='o', typ= 'R'),\r
- CotesVolume = FACT(statut='f',\r
- fr="Si, quelque part dans l'étude (usine ou réservoir), il y a des cotes (ie on travaille en mètres), il faut les cotes volumes car le coeur de calcul travaille en volume",\r
- CoteVolume = FACT (statut='o', max='**',\r
- Cote = SIMP(statut='o', typ='R', defaut=0, val_min=0),\r
- Volume = SIMP(statut='o', typ='R', defaut=0, val_min=0),\r
- Surface = SIMP(statut='o', typ='R', defaut=0, val_min=0),\r
- ),\r
- ),\r
- ),\r
- ), # Reservoirs\r
-\r
- Usines = FACT(statut ='o', \r
- fr="Attention, l'ordre des usines a une importance", \r
- Usine = FACT ( statut ='o', max='**', \r
- fr="Les usines sont des turbines, des pompes ou des non énergétiques. Leur description dépend de ce type",\r
- NomDUsine = SIMP(statut='o', typ=(usine,'createObject'),), \r
- TypeDUsine = SIMP(statut='o', typ= 'TXM', into = ['Turbine', 'Pompe', 'NonEnergetique']), \r
- b_TypeDUsine_Turbine = BLOC( condition = 'TypeDUsine == "Turbine"', \r
- CaracteristiquesTurbine=FACT( statut='o', \r
- fr="Caractéristiques spécifiques aux turbines", DebitMaxPhysique = SIMP(typ='I', statut='o',defaut=100000, val_min=0), \r
- TypeDeDeversement = SIMP(typ= 'TXM', into = ['CapaciteFixe', 'NonAutorise', 'DebitMaxGestion']),\r
- b_Turbine_CapaciteFixe = BLOC( condition = 'TypeDeDeversement == "CapaciteFixe"', \r
- Capacite = SIMP(typ='I', defaut=0, val_min=0),\r
- ), \r
- HauteurChute = SIMP(typ='R', defaut=0, statut='o', val_min=0),\r
- Puissance = SIMP(typ='R', defaut=0,statut='o', val_min=0),\r
- Debit = SIMP(typ='R', defaut=0, statut='o', val_min=0),\r
- BandePrimaire = SIMP(typ='R', defaut=0 , statut='o', val_min=0),\r
- BandeSecondaire = SIMP(typ='R', defaut=0, statut='o', val_min=0),\r
- ),\r
- ), # fin Turbine\r
- b_TypeDUsine_Pompe = BLOC( condition = 'TypeDUsine == "Pompe"',\r
- fr="Caractéristiques spécifiques aux pompes",\r
- CaracteristiquesPompe=FACT( statut='o',\r
- DebitMaxPhysique = SIMP(typ='I', statut='o',defaut=-100000, val_max=0),\r
- HauteurChute = SIMP(typ='R', defaut=0, statut='o', val_min=0),\r
- Puissance = SIMP(typ='R', defaut=0, statut='o', val_min=0),\r
- Debit = SIMP(typ='R', defaut=0, statut='o', val_min=0),\r
- ),\r
- ), # fin Pompe\r
- b_TypeDUsine_NonEnergetique = BLOC( condition = 'TypeDUsine == "NonEnergetique"',\r
- CaracteristiquesNonEnergetique=FACT( statut='o',\r
- DebitMaxPhysique = SIMP(typ='I', statut='o', defaut=100000, val_min=0),\r
- ),\r
- ),\r
- b_TypeDUsine = BLOC( condition = 'TypeDUsine != None',\r
- DelaiAval = SIMP(typ='I', statut='o',defaut=0, val_min=0),\r
- UniteHauteurChute = SIMP(typ="TXM", statut='o', into=unitesChute, defaut="hm3"),\r
- Interpolation = SIMP(typ="TXM", statut='o', into=["EnVolume", "EnCote"], defaut="EnCote"),\r
- ReservoirAmont = SIMP(typ=reservoir,statut='o'),\r
- b_DelaiAval_NonNul = BLOC( condition = "DelaiAval != 0",\r
- ReservoirAval = SIMP(typ=reservoir,statut='o'),\r
- ),\r
- ), # fin bloc commun\r
- ), # fin Usine\r
- \r
- ), # Usines\r
-)\r
--- /dev/null
+../WebTest/cata_Vallee.py
\ No newline at end of file
sys.path.append('/home/eric/FLASK/eficas.eecj.git/testFlask') #TODO : supprimer
from connectEficas import accasConnecteur
+#code='Morgane'
code='Essai'
from flask import Flask, request, render_template, url_for, jsonify, make_response, session, g, Response
ALLOWED_EXTENSIONS = set(['py','comm','txt', 'gif', 'png', 'jpg', 'jpeg', 'bmp', 'rar', 'zip', '7zip', 'doc', 'docx'])
IGNORED_FILES = set(['.gitignore'])
-#TODO:
-#from fileManagement import *
-
-def allowed_file(filename):
- return '.' in filename and \
- filename.rsplit('.', 1)[1].lower() in ALLOWED_EXTENSIONS
-
-
-def gen_file_name(filename):
- """
- If file was exist already, rename it and return a new name
- """
-
- i = 1
- while os.path.exists(os.path.join(app.config['UPLOAD_FOLDER'], filename)):
- name, extension = os.path.splitext(filename)
- filename = '%s_%s%s' % (name, str(i), extension)
- i += 1
-
- return filename
-
-
-def create_thumbnail(image):
- try:
- base_width = 80
- img = Image.open(os.path.join(app.config['UPLOAD_FOLDER'], image))
- w_percent = (base_width / float(img.size[0]))
- h_size = int((float(img.size[1]) * float(w_percent)))
- img = img.resize((base_width, h_size), PIL.Image.ANTIALIAS)
- img.save(os.path.join(app.config['THUMBNAIL_FOLDER'], image))
-
- return True
-
- except:
- print(traceback.format_exc())
- return False
-
-
-@app.route("/upload", methods=['GET', 'POST'])
-def upload():
- if request.method == 'POST':
- files = request.files['file']
-
- if files:
- filename = secure_filename(files.filename)
- filename = gen_file_name(filename)
- mime_type = files.content_type
-
- if not allowed_file(files.filename):
- result = uploadfile(name=filename, type=mime_type, size=0, not_allowed_msg="File type not allowed")
-
- else:
- # save file to disk
- uploaded_file_path = os.path.join(app.config['UPLOAD_FOLDER'], filename)
- files.save(uploaded_file_path)
-
- # create thumbnail after saving
- if mime_type.startswith('image'):
- create_thumbnail(filename)
-
- # get file size after saving
- size = os.path.getsize(uploaded_file_path)
-
- # return json for js call back
- result = uploadfile(name=filename, type=mime_type, size=size)
-
- return simplejson.dumps({"files": [result.get_file()]})
-
- if request.method == 'GET':
- # get all file in ./data directory
- files = [f for f in os.listdir(app.config['UPLOAD_FOLDER']) if os.path.isfile(os.path.join(app.config['UPLOAD_FOLDER'],f)) and f not in IGNORED_FILES ]
-
- file_display = []
-
- for f in files:
- size = os.path.getsize(os.path.join(app.config['UPLOAD_FOLDER'], f))
- file_saved = uploadfile(name=f, size=size)
- file_display.append(file_saved.get_file())
-
- return simplejson.dumps({"files": file_display})
-
- return redirect(url_for('index'))
-
-
-
-@app.route("/delete/<string:filename>", methods=['DELETE'])
-def delete(filename):
- file_path = os.path.join(app.config['UPLOAD_FOLDER'], filename)
- file_thumb_path = os.path.join(app.config['THUMBNAIL_FOLDER'], filename)
-
- if os.path.exists(file_path):
- try:
- os.remove(file_path)
-
- if os.path.exists(file_thumb_path):
- os.remove(file_thumb_path)
-
- return simplejson.dumps({filename: 'True'})
- except:
- return simplejson.dumps({filename: 'False'})
-
-
-# serve static files
-@app.route("/thumbnail/<string:filename>", methods=['GET'])
-def get_thumbnail(filename):
- return send_from_directory(app.config['THUMBNAIL_FOLDER'], filename=filename)
-
-
-@app.route("/data/<string:filename>", methods=['GET'])
-def get_file(filename):
- return send_from_directory(os.path.join(app.config['UPLOAD_FOLDER']), filename=filename)
-
-
-# @app.route("/_upload", methods=['POST'])
-# def _upload():
-
-# # Validate the request body contains JSON
-# if request.is_json:
-# # Parse the JSON into a Python dictionary
-# req = request.get_json()
-# # Print the dictionary
-# uploadRequest=json.dumps([req],indent=4); #TODO : remove indent if not DEBUG
-# pprint(uploadRequest);
-
-# return make_response(json.dumps( {'source':node, 'changeIsAccepted' : changeDone, 'message': message} ))
-# # Return a string along with an HTTP status code
-# # return "JSON received!", 200
-# else:
-# print(request)
-# files = request.files['files']
-# if files:
-# result=catalogs.save(files)
-# return make_response(json.dumps( {"files": ["coucou"]} ))
-# # if request.method == 'POST' and 'files' in request.files:
-
-
-# # The request body wasn't JSON so return a 400 HTTP status code
-# return "Request was not JSON", 400
-# #return make_response(jsonify({"message": "Request body must be JSON"}), 400)
-
-# For example, you may want to override how request parameters are handled to preserve their order:
-# from flask import Flask, Request
-# from werkzeug.datastructures import ImmutableOrderedMultiDict
-# class MyRequest(Request):
-# """Request subclass to override request parameter storage"""
-# parameter_storage_class = ImmutableOrderedMultiDict
-# class MyFlask(Flask):
-# """Flask subclass using the custom request class"""
-# request_class = MyReq
### Server Side Event config
app.config["REDIS_URL"] = "redis://localhost"
# sse.publish({"message": "Hello!"}, type='update')
# return "Message sent!"
-@app.route('/')
-def index():
- tree4treeview = """ [
- {
- "text": "Parent 1",
- "nodes": [
- {
- "text": "Child 1.1",
- "nodes": [
- {
- "text": "Grandchild 1.1"
- },
- {
- "text": "Grandchild 1.2"
- }
- ]
- },
- {
- "text": "Child 1.2",
- "nodes": [
- {
- "text": "Grandchild 1.1"
- },
- {
- "text": "Grandchild 1.2"
- }
- ]
- },
- {
- "text": "Child 2"
- }
- ]
- },
- {
- "text": "Parent 2"
- },
- {
- "text": "<span class='icon node-icon' id='idtest0'>Parent 3</span>",
- "nodes": [{"text":"<span class='icon node-icon' id='idtest1'>3.5</span>"}]
- },
- {
- "txt": "Parent 4"
- },
- {
- "text": "Parent 5"
- }
- ]
- """.replace('\n','')
-
- treeB = """ [
- {
- "nodes": [
- {
- "text": "Child 1.1",
- "nodes": [
- {
- "text": "Grandchild 1.1"
- },
- {
- "text": "Grandchild 1.2"
- }
- ]
- }
- ]
- }
- ]
- """.replace('\n','')
-
-
- tree4Fancy = """ [
- {"title": "Node 1", "key": "1"},
- {"title": "Folder 2", "key": "2", "folder": true, "children": [
- {"title": "Node 2.1", "key": "3"},
- {"title": "Node 2.2", "key": "4"}
- ]}
- ]
- """.replace('\n','')
-
- print("treeB : %s"%treeB);
-
- dictC={'nodes': [{'text': 'Child 1.1', 'nodes': [{'text': 'Grandchild 1.1'}, {'text': 'Grandchild 1.2'}]}]}
- treeC=[dictC]
-
- # print("mytree : %s"%mytree);
- mcTraite={'MonProc2': {'s1': ('I', 2), 'F2': {'s2': ('I', 3), 'F3': {'s3': ('I', 4)}}}};
-
- monConnecteur.litFichierComm('../WebTest/web_tres_simple_avec_2Fact.comm')
- #monConnecteur.litFichierComm('../WebTest/edg_REP1300_FULL_PN.comm')
- #myTreeDico=monConnecteur.getDicoObjetsCompletsPourTree(monConnecteur.monEditeur.tree.racine)
- myFancyTreeDico=monConnecteur.getDicoForFancy(monConnecteur.monEditeur.tree.racine)
- print (myFancyTreeDico)
-
- #myTreeJS=json.dumps([myTreeDico])
- myFancyTreeJS=json.dumps([myFancyTreeDico])
- myFancyTreeJS=json.dumps([myFancyTreeDico],indent=4) #TODO : remove indent if not DEBUG
-
- print("---- myFancyTreeDico ----")
- pprint(myFancyTreeDico)
- print("---- myFancyTreeJS ----")
- pprint( myFancyTreeJS)
-
- return render_template('commandes_2.html',
- titre=code,
- listeCommandes = monConnecteur.getListeCommandes(),
- # profondeur=4,
- mcTraite={'MonProc2': {'s1': ('I', 2), 'F2': {'s2': ('I', 3), 'F3': {'s3': ('I', 4)}}}},
- mcTraiteJson=json.dumps(mcTraite),
- tree=myFancyTreeJS,
- # tree=tree4Fancy,
- # tree=myTreeJS
- # tree='['+myTreeJS+']'
- )
- # etape = str(escape(request.args.get("etape", "")))
## WebApp -> Eficas :
# Pour SIMP : Ajoute, Supprime (MC facultatif), Change la valeur
return "Request was not JSON", 400
#return make_response(jsonify({"message": "Request body must be JSON"}), 400)
+@app.route("/updateSDName", methods=['POST'])
+def updateSDName():
+ # Validate the request body contains JSON
+ if request.is_json:
+ # Parse the JSON into a Python dictionary
+ req = request.get_json()
+ # Print the dictionary
+ print(req)
+ print(req['id'])
+ id=req['id'];value=req['value']
+ # id, value = req.values() # Dangereux correspondance implicite
+ value = str(value) #On peut écrire Pi
+ rId,message,changeDone = monConnecteur.updateSDName(id,value);
+ assert(rId==id)
+ #changeDone = True
+ print ("changeDone : ",changeDone)
+
+ #return make_response(json.dumps( {'id':id , 'changeIsAccepted' : changeDone, 'message': message} ))
+ return make_response(json.dumps( {'changeIsAccepted' : changeDone, 'message': message} ))
+ # Return a string along with an HTTP status code
+ # return "JSON received!", 200
+ else:
+ # The request body wasn't JSON so return a 400 HTTP status code
+ return "Request was not JSON", 400
+ #return make_response(jsonify({"message": "Request body must be JSON"}), 400)
+
@app.route("/removeNode", methods=['POST'])
def removeNode():
return "Request was not JSON", 400
#return make_response(jsonify({"message": "Request body must be JSON"}), 400)
+@app.route('/')
+def index():
+
+ # tree4Fancy = """ [
+ # {"title": "Node 1", "key": "1"},
+ # {"title": "Folder 2", "key": "2", "folder": true, "children": [
+ # {"title": "Node 2.1", "key": "3"},
+ # {"title": "Node 2.2", "key": "4"}
+ # ]}
+ # ]
+ # """.replace('\n','')
+
+
+ monConnecteur.litFichierComm('../WebTest/web_tres_simple_avec_2Fact.comm')
+ #monConnecteur.litFichierComm('../WebTest/edg_REP1300_FULL_PN.comm')
+ myFancyTreeDico=monConnecteur.getDicoForFancy(monConnecteur.monEditeur.tree.racine)
+ #print (myFancyTreeDico)
+
+ #myFancyTreeJS=json.dumps([myFancyTreeDico])
+ myFancyTreeJS=json.dumps([myFancyTreeDico],indent=4) #TODO : remove indent if not DEBUG
+
+ print("---- myFancyTreeDico ----")
+ pprint(myFancyTreeDico)
+ print("---- myFancyTreeJS ----")
+ pprint( myFancyTreeJS)
+
+ return render_template('commandes_2.html',
+ titre=code,
+ listeCommandes = monConnecteur.getListeCommandes(),
+ tree=myFancyTreeJS,
+ # tree=tree4Fancy,
+ )
+ # etape = str(escape(request.args.get("etape", "")))
+
+
@app.route("/forward/", methods=['POST'])
def move_forward():
return make_response(jsonify({"message": "Request body must be JSON"}), 400)
+#TODO:
+#from fileManagement import *
+
+def allowed_file(filename):
+ return '.' in filename and \
+ filename.rsplit('.', 1)[1].lower() in ALLOWED_EXTENSIONS
+
+
+def gen_file_name(filename):
+ """
+ If file was exist already, rename it and return a new name
+ """
+
+ i = 1
+ while os.path.exists(os.path.join(app.config['UPLOAD_FOLDER'], filename)):
+ name, extension = os.path.splitext(filename)
+ filename = '%s_%s%s' % (name, str(i), extension)
+ i += 1
+
+ return filename
+
+
+def create_thumbnail(image):
+ try:
+ base_width = 80
+ img = Image.open(os.path.join(app.config['UPLOAD_FOLDER'], image))
+ w_percent = (base_width / float(img.size[0]))
+ h_size = int((float(img.size[1]) * float(w_percent)))
+ img = img.resize((base_width, h_size), PIL.Image.ANTIALIAS)
+ img.save(os.path.join(app.config['THUMBNAIL_FOLDER'], image))
+
+ return True
+
+ except:
+ print(traceback.format_exc())
+ return False
+
+
+@app.route("/upload", methods=['GET', 'POST'])
+def upload():
+ if request.method == 'POST':
+ files = request.files['file']
+
+ if files:
+ filename = secure_filename(files.filename)
+ filename = gen_file_name(filename)
+ mime_type = files.content_type
+
+ if not allowed_file(files.filename):
+ result = uploadfile(name=filename, type=mime_type, size=0, not_allowed_msg="File type not allowed")
+
+ else:
+ # save file to disk
+ uploaded_file_path = os.path.join(app.config['UPLOAD_FOLDER'], filename)
+ files.save(uploaded_file_path)
+
+ # create thumbnail after saving
+ if mime_type.startswith('image'):
+ create_thumbnail(filename)
+
+ # get file size after saving
+ size = os.path.getsize(uploaded_file_path)
+
+ # return json for js call back
+ result = uploadfile(name=filename, type=mime_type, size=size)
+
+ return simplejson.dumps({"files": [result.get_file()]})
+
+ if request.method == 'GET':
+ # get all file in ./data directory
+ files = [f for f in os.listdir(app.config['UPLOAD_FOLDER']) if os.path.isfile(os.path.join(app.config['UPLOAD_FOLDER'],f)) and f not in IGNORED_FILES ]
+
+ file_display = []
+
+ for f in files:
+ size = os.path.getsize(os.path.join(app.config['UPLOAD_FOLDER'], f))
+ file_saved = uploadfile(name=f, size=size)
+ file_display.append(file_saved.get_file())
+
+ return simplejson.dumps({"files": file_display})
+
+ return redirect(url_for('index'))
+
+
+
+@app.route("/delete/<string:filename>", methods=['DELETE'])
+def delete(filename):
+ file_path = os.path.join(app.config['UPLOAD_FOLDER'], filename)
+ file_thumb_path = os.path.join(app.config['THUMBNAIL_FOLDER'], filename)
+
+ if os.path.exists(file_path):
+ try:
+ os.remove(file_path)
+
+ if os.path.exists(file_thumb_path):
+ os.remove(file_thumb_path)
+
+ return simplejson.dumps({filename: 'True'})
+ except:
+ return simplejson.dumps({filename: 'False'})
+
+
+# serve static files
+@app.route("/thumbnail/<string:filename>", methods=['GET'])
+def get_thumbnail(filename):
+ return send_from_directory(app.config['THUMBNAIL_FOLDER'], filename=filename)
+
+
+@app.route("/data/<string:filename>", methods=['GET'])
+def get_file(filename):
+ return send_from_directory(os.path.join(app.config['UPLOAD_FOLDER']), filename=filename)
+
+
+# @app.route("/_upload", methods=['POST'])
+# def _upload():
+
+# # Validate the request body contains JSON
+# if request.is_json:
+# # Parse the JSON into a Python dictionary
+# req = request.get_json()
+# # Print the dictionary
+# uploadRequest=json.dumps([req],indent=4); #TODO : remove indent if not DEBUG
+# pprint(uploadRequest);
+
+# return make_response(json.dumps( {'source':node, 'changeIsAccepted' : changeDone, 'message': message} ))
+# # Return a string along with an HTTP status code
+# # return "JSON received!", 200
+# else:
+# print(request)
+# files = request.files['files']
+# if files:
+# result=catalogs.save(files)
+# return make_response(json.dumps( {"files": ["coucou"]} ))
+# # if request.method == 'POST' and 'files' in request.files:
+
+
+# # The request body wasn't JSON so return a 400 HTTP status code
+# return "Request was not JSON", 400
+# #return make_response(jsonify({"message": "Request body must be JSON"}), 400)
+
+# For example, you may want to override how request parameters are handled to preserve their order:
+# from flask import Flask, Request
+# from werkzeug.datastructures import ImmutableOrderedMultiDict
+# class MyRequest(Request):
+# """Request subclass to override request parameter storage"""
+# parameter_storage_class = ImmutableOrderedMultiDict
+# class MyFlask(Flask):
+# """Flask subclass using the custom request class"""
+# request_class = MyReq
+
if __name__ == "__main__":
app.run(host="localhost", port=8321, debug=True)
--- /dev/null
+# -*- coding: utf-8 -*-
+# maConfiguration MANAGEMENT OF EDF VERSION
+# ======================================================================
+# COPYRIGHT (C) 2007-2021 EDF R&D
+# THIS PROGRAM IS FREE SOFTWARE; YOU CAN REDISTRIBUTE IT AND/OR MODIFY
+# IT UNDER THE TERMS OF THE GNU GENERAL PUBLIC LICENSE AS PUBLISHED BY
+# THE FREE SOFTWARE FOUNDATION; EITHER VERSION 2 OF THE LICENSE, OR
+# (AT YOUR OPTION) ANY LATER VERSION.
+#
+# THIS PROGRAM IS DISTRIBUTED IN THE HOPE THAT IT WILL BE USEFUL, BUT
+# WITHOUT ANY WARRANTY; WITHOUT EVEN THE IMPLIED WARRANTY OF
+# MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. SEE THE GNU
+# GENERAL PUBLIC LICENSE FOR MORE DETAILS.
+#
+# YOU SHOULD HAVE RECEIVED A COPY OF THE GNU GENERAL PUBLIC LICENSE
+# ALONG WITH THIS PROGRAM; IF NOT, WRITE TO EDF R&D CODE_ASTER,
+# 1 AVENUE DU GENERAL DE GAULLE, 92141 CLAMART CEDEX, FRANCE.
+#
+#
+# ======================================================================
+
+import os,sys
+# repIni sert a localiser le fichier editeur.ini
+# Obligatoire
+repIni=os.path.dirname(os.path.abspath(__file__))
+INSTALLDIR=os.path.join(repIni,'..')
+sys.path[:0]=[INSTALLDIR]
+
+
+# lang indique la langue utilisee pour les chaines d'aide : fr ou ang
+lang='ang'
+
+# Codage des strings qui accepte les accents (en remplacement de 'ascii')
+encoding='iso-8859-1'
+code = 'Morgane'
+
+#
+catalogues=(
+ ('Morgane','Morgane',os.path.join(repIni,'cata_Vallee.py'),'python','python'),
+)
<script src="https://cdn.jsdelivr.net/npm/bootstrap-select@1.13.14/dist/js/bootstrap-select.min.js"></script>
<!-- (Optional) Latest compiled and minified JavaScript translation files -->
<script src="https://cdn.jsdelivr.net/npm/bootstrap-select@1.13.14/dist/js/i18n/defaults-*.min.js"></script>
+
+
+ <!-- Add the tablenavigator javascript and CSS file -->
+ <!-- <script src="{{ url_for('static', filename='tablenavigator.jquery.js') }}"></script> -->
+
+ <!-- Add the handsontable javascript and CSS file -->
+ <script type="text/javascript" src="https://cdn.jsdelivr.net/npm/handsontable/dist/handsontable.full.min.js"></script>
+ <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/handsontable/dist/handsontable.full.min.css" />
+
<meta name="description" content={{description}}>
<!-- <link rel="shortcut icon" href="../images/favicon-32x32.png"> -->
{% block content %}
-<!-- {%- for key, value in mcTraite.items() recursive %} -->
-<!-- <h3>{{ key }} </h3> -->
-<!-- {%- if value %} -->
-<!-- {% if value is mapping %} -->
-<!-- <ul>{{ loop(value.items())}}</ul> -->
-<!-- {%- else %} -->
-<!-- type {{value[0]}} valeur{{value[1]}} -->
-<!-- {%- endif %} -->
-<!-- {%- endif %} -->
+
+<!-- {#- for key, value in mcTraite.items() recursive #} -->
+<!-- <h3>{#{ key }#} </h3> -->
+<!-- {#- if value #} -->
+<!-- {# if value is mapping #} -->
+<!-- <ul>{#{ loop(value.items())}#}</ul> -->
+<!-- {#- else #} -->
+<!-- type {#{value[0]}#} valeur{#{value[1]}#} -->
+<!-- {#- endif #} -->
+<!-- {#- endif #} -->
<!-- <\!-- </li> -\-> -->
-<!-- {%- endfor %} -->
+<!-- {#- endfor #} -->
<!-- <div id="tree2"></div> -->
</div> <!-- col -->
</div> <!-- row -->
+
+ <div id='handsontable_test1'/>
+
<script>
+
+const handsontable_data0 = [
+ { id: 1, name: 'Ted Right', address: '',col3: 3, col4: 4, col5: 5, col6: 6 },
+ { id: 2, name: 'Frank Honest', address: '' },
+ { id: 3, name: 'Joan Well', address: '' },
+ { id: 4, name: 'Gail Polite', address: '' },
+ { id: 5, name: 'Michael Fair', address: '' },
+];
+const handsontable_data1 = [
+ { id: 1, name: 'Ted Right', address: '',col3: 3, col4: 4, col5: 5, col6: 6 },
+ { id: 2, name: 'Frank Honest', address: '' },
+ { id: 3, name: 'Joan Well', address: '' },
+ { id: 4, name: 'Gail Polite', address: '' },
+ { id: 5, name: 'Michael Fair', address: '' },
+];
+
+ <!-- const container0= document.getElementById('handsontable_test1'); -->
+ <!-- const hot0 = new Handsontable(container0, { -->
+ <!-- data: handsontable_data0, -->
+ <!-- colHeaders: false, -->
+ <!-- height: 'auto', -->
+ <!-- width: 'auto', -->
+ <!-- minSpareRows: 0, -->
+ <!-- licenseKey: 'non-commercial-and-evaluation' -->
+ <!-- }); -->
+
//$("#navbar-optionals").affix({offset: {top: $("#row-commands_menu").outerHeight(true)} });
$("#col-optional_tree").affix({offset: {top: $("#row-commands_menu").outerHeight(true)} }).css('right',0);
</script>
});
});
-//$.ui.fancytree.debugLevel=4; // Set the fancyTree debug level
+// if tree.options.debug is null: use global setting $.ui.fancytree.debugLevel)
+// $.ui.fancytree.debugLevel=4; // Set the fancyTree debug level
-//Créer une fonction pour désactiver toutes les classes d'alert pour positionner une seule
+//Créer une fonction pour désactiver toutes les classes d'alert et pour en positionner une seule
let treeMessage=function(msgCssSelStr,messageClass,message) {
const messageClasses = new Set(["alert-success","alert-info","alert-warning","alert-danger"]);
if (messageClasses.has(messageClass)) {
$.ui.fancytree.info(message); // debugLevel >= 3
} else {
console.debug(message); // debugLevel >= 4
+ $.ui.fancytree.debug(message); // debugLevel >= 4
};
$(msgCssSelStr).text(message);
} else {
treeMessage(_msgCssSelStr,"alert-danger",msgerror);
return;
};
- console.log("------------- message 2a: "+ node.data.title);
- console.log("------------- message 2b: "+ info.title);
+ // console.log("------------- message 2a: "+ node.data.title);
+ // console.log("------------- message 2b: "+ info.title);
// En fait, il faut que fancytree trie les propriétés qui l'interesse de celles qui vont dans data
// Object.assign(node.data,info); //merge new options to node.data
node.fromDict(info);
- console.log("------------- message 2c: "+ node.data.title);
+ // console.log("------------- message 2c: "+ node.data.title);
node.render(true,false); //force rendering the node (not parents nor descendants)
//node.renderStatus(); //CSS element updates only
}, false);
}
- // function getTree2() {
- // // Some logic to retrieve, or generate tree structure
- // return {{ mcTraiteJson|tojson }};
- // }
// $("#tree1").fancytree({ source: [ {title: "Node 1", key: "1000"},{title: "Folder 2", key: "2", folder: true, children: [ {title: "Node 2.1", key: "3000"},{title: "Node 2.2", key: "44"} ]} ], })
$(function(){
$("#tree1").fancytree({
//focusOnSelect:true,
- debug:4,
+ debug:4, //if null: use global setting $.ui.fancytree.debugLevel
+ debuLevel:4, //if null: use global setting $.ui.fancytree.debugLevel
//extensions: ["dnd5", "edit", "glyph", "wide", "table", "gridnav"],
- extensions: [ "glyph", "table", "ariagrid"],
+ extensions: [ "glyph", "table", "ariagrid"], // https://github.com/mar10/fancytree/wiki/ExtTable
//extensions: [ "glyph", "table", "gridnav"],
checkbox: true, // Activate the use of checkboxes next to the nodes
},
gridnav: {
autofocusInput: true, // Focus first embedded input if node gets activated
- handleCursorKeys: true // Allow UP/DOWN in inputs to move to prev/next node
+ handleCursorKeys: false // Allow UP/DOWN in inputs to move to prev/next node
},
ariagrid: {
cellFocus: 'allow'
// data.result = {url: "ajax-sub2.json", debugDelay: 1000};
//}
// renderStatusColumns: Pour le CSS
- renderColumns: function(event, data) {
+ renderColumns: function(event, data) { //TODO : use createNode event to avaoid recreating content when rendering
// Pour tester ds la console :
//var tree=$.ui.fancytree.getTree("#tree1")
const node = data.node,
$tdList = $(node.tr).find(">td");
- const classeAccas = node.data.classeAccas;
+ const classeAccas = node.data.classeAccas; //TODO : Utiliser les types fancytree
const validite = node.data.validite;
const wValue = node.data.wValue;
const statut = node.data.statut;
- const cmdName = node.data.nomCommande; // undefined if classeAccas != 'MCFACT'
- const repeatable = node.data.repetable; // ?? undefined if classeAccas != 'MCFACT' ??
+ const cmdName = node.data.nomCommande; // undefined if classeAccas != 'MCFACT'
+ const repeatable = node.data.repetable; // ?? undefined if classeAccas != 'MCFACT' ??
const infoOptionnels = node.data.infoOptionnels;
const key = node.key;
const name = node.title;
"<form>"+
"<div class='form-group'>" +
"<input type='input' class='form-control input-sm' id='"+key+"' placeholder='"
- + wValue + //TODO:intosugg
- "' value='"+wValue+"' required>"+
+ + wValue + //TODO:intosugg
+ "' value='"+wValue+"' required>"+
+ // "<input type='input' class='form-control input-sm' id='"+key+"' placeholder='"
+ // + wValue + //TODO:intosugg
+ // "' value='"+wValue+"' required>"+
+ "<div id='handsontable_"+key+"' />"+
"</div>"+
- "</form>"
+ "</form>"
)
.addClass(_attr)
.find("input").css('color','black'); //TODO : A placer ds le CSS
+ // const container = document.getElementById('handsontable_'+key);
+ // const hot = new Handsontable(container, {
+ // data: handsontable_data0,
+ // colHeaders: false,
+ // height: 'auto',
+ // width: 'auto',
+ // minSpareRows: 1,
+ // licenseKey: 'non-commercial-and-evaluation'
+ // });
+ // hot.render();
+ // hot.addHook('afterCreateRow', (row, amount) => {
+ // console.log(`${amount} row(s) were created, starting at index ${row}`);
+ // });
}; // Not classeAccas == "MCSIMP"
let buildOptionalTreeSrc=function(node) {
if ( node == null ) return [];
- let parentList = node.getParentList(false,true); // default : (false,false)==(rootNode exclus, not self)
+ let parentList = node.getParentList(false,hasOpt(node)); // default : (false,false)==(rootNode exclus, not self)
if ( parentList.length > 0 ) { parentList=parentList.slice(1);}; // The first node is the current dataset name node
// La construction des optionals en suivant les parents fonctionnent car les SIMP ne portent pas les optionnals
// [ {title: "Node 1"}, {title: "Folder 2", children: [ {title: "Node 2.1"}, {title: "Node 2.2"} ]} ]
// },
defaultGridAction: function( event, data ) { //(used by ext-aria) The user hit enter on the active row or cell.
+ //return true;
const node = data.node
// var rValue,rValidite,rChangeIsAccepted
const _msgCssSelStr='#tree1-messages'; //TODO: A déplacer
// Return false to prevent default
// data.activeTd contains the currently active <td> element or null
// data.colIdx contains the 0-based column index or -1
- // console.log("event.type, data :"+event.type+" , "+data);
if( !data.activeTd ) {
alert( "Custom default action for row: " + data.node.title );
// we don't return false, so default action is applied:
//node.fromDict()
//source=JSON.parse(getTree1())
if ( changeIsAccepted ) {
- // $.ui.fancytree.assert(value == wValue); il faut gérer les représentations des types pour activer cet assert
+ // $.ui.fancytree.assert(value == wValue); il faut gérer les représentations des types pour activer cet assert (ex: string vs int)
node.data.wValue = wValue
node.data.validite = validite
treeMessage(_msgCssSelStr,"alert-success","Changing SIMP "+node.title+" value to "+value+" has been accepted.");
keydown: function(event, data) {
console.log("event.type, data :"+event.type+" , "+data);
},
+ // renderColumns: function(event, data) {
+ // console.log("event.type, data :"+event.type+" , "+data);
+ // },
+ renderStatusColumns: function(event, data) {
+ console.log("event.type, data :"+event.type+" , "+data);
+ },
+ renderNode: function(event, data) {
+ console.log("event.type, data :"+event.type+" , "+data);
+ },
});
});
// optTree=$optTree.fancytree()
// #var optTree=$.ui.fancytree.getTree("#bebe")
// optTree.expandAll()
+
+//TRICKS :
+// Tester si un objet existe :
+// if (typeof myObj !== "undefined" && myObj !== null)