Annotation of versionedFile/extVersionedFile.py, revision 1.4
1.3 dwinter 1: """actual version of the versioned file folder with external filestorage,
2: using the ExtFile Product, this version replaces externaVersionedFile.py
3: DW 11.10.2006
4: """
5:
1.1 dwinter 6: from OFS.Folder import Folder
7: from OFS.Image import File
8: from OFS.Image import cookId
9: from Globals import DTMLFile, InitializeClass,package_home
10: from Products.PageTemplates.PageTemplateFile import PageTemplateFile
11: from AccessControl import getSecurityManager
12: from Products.PageTemplates.PageTemplate import PageTemplate
13: from Products.PageTemplates.ZopePageTemplate import ZopePageTemplate
14: from AccessControl import ClassSecurityInfo
15: from difflib import Differ
16: from pprint import pprint
17: from Products.ExtFile.ExtFile import *
18: from Products.ZCatalog.CatalogPathAwareness import CatalogAware
19:
20: try:
21: from Products.ImageArchive.ImageArchive import manage_AddImageZogiLib
22: except:
23: print "no images"
24:
25:
26: from threading import Thread
27: import shutil
28: import tempfile
29: import os.path
30: import urllib
31:
32: import time
33: try:
34: from Products.ECHO_content.ECHO_collection import ECHO_basis
35: except:
36: print "ECHO Elements not imported"
37: class ECHO_basis:
38: """leer"""
39: manage_options=()
40:
41:
42: def sortv(x,y):
43: return cmp(x[0],y[0])
44: tdir = "/tmp/downloadVersionedFiles"
45:
46: class generateDownloadZip:
47: """generateDownloadSet"""
48:
49: def __init__(self,folderObject,url):
50: """init downloadzip"""
51: self.folder=folderObject
52: self.done=None
53: self.response=""
54: self.url=url
55:
56: def __call__(self):
57: """call generate download zip"""
58: storeTempDir=tempfile.tempdir
59: tempfile.tempdir=tdir
60:
61: tmpPath=tempfile.mktemp()
62: tmpZip=tempfile.mktemp()+".gtz"
63: tmpFn=os.path.split(tmpZip)[1]
64:
65: if not os.path.exists(tempfile.tempdir):
66: os.mkdir(tempfile.tempdir)
67:
68: if not os.path.exists(tmpPath):
69: os.mkdir(tmpPath)
70:
71: self.response="<h3>1. step: getting the files</h3>"
72:
73: for files in self.folder.ZopeFind(self.folder,obj_metatypes=['extVersionedFile']):
74: lastV=files[1].getLastVersion()
75: self.response+=str("<p>Get File: %s<br>\n"%lastV.title)
76:
77: savePath=os.path.join(tmpPath,lastV.title)
78: fh=file(savePath,"w")
1.2 dwinter 79: fh.write(lastV.getData())
1.1 dwinter 80: fh.close()
81:
82: self.response+="<h3>2. step: creating the downloadable file</h3>"
83: self.response+="<p>Create gtar<br>"
84: self.response+="<p>This can take a while....<br>\n"
85:
86: fh=os.popen2("tar zcvf %s %s/*"%(tmpZip,tmpPath),1)[1]
87: self.response+="<br>"
88: for c in fh.read():
89: self.response+=c
90: if c==")":
91: self.response+="<br>\n"
92:
93:
94:
95:
96: shutil.rmtree(tmpPath)
97:
98: self.response+="<p>finished<br>\n"
99:
100: len=os.stat(tmpZip)[6]
101: downloadUrl=self.url+"/downloadSet"
102: self.response+="""<h1><a href="downloadSet?fn=%s">Click here for download ( %i Byte)</a></h1>\n"""%(tmpFn,len)
103: self.response+="""<p>The file you receive is a tar (gnutar) compressed file, after unpacking you will find a new folder <emph>tmp</emph> where the files are stored in.</p>"""
104: self.response+="""<p>The file will be stored for a while, you can download it later, the URL is:</p>
105: <p><a href="downloadSet?fn=%s">%s?fn=%s</a></h1>\n"""%(tmpFn,downloadUrl,tmpFn)
106:
107: self.done=True
108:
109:
110: def getResult(self):
111: """get result"""
112: return self.response
113:
114: def isDone(self):
115: if self.done:
116: return True
117: else:
118: return False
119:
120:
121: class extVersionedFileFolder(Folder,ECHO_basis):
122: """Folder with versioned files"""
123:
124:
125: meta_type = "extVersionedFileFolder"
126:
127: security= ClassSecurityInfo()
128: security.declareProtected('AUTHENTICATED_USER','addFileForm')
129: filesMetaType=['extVersionedFile']
130: if ECHO_basis:
131: optTMP= Folder.manage_options+ECHO_basis.manage_options
132: else:
133: optTMP= Folder.manage_options
134:
135: manage_options =optTMP+(
136: {'label':'Generate Index.html','action':'generateIndexHTML'},
137: {'label':'Generate Image Index.html','action':'generateIndexHTML_image'},
138: {'label':'Generate history_template.html','action':'generateHistoryHTML'},
139: {'label':'Import Folder','action':'importFolderForm'},
140: {'label':'Export Folder','action':'exportFolder'},
141: {'label':'Position of version number','action':'changeHistoryFileNamesForm'},
142: )
143:
144:
145: def changeHistoryFileNamesForm(self):
146: """change position of version num"""
147: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','changeHistoryFileNamesForm.zpt')).__of__(self)
148: return pt()
149:
150:
151: def changeHistoryFileNames(self,positionVersionNum="front",RESPONSE=None):
152: """change position of version num"""
153:
154:
155:
156: versions=self.ZopeFind(self,obj_metatypes=['extVersionedFileObject'],search_sub=1)
157:
158: if not (getattr(self,'positionVersionNum','front')==positionVersionNum):
159:
160: for version in versions:
161:
162: if positionVersionNum=="front":
163:
164: titleTmp=os.path.splitext(version[1].title)
165: titleTmp2="_".join(titleTmp[0].split("_")[0:-1])
166: if len(titleTmp)>1:
167: id=titleTmp[0].split("_")[-1]+"_"+titleTmp2+"."+titleTmp[1]
168: else:
169: id=titleTmp[0].split("_")[-1]+"_"+titleTmp2
170:
171: else:
172: titleTmp="_".join(version[1].getId().split("_")[1:])
173: tmp=os.path.splitext(titleTmp)
174: if len(tmp)>1:
175: id=tmp[0]+"_"+version[1].getId().split("_")[0]+tmp[1]
176: else:
177: id=tmp[0]+"_"+version[1].getId().split("_")[0]
178:
179:
180:
181: version[1].aq_parent.manage_renameObjects(ids=[version[1].getId()],new_ids=[id])
182: version[1].title=id
183:
184:
185: self.positionVersionNum=positionVersionNum
186: if RESPONSE:
187: RESPONSE.redirect("manage_main")
188:
189:
190:
191: def importFolderForm(self):
192: """form fuer folder import"""
193: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','importFolderForm.zpt')).__of__(self)
194: return pt()
195:
196: def importFolder(self,path,comment="",author=None,lockedBy=None,RESPONSE=None):
197: """importiere inhalt eines folders"""
198:
199: for fileName in os.listdir(path):
200: if os.path.isfile(os.path.join(path,fileName)):
201: manage_addextVersionedFile(self,fileName,'','')
202: id=fileName
203: ob=self._getOb(fileName)
204: ob.title=id
205: file2=file(os.path.join(path,fileName))
206:
207: obj=ob.manage_addextVersionedFileObject(id,comment,author,file2,content_type='')
208:
209: if RESPONSE:
210: RESPONSE.redirect(self.REQUEST['URL1'])
211:
212: zipThreads={}
213: zipThreads2={}
214:
215: def refreshTxt(self):
216: """txt fuer refresh"""
217: tn=self.REQUEST.SESSION['threadName']
218: return """ 2;url=%s?repeat=%s """%(self.absolute_url()+"/exportFolder",tn)
219:
220: def exportFolder(self,repeat=None):
221: """exportiert alle akutellen files des folders"""
222: threadName=repeat
223:
224: downloadZip=generateDownloadZip(self,self.absolute_url())
225: downloadZip()
226: return downloadZip.getResult()
227: ## if not threadName or threadName=="":
228: ## threadStart=generateDownloadZip(self,self.absolute_url())
229: ## thread=Thread(target=threadStart)
230:
231: ## thread.start()
232:
233:
234: ## self.zipThreads[thread.getName()[0:]]=threadStart
235: ## self.zipThreads2[thread.getName()[0:]]=thread
236: ## self.REQUEST.SESSION['threadName']=thread.getName()[0:]
237: ## wait_template=self.aq_parent.ZopeFind(self.aq_parent,obj_ids=['zip_wait_template'])
238: ## if wait_template:
239: ## return wait_template[0][1]()
240: ## pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','zip_wait.zpt')).__of__(self)
241: ## return pt()
242:
243: ## else:
244: ## self.REQUEST.SESSION['threadName']=threadName
245:
246: ## if (self.zipThreads[threadName].getResult()==None):
247:
248: ## wait_template=self.aq_parent.ZopeFind(self.aq_parent,obj_ids=['wait_template'])
249: ## if wait_template:
250: ## return wait_template[0][1]()
251:
252: ## pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','zip_wait.zpt')).__of__(self)
253: ## return pt()
254: ## else:
255: ## if self.zipThreads[threadName].isDone():
256: ## self.REQUEST.SESSION['result']=self.zipThreads[threadName].getResult()
257: ## self.zipThreads2[threadName].join()
258: ## del(self.zipThreads2[threadName])
259: ## del(self.zipThreads[threadName])
260: ## pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','zip_result.zpt')).__of__(self)
261: ## return pt()
262:
263: ## else:
264: ## self.REQUEST.SESSION['result']=self.zipThreads[threadName].getResult()
265: ## self.REQUEST.SESSION['threadName']=threadName
266: ## pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','zip_wait_result.zpt')).__of__(self)
267: ## return pt()
268:
269: def downloadSet(self,fn):
270: """download prepared set"""
271: filename=os.path.join(tdir,fn)
272:
273:
274: self.REQUEST.RESPONSE.setHeader("Content-Disposition","""attachement; filename="%s" """%"downloadFileFolder.tgz")
275: self.REQUEST.RESPONSE.setHeader("Content-Type","application/octet-stream")
276: len=os.stat(filename)[6]
277: self.REQUEST.RESPONSE.setHeader("Content-Length",len)
278: images=file(filename).read()
279: self.REQUEST.RESPONSE.write(images)
280: self.REQUEST.RESPONSE.close()
281:
282:
283:
284: def helpDownload(self):
285: """download help"""
286:
287: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','helpDownload')).__of__(self)
288: return pt()
289:
290: def generateIndexHTML_image(self,RESPONSE=None):
291: """lege standard index.html an"""
292:
293:
294: if not self.ZopeFind(self,obj_ids=['index.html']):
295: zt=ZopePageTemplate('index.html')
296: self._setObject('index.html',zt)
297: default_content_fn = os.path.join(package_home(globals()),
298: 'zpt/versionFileFolderMain_image.zpt')
299: text = open(default_content_fn).read()
300: zt.pt_edit(text, 'text/html')
301:
302: else:
303: return "already exists!"
304:
305: if RESPONSE is not None:
306: RESPONSE.redirect('manage_main')
307:
308:
309: def generateAddFileForm(self,RESPONSE=None):
310: """lege standard addfileform an"""
311: #TODO: write generateaddfileform only a dummy at them moment
312:
313: if not self.ZopeFind(self,obj_ids=['addFileForm.dtml']):
314: zt=ZopePageTemplate('index.html')
315: self._setObject('index.html',zt)
316: default_content_fn = os.path.join(package_home(globals()),
317: 'zpt/versionFileFolderMain.zpt')
318: text = open(default_content_fn).read()
319: zt.pt_edit(text, 'text/html')
320:
321: else:
322: return "already exists!"
323:
324: if RESPONSE is not None:
325: RESPONSE.redirect('manage_main')
326:
327:
328: def generateIndexHTML(self,RESPONSE=None):
329: """lege standard index.html an"""
330:
331:
332: if not self.ZopeFind(self,obj_ids=['index.html']):
333: zt=ZopePageTemplate('index.html')
334: self._setObject('index.html',zt)
335: default_content_fn = os.path.join(package_home(globals()),
336: 'zpt/versionFileFolderMain.zpt')
337: text = open(default_content_fn).read()
338: zt.pt_edit(text, 'text/html')
339:
340: else:
341: return "already exists!"
342:
343: if RESPONSE is not None:
344: RESPONSE.redirect('manage_main')
345:
346:
347: def generateHistoryHTML(self,RESPONSE=None):
348: """lege standard index.html an"""
349:
350:
351:
352: if not self.ZopeFind(self,obj_ids=['history_template.html']):
353: zt=ZopePageTemplate('history_template.html')
354: self._setObject('history_template.html',zt)
355: default_content_fn = os.path.join(package_home(globals()),
356: 'zpt/versionHistory.zpt')
357: text = open(default_content_fn).read()
358: zt.pt_edit(text, 'text/html')
359:
360: else:
361: return "already exists!"
362:
363: if RESPONSE is not None:
364: RESPONSE.redirect('manage_main')
365:
366:
367:
368:
369: def getVersionedFiles(self,sortField='title'):
370: """get all versioned files"""
371:
372: def sortName(x,y):
373: return cmp(x[1].title.lower(),y[1].title.lower())
374:
375: def sortDate(x,y):
376: return cmp(y[1].getLastVersion().getTime(),x[1].getLastVersion().getTime())
377:
378:
379: def sortComment(x,y):
380:
381:
382:
383: try:
384: xc=getattr(x[1],'comment','ZZZZZZZZZZZZZ').lower()
385: except:
386: xc='ZZZZZZZZZZZZZ'.lower()
387: try:
388: yc=getattr(y[1],'comment','ZZZZZZZZZZZZZ').lower()
389: except:
390: yc='ZZZZZZZZZZZZZ'.lower()
391:
392:
393: if (xc=='') or (xc=='ZZZZZZZZZZZZZ'.lower()):
394:
395: try:
396: xc=x[1].getLastVersion().getVComment().lower()
397: except:
398: xc='ZZZZZZZZZZZZZ'.lower()
399:
400: if (yc=='') or (yc=='ZZZZZZZZZZZZZ'.lower()):
401: try:
402: yc=y[1].getLastVersion().getVComment().lower()
403: except:
404: yc='ZZZZZZZZZZZZZ'.lower()
405:
406:
407: return cmp(xc,yc)
408:
409: def sortAuthor(x,y):
410:
411: return cmp(x[1].getLastVersion().lastEditor().lower(),y[1].getLastVersion().lastEditor().lower())
412:
413: versionedFiles=self.ZopeFind(self,obj_metatypes=self.filesMetaType)
414:
415:
416: if sortField=='title':
417: versionedFiles.sort(sortName)
418: elif sortField=='date':
419: versionedFiles.sort(sortDate)
420: elif sortField=='author':
421: versionedFiles.sort(sortAuthor)
422: elif sortField=='comment':
423: versionedFiles.sort(sortComment)
424:
425: return versionedFiles
426:
427:
428: def header_html(self):
429: """zusätzlicher header"""
430: ext=self.ZopeFind(self,obj_ids=["header.html"])
431: if ext:
432: return ext[0][1]()
433: else:
434: return ""
435:
436:
437: security.declareProtected('View','index_html')
438: def index_html(self):
439: """main"""
440: ext=self.ZopeFind(self,obj_ids=["index.html"])
441: if ext:
442: return ext[0][1]()
443:
444: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','versionFileFolderMain')).__of__(self)
445: return pt()
446:
447:
448:
449: def addFileForm(self):
450: """add a file"""
451: ext=self.ZopeFind(self,obj_ids=["addFileForm.dtml"])
452: if ext:
453: return ext[0][1]('',globals(),version='1',AUTHENTICATED_USER=self.REQUEST.AUTHENTICATED_USER)
454:
455: out=DTMLFile('dtml/newFileAdd', globals(),Kind='versionedFileObject',kind='versionedFileObject',version='1').__of__(self)
456: return out()
457:
458:
459: def addFile(self,vC,file,author,newName='',content_type='',RESPONSE=None):
460: """ add a new file"""
461: if newName=='':
462: filename=file.filename
463: id=filename[max(filename.rfind('/'),
464: filename.rfind('\\'),
465: filename.rfind(':'),
466: )+1:]
467:
468: else:
469: id=newName
470:
471: vC=self.REQUEST.form['vC']
472: manage_addextVersionedFile(self,id,'','')
473: #if (getattr(self,'commentNonEmpty',0)==1) and vC.strip()=="":
474:
475:
476: ob=self._getOb(id)
477: ob.title=id
478: file2=file
479:
480: obj=ob.manage_addextVersionedFileObject(id,vC,author,file2,content_type=content_type)
481: self.REQUEST.SESSION['objID']=ob.getId()
482: self.REQUEST.SESSION['objID_parent']=None
483:
484: if obj.getSize()==0:
485: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','errorUploadFile')).__of__(self)
486: return pt()
487:
488: RESPONSE.redirect(self.REQUEST['URL1'])
489:
490:
491: def deleteEmptyObject(self,submit,RESPONSE=None):
492: """deleteemptyobject"""
493: if submit=="delete it":
494: if self.REQUEST.SESSION['objID_parent']:
495: obj=getattr(self,self.REQUEST.SESSION['objID_parent'])
496:
497: else:
498: obj=self
499: obj.manage_delObjects([self.REQUEST.SESSION['objID']])
500:
501: RESPONSE.redirect(self.REQUEST['URL1'])
502:
503:
504: manage_addextVersionedFileFolderForm=DTMLFile('dtml/extfolderAdd', globals())
505:
506:
507: def manage_addextVersionedFileFolder(self, id, title='',
508: createPublic=0,
509: createUserF=0,
510: REQUEST=None):
511: """Add a new Folder object with id *id*.
512:
513: If the 'createPublic' and 'createUserF' parameters are set to any true
514: value, an 'index_html' and a 'UserFolder' objects are created respectively
515: in the new folder.
516: """
517: ob=extVersionedFileFolder()
518: ob.id=str(id)
519: ob.title=title
520: self._setObject(id, ob)
521: ob=self._getOb(id)
522:
523: checkPermission=getSecurityManager().checkPermission
524:
525: if createUserF:
526: if not checkPermission('Add User Folders', ob):
527: raise Unauthorized, (
528: 'You are not authorized to add User Folders.'
529: )
530: ob.manage_addUserFolder()
531:
532:
533: if REQUEST is not None:
534: return self.manage_main(self, REQUEST, update_menu=1)
535:
536:
537:
538: class extVersionedFileObject(ExtFile):
539: """File Object im Folder"""
540: security= ClassSecurityInfo()
541: meta_type = "extVersionedFileObject"
542:
543: manage_editForm =DTMLFile('dtml/fileEdit',globals(),
544: Kind='File',kind='file')
545: manage_editForm._setName('manage_editForm')
546:
547:
548:
549:
550: security.declarePublic('getTitle')
551:
552: def getTitle(self):
553: """get title"""
554: return self.title
555:
556: security.declarePublic('getVComment')
557: def getVComment(self):
558: """get the comment of this file"""
559: if not hasattr(self,'vComment') or (not self.vComment) or (self.vComment.lstrip()==""):
560: return "Add comment"
561:
562: else:
563: return self.vComment
564:
565: def manageVCommentForm(self):
566: """add a comment"""
567:
568: self.REQUEST.SESSION['refer']=self.REQUEST['HTTP_REFERER']
569:
570:
571:
572: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','addVComment')).__of__(self)
573: return pt()
574:
575: def manageVComment(self,text,comment_author,submit,REQUEST=None):
576: """manage comments"""
577: if submit =='change':
578: if text=='':
579: self.vComment=None
580: else:
581: self.vComment=text
582: self.vComment_author=comment_author
583:
584: self.vComment_date=time.strftime("%Y-%m-%d %H:%M:%S",time.localtime())
585:
586: if self.REQUEST.SESSION.has_key('refer'):
587:
588: return REQUEST.RESPONSE.redirect(self.REQUEST.SESSION['refer'])
589: return REQUEST.RESPONSE.redirect(self.aq_parent.absolute_url()+"/history")
590:
591:
592: security.declarePublic('getVersionComment')
593: def getVersionComment(self):
594: """getversioncomment"""
595: return self.versionComment
596:
597: security.declarePublic('getTime')
598:
599: def getTime(self):
600: """getTime"""
601: #return self.bobobase_modification_time().ISO()
602: if hasattr(self,'time'):
603: return time.strftime("%Y-%m-%d %H:%M:%S",self.time)
604: elif hasattr(self,'timefixed'):
605: return self.timefixed
606: else:
607: setattr(self,'timefixed',self.bobobase_modification_time().ISO())
608: return self.bobobase_modification_time().ISO()
609:
610:
611:
612:
613:
614: def download(self,REQUEST=None,RESPONSE=None):
615: """download and lock"""
616:
617: self.REQUEST.RESPONSE.setHeader("Content-Disposition","""attachement; filename=%s"""%self.getId())
618: self.REQUEST.RESPONSE.setHeader("Content-Type","application/octet-stream")
619: #try:
620: # txt=self.index_html()
621: #except:
622: # txt=self.index_html(REQUEST,RESPONSE)
623: #
624: #self.REQUEST.RESPONSE.setHeader("Content-Length","str(len(txt)+1000)")
625:
626: self.content_type="application/octet-stream"
627: self.REQUEST.RESPONSE.redirect(self.absolute_url())
628: #txt=urllib.urlopen(self.absolute_url()).read()
629: #self.REQUEST.RESPONSE.write(txt)
630:
631:
632: #self.REQUEST.close()
633:
634: security.declareProtected('AUTHENTICATED_USER','downloadLocked')
635: def downloadLocked(self):
636: """download and lock"""
637:
638:
639: if repr(self.REQUEST['AUTHENTICATED_USER'])=='Anonymous User':
640: return "please login first"
641: if not self.aq_parent.lockedBy=="":
642: return "cannot be locked because is already locked by %s"%self.lockedBy
643: self.aq_parent.lockedBy=self.REQUEST['AUTHENTICATED_USER']
644:
645: self.content_type="application/octet-stream"
646: self.REQUEST.RESPONSE.redirect(self.absolute_url())
647:
648: def setVersionNumber(self,versionNumber):
649: """set version"""
650: self.versionNumber=versionNumber
651:
652:
653: security.declarePublic('getVersionNumber')
654:
655: def getVersionNumber(self):
656: """get version"""
657: return self.versionNumber
658:
659: security.declarePublic('getVersionComment')
660: def getVersionComment(self):
661: """get version"""
662: return self.versionComment
663:
664:
665:
666: security.declarePublic('lastEditor')
667:
668: def lastEditor(self):
669: """last Editor"""
670: if hasattr(self,'author'):
671: try:
672: ret=self.author.replace("-","\n")
673: except:#old version of versionded file sometimes stored the user object and not only the name the following corrects this
674: ret=str(self.author).replace("-","\n")
675: ret=ret.replace("\r","\n")
676: return ret.lstrip().rstrip()
677:
678: else:
679: jar=self._p_jar
680: oid=self._p_oid
681:
682: if jar is None or oid is None: return None
683:
684: return jar.db().history(oid)[0]['user_name']
685:
686:
687:
688:
689: manage_addextVersionedFileObjectForm=DTMLFile('dtml/fileAdd', globals(),Kind='extVersionedFileObject',kind='extVersionedFileObject', version='1')
690:
691: def manage_addextVersionedFileObject(self,id,vC='',author='', file='',title='',precondition='', content_type='',
692: REQUEST=None):
693: """Add a new File object.
694:
695: Creates a new File object 'id' with the contents of 'file'"""
696:
697: id=str(id)
698: title=str(title)
699: content_type=str(content_type)
700: precondition=str(precondition)
701:
702: id, title = cookId(id, title, file)
703:
704: self=self.this()
705:
706: # First, we create the file without data:
707: self._setObject(id, extVersionedFileObject(id,title,'',content_type, precondition))
708: self._getOb(id).versionComment=str(vC)
709: self._getOb(id).time=time.localtime()
710:
711: setattr(self._getOb(id),'author',author)
712:
713: # Now we "upload" the data. By doing this in two steps, we
714: # can use a database trick to make the upload more efficient.
715: if file:
716: self._getOb(id).manage_upload(file)
717: if content_type:
718: self._getOb(id).content_type=content_type
719:
720: if REQUEST is not None:
721: REQUEST['RESPONSE'].redirect(self.absolute_url()+'/manage_main')
722:
723:
724:
725:
726: class extVersionedFile(CatalogAware,Folder):
727: """Versioniertes File"""
728:
729: default_catalog='fileCatalog'
730:
731: security= ClassSecurityInfo()
732:
733: security.declarePublic('getTitle')
734: def getTitle(self):
735: """get title"""
736: return self.title
737:
738: def PrincipiaSearchSource(self):
739: """Return cataloguable key for ourselves."""
740: return str(self)
741:
742: def __init__(self, id, title, lockedBy,author):
743: """init"""
744: self.id=id
745: self.title=title
746: self.lockedBy=lockedBy
747: self.author=author
748:
749: def manageImagesForm(self):
750: """manage Images attached to the file"""
751:
752: self.REQUEST.SESSION['refer']=self.REQUEST['HTTP_REFERER']
753:
754: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','manageImage')).__of__(self)
755: return pt()
756:
757: def manageImages(self,imageUrl=None,caption=None,REQUEST=None):
758: """manage URL"""
759: if imageUrl and (not imageUrl==""):
760: manage_AddImageZogiLib(self,libPath=imageUrl,caption=caption)
761:
762: if self.REQUEST.SESSION.has_key('refer'):
763:
764: return REQUEST.RESPONSE.redirect(self.REQUEST.SESSION['refer'])
765: return REQUEST.RESPONSE.redirect(self.aq_parent.absolute_url())
766:
767:
768:
769: def changeImages(self,caption=None,submit=None,id=None,REQUEST=None):
770: """manage URL"""
771: if submit=="change caption":
772: image=self.ZopeFind(self,obj_ids=[id])
773: if image:
774: image[0][1].caption=caption[0:]
775:
776: elif submit=="delete":
777: image=self.ZopeFind(self,obj_ids=[id])
778: if image:
779: self.manage_delObjects([image[0][1].getId()])
780:
781:
782: if self.REQUEST.SESSION.has_key('refer'):
783:
784: return REQUEST.RESPONSE.redirect(self.REQUEST.SESSION['refer'])
785: return REQUEST.RESPONSE.redirect(self.aq_parent.absolute_url())
786:
787:
788:
789:
790: def getImages(self):
791: """get Images"""
792: images=self.ZopeFind(self,obj_metatypes=["ImageZogiLib"])
793: if not images:
794: return None
795: else:
796: return images
797:
798: security.declarePublic('getComment')
799: def getComment(self):
800: """get the comment of this file"""
801: if not hasattr(self,'comment') or (not self.comment) or (self.comment.lstrip()==""):
802: return "Add comment"
803:
804: else:
805: return self.comment
806:
807:
808: meta_type="extVersionedFile"
809:
810: def manageCommentForm(self):
811: """add a comment"""
812: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','addComment')).__of__(self)
813: return pt()
814:
815: def manageComment(self,text,comment_author,submit,REQUEST=None):
816: """manage comments"""
817: if submit =='change':
818: if text=='':
819: self.comment=None
820: else:
821: self.comment=text
822: self.comment_author=comment_author
823:
824: self.comment_date=time.strftime("%Y-%m-%d %H:%M:%S",time.localtime())
825:
826: return REQUEST.RESPONSE.redirect(self.aq_parent.absolute_url())
827:
828: security.declarePublic('getLastChangeDate')
829:
830: def getLastChangeDate(self):
831: """get last change date"""
832: lv=self.getLastVersion()
833: time=lv.getTime()
834: return time
835:
836: def getLastEditor(self):
837: """get last change date"""
838: lv=self.getLastVersion()
839: le=lv.lastEditor()
840: return le
841:
842: def getLockedBy(self):
843: """get locked by"""
844: return str(self.lockedBy)
845:
846: security.declarePublic('getLastVersion')
847: def getLastVersion(self):
848: """Last Version"""
849: tmp=0
850: lastVersion=None
851:
852:
853: for version in self.ZopeFind(self):
854:
855: if hasattr(version[1],'versionNumber'):
856:
857: if int(version[1].versionNumber) > tmp:
858: tmp=int(version[1].versionNumber,)
859: lastVersion=version[1]
860: if lastVersion==None:
861: lastVersion=version[1]
862: lastVersion.versionNumber=1
863: return lastVersion
864:
865:
866: def diff(self,data):
867: """differenz between lastversion and data"""
868: d=Differ()
1.2 dwinter 869: tmp=self.getLastVersion().getData()
1.1 dwinter 870: #print "XX",data,tmp
871: try:
872: l=list(d.compare(data.splitlines(1),tmp.splitlines(1)))
873: except:
874: return 0,""
875: plus=0
876: minus=0
877: for a in l:
878: if a[0]=='+':
879: plus+=1
880: if a[0]=='-':
881: minus+=1
882:
883:
884: return max([plus,minus]),l
885: security.declarePublic('index_html')
886: def index_html(self):
887: """main view"""
1.4 ! dwinter 888: #lastVersion=self.getLastVersion()
1.1 dwinter 889: #return "File:"+self.title+" Version:%i"%lastVersion.versionNumber," modified:",lastVersion.bobobase_modification_time()," size:",lastVersion.getSize(),"modified by:",lastVersion.lastEditor()
1.4 ! dwinter 890: #return "File: %s Version:%i modified:%s size:%s modified by:%s"%(self.title,lastVersion.versionNumber,lastVersion.getTime(),lastVersion.getSize(),lastVersion.lastEditor())
! 891: return self.history()
1.1 dwinter 892:
893:
894: security.declarePublic('getVersion')
895: def getVersion(self):
896: tmp=0
897: for version in self.ZopeFind(self):
898:
899: if hasattr(version[1],'versionNumber'):
900:
901: if int(version[1].versionNumber) > tmp:
902: tmp=int(version[1].versionNumber,)
903: return tmp+1
904:
905:
906: security.declareProtected('AUTHENTICATED_USER','unlock')
907:
908: def history(self):
909: """history"""
910:
911: ext=self.ZopeFind(self.aq_parent,obj_ids=["history_template.html"])
912: if ext:
913: return getattr(self,ext[0][1].getId())()
914:
915: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','versionHistory')).__of__(self)
916: return pt()
917:
918: def getVersions(self):
919: """get all versions"""
920: ret=[]
921: for version in self.ZopeFind(self):
922: if hasattr(version[1],'versionNumber'):
923: ret.append((version[1].versionNumber,version[1]))
924: ret.sort(sortv)
925: return ret
926:
927: security.declareProtected('AUTHENTICATED_USER','forceunlock')
928: def forceunlock(self,RESPONSE=None):
929: """unlock"""
930: #safe who had the lock
931: if self.lockedBy:
932: self.brokenLock=str(self.lockedBy)
933: else:
934: self.brokenLock=""
935: self.lockedBy=''
936: return self.brokenLock
937:
938: security.declareProtected('AUTHENTICATED_USER','unlock')
939: def unlock(self,RESPONSE):
940: """unlock"""
941: if str(self.lockedBy) in [str(self.REQUEST['AUTHENTICATED_USER'])]:
942: self.lockedBy=''
943: RESPONSE.redirect(self.REQUEST['HTTP_REFERER'])
944: else:
945: return "Sorry, not locked by you! (%s,%s)"%(self.lockedBy,self.REQUEST['AUTHENTICATED_USER'])
946:
947:
948:
949: security.declareProtected('AUTHENTICATED_USER','addVersionedFileObjectForm')
950:
951: def addVersionedFileObjectForm(self):
952: """add a new version"""
953:
954: if str(self.REQUEST['AUTHENTICATED_USER']) in ["Anonymous User"]:
955: return "please login first"
956: if (self.lockedBy==self.REQUEST['AUTHENTICATED_USER']) or (self.lockedBy==''):
957: ext=self.ZopeFind(self.aq_parent,obj_ids=["addNewVersion.dtml"])
958: if ext:
959: return ext[0][1]('',globals(),version=self.getVersion(),lastComment=self.getLastVersion().getVersionComment(),AUTHENTICATED_USER=self.REQUEST.AUTHENTICATED_USER)
960: else:
961: out=DTMLFile('dtml/fileAdd', globals(),Kind='VersionedFileObject',kind='versionedFileObject',version=self.getVersion()).__of__(self)
962: return out()
963: else:
964: return "Sorry file is locked by somebody else"
965:
966: def manage_addVersionedFileObject(self,id,vC,author,file='',title='',precondition='', content_type='',changeName='no',newName='', RESPONSE=None):
967: """add"""
968: try: #der ganze vC unsinn muss ueberarbeitet werden
969: vC=self.REQUEST['vC']
970: except:
971: pass
972:
973: author=self.REQUEST['author']
974:
975: if changeName=="yes":
976: filename=file.filename
977: self.title=filename[max(filename.rfind('/'),
978: filename.rfind('\\'),
979: filename.rfind(':'),
980: )+1:]
981:
982:
983: if not newName=='':
984: self.title=newName[0:]
985:
986:
987:
988:
989:
990: positionVersionNum=getattr(self,'positionVersionNum','front')
991:
992: if positionVersionNum=='front':
993: id="V%i"%self.getVersion()+"_"+self.title
994: else:
995: tmp=os.path.splitext(self.title)
996: if len(tmp)>1:
997: id=tmp[0]+"_V%i"%self.getVersion()+tmp[1]
998: else:
999: id=tmp[0]+"_V%i"%self.getVersion()
1000:
1001:
1002: manage_addextVersionedFileObject(self,id,vC,author,file,id,precondition, content_type)
1003: objs=self.ZopeFind(self,obj_ids=[id])[0][1].setVersionNumber(int(self.getVersion()))
1004: self.REQUEST.SESSION['objID_parent']=self.getId()
1005:
1006: if getattr(self,'defaultFileCatalog',None):
1007:
1008: self.reindex_object()
1009:
1010: if RESPONSE:
1011: obj=self.ZopeFind(self,obj_ids=[id])[0][1]
1012: if obj.getSize()==0:
1013: self.REQUEST.SESSION['objID']=obj.getId()
1014: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','errorUploadFile')).__of__(self)
1015: return pt()
1016:
1017: else:
1018: RESPONSE.redirect(self.REQUEST['URL2'])
1019:
1020: else:
1021: return self.ZopeFind(self,obj_ids=[id])[0][1]
1022:
1023: security.declareProtected('AUTHENTICATED_USER','downloadLocked')
1024:
1025: def download(self):
1026: """download and lock"""
1027:
1028: self.REQUEST.RESPONSE.setHeader("Content-Disposition","""attachement; filename=%s"""%self.getLastVersion().getId())
1029: self.REQUEST.RESPONSE.setHeader("Content-Type","application/octet-stream")
1030:
1031: #try:
1032: # txt=self.getLastVersion.index_html()
1033: #except:
1034: # txt=self.getLastVersion.index_html(REQUEST,RESPONSE)
1035:
1036: #self.REQUEST.RESPONSE.setHeader("Content-Length","str(len(txt)+1000)")
1037:
1038: self.content_type="application/octet-stream"
1039: #self.REQUEST.RESPONSE.write("bl")
1040: #self.REQUEST.RESPONSE.write(txt)
1041: #self.REQUEST.close()
1042:
1043: #self.getLastVersion().content_type="application/octet-stream"
1044: self.REQUEST.RESPONSE.redirect(self.REQUEST['URL1']+'/'+self.getId()+'/'+self.getLastVersion().getId())
1045:
1046: security.declareProtected('AUTHENTICATED_USER','downloadLocked')
1047: def downloadLocked(self):
1048: """download and lock"""
1049:
1050: if repr(self.REQUEST['AUTHENTICATED_USER'])=='Anonymous User':
1051: return "please login first"
1052: if not self.lockedBy=="":
1053: return "cannot be locked because is already locked by %s"%self.lockedBy
1054: self.lockedBy=self.REQUEST['AUTHENTICATED_USER']
1055: self.getLastVersion().content_type="application/octet-stream"
1056: self.REQUEST.RESPONSE.redirect(self.REQUEST['URL1']+'/'+self.getId()+'/'+self.getLastVersion().getId())
1057:
1058: def manage_addextVersionedFileForm(self):
1059: """interface for adding the OSAS_root"""
1060: pt=PageTemplateFile(os.path.join(package_home(globals()),'zpt','addextVersionedFile.zpt')).__of__(self)
1061: return pt()
1062:
1063: def manage_addextVersionedFile(self,id,title,lockedBy, author=None, RESPONSE=None):
1064: """add the OSAS_root"""
1065: newObj=extVersionedFile(id,title,lockedBy,author)
1066: self._setObject(id,newObj)
1067:
1068: if RESPONSE is not None:
1069: RESPONSE.redirect('manage_main')
1070:
1071:
1072: InitializeClass(extVersionedFile)
1073: InitializeClass(extVersionedFileFolder)
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>