1: """This contains the class MPIWG Projects
2: for organizing and maintaining the different project pages
3:
4: $author dwinter - last change 26.06.2008
5:
6: """
7: from Products.PageTemplates.PageTemplateFile import PageTemplateFile
8: from Products.PageTemplates.ZopePageTemplate import ZopePageTemplate
9: from Products.ZCatalog.CatalogPathAwareness import CatalogAware
10: from OFS.Image import Image
11: from Globals import package_home
12: import urllib
13: import re
14: import os
15: from types import *
16: import logging
17: import xmlhelper # Methoden zur Verwaltung der projekt xml
18: from OFS.SimpleItem import SimpleItem
19: from OFS.Folder import Folder
20:
21: from AccessControl import ClassSecurityInfo
22: from bibliography import *
23: import time
24: #import xml.dom.minidom
25: import sys
26: #from Ft.Xml.XPath import Evaluate
27: #from Ft.Xml.XPath.Context import Context
28: #from Ft.Xml.Domlette import NonvalidatingReader,PrettyPrint, Print
29: #from Ft.Xml import EMPTY_NAMESPACE
30: #import copy
31: #import updatePersonalWWW
32:
33: #import MPIWGStaff
34:
35: from MPIWGHelper import *
36:
37: import MPIWGRoot
38: import MPIWGLink
39: import MPIWGTemplate
40:
41: # die folgenden Klassen sind jetzt in einzelne Files ausgelagert aus KompatibilitŠtsgrŸnden, bleiben die Klassen hier noch drin.
42: # Sonst funktionieren die alten Webseiten nicht mehr.
43:
44: class MPIWGRoot(MPIWGRoot.MPIWGRoot):
45: """depricated"""
46:
47: class MPIWGLink(MPIWGLink.MPIWGLink):
48: """depricated"""
49:
50: class MPIWGTemplate(MPIWGTemplate.MPIWGTemplate):
51: """depricated"""
52:
53: class MPIWGProject_publication(SimpleItem):
54: """publications object fuer project"""
55:
56: meta_type="MPIWGProject_publication"
57:
58: def editPublication(self,text=None,RESPONSE=None):
59: """edit a publication"""
60:
61: if (not text):
62: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','edit_publicationForm.zpt')).__of__(self)
63: return pt()
64:
65:
66: self.text=text[0:]
67:
68: if RESPONSE:
69: RESPONSE.redirect("../managePublications")
70:
71: class MPIWGProject_image(Image):
72: """Images for Projects"""
73:
74: meta_type="MPIWGProject_image"
75:
76: def showImage(self,imageUrl=None):
77: """show Images at an extra page"""
78: self.getContent('WEB_project_description',filter='yes') #get the content and store image infos into session
79: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','projectImageView.zpt')).__of__(self)
80: return pt()
81:
82: def editImage(self,file=None,caption=None,RESPONSE=None):
83: """edit the Image"""
84: if (not file) and (not caption):
85: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','edit_imageForm.zpt')).__of__(self)
86: return pt()
87:
88: if file and (not file.filename.lstrip().rstrip()==""):
89: self.manage_upload(file)
90:
91: if caption:
92: self.caption=caption[0:]
93:
94: if RESPONSE:
95: RESPONSE.redirect("../manageImages")
96:
97: class MPIWGProject(CatalogAware,Folder):
98: """Class for Projects"""
99:
100:
101: security=ClassSecurityInfo()
102: meta_type='MPIWGProject'
103: default_catalog='ProjectCatalog'
104:
105: def decode(self,str):
106: """return unicode object"""
107: return unicodify(str)
108:
109: def sortedByPlace(self,metatype):
110: """find metatype and sort by place"""
111: def sort(x,y):
112: return cmp(getattr(x[1],'place',0),getattr(y[1],'place',0))
113:
114: founds=self.ZopeFind(self,obj_metatypes=[metatype]);
115:
116: founds.sort(sort)
117:
118: return founds
119:
120:
121: def copyPublicationsToList(self,RESPONSE=None):
122: """copy publications in to list"""
123:
124: publicationTxt=self.getContent('WEB_related_pub')
125:
126: pubSplits=publicationTxt.split("<p>")
127:
128: for pubSplit in pubSplits:
129: pubSplit=pubSplit.replace("</p>","")
130: self.addPublication(pubSplit)
131:
132: if RESPONSE:
133: RESPONSE.redirect('managePublications')
134:
135:
136: def copyImageToMargin(self,RESPONSE=None):
137: """copy inline images to marginal images"""
138:
139:
140: #getImages from WEB_project_description
141: description=self.getContent('WEB_project_description')
142:
143: text2=description
144: splitted=text2.split("""<p class="picture">""")
145:
146: imageURLs=[]
147: imageCaptions=[]
148: for split in splitted[1:]:
149: tmp=split.split("</p>")
150: #return repr(splitted[1])
151:
152: try:
153: imageURLs.append(tmp[0].split("\"")[1].encode('utf-8'))
154: except:
155:
156: try:
157: imageURLs.append(tmp[0].split("src=")[1].split(" ")[0].encode('utf-8'))
158: except:
159: imageURLs.append("")
160:
161: split2="</p>".join(tmp[1:])
162:
163:
164: splitted=split2.split("""<p class="picturetitle">""")
165: if len(splitted)>1:
166: tmp=splitted[1].split("</p>")
167: imageCaptions.append(tmp[0].encode('utf-8'))
168:
169:
170: else:
171: #keine caption
172:
173: imageCaptions.append("")
174:
175:
176: #eintragen:
177: for imageURL in imageURLs:
178: filename=imageURL.split("/")[-1]
179: #lege neues images object an, mit leerem bild
180:
181: if self.ZopeFind(self,obj_ids=[filename]):
182: #existiert das bild schon, dann neuen filenamen
183: filename="project_image_"+filename
184:
185: self.addImage(None,imageCaptions[imageURLs.index(imageURL)],filename=filename)
186: #hole die bilddaten aus der url
187: url=self.absolute_url()+"/"+imageURL
188: #url=self.absolute_url()+"/"+filename
189:
190: try:#relative url
191: data=urllib.urlopen(url).read()
192: except:
193: try:#absolute
194: data=urllib.urlopen(self.imageURL).read()
195: except:
196: logger("MPIWG Project",logging.ERROR,"can't open: %s"%url)
197:
198: obj=getattr(self,filename)
199: obj.update_data(data)
200:
201: if RESPONSE:
202: RESPONSE.redirect('manageImages')
203:
204: def manageImages(self,imageName=None,op=None):
205: """managage images"""
206:
207:
208: if imageName and op:
209: if op=='up':
210: images=self.getImages()
211: for image in images:
212: if image[0]==imageName:
213: nr=images.index(image)
214: if not nr==0:
215: images[nr-1][1].place+=1
216: images[nr][1].place-=1
217: pass
218: elif op=='down':
219: images=self.getImages()
220: for image in images:
221: if image[0]==imageName:
222: nr=images.index(image)
223: if not (nr==len(images)-1):
224: images[nr+1][1].place-=1
225: images[nr][1].place+=1
226: pass
227:
228:
229: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','MPIWGProject_manageImagesForm.zpt')).__of__(self)
230: return pt()
231:
232: def managePublications(self,pubName=None,op=None):
233: """managage images"""
234:
235:
236: if pubName and op:
237: if op=='up':
238: publications=self.getPublications()
239: for publication in publications:
240: if publication[0]==pubName:
241: nr=publications.index(publication)
242: if not nr==0:
243: publications[nr-1][1].place+=1
244: publications[nr][1].place-=1
245: pass
246: elif op=='down':
247: publications=self.getPublications()
248: for publication in publications:
249: if publication[0]==pubName:
250: nr=publications.index(publication)
251: if not (nr==len(publications)-1):
252: publications[nr+1][1].place-=1
253: publications[nr][1].place+=1
254: pass
255:
256:
257: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','MPIWGProject_managePublicationsForm.zpt')).__of__(self)
258: return pt()
259:
260: def getPublications(self):
261: """get all Publications"""
262: def sort_images(x,y):
263: return cmp(getattr(x[1],'place',0),getattr(y[1],'place',0))
264:
265: publications=self.ZopeFind(self,obj_metatypes=['MPIWGProject_publication'])
266:
267: publications.sort(sort_images)
268: return publications
269:
270: def addPublication(self,text,RESPONSE=None):
271: """add an MPIWG_Publication"""
272:
273: name="publication_"+str(self.getLastPublicationNumber()+1)
274:
275: newPublication=MPIWGProject_publication(name)
276:
277: self._setObject(name,newPublication)
278: obj=getattr(self,name)
279: obj.text=text[0:]
280: obj.enabled=True;
281: obj.place=self.getLastPublicationNumber()+1
282: obj.id=name
283:
284: if RESPONSE is not None:
285: RESPONSE.redirect('managePublications')
286:
287:
288: def getLastPublicationNumber(self):
289: publications=self.getPublications()
290:
291: if not publications:
292: return 0
293: else:
294: return getattr(publications[-1][1],'place',0)
295:
296: def deletePublication(self,id,RESPONSE=None):
297: """delete Publication id"""
298: self.manage_delObjects([id])
299: if RESPONSE:
300: RESPONSE.redirect('managePublications')
301:
302: def getImages(self):
303: """get all Images"""
304:
305: def sort_images(x,y):
306: return cmp(getattr(x[1],'place',0),getattr(y[1],'place',0))
307:
308:
309: if (getattr(self,'imageURL','')!='') or (getattr(self,'imagecap','')!='') :
310: try:
311: self.addImage(None,getattr(self,'imagecap',''),RESPONSE=None,filename=getattr(self,'imageURL',''))
312: except:
313: pass
314: self.imageURL=''
315: self.imagecap=''
316:
317: images=self.ZopeFind(self,obj_metatypes=['MPIWGProject_image'])
318:
319: images.sort(sort_images)
320: return images
321:
322: def getLastImageNumber(self):
323: images=self.getImages()
324:
325: if not images:
326: return 0
327: else:
328: return getattr(images[-1][1],'place',0)
329:
330: def deleteImage(self,id,RESPONSE=None):
331: """delete Image id"""
332: self.manage_delObjects([id])
333: if RESPONSE:
334: RESPONSE.redirect('manageImages')
335:
336:
337: def hasChildren(self,date=None,onlyActive=1,onlyArchived=1):
338: """check if project has children"""
339: ct=self.getContexts(childs=self.getContent('xdata_05'),
340: depth=1,date=date,onlyActive=onlyActive)
341:
342: if ct and len(ct)>0:
343: return True
344: else:
345: return False
346:
347:
348: def addImage(self,fileHd,caption,RESPONSE=None,filename=None):
349: """add an MPIWG_Project_image"""
350:
351: if not filename:
352: filename=fileHd.filename
353:
354: if not fileHd:
355: fileHd=file(os.path.join(package_home(globals()),'blank.gif'))
356:
357: newImage=MPIWGProject_image(filename,filename,fileHd)
358:
359: self._setObject(filename,newImage)
360: obj=getattr(self,filename)
361: obj.caption=caption[0:]
362: obj.enabled=True;
363: obj.place=self.getLastImageNumber()+1
364: obj.id=filename
365:
366: if RESPONSE is not None:
367: RESPONSE.redirect('manageImages')
368:
369: def PrincipiaSearchSource(self):
370: """Return cataloguable key for ourselves."""
371: return str(self)
372:
373: def versionHeader(self):
374: """version Header, gibt header text entsprechend der aktuellen version aus"""
375:
376: actualTime=time.localtime()
377: retTXT="""<h2>This is an outdated version, for the actual version please refer to <a href="%s">%s</a></h2>"""
378: s=self.aq_parent.absolute_url()
379: #print getattr(self,'archiveTime',actualTime)
380: if getattr(self,'archiveTime',actualTime)< actualTime:
381: return retTXT%(s,s)
382: else:
383: return ""
384:
385: def getActualVersion(self,date=None):
386: """actuelle version"""
387: def sortProjectsByTime(x,y):
388: return cmp(x[1].archiveTime,y[1].archiveTime)
389:
390: if not date:
391: if self.isActual():
392: return self
393: else:
394: return None
395:
396: #suche ob aeltere versionen vorhanden sind
397:
398: finds=self.ZopeFind(self,obj_metatypes=['MPIWGProject'])
399: if not finds: #wenn nicht dann teste ob die aktuelle version schon existiert hat.
400: ad=getattr(self,'creationTime','20050101000000')
401: if int(date)>int(ad):
402: return self
403: else:
404: return None
405:
406:
407: else:
408: finds.sort(sortProjectsByTime)
409:
410: for find in finds:
411: #gehe durch die alten Projekte und finde das entprechende
412: if (int(find[1].archiveTime) > int(date)) and (int(date)>int(getattr(find[1],'creationTime','20050101000000'))):
413: return find[1]
414:
415: #kein passendes gefunden, dann teste ob das aktuelle in frage kommt
416: ad=getattr(self,'creationTime','20050101000000')
417:
418: if int(date)>int(ad):
419:
420: return self
421: else:
422: return None
423:
424:
425: def isActual(self):
426: """gibt 1 zurueck wenn aktuell, 0 sonst"""
427: actualTime=time.localtime()
428:
429:
430: #print getattr(self,'archiveTime',actualTime)
431: if getattr(self,'archiveTime',actualTime)< actualTime:
432: return 0
433: else:
434: return 1
435:
436: def copyObjectToArchive(self):
437: """kopiere aktuelles objekt ins archiv"""
438: cb=self.aq_parent.manage_copyObjects(self.getId())
439: self.manage_pasteObjects(cb)
440: actualTime=time.localtime()
441:
442: self.manage_renameObject(self.getId(),self.getId()+"_"+time.strftime("%Y%m%d%H%M%S",actualTime))
443: obj=getattr(self,self.getId()+"_"+time.strftime("%Y%m%d%H%M%S",actualTime))
444: obj.setArchiveTime(time.strftime("%Y%m%d%H%M%S",actualTime))
445: ids=[x[0] for x in self.ZopeFind(obj,obj_metatypes=['MPIWGProject'])]
446: obj.manage_delObjects(ids)
447:
448: def setArchiveTime(self,time):
449: """set Archive Time"""
450: self.archiveTime=time[0:]
451:
452: def versionManageForm(self):
453: """version Manage form:currently only set to invisible"""
454: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','MPIWGProject_versionManageForm.zpt')).__of__(self)
455: return pt()
456:
457: def versionManage(self,invisible=None,RESPONSE=None):
458: """version Manage form:currently only set to invisible"""
459: self.invisible=invisible
460:
461: if RESPONSE is not None:
462: RESPONSE.redirect('manage_main')
463:
464:
465: def crossLinker(self):
466: """experimental crosslinker"""
467: splitted=self.WEB_project_description[0].split()
468: new=[]
469: for split in splitted:
470: try:
471: found=self.DescriptionCatalog({'fulltext':split})
472:
473: if len(found)>1:
474:
475: new.append("<a href=%s>%s</a>"%(split,split))
476: else:
477: new.append(split)
478: except:
479: new.append(split)
480: return " ".join(new)
481:
482:
483:
484:
485: def generateTemplate(self,RESPONSE=None):
486: """Erzeuge Template fuer defined fields not_used"""
487:
488: id="index_html"
489: title=id
490: if self._getOb('index_html'):
491: self._delObject('index_html')
492:
493:
494: newObj=ZopePageTemplate(id,'TEXT')
495: self._setObject(id,newObj)
496: #self.manage_addPageTemplate(id,title)
497: if RESPONSE is not None:
498: RESPONSE.redirect('manage_main')
499:
500: def __init__(self, id, argv=None):
501: """initiere classe"""
502:
503: self.creationTime=time.strftime("%Y%m%d%H%M%S",time.localtime())[0:]
504: self.id=id
505: self.title=id
506: self.isActiveFlag=True #Flag is true is the project is still active, False if accomplished
507: self.responsibleScientistsList=[] # enthaelt die Lister der verantwortlichen Wissenschaftler in der Form (NAME, KEY), key ist "" flass Wissenschaftler nicht an unserem Haus
508:
509: if argv:
510: for arg in definedFields:
511: try:
512: setattr(self,arg,argv[arg])
513: except:
514: setattr(self,arg,"")
515: else:
516: for arg in definedFields:
517: setattr(self,arg,'')
518:
519: manage_options = Folder.manage_options+(
520: {'label':'Load New File','action':'loadNewFileForm'},
521: {'label':'Edit ProjectInfo','action':'editMPIWGProjectForm'},
522: {'label':'Edit BasisInfo','action':'editMPIWGBasisForm'},
523: {'label':'Edit Publications','action':'editMPIWGRelatedPublicationsForm'},
524: {'label':'Edit Themes & Disciplines','action':'editMPIWGDisciplinesThemesForm'},
525: {'label':'Versionmanager','action':'versionManageForm'},
526: )
527:
528:
529: def isActiveProject(self):
530: """check if the project is still active, default is true, set to false is the project is accomplished"""
531: return getattr(self,'isActiveFlag',True)
532:
533: def isArchivedProject(self):
534: """check if the project is archived"""
535:
536: completed=getattr(self,'completedAt',0)
537:
538: #completed leer
539: if completed=="" :
540: return False;
541: if completed == 0:
542: return False;
543:
544:
545: return True
546:
547:
548: def setActiveFlag(self,status=True):
549: """set the active flag"""
550: self.isActiveFlag=status
551:
552: def setCompletedAt(self,date):
553: """set the date of completion, date should be in the form DD.MM.YYYY or MM.YYYY or YYYY"""
554: logging.info("DATE:"+repr(date))
555: transformedDate=self.transformDate(date);
556: logging.info("transformed"+repr(transformedDate))
557: if transformedDate is not None:
558: setattr(self,"completedAt",transformedDate)
559: return True;
560: else:
561: return False;
562:
563: def setStartedAt(self,date):
564: """set the date of start, date should be in the form DD.MM.YYYY or MM.YYYY or YYYY"""
565: logging.info("DATE:"+repr(date))
566: transformedDate=self.transformDate(date);
567: logging.info("transformed"+repr(transformedDate))
568: if transformedDate is not None:
569: setattr(self,"startedAt",transformedDate)
570: return True;
571: else:
572: return False;
573: def getCompletedAt(self):
574: """gibt das transformierte Datum zurueck, an dem das Projekt beendet wurde."""
575: date=getattr(self,'completedAt','')
576: if date:
577: return self.reTransformDate(date);
578: else:
579: return '';
580:
581: def getStartedAt(self):
582: """gibt das transformierte Datum zurŸck, an dem Projekt begonnen wurde."""
583: date=getattr(self,'startedAt','')
584: if date:
585: return self.reTransformDate(date);
586: else:
587: return '';
588:
589: def reTransformDate(self,date):
590: """transformiert , transformdate zurueck"""
591: year=int(date/10000)
592: month=int((date-year*10000)/100)
593: day=int((date-year*10000-month*100))
594: if (day==0) and (month==0):
595: return """%s"""%year;
596: if day==0 :
597: return """%s.%s"""%(month,year);
598:
599: return """%s.%s.%s"""%(day,month,year);
600:
601:
602: def transformDate(self,date):
603: """transformiert ein Datum von DD.MM.YYYY, MM.YYYY,YYYY nach YYYYMMDD, alle nicht angebebenn Werte
604: werden auf 0 gesetzt, es wird null zurŸckgegeben falls das Datum ungueltig ist"""
605:
606: if (date==None):
607: return None;
608:
609:
610: if (date.lstrip().rstrip()=="" ) :
611: return "";
612:
613: splitted=date.split(".")
614: length=len(splitted)
615: year=0
616: month=0
617: day=0
618: if length > 3:
619: return "";
620: if length==3:
621: day = int(splitted[0])
622: if length>1:
623: month=int(splitted[length-2])
624:
625: if length > 0:
626: try:
627: year = int(splitted[length-1])
628: except:
629: pass
630:
631: ## logging.info("month:"+(month))
632: if not (0<=month<13):
633: return None;
634:
635: if not(0<=day<32):
636: return None;
637:
638: if (year>0) and (year<1900): #jahr nicht vierstellig eingegeben
639: year=2000+year;
640: return year*10000+month*100+day
641:
642:
643:
644: def checkDate(self,date):
645: """teste ob zum Zeitpunkt date eine andere version existierte"""
646:
647:
648: def sortProjectsByTime(x,y):
649: return cmp(x[1].archiveTime,y[1].archiveTime)
650:
651: #suche ob aeltere versionen vorhanden sind
652:
653: finds=self.ZopeFind(self,obj_metatypes=['MPIWGProject'])
654: if not finds: #wenn nicht dann teste ob die aktuelle version schon existiert hat.
655: ad=getattr(self,'creationTime','20050101000000')
656: if int(date)>int(ad):
657: return self.REQUEST['URL1']+"/"+self.getId()
658: else:
659: return self.REQUEST['URL1']+"/no_project"
660:
661:
662: else:
663: finds.sort(sortProjectsByTime)
664:
665: for find in finds:
666: #gehe durch die alten Projekte und finde das entprechende
667: if (int(find[1].archiveTime) > int(date)) and (int(date)>int(getattr(find[1],'creationTime','20050101000000'))):
668: return self.REQUEST['URL1']+"/"+find[1].getId()
669:
670: #kein passendes gefunden, dann teste ob das aktuelle in frage kommt
671: ad=getattr(self,'creationTime','20050101000000')
672:
673: if int(date)>int(ad):
674:
675: return self.REQUEST['URL1']+"/"+self.getId()
676: else:
677: return self.REQUEST['URL1']+"/no_project"
678:
679:
680: def no_project(self):
681: """warnung: project noch nicht existent"""
682: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','no_project')).__of__(self)
683: return pt()
684:
685: def getGetNeighbourhood(self,wordStr, length=100,tagging=True):
686: """finde umgebung um die worte in wordStr, zurueckgegeben wird eine Array mit den Umgebungen von Fundstellen der Worte
687: alle Tags werden entfernt, die Fundstellen werden mit <span class="found">XX</span> getaggt, die Umgebungen werden
688: case insensitive gesucht
689: @param wordStr: string mit Worten getrennt durch Leerzeichen, Phrasen sind mit " gekennzeichnet
690: "eine phrase", "*" bezeichnet wildcards und wird ignoriert"
691: @param length: optional, default wert 100, 2*length ist die groesse der Umgebung
692: @param tagging: optional default wert true, kein span tag wird erzweugt falls tag=false
693: """
694:
695: ret=[] # nimmt das Array auf, dass spaeter zurueckgegeben wird
696: ranges=[] #Array mit tupeln x,y wobei x die Position des Anfang und y des Endes der i-ten Umgebung angiebt
697:
698: def isInRanges(nr,length):
699: """test ob eine gegeben Position nr schon irgendwo in einer Umgebung ist, gibt den Index des ersten Wertes aus ranges zurueck,
700: -1, wenn kein Treffer
701:
702: @param nr: Position die geprueft werden soll
703: @param length: Laenge des Wortes das geprueft werden soll
704: """
705: for x in ranges:
706: if (x[0]<=nr) and (nr < (x[1]-length)):
707: return ranges.index(x)
708: return -1
709:
710: # deal with phrases, in Phrasen werden die Leerzeichen durch "_" ersetzt.
711: def rep_empty(str):
712: x= re.sub(" ","_",str.group(0))
713: return re.sub("\"","",x)
714:
715: wordStr=re.sub("\".*?\"", rep_empty,wordStr)#ersetze leerzeichen in " " durch "_" und loesche "
716:
717: #deal with wildcards, for our purposes it is enough to delete the wildcard
718: wordStr=wordStr.replace("*","")
719:
720: words=wordStr.split(" ")
721: #if not words is ListType:
722: # words=[words]
723:
724: txt=self.harvest_page()
725: if not txt:
726: return ret
727: txt=re.sub("<.*?>", "", txt) # loesche alle Tags
728: for word in words:
729: word=re.sub("_"," ",word) # ersetze zurueck "_" durch " "
730: pos=0
731:
732: n=txt.lower().count(word.lower()) # wie oft tritt das Wort auf
733:
734: for i in range(n):
735: pos=txt.lower().find(word.lower(),pos)
736:
737: if pos > 0:
738: x=max(0,pos-length)
739: y=min(len(txt),pos+length)
740:
741:
742: #is word already in one of the results
743: nr=isInRanges(pos,len(word))
744: if nr >=0:# word ist in einer schon gefunden Umgebung, dann vergroessere diese
745: x=min(ranges[nr][0],x)
746: y=max(ranges[nr][1],y)
747:
748: str=txt[x:y]
749:
750: if nr >=0: # word ist in einer schon gefunden Umgebung
751: ranges[nr]=(x,y) # neue Position der Umgebung
752:
753: ret[nr]=str # neue Umgebung
754: else: # andernfalls neue Umgebung hinzufuegen
755: ranges.append((x,y))
756:
757: ret.append(str)
758:
759: pos=pos+len(word)
760: else:
761: break;
762:
763: # now highlight everything
764: if tagging:
765: for x in range(len(ret)):
766: for word in words:
767: repl=re.compile(word,re.IGNORECASE)
768: ret[x]=repl.sub(""" <span class="found">%s</span>"""%word.upper(),ret[x])
769:
770: return ret
771:
772: def harvest_page(self,context=None):
773: """seite fuer harvesting fuer die Projektsuche"""
774: if not context:
775: context=self
776:
777: if self.isActiveProject() and self.isActual():
778: ext=getattr(self,"harvest_main",None)
779: if ext:
780: return getattr(self,ext.getId())()
781:
782: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','harvest_main')).__of__(context)
783:
784:
785: return pt()
786:
787: def index_html(self,request=True,context=None):
788: """show homepage"""
789: if not context:
790: context=self
791: if request:
792: if self.REQUEST.has_key('date') and self.REQUEST.SESSION.get('MPI_redirected',None)==None:
793: self.REQUEST.SESSION['MPI_redirected']=1
794: self.REQUEST.RESPONSE.redirect(self.checkDate(self.REQUEST['date'])+"?date="+self.REQUEST['date'])
795: else:
796: self.REQUEST.SESSION['MPI_redirected']=None
797:
798: #ext=self.ZopeFind(self.aq_parent,obj_ids=["project_main"])
799: ext=getattr(self,"project_main",None)
800: if ext:
801: return getattr(self,ext.getId())()
802:
803: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','project_main')).__of__(context)
804:
805: return pt()
806:
807:
808: def getDataFields(self):
809: """giveListofDatafields"""
810: ret=[]
811: for x in range(1,14):
812: if not x in [6,10,9]: # not used fields
813: ret.append('xdata_%02i'%x)
814: return ret
815:
816: def getDefinedFields(self):
817: """show all defined fields"""
818:
819: return definedFields
820:
821: def getAttribute(self,field):
822: """get attrbiute"""
823: return getattr(self,field)
824:
825: def getContent(self,field,filter=None):
826: """Inhalt des Feldes"""
827:
828: text=u''
829:
830: for x in getattr(self,field):
831:
832: try:
833: text +=x
834: except:
835: text = x
836:
837:
838:
839: try:
840: if text[len(text)-1]==";":
841: text=text[0:len(text)-1]
842:
843:
844: except:
845: pass
846:
847: if text=='':
848: text2=text
849: else:
850: text2=re.sub(r';([^\s])','; \g<1>',text)
851:
852: #teste ob ergebnis leer und header dann nehme title
853:
854: if (text2=='') and (field=='WEB_project_header'):
855: return self.getContent('WEB_title')
856:
857: if filter:
858: splitted=text2.split("""<p class="picture">""")
859: if len(splitted)>1:
860: tmp=splitted[1].split("</p>")
861: #return repr(splitted[1])
862: try:
863: self.imageURL=tmp[0].split("\"")[1].encode('utf-8')
864: except:
865: try:
866: self.imageURL=tmp[0].split("src=")[1].split(" ")[0].encode('utf-8')
867: except:
868: self.imageURL=""
869:
870: split2="</p>".join(tmp[1:])
871:
872: text3=splitted[0]+split2
873:
874: splitted=text3.split("""<p class="picturetitle">""")
875: if len(splitted)>1:
876: tmp=splitted[1].split("</p>")
877: self.imagecap=tmp[0].encode('utf-8')
878:
879: split4="".join(tmp[1:])
880:
881: text5=splitted[0]+split4
882: else:
883: #keine caption
884: text5=text3
885: else:
886: #kein bild
887: text5=text2
888: else:
889: text5=text2
890:
891: #teste ob WEB_project_description und keine fuehrenden p tags
892: if (len(text5)>4) and (not text5[0:3]=='<p>') and (field=='WEB_project_description'):
893: text5= "<p>"+text5+"</p>"
894:
895:
896: #filter image
897:
898: text5=text5.lstrip().rstrip() #loescher leerzeichen und einzelndes br
899: if (text5=="<br>") or (text5=="<br/>"):
900: text5=""
901:
902: logging.debug("getcontent: field=%s filter=%s -> %s"%(field,filter,repr(text5)))
903: #return unicodify(text5)
904: return utf8ify(text5) # return as utf-8 byte string
905:
906:
907: def showImagesOfPage(self,imageUrl=None):
908: """show Images of project"""
909: self.getContent('WEB_project_description',filter='yes') #get the content and store image infos into session
910: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','projectImageView.zpt')).__of__(self)
911: return pt()
912:
913:
914: def show_html(self):
915: """simple index"""
916: #return "HI"
917: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','MPIWGProject_index.zpt')).__of__(self)
918: return pt()
919:
920: def saveFromPreview(self):
921: """save content aus preview"""
922: self.WEB_project_description=self.previewTemplate.WEB_project_description[0:]
923: self.REQUEST.RESPONSE.redirect("./index.html")
924:
925: def saveEditedContent(self,kupu=None,preview=None):
926: """save Edited content"""
927:
928: if preview:
929: kupu=preview
930: #find content of body tags
931: start=kupu.find("<body>")
932: end=kupu.find("</body>")
933: newcontent= kupu[start+6:end]
934:
935: if preview:
936:
937: return self.preview(newcontent)
938:
939: self.copyObjectToArchive()
940: self.WEB_project_description=newcontent[0:]
941:
942: self.REQUEST.RESPONSE.redirect("./index.html")
943:
944: return True
945:
946: security.declareProtected('View management screens','edit')
947: def edit(self,western=None):
948: """Edit pages"""
949: if western:
950: self.REQUEST.RESPONSE.setCookie("MP_debug_code","western",path="/")
951:
952:
953: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','edit_MPIWGProjectNeu.zpt')).__of__(self)
954: return pt()
955:
956: edit_MPIWGProject_main = PageTemplateFile('zpt/edit_MPIWGProject_main', globals())
957:
958: def getPathStyle(self, path, selected, style=""):
959: """returns a string with the given style + 'sel' if path == selected."""
960:
961: if path == selected:
962: return style + 'sel'
963: else:
964: return style
965:
966: def preview(self,description):
967: """preview"""
968: tmpPro=getattr(self,"previewTemplate",None)
969: if not tmpPro:
970: tmpPro=MPIWGProject("previewTemplate")
971: self._setObject("previewTemplate",tmpPro)
972: for field in definedFields:
973: setattr(tmpPro,field,getattr(self,field))
974: tmpPro.WEB_project_description=description[0:]
975: tmpPro.invisible=True
976: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','previewFrame.zpt')).__of__(self)
977: return pt()
978:
979: #return self.REQUEST.RESPONSE.redirect(self.REQUEST['URL1']+"/previewTemplate")
980:
981:
982: def getWebProject_description(self):
983: """get description"""
984: debug= self.REQUEST.cookies.get("MP_debug_code",None)
985:
986: if debug and debug=="western":
987: return """
988: <html>
989: <head>
990: <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
991: </head>
992: <body>%s
993: </html></body>
994: """%self.WEB_project_description[0]
995:
996: return """
997: <html>
998: <head>
999: <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
1000: </head>
1001: <body>%s
1002: </html></body>
1003: """%self.getContent('WEB_project_description')
1004:
1005:
1006:
1007: def editMPIWGProjectForm(self):
1008: """editform"""
1009: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','edit_MPIWGProject.zpt')).__of__(self)
1010: return pt()
1011:
1012: def isResponsibleScientist(self,key):
1013: """teste ob eine Person in der Liste der respl. scientists auftaucht"""
1014: #logging.info("XXXXXXXXXXXXX"+repr(self.responsibleScientistsList))
1015:
1016:
1017: keys = [x[1] for x in getattr(self,"responsibleScientistsList",[])]
1018:
1019: if key in keys:
1020: return True
1021: else:
1022: return False
1023:
1024: def getPersonKeyList(self):
1025: """gibt die key Lister der beteiligten Personen zurŸck"""
1026: return [x[1] for x in getattr(self,'responsibleScientistsList',[])]
1027:
1028:
1029:
1030:
1031: def identifyNames(self,nameList):
1032: """Bekommt eine Komma oder Semikolon getrennte Liste mit Name der Form Vorname MittelName(n) Nachname
1033: und ordnet diese dann Mitarbeiter IDs zu falls es schone eine Liste gibt wird im Projekte gibt wird diese Upgedated.
1034: @param nameList
1035: """
1036: nameList=nameList.replace(";",",") # falls ; als Trenner ersetze
1037: names=nameList.split(",")
1038:
1039: returnNamesDict={}
1040:
1041:
1042: for name in names:
1043: name=name.lstrip().rstrip()
1044: nameSplitted = name.split(" ")
1045: if len(nameSplitted)>1: #vor und nachname angegeben)
1046:
1047: lastname=nameSplitted[-1]
1048: firstname=nameSplitted[0]
1049: else:
1050: firstname =""
1051: lastname=nameSplitted[0]
1052:
1053: #finde Mitarbeiter mit den entsprechenden Name
1054: logging.info("Search: %s %s %s"%(name,firstname,lastname))
1055: firstname=firstname.capitalize()
1056: lastname=lastname.capitalize()
1057: cataloggedNames=self.MembersCatalog(firstName=firstname,lastName=lastname)
1058:
1059: #Teste ob die ensprechenden Namen schon der Liste zu geordnet sind
1060: #if not hasattr(self,'responsibleScientistsList'):
1061: # self.responsibleScientistsList={}
1062: #
1063: # if name in self.responsibleScientistsList.values()
1064:
1065: if len(cataloggedNames)>0:
1066: returnNamesDict[name]=cataloggedNames
1067: else:
1068: returnNamesDict[name]=[]
1069:
1070: return returnNamesDict
1071:
1072: def editMPIWGProject(self,RESPONSE=None,fromEdit=None):
1073: """edit the project and archive the old version"""
1074:
1075: self.copyObjectToArchive() # archive the object
1076:
1077:
1078: for x in definedFields:
1079: if self.REQUEST.has_key(x):
1080:
1081: setattr(self,x,[self.REQUEST[x].decode('utf-8')])
1082:
1083:
1084:
1085:
1086: completedAt = self.REQUEST.get('completedAt')
1087: if not self.setCompletedAt(completedAt):
1088: RESPONSE.redirect('./editMPIWGBasisEditor?error="dateWrong')
1089:
1090: startedAt = self.REQUEST.get('startedAt')
1091: if not self.setStartedAt(startedAt):
1092: RESPONSE.redirect('./editMPIWGBasisEditor?error="dateWrong')
1093:
1094: if self.REQUEST.has_key('historicalNames'):
1095: self.en.changeHistoricalNames(self.getId(),self.REQUEST['historicalNames'].split("\n"))
1096:
1097: if self.REQUEST.has_key('active'):
1098: self.setActiveFlag(True)
1099: else:
1100: self.setActiveFlag(False)
1101:
1102: self.responsibleScientistsList=[] # setze die Liste der verantwortlichen Wissenschaftler zurueck
1103:
1104: names={}
1105: keys={}
1106: tmpList=[]
1107: for key in self.REQUEST.keys(): #gehe durch das Formular
1108: splitted=key.split("_")
1109: if splitted[0]=="responsibleScientist": #wenn es ein Feld der Form reponsibleScientist_nr_KEY gibt
1110: nr=splitted[2]
1111: if splitted[1]=="name":
1112: names[nr]=self.REQUEST[key]
1113: elif splitted[1]=="key":
1114: keys[nr]=self.REQUEST[key]
1115:
1116:
1117: for nr in names.keys():
1118: tmpList.append((names[nr],keys.get(nr,"")))
1119:
1120: self.responsibleScientistsList=tmpList
1121: if fromEdit and (RESPONSE is not None):
1122: #RESPONSE.redirect('./editMPIWGBasisEditor')
1123: return self.editMPIWGBasisEditor(identifiedNames=self.identifyNames(self.REQUEST.get('xdata_01','')))
1124:
1125: else:
1126: if RESPONSE is not None:
1127: RESPONSE.redirect('manage_main')
1128:
1129:
1130:
1131: security.declareProtected('View managment screens','editMPIWGDisciplinesThemesEditor')
1132: def editMPIWGDisciplinesThemesEditor(self):
1133: """edit from edit"""
1134: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','edit_MPIWGDisciplinesThemesNeu.zpt')).__of__(self)
1135: return pt()
1136:
1137:
1138: def editMPIWGDisciplinesThemesForm(self):
1139: """edit the disciplines and themes Form"""
1140:
1141: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','edit_MPIWGDisciplinesThemes.zpt')).__of__(self)
1142: return pt()
1143:
1144: def editMPIWGDisciplinesThemes(self,disciplines=None,themes=None,RESPONSE=None,fromEdit=None):
1145: """edit disciplin and form"""
1146: if disciplines:
1147: if type(disciplines) is StringType:
1148: self.xdata_09=disciplines
1149: else:
1150: self.xdata_09=";".join(disciplines)
1151: else:
1152: self.xdata_09=""
1153: if themes:
1154: if type(themes) is StringType:
1155: self.xdata_10=themes
1156: else:
1157: self.xdata_10=";".join(themes)
1158: else:
1159: self.xdata_10=""
1160:
1161: if fromEdit and (RESPONSE is not None):
1162: RESPONSE.redirect('./editMPIWGDisciplinesThemesEditor')
1163:
1164: else:
1165: if RESPONSE is not None:
1166: RESPONSE.redirect('manage_main')
1167:
1168:
1169: def isChecked(self,wert,list):
1170: """check if wert is in ; seperated list"""
1171:
1172: #felder sind manchmnal als liste mit einem element definiert
1173: if type(list) is StringType or UnicodeType:
1174: splitted=list.split(";")
1175: else:
1176: splitted=list[0].split(";")
1177:
1178: splitted=[y.rstrip().lstrip() for y in splitted]
1179:
1180: for x in splitted:
1181: x=re.sub(r"[^A-z ]","",x)
1182: if (not x==u'') and x in wert:
1183: return 1
1184: return 0
1185:
1186: security.declareProtected('View management screens','editMPIWGBasisEditor')
1187: def editMPIWGBasisEditor(self, identifiedNames=None):
1188:
1189: """editform"""
1190: if not identifiedNames:
1191: identifiedNames=self.identifyNames(self.getContent('xdata_01'))
1192: # identifiedNames=self.getFullNameEntries()
1193:
1194: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','edit_MPIWGBasisNeu.zpt')).__of__(self)
1195: return pt(identifiedNames=identifiedNames)
1196:
1197: security.declareProtected('View management screens','editMPIWGBasisForm')
1198: def editMPIWGBasisForm(self):
1199: """editform"""
1200: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','edit_MPIWGBasis.zpt')).__of__(self)
1201: return pt()
1202:
1203: security.declareProtected('View management screens','editMPIWGRelatedPublicationsForm')
1204: def editMPIWGRelatedPublicationsForm(self):
1205: """Edit related Publications"""
1206: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','edit_MPIWGRelatedPublications.zpt')).__of__(self)
1207: return pt()
1208:
1209:
1210: def loadNewFileForm(self):
1211: """Neues XML-File einlesen"""
1212: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','MPIWGProject_newfile.zpt')).__of__(self)
1213: return pt()
1214:
1215: def loadNewFile(self,RESPONSE=None):
1216: """einlesen des neuen files"""
1217: fileupload=self.REQUEST['fileupload']
1218: if fileupload:
1219: file_name=fileupload.filename
1220: filedata=fileupload.read()
1221:
1222: argv=xmlhelper.proj2hash(filedata)
1223: #print argv.keys()
1224: for arg in definedFields:
1225:
1226: #print arg,argv[arg],getattr(self,arg)
1227: try:
1228: temp=argv[arg][0:]
1229: #old=getattr(self,arg)
1230: setattr(self,arg,temp)
1231: #print old,getattr(self,arg)
1232: except:
1233: """nothing"""
1234:
1235: if RESPONSE is not None:
1236: RESPONSE.redirect('manage_main')
1237:
1238: def manage_addMPIWGProjectForm(self):
1239: """form for adding the project"""
1240: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','addMPIWGProjectForm.zpt')).__of__(self)
1241: return pt()
1242:
1243: def manage_addMPIWGProject(self,id,RESPONSE=None):
1244: """method to add a project"""
1245: #print argv
1246: fileupload=self.REQUEST.get('fileupload',None)
1247: if fileupload:
1248:
1249: file_name=fileupload.filename
1250: filedata=fileupload.read()
1251:
1252: argv=xmlhelper.proj2hash(filedata)
1253:
1254: #print argv
1255: newObj=MPIWGProject(id,argv)
1256: else:
1257: newObj=MPIWGProject(id)
1258:
1259: self._setObject(id,newObj)
1260:
1261:
1262: if RESPONSE is not None:
1263: RESPONSE.redirect('manage_main')
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>