""" Classes for displaying, browsing and organizing the archive """ import OSAS_helpers from AccessControl import ClassSecurityInfo from Products.PageTemplates.PageTemplateFile import PageTemplateFile from OFS.Folder import Folder from OFS.SimpleItem import SimpleItem from Globals import InitializeClass,package_home import zLOG import os import os.path import stat import xml.dom.minidom from types import * class OSAS_storeOnline(SimpleItem): """Webfrontend für das Storagesystem liefert Browserumgebung """ meta_type="OSAS_StoreOnline__neu" security=ClassSecurityInfo() _v_fileSystem={} #chache fuer filesystem _v_metaFiles={} #chache fuer indexMeta def __init__(self,id): """initialize a new instance""" self.id = id security.declareProtected('View','index_html') def index_html(self): """main view either standard template zpt/storeOnline_index_html.zpt or storeOnline_index.html in tree""" if hasattr(self,'storeOnline_index.html'): return getattr(self,'storeOnline_index.html')() else: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','storeOnline_index_html.zpt')).__of__(self) return pt() def findIndexMeta(self,path=""): """finde index_meta fuer diesen eventuell virtuellen Pfad @param path: optional, default ist "", Pfad auf das Object relativ zum rootFolderName @return: None falls kein index.meta existiert sonst Pfad auf das index.meta """ realPath=os.path.normpath(os.path.join(self.rootFolderName,path)) #suche index.meta while (not os.path.exists(os.path.join(realPath,'index.meta'))) and (not ((realPath=="") or (realPath=="/"))): realPath=os.path.split(realPath)[0] if realPath=='' or realPath=='/': return None else: return os.path.join(realPath,'index.meta') def findEntryInIndexMeta(self,path): """fragm xml zum path @param path: Pfad auf das Object relativ zum rootFolderName @return: den Teil von Index.meta der Informationen zu path enthaelt, None wenn error. """ indexMeta=self.findIndexMeta(path) if not indexMeta: return None realPath=os.path.split(indexMeta)[0] path=os.path.normpath(os.path.join(self.rootFolderName,path)) dom=xml.dom.minidom.parse(indexMeta) #ist path ein directory? dirs=dom.getElementsByTagName('dir') for dir in dirs: pathes=dir.getElementsByTagName('path') if pathes: pathX=OSAS_helpers.getText(pathes[0].childNodes) else: pathX="" names=dir.getElementsByTagName('name') if names: name=OSAS_helpers.getText(names[0].childNodes) else: name="" checkpath=os.path.normpath(os.path.join(realPath,pathX,name)) if checkpath==path: return dir.toxml() #ist path ein file? files=dom.getElementsByTagName('file') for dir in dirs: pathes=dir.getElementsByTagName('path') if pathes: pathX=OSAS_helpers.getText(pathes[0].childNodes) else: pathX="" names=dir.getElementsByTagName('name') if names: name=OSAS_helpers.getText(names[0].childNodes) else: name="" checkpath=os.path.normpath(os.path.join(realPath,pathX,name)) if checkpath==path: return dir.toxml() return None def getSubDirsFromIndexMeta(self,path): """Gebe alle path untergeordenten Objekte aus @param path: optional, default ist "", Pfad auf das Object relativ zum rootFolderName @return: Directory [pfad auf das Objekt]->(fileType,''), fileType ist hierbei OSAS_dir_archive falls Object ein directory und OSAS_file_archive falls das Object ein File ist,der zweite Eintrag des Tupels ist zur Zeit immer '', spaeter wird hier die Beschreibung gemaess Metadaten stehen, wie bei readObjectsFromPath. """ ret={} indexMeta=self.findIndexMeta(path) if not indexMeta: return ret realPath=os.path.split(indexMeta)[0] path=path.replace(realPath,"") if path and (path[0]==os.sep): path=path[1:] stats=os.stat(indexMeta) #teste ob schon im cache if self._v_metaFiles.has_key(indexMeta) and (self._v_metaFiles[indexMeta][0]==stats[stat.ST_MTIME]): return self._v_metaFiles[indexMeta][1] dom=xml.dom.minidom.parse(indexMeta) dirs=[] dirs=dom.getElementsByTagName('dir')+dom.getElementsByTagName('file') for dir in dirs: pathes=dir.getElementsByTagName('path') if pathes: pathX=OSAS_helpers.getText(pathes[0].childNodes) else: pathX="" names=dir.getElementsByTagName('name') if names: name=OSAS_helpers.getText(names[0].childNodes) else: name="" if pathX==path: if dir.tagName=="dir": fileType="OSAS_dir_archive" else: fileType="OSAS_file_archive" object=os.path.join(realPath,pathX,name) ret[object]=(fileType,'') self._v_metaFiles[indexMeta]=(stats[stat.ST_MTIME],ret) # speicher im chache return ret def getMetaInfoFromIndexMeta(self,path): """metadaten zu path als html aus dem index.meta file zu path @param path: optional, default ist "", Pfad auf das Object relativ zum rootFolderName @return: metadata als html """ xmlInfos=self.findEntryInIndexMeta(path) if xmlInfos: return OSAS_helpers.getMetaInfoFromXML(path,xmlInfos) else: return "" def readObjectsFromPath(self,path=""): """Liest files aus dem path und speichert im cache _v_filesystem. @param path : path relativ zum root folder des Storagesystems @return: directory der Form [pfad zum Objekt] -> (fileType,metadatum als String) """ realPath=os.path.normpath(os.path.join(self.rootFolderName,path)) metaData=self.testmd #test if realPath.find(self.rootFolderName) <0: #versuch auf Pfad unterhalb des Rootfolder zuzugreifen return {} if not os.path.exists(realPath): #return None,"(ERROR) path %s does not exist."%path return None stats=os.stat(realPath) #teste ob schon im cache if self._v_fileSystem.has_key(realPath) and (self._v_fileSystem[realPath][0]==stats[stat.ST_MTIME]): return self._v_fileSystem[realPath][1] dir=os.listdir(realPath) ret={} for filename in dir: object=os.path.join(realPath,filename) fileType=OSAS_helpers.checkOSASFileType(object) if fileType: ret[object]=(fileType,metaData.getDisplayFieldsAsStr(object)) self._v_fileSystem[realPath]=(stats[stat.ST_MTIME],ret) # speicher im chache return ret def giveHandlers(self,path,type): """teste ob fuer diesen Typ, handler definiert sind und gibt einen entsprechenden Link zurueck, der das Object mit diesem Handler ausfuehrt. @param path: Pfad auf das Objekt @param type: Typ des Objektes @return: (string) html-Fragment, link der das Objekt mit diesem Handler anzeigt. """ ret=[] for handler in self.ZopeFind(self.aq_parent,obj_metatypes=['OSAS_HandlerObject__neu'],search_sub=1): if type in handler[1].objectTypes: path=path.replace(getattr(handler[1],'ignorePath',''),'') url=handler[1].prefix%path text=handler[1].title string="""%s"""%(url,text) ret.append(string) return ret def generateTree(self,path=""): """erzeuge liest die Objekte aus die im Pfad gespeichert sind @param path: optional mit default='', Pfad relativ zu rootFolderName @return: List von Tripeln, (link_html,array of handlers,metainformationen) hierbei ist - (string) link_html ein html-Fragement, falls das Objekt vom Typ OSAS_dir ist, ist dies ein Link auf dieses Verzeichnis, sonst der Dateiname - (string) handler sind die Ergebnisse von giveHandlers fuer dieses Objekt - (string) metainformationen die Metainformationen zum Objekt als Ergebnis von readObjectsFromPath """ objects=self.readObjectsFromPath(path) if not objects: objects={} im=self.getSubDirsFromIndexMeta(path) for key in im.keys(): #virtuelle pfade hinzufuegen if not objects.has_key(key): objects[key]=im[key] def sortLow(x,y): return cmp(x.lower(),y.lower()) ret=[] objectSorted=objects.keys() objectSorted.sort(sortLow) for object in objectSorted: handler=self.giveHandlers(object,objects[object][0]) if objects[object][0]=="OSAS_dir": string="""%s"""%(object,os.path.split(object)[1]) ret.append((string,handler,objects[object][1])) elif objects[object][0]=="OSAS_dir_archive": string="""%s (A)"""%(object,os.path.split(object)[1]) ret.append((string,handler,objects[object][1])) else: ret.append((os.path.split(object)[1],handler,objects[object][1])) return ret def path_to_link(self,pathTmp=""): """generates navigation bar for viewfiles""" path=os.path.normpath(os.path.join(self.rootFolderName,pathTmp)) URL=self.absolute_url() string="" tmppath=os.path.dirname(path) i=0 pathes=[[path, os.path.basename(path)]] while not (len(tmppath)==1): i=i+1 if i>20: break pathes.append([tmppath, os.path.basename(tmppath)]) tmppath=os.path.dirname(tmppath) while i>=0: if pathes[i][0].find(self.rootFolderName) <0: #versuch auf Pfad unterhalb des Rootfolder zuzugreifen string=string+""+pathes[i][1]+"/" else: string=string+""+pathes[i][1]+"/" i=i-1 return string def getMetaFile(self,path): """Lese Metafile ein""" tmp=OSAS_helpers.getMetaFile(self,path) #zLOG.LOG("EE",zLOG.INFO,type(tmp)) return tmp InitializeClass(OSAS_storeOnline) def manage_addOSAS_storeOnlineForm(self): """interface for adding the OSAS_root""" pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','addStoreOnline.zpt')).__of__(self) return pt() def manage_addOSAS_storeOnline(self,id,RESPONSE=None): """add the OSAS_root""" newObj=OSAS_storeOnline(id) self._setObject(id,newObj) if RESPONSE is not None: RESPONSE.redirect('manage_main')