# -*- coding: utf-8 -*- """ v.1.12 ajout de FieldSetFocus ajout de FieldPasteClip v.1.13 ajout de FieldBlur v.1.14 ajout de getField v.1.15 ajout de etat ajout de calljscript v.1.16 ajout de name (nom du fichier en mode explorateur de fichier) ajout de addressbar (visible ou cachée) ajout de menubar (visible ou cachée) ajout de statusbar (visible ou cachée) ajout de toolsbar (visible ou cachée) ajout de title (get ou set) ajout de left (position de la fenêtre du navigateur) ajout de top (position de la fenêtre du navigateur) ajout de width (taille de la fenêtre du navigateur) ajout de height (taille de la fenêtre du navigateur) v.1.17 ajout de connectid (retourne un objet pointant sur un élément HTML idéntifié par son ID) v.1.18 transfert de Tablet de calljscript (appel d'une fonction javascript) modif de Tablet de loadLists (gestion des scripts) transfert de Tablet de strScripts (liste du contenu des scripts) transfert de Tablet de setScript (affecte (met) un script ; non-fonctionnel) transfert de Tablet de FieldChange (force le onChange) transfert de Tablet de GetHead (retourne le
) v.1.19 accès au noeud racine 'window' du DOM ajout d'un attribut 'document', synomyne de 'ie.doc', pour accès au noeud'document' du DOM v.1.20 possibilité visible/invisible à l'ouverture v.1.21 ajout de alert v.1.22 modif mode de démarrage v.1.23 suppression qq messages de déboguage v.1.24 ajout de NavigUrlsuite v.1.25 modif initinstance v.1.26 correction mineure sur width et Width (majuscule 1ère lettre) propriété: width (minuscule) methode : Width() (Majuscule) self.ie.Width (minuscule) ajout de setbodyhtml( html) v.1.27 remplacement des fonctions width par fwidth et height par fheight propriété: width (minuscule) methode : fwidth() (minuscules) self.ie.Width (Majuscule) v.1.28 correction sur la connexion à une instance déjà ouverte (paramètre instanceurl) v.1.29 correction sur connexion à instance déjà ouverte : récupération de x,y,width,height sur l'instance, en ignorant x,y,width,height dans args v.1.30 ajout de traitefield (combinaison de focus + setfield v.1.31 loadslist conditionnel à plein d'endroit (grande accélération sur les grosses pages) if len(self.fields)<2 and len(self.links)<2: v.1.32 conversion du fichier-source en UTF-8 v.1.33 protection contre une erreur en recherchant la liste des liens, sur des pages vides v.1.34 protection contre une erreur en recherchant le nom d'un élément sans nom v.1.35 protection contre une erreur en recherchant le type d'un élément vide v.1.36 protection contre une erreur en listant les boutons ou les submit, s'il n'y a pas de formulaire v.1.37 remplacement des '==None' par 'is None' v.1.38 ajout paramètres à l'ouverture : ToolBar(False), AddressBar(False), MenuBar(False), StatusBar(True) v.1.39 ajout paramètres à l'ouverture : attendurl, attend 12 s qu'une instance soit ouverte sur cette adresse v.1.40 ajout de setbodyinnerhtml v.1.41 suppression de la connection à self.window systématique (navigUrl et navigUrlsuite) ajout de la méthode trouvewindow(self) Divers: http://msdn.microsoft.com/en-us/library/aa752084(VS.85).aspx http://msdn.microsoft.com/en-us/library/aa752043(v=VS.85).aspx erreurs HTML/web http://msdn.microsoft.com/en-us/library/aa384325(v=VS.85).aspx """ import win32com.client import win32clipboard import ctypes import time GlobalPVersion='1.41' import sys #*** piqué à Ponx *** def clipboardtxt(chaine=None): global chaineretour import win32clipboard,win32con try: win32clipboard.OpenClipboard() if chaine is None: try: chaine=win32clipboard.GetClipboardData(win32con.CF_TEXT) #win32clipboard.EmptyClipboard() #win32clipboard.SetClipboardText(chaine) chaineretour=chaine return(chaine) except: chaineretour='' return('') else: try: win32clipboard.EmptyClipboard() win32clipboard.SetClipboardText(chaine) except: pass except: pass try: win32clipboard.CloseClipboard() except: pass def u1252(chu): try: if type(chu) is unicode: return chu.encode('cp1252','replace') else: return chu except: return repr(chu) def u850(chu): try: if type(chu) is unicode: return chu.encode('cp850','replace') else: return chu.decode('cp1252').encode('cp850','replace') except: return repr(chu) def u437(chu): try: if type(chu) is unicode: return chu.encode('cp437','replace') else: return chu.decode('cp1252').encode('cp437','replace') except: return repr(chu) def upe(chu): return str(chu) class sout(object): def __init__(self): self.buf='' def pr(self,*txt): for i in txt: self.buf=self.buf+' '+i.encode('cp1252','replace') self.buf=self.buf+'\r\n' def prrc(self,*txt): for i in txt: self.buf=self.buf+i.encode('cp1252','replace')+'\r\n' def pt(self,*txt): for i in txt: self.buf=self.buf+i.encode('cp1252','replace')+' ' def raz(self): self.buf='' def sprint(self): print self.buf class IEpilot(object): def __init__(self, url=None, visible=1, **args): args.setdefault('instanceurl',None) args.setdefault('attendurl',None) args.setdefault('x',200) args.setdefault('y',100) args.setdefault('width',400) args.setdefault('height',300) args.setdefault('ToolBar',False) args.setdefault('AddressBar',False) args.setdefault('MenuBar',False) args.setdefault('StatusBar',True) args.setdefault('ToolBar',True) args.setdefault('AddressBar',True) args.setdefault('MenuBar',True) args.setdefault('StatusBar',True) for k,v in args.items(): setattr(self,k,v) self.doc='' self.links=[] self.link={} self.forms=[] self.form={} self.nbforms=0 self.felems=[] self.fields=[] self.fieldTyp={} self.fieldVposs={} self.field={} self.buttons=[] self.button={} self.scripts=[] self.script={} self.flagnew=True self.ie=None if self.attendurl is not None: nbs=12*4 flagcontinue=True while flagcontinue and nbs>0: clsid= '{9BA05972-F6A8-11CF-A442-00A0C90A8F39}' hie=win32com.client.Dispatch(clsid) for instance in hie: #print 236,instance.LocationURL, self.attendurl, (instance.LocationURL.startswith(self.attendurl)) #import ponx #ponx.msginfo("206",str(instance.LocationURL)) ###if instance.LocationURL==self.attendurl: if instance.LocationURL.find(self.attendurl)>-1: self.ie=instance self.x=self.ie.Left self.y=self.ie.Top self.width=self.ie.Width self.height=self.ie.Height print 283 self.ToolBar=True #False self.AddressBar=True #False #self.setdefault=MenuBar=False #self.setdefault=StatusBar=False self.MenuBar=True self.StatusBar=True flagcontinue=False #print "Trouvé !!!!",252 break if flagcontinue: time.sleep(0.250) nbs-=1 return if self.instanceurl is not None: clsid= '{9BA05972-F6A8-11CF-A442-00A0C90A8F39}' hie=win32com.client.Dispatch(clsid) for instance in hie: #print 197,instance.LocationURL,instance.LocationURL==self.instanceurl #import ponx #ponx.msginfo("206",str(instance.LocationURL)) if instance.LocationURL==self.instanceurl: self.ie=instance #import ponx #ponx.msginfo("206",str(args)) self.x=self.ie.Left self.y=self.ie.Top self.width=self.ie.Width self.height=self.ie.Height break if self.ie is None: if url is None: url=self.instanceurl self.instanceurl=None if self.ie is None: self.ie=win32com.client.Dispatch('InternetExplorer.Application') #self.ie=win32com.client.DispatchEx('InternetExplorer.Application', machine='ServeurMCI', userName='Administrateur') #self.ie=win32com.client.dynamic.Dispatch('InternetExplorer.Application') #sel.ie._print_details_() #print self.ie.CLSID #marche pas sous win-2000 """ self.ie.ToolBar=False self.ie.AddressBar=False self.ie.MenuBar=False self.ie.StatusBar=True """ self.ie.ToolBar=self.ToolBar self.ie.AddressBar=self.AddressBar self.ie.MenuBar=self.MenuBar self.ie.StatusBar=self.StatusBar #print 343,self.MenuBar self.ie.ToolBar=True self.ie.AddressBar=True self.ie.MenuBar=True self.ie.StatusBar=True self.ie.Left=self.x self.ie.Top=self.y self.ie.Width=self.width self.ie.Height=self.height self.ie.Visible=visible if url is None and self.instanceurl is None: self.ie.Navigate('about:blank') else: if self.instanceurl is None: self.ie.Navigate(url) self.navigUrlsuite() #self.ie.Visible=visible #*** 13.11.05 v1.07 *** def initinstance(self, url): """se connecte sur une instance d'après l'URL """ clsid= '{9BA05972-F6A8-11CF-A442-00A0C90A8F39}' hie=win32com.client.Dispatch(clsid) for instance in hie: if instance.LocationURL==url: self.ie=instance if self.ie: self.waitBusy() self.doc=self.ie.Document self.flagnew=True #*** 13.11.05 v1.07 *** def navigInstance(self, idpar=0): """charge une page, d'après l'instance """ clsid= '{9BA05972-F6A8-11CF-A442-00A0C90A8F39}' hie=win32com.client.Dispatch(clsid) import types if type(idpar) is types.StringType: for instance in hie: #print "instance.LocationURL",instance.LocationURL if instance.LocationURL==idpar: self.ie=instance else: nb=0 for instance in hie: if nb==idpar: self.ie=instance nb+=1 if self.ie: self.waitBusy() self.doc=self.ie.Document self.flagnew=True def navigUrl(self,url): """charge une page, d'après son URL """ self.ie.Navigate(url) self.waitBusy() self.document=self.ie.Document self.doc=self.ie.Document self.body=self.ie.Document.Body ###self.window=self.ie.Document.parentWindow self.flagnew=True def navigUrlsuite(self): """comme navigUrl, mais après l'URL mise en place """ self.waitBusy() self.document=self.ie.Document self.doc=self.ie.Document self.body=self.ie.Document.Body ###self.window=self.ie.Document.parentWindow self.flagnew=True def trouvewindow(self): self.window=self.ie.Document.parentWindow # Attention, long ! #*** 19.11.06 v1.18 *** def calljscript(self,code): """appelle une fonction javascript """ self.ie.Navigate(' javascript:'+code) self.waitBusy() #*** 13.11.05 v1.08 *** @staticmethod def listInstances(): """liste les instances d'InternetExplorer """ clsid= '{9BA05972-F6A8-11CF-A442-00A0C90A8F39}' hie=win32com.client.Dispatch(clsid) st='' lret=[] nb=0 for instance in hie: st=st+str(nb)+' \t'+instance.LocationURL+'\r\n' lret.append([nb,instance.LocationURL]) nb+=1 return st,lret #*** 16.09.06 v1.15 *** def etat(self): """ Retourne True ou False, pour indiquer si l'instance d'I.E. est encore là """ try: self.ie.Busy vret=True except pythoncom.com_error: vret=False return vret def waitBusy(self): """attend qu'IE ait fini (soit prêt) """ while self.ie.Busy==True: time.sleep(0.125) #*** modif 19.11.06 v1.18 *** def loadLists(self): """charge les listes+dictionnaires de : liens (links) ; boutons (button/input) ; champs (submit) ; formulaires (form) """ if self.flagnew==True: n=0 self.fields=[] self.field={} self.buttons=[] self.button={} self.links=[] self.link={} self.scripts=[] self.script={} for tmp in self.doc.links: try: self.links.append(tmp.href) except: pass try: self.link[tmp.href]=tmp except: pass self.forms=self.doc.forms tmp=self.doc.all.tags("script") n=0 try: for i in tmp: n+=1 try: tname=i.name except: tname=str(n) try: tname=i.id except: tname=str(n) if tname is None: tname=str(n) tname=str(n) #print tname,type(tname) self.script[tname]=i self.scripts.append(tname) except: pass tmp=self.doc.all.tags("button") try: for i in tmp: tname=i.name if tname=='' or tname is None: tname=i.id self.button[tname]=i self.buttons.append(tname) except: pass tmp=self.doc.all.tags("submit") try: for i in tmp: tname=i.name if tname=='' or tname is None: tname=i.id self.field[tname]=i self.fields.append(tname) except: pass self.nbforms=self.doc.forms.length self.felems={} num=-1 for f in self.forms: num+=1 form=f.name if form=='' or form is None: form=f.id if form=='' or form is None: form=num self.form[form]=f self.felems[form]=self.doc.forms[num].elements #self.felems[form]=self.doc.forms[form].elements #ancienne version remplacée le 14.06.06 snum=-1 for i in self.felems[form]: snum+=1 try: tname=i.name except: tname='' if tname=='' or tname is None: try: tname=i.id except: tname='' if tname=='' or tname is None: tname=snum try: if i.type=='input' or i.type=='text' or i.type=='password' or i.type=='textfield' or i.type=='textarea': self.field[str(form)+'.'+str(tname)]=i self.fields.append(str(form)+'.'+str(tname)) self.fieldTyp[str(form)+'.'+str(tname)]=i.type if i.type=='select-one': self.field[str(form)+'.'+str(tname)]=i self.fields.append(str(form)+'.'+str(tname)) self.fieldTyp[str(form)+'.'+str(tname)]=i.type self.fieldVposs[str(form)+'.'+str(tname)]=[] for ii in i: self.fieldVposs[str(form)+'.'+str(tname)].append(ii.value) if i.type=='checkbox': self.field[str(form)+'.'+str(tname)]=i self.fields.append(str(form)+'.'+str(tname)) self.fieldTyp[str(form)+'.'+str(tname)]=i.type if i.type=='radio': self.button[str(form)+'.'+str(tname)+'.'+str(i.value)]=i self.buttons.append(str(form)+'.'+str(tname)+'.'+str(i.value)) if i.type=='submit' or i.type=='reset' or i.type=='button': self.button[str(form)+'.'+str(tname)+'.'+str(i.type)]=i self.buttons.append(str(form)+'.'+str(tname)+'.'+str(i.type)) except: pass #print i.name,' Type:',i.type,' value:',i.value,' id:',i.id self.flagnew==False def listLinks(self): """retourne la liste des liens """ self.loadLists() return self.links def listFields(self): """retourne la liste des champs """ self.loadLists() return self.fields def listForms(self): """retourne la liste des formulaires """ self.loadLists() return self.form def listButtons(self): """retourne la liste des boutons """ self.loadLists() return self.buttons def strLinks(self): """retourne la liste formatée (une chaîne) des liens """ self.loadLists() s='Liens \r\n----- \r\n' for i,j in enumerate(self.links): s+=str(i)+' \t\t '+str(j)+'\r\n' return s def strFields(self): """retourne la liste formatée (une chaîne) des champs """ self.loadLists() s='Champs \r\n------ \r\n' for i,j in enumerate(self.fields): vposs='' if self.fieldTyp[str(j)]=='select-one': vposs=str(self.fieldVposs[str(j)]) s+=str(i)+' \t\t '+str(j)+' '+vposs+'\r\n' return s def strForms(self): """retourne la liste formatée (une chaîne) des formulaires """ self.loadLists() s='Formulaires \r\n----------- \r\n' for i,j in enumerate(self.form): s+=str(i)+' \t\t '+str(j)+'\r\n' return s def strButtons(self): """retourne la liste formatée (une chaîne) des boutons """ self.loadLists() s='Boutons \r\n------- \r\n' for i,j in enumerate(self.buttons): s+=str(i)+' \t\t '+str(j)+'\r\n' return s def strContenu(self): """retourne la liste formatée (une chaîne) des boutons """ self.loadLists() s='Contenu \r\n======= \r\n\r\n' s+=self.strLinks()+'\r\n\r\n' s+=self.strFields()+'\r\n\r\n' s+=self.strForms()+'\r\n\r\n' s+=self.strButtons()+'\r\n\r\n' return s #*** 19.11.06 v1.18 *** def strScripts(self,num=None): """retourne la liste formatée (une chaîne) des scripts """ self.loadLists() if num is None: s='Scripts \r\n------- \r\n'+str(len(self.script)) for i in self.script: print str(i) s+=str(i)+' \r\n '+(self.script[i].outerHTML).encode('cp1252','replace')+'\r\n'+'-'*55+'\r\n' return s else: s=(self.script[num].outerHTML).encode('cp1252','replace') return s #*** 19.11.06 v1.18 *** def setScript(self,num='1',source=''): """affecte (met en place) un script ; attention, le script n'est pas évalué car l'évaluation se fait au chargement de la page. """ self.loadLists() print'-'*55 print self.script[num].innerHTML print'-'*55 time.sleep(0.2) self.script[num].innerHTML='\n\n '+source time.sleep(0.2) self.loadLists() print'='*55 print source print'='*55 print num,type(num) print'-'*55 print self.script[num].innerHTML print'*'*55 def containLink(self,url): """la page (la liste) contient-elle ce lien ? """ self.loadLists() pass def containField(self,url): """la page (la liste) contient-elle ce champ ? """ self.loadLists() pass def containButton(self,url): """la page (la liste) contient-elle ce bouton ? """ self.loadLists() pass def containDocument(self): """Renvoie le ie.Document """ return self.ie.Document def clicLink(self,nom): """clique sur un lien """ self.loadLists() import types if type(nom) is types.IntType: self.link[self.links[nom]].click() self.flagnew=True else: try: self.link[nom].click() self.flagnew=True except: pass def clicButton(self,nom): """clique sur un bouton """ if len(self.fields)<2: self.loadLists() import types if type(nom) is types.IntType: self.button[self.buttons[nom]].click() else: try: self.button[nom].click() except: print "Click-error on button ",nom pass def clicButtonRadio(self,nom): """même effet que clicButton ; inutile ? """ if len(self.fields)<2: self.loadLists() import types if type(nom) is types.IntType: self.button[self.buttons[nom]].checked = True try: self.button[self.buttons[nom]].fireEvent('onclick') except: pass else: try: self.button[nom].checked = True self.button[nom].fireEvent('onclick') except: pass def traitefield(self,prefix,champ,valeur): self.FieldSetFocus(prefix+champ) self.setField(prefix+champ,valeur) #self.FieldBlur(prefix+champ) def setField(self, name, txt): """remplit un champ """ if len(self.fields)<2: self.loadLists() import types if type(name) is types.IntType: self.field[self.fields[name]].value=txt else: try: self.field[name].value=txt except: print "Field",name,"introuvable." pass def getField(self, name): """retourne le contenu d'un champ """ if len(self.fields)<2: self.loadLists() import types if type(name) is types.IntType: return self.field[self.fields[name]].value else: try: return self.field[name].value except: return 'None :'+name pass def FieldClick(self, name): """click sur un champ (normalement pour les cases à cocher) """ if len(self.fields)<2: self.loadLists() import types if type(name) is types.IntType: self.field[self.fields[name]].click() else: try: self.field[name].click() except: print "Field",name,"introuvable." pass #new v.1.18 def FieldChange(self, name): """force le onChange """ if len(self.fields)<2: self.loadLists() import types if type(name) is types.IntType: self.field[self.fields[name]].onChange() else: self.field[name].onChange() #new v.1.12 def FieldSetFocus(self, name): """met le focus dans un champ """ if len(self.fields)<2: self.loadLists() import types if type(name) is types.IntType: self.field[self.fields[name]].focus() else: try: self.field[name].focus() except: print "Field",name,"introuvable." pass #new v.1.13 def FieldBlur(self, name): """met le blur d'un champ """ if len(self.fields)<2: self.loadLists() import types if type(name) is types.IntType: self.field[self.fields[name]]. blur() else: try: self.field[name].blur() except: print "Field",name,"introuvable." pass #new v.1.12 def FieldPasteClip(self, name): """remplit un champ """ self.FieldSetFocus(name) self.loadLists() import types txt=clipboardtxt() if type(name) is types.IntType: self.field[self.fields[name]].value=txt else: try: self.field[name].value=txt except: print "Field",name,"introuvable." pass def FieldCheck(self, name): """coche un champ (normalement pour les cases à cocher) """ self.loadLists() import types if type(name) is types.IntType: if self.field[self.fields[name]].checked==False: self.field[self.fields[name]].click() else: try: if self.field[name].checked==False: self.field[name].click() except: print "Field",name,"introuvable." pass def FieldUnCheck(self, name): """coche un champ (normalement pour les cases à cocher) """ self.loadLists() import types if type(name) is types.IntType: if self.field[self.fields[name]].checked==True: self.field[self.fields[name]].click() else: try: if self.field[name].checked==True: self.field[name].click() except: print "Field",name,"introuvable." pass def setFieldSelect(self, name, txt): """remplit un champ """ if len(self.fields)<2: self.loadLists() import types if type(name) is types.IntType: self.field[self.fields[name]].value=txt try: self.field[self.fields[name]].selected=True except: pass else: try: self.field[name].value=txt try: self.field[name].selected=True except: pass except: print "Field",name,"introuvable." pass def GetUrl(self): """retourne l'URL courante """ return self.ie.LocationURL def GetHtml(self): """retourne le code HTML de la page courante """ return self.doc.body.outerHTML def GetinnerHtml(self): """retourne le code HTML de la page courante """ return self.doc.body.innerHTML def setbodyhtml(self, html): """affecte le contenu de BODY """ self.doc.body.outerHTML=html def setbodyinnerhtml(self, html): """affecte le contenu de BODY """ self.doc.body.innerHTML=html #*** v1.18 def GetHead(self): """retourne le code HTML de l'en-tête de la page courante """ tmp=self.doc.all.tags("head") self.head=None self.headhtml=None for i in tmp: self.head=i self.headhtml=i.innerHTML return self.headhtml def GetDocument(self): """retourne le code HTML de la page courante """ return self.ie.Document def test(self): print "mars0" #w=self.ie.mars() """ pa = win32com.client.Dispatch(self.ie.Document) pb = self.ie.Document if pa==pb: print "égal" """ print '-'*55 win=self.ie.Document.parentWindow print win.name print win.ggg print win.ZORRO print win.zorro2.txt print type(win.hhh),win.hhh,win.hhh.__class__ print win.hhh('XyZ ') #print dir(win32com.client.CDispatch) #print help(win32com.client.CDispatch) print win.mars('Titi ') print '-'*55 print self.ie.Document.parentWindow.name print self.ie.Document.parentWindow.mars('000 111 ') print 'parentWindow',self.ie.GetProperty('parentWindow') print self.ie.Document.fff WIN=self.ie.Document.win print WIN.name print WIN.mars('MaAaRrSs') #tmp=win32com.client.Dispatch(self.ie.Document.mmaarrss) tmp=self.ie.Document.mmaarrss s=u''' ABCDé 123 456''' print "mars1:",tmp.f2(s) print "mars2" #self.doc.execCommand ('SaveAs',True,'C:\\tst.mst') #print u1252(self.doc.body.innerHTML) def tst(self): def walknode(nod,niveau): niveau += 1 nbch=nod.childNodes.length try: if nod.nodeValue: print niveau," / ",nod.innerHTML print niveau," / ",nod.nodeValue except: print pass if nbch>0: for i in range(nbch): walknode(nod.childNodes[i],niveau) niveau -= 1 #walknode(self.body,0) print '-'*55 tempelement=self.doc.createElement('div') tempelement.setAttribute('id',"ZZZ") tempelement.setAttribute('innerHTML','ZZZZZZZ