def _bibdoc_modify_files(recid, form): from invenio.legacy.bibdocfile.api import BibRecDocs try: recdocs = BibRecDocs(recid) except: current_app.logger.error( "REST API: Error while building BibRecDocs for record %d" % (recid, )) return [] actions = {} for (k, v) in form.items(): if k.startswith('__file__name__'): docid = int(k[len('__file__name__'):]) docname = recdocs.get_docname(docid) if docname != v: actions[docid] = ('rename', docname, v) if k.startswith('__file__delete__') and v == 'Delete': docid = int(k[len('__file__delete__'):]) docname = recdocs.get_docname(docid) actions[docid] = ('delete', docname, None) # overwrite rename for (_, (act, docname, newname)) in actions.items(): if act == 'delete': current_app.logger.info("deleting bibdoc/file: {}/'{}'".format( recid, docname)) recdocs.delete_bibdoc(docname) elif act == 'rename': current_app.logger.info( "renaming bibdoc/file: {}/'{}' -> '{}'".format( recid, docname, newname)) recdocs.change_name(newname=newname, oldname=docname)
def _bibdoc_modify_files(recid, form): from invenio.legacy.bibdocfile.api import BibRecDocs try: recdocs = BibRecDocs(recid) except: current_app.logger.error("REST API: Error while building BibRecDocs for record %d" % (recid,)) return [] actions = {} for (k,v) in form.items(): if k.startswith('__file__name__'): docid = int(k[len('__file__name__'):]) docname = recdocs.get_docname(docid) if docname != v: actions[docid] = ('rename', docname, v) if k.startswith('__file__delete__') and v == 'Delete': docid = int(k[len('__file__delete__'):]) docname = recdocs.get_docname(docid) actions[docid] = ('delete', docname, None) # overwrite rename for (_,(act, docname, newname)) in actions.items(): if act == 'delete': current_app.logger.info("deleting bibdoc/file: {}/'{}'".format(recid, docname)) recdocs.delete_bibdoc(docname) elif act == 'rename': current_app.logger.info("renaming bibdoc/file: {}/'{}' -> '{}'".format(recid, docname, newname)) recdocs.change_name(newname=newname, oldname=docname)
def Move_Files_Archive(parameters, curdir, form, user_info=None): """DEPRECATED: Use FFT instead.""" MainDir = "%s/files/MainFiles" % curdir IncludeDir = "%s/files/AdditionalFiles" % curdir watcheddirs = {'Main' : MainDir, 'Additional' : IncludeDir} for type, dir in iteritems(watcheddirs): if os.path.exists(dir): formats = {} files = os.listdir(dir) files.sort() for file in files: dummy, filename, extension = decompose_file(file) if filename not in formats: formats[filename] = [] formats[filename].append(normalize_format(extension)) # first delete all missing files bibarchive = BibRecDocs(sysno) existingBibdocs = bibarchive.list_bibdocs(type) for existingBibdoc in existingBibdocs: if bibarchive.get_docname(existingBibdoc.id) not in formats: existingBibdoc.delete() # then create/update the new ones for key in formats.keys(): # instanciate bibdoc object bibarchive.add_new_file('%s/%s%s' % (dir, key, formats[key]), doctype=type, never_fail=True) return ""
def fix_recid(recid, logfile): """Fix a given recid.""" print("Upgrading record %s ->" % recid, end=' ') print("Upgrading record %s:" % recid, file=logfile) bibrec = BibRecDocs(recid) print(bibrec, file=logfile) docnames = bibrec.get_bibdoc_names() try: for docname in docnames: print(docname, end=' ') new_bibdocs = bibrec.fix(docname) new_bibdocnames = [ bibrec.get_docname(bibdoc.id) for bibdoc in new_bibdocs ] if new_bibdocnames: print("(created bibdocs: '%s')" % "', '".join(new_bibdocnames), end=' ') print("(created bibdocs: '%s')" % "', '".join(new_bibdocnames), file=logfile) except InvenioBibDocFileError as e: print(BibRecDocs(recid), file=logfile) print("%s -> ERROR", e) return False else: print(BibRecDocs(recid), file=logfile) print("-> OK") return True
def _getfile_py(req, recid=0, docid=0, version="", name="", docformat="", ln=CFG_SITE_LANG): if not recid: ## Let's obtain the recid from the docid if docid: try: bibdoc = BibDoc(docid=docid) recid = bibdoc.bibrec_links[0]["recid"] except InvenioBibDocFileError: return warning_page( _("An error has happened in trying to retrieve the requested file." ), req, ln) else: return warning_page( _('Not enough information to retrieve the document'), req, ln) else: brd = BibRecDocs(recid) if not name and docid: ## Let's obtain the name from the docid try: name = brd.get_docname(docid) except InvenioBibDocFileError: return warning_page( _("An error has happened in trying to retrieving the requested file." ), req, ln) docformat = normalize_format(docformat) redirect_to_url( req, '%s/%s/%s/files/%s%s?ln=%s%s' % (CFG_SITE_URL, CFG_SITE_RECORD, recid, name, docformat, ln, version and 'version=%s' % version or ''), apache.HTTP_MOVED_PERMANENTLY)
def _getfile_py(req, recid=0, docid=0, version="", name="", docformat="", ln=CFG_SITE_LANG): if not recid: ## Let's obtain the recid from the docid if docid: try: bibdoc = BibDoc(docid=docid) recid = bibdoc.bibrec_links[0]["recid"] except InvenioBibDocFileError: return warning_page(_("An error has happened in trying to retrieve the requested file."), req, ln) else: return warning_page(_('Not enough information to retrieve the document'), req, ln) else: brd = BibRecDocs(recid) if not name and docid: ## Let's obtain the name from the docid try: name = brd.get_docname(docid) except InvenioBibDocFileError: return warning_page(_("An error has happened in trying to retrieving the requested file."), req, ln) docformat = normalize_format(docformat) redirect_to_url(req, '%s/%s/%s/files/%s%s?ln=%s%s' % (CFG_SITE_URL, CFG_SITE_RECORD, recid, name, docformat, ln, version and 'version=%s' % version or ''), apache.HTTP_MOVED_PERMANENTLY)
def fix_recid(recid, logfile): """Fix a given recid.""" print("Upgrading record %s ->" % recid, end=' ') print("Upgrading record %s:" % recid, file=logfile) bibrec = BibRecDocs(recid) print(bibrec, file=logfile) docnames = bibrec.get_bibdoc_names() try: for docname in docnames: print(docname, end=' ') new_bibdocs = bibrec.fix(docname) new_bibdocnames = [bibrec.get_docname(bibdoc.id) for bibdoc in new_bibdocs] if new_bibdocnames: print("(created bibdocs: '%s')" % "', '".join(new_bibdocnames), end=' ') print("(created bibdocs: '%s')" % "', '".join(new_bibdocnames), file=logfile) except InvenioBibDocFileError as e: print(BibRecDocs(recid), file=logfile) print("%s -> ERROR", e) return False else: print(BibRecDocs(recid), file=logfile) print("-> OK") return True
def Move_Photos_to_Storage(parameters, curdir, form, user_info=None): """ The function moves files received from the submission's form through the PHOTO_MANAGER element and its asynchronous uploads at CFG_SITE_URL/submit/uploadfile. Parameters: @iconsize - Seperate multiple sizes with commas. The ImageMagick geometry inputs are supported. Use type 'geometry' as defined in ImageMagick. (eg. 320 or 320x240 or 100> or 5%) Example: "180>,700>" will create two icons, one with maximum dimension 180px, one 700px @iconformat - Allowed extensions (as defined in websubmit_icon_creator.py) are: "pdf", "gif", "jpg", "jpeg", "ps", "png", "bmp" "eps", "epsi", "epsf" The PHOTO_MANAGER elements builds the following file organization in the directory curdir:: curdir/ | ______________________________________________________________________ | | | files/ PHOTO_MANAGER_ICONS icons/ | PHOTO_MANAGER_ORDER | (user id)/ PHOTO_MANAGER_DELETE (user id)/ | PHOTO_MANAGER_NEW | NewFile/ PHOTO_MANAGER_DESCRIPTION_X NewFile/ | | _______________________ _____________________ | | | | | | photo1.jpg myPhoto.gif ... photo1.jpg myPhoto.gif ... where the files are: - PHOTO_MANAGER_ORDER: ordered list of file IDs. One per line. - PHOTO_MANAGER_ICONS: mappings from file IDs to URL of the icons. One per line. Separator: / - PHOTO_MANAGER_NEW: mapping from file ID to filename on disk. Only applicable to files that have just been uploaded (i.e. not bibdocfiles). One per line. Separator: / - PHOTO_MANAGER_DELETE: list of files IDs that must be deleted. One per line - PHOTO_MANAGER_DESCRIPTION_X, where X is file ID: contains photos descriptions (one per file) """ global sysno icon_sizes = parameters.get('iconsize').split(',') icon_format = parameters.get('iconformat') if not icon_format: icon_format = 'gif' PHOTO_MANAGER_ICONS = read_param_file(curdir, 'PHOTO_MANAGER_ICONS', split_lines=True) photo_manager_icons_dict = dict([value.split('/', 1) \ for value in PHOTO_MANAGER_ICONS \ if '/' in value]) PHOTO_MANAGER_ORDER = read_param_file(curdir, 'PHOTO_MANAGER_ORDER', split_lines=True) photo_manager_order_list = [value for value in PHOTO_MANAGER_ORDER if value.strip()] PHOTO_MANAGER_DELETE = read_param_file(curdir, 'PHOTO_MANAGER_DELETE', split_lines=True) photo_manager_delete_list = [value for value in PHOTO_MANAGER_DELETE if value.strip()] PHOTO_MANAGER_NEW = read_param_file(curdir, 'PHOTO_MANAGER_NEW', split_lines=True) photo_manager_new_dict = dict([value.split('/', 1) \ for value in PHOTO_MANAGER_NEW \ if '/' in value]) ## Create an instance of BibRecDocs for the current recid(sysno) bibrecdocs = BibRecDocs(sysno) for photo_id in photo_manager_order_list: photo_description = read_param_file(curdir, 'PHOTO_MANAGER_DESCRIPTION_' + photo_id) # We must take different actions depending if we deal with a # file that already exists, or if it is a new file if photo_id in photo_manager_new_dict.keys(): # New file if photo_id not in photo_manager_delete_list: filename = photo_manager_new_dict[photo_id] filepath = os.path.join(curdir, 'files', str(user_info['uid']), 'NewFile', filename) icon_filename = os.path.splitext(filename)[0] + ".gif" fileiconpath = os.path.join(curdir, 'icons', str(user_info['uid']), 'NewFile', icon_filename) # Add the file if os.path.exists(filepath): _do_log(curdir, "Adding file %s" % filepath) bibdoc = bibrecdocs.add_new_file(filepath, doctype="picture", never_fail=True) has_added_default_icon_subformat_p = False for icon_size in icon_sizes: # Create icon if needed try: (icon_path, icon_name) = create_icon( { 'input-file' : filepath, 'icon-name' : icon_filename, 'icon-file-format' : icon_format, 'multipage-icon' : False, 'multipage-icon-delay' : 100, 'icon-scale' : icon_size, # Resize only if width > 300 'verbosity' : 0, }) fileiconpath = os.path.join(icon_path, icon_name) except InvenioWebSubmitIconCreatorError as e: _do_log(curdir, "Icon could not be created to %s: %s" % (filepath, e)) pass if os.path.exists(fileiconpath): try: if not has_added_default_icon_subformat_p: bibdoc.add_icon(fileiconpath) has_added_default_icon_subformat_p = True _do_log(curdir, "Added icon %s" % fileiconpath) else: icon_suffix = icon_size.replace('>', '').replace('<', '').replace('^', '').replace('!', '') bibdoc.add_icon(fileiconpath, subformat=CFG_BIBDOCFILE_DEFAULT_ICON_SUBFORMAT + "-" + icon_suffix) _do_log(curdir, "Added icon %s" % fileiconpath) except InvenioBibDocFileError as e: # Most probably icon already existed. pass if photo_description and bibdoc: for file_format in [bibdocfile.get_format() \ for bibdocfile in bibdoc.list_latest_files()]: bibdoc.set_comment(photo_description, file_format) _do_log(curdir, "Added comment %s" % photo_description) else: # Existing file bibdocname = bibrecdocs.get_docname(int(photo_id)) if photo_id in photo_manager_delete_list: # In principle we should not get here. but just in case... bibrecdocs.delete_bibdoc(bibdocname) _do_log(curdir, "Deleted %s" % bibdocname) else: bibdoc = bibrecdocs.get_bibdoc(bibdocname) for file_format in [bibdocfile.get_format() \ for bibdocfile in bibdoc.list_latest_files()]: bibdoc.set_comment(photo_description, file_format) _do_log(curdir, "Added comment %s" % photo_description) # Now delete requeted files for photo_id in photo_manager_delete_list: try: bibdocname = bibrecdocs.get_docname(int(photo_id)) bibrecdocs.delete_bibdoc(bibdocname) _do_log(curdir, "Deleted %s" % bibdocname) except: # we tried to delete a photo that does not exist (maybe already deleted) pass # Update the MARC _do_log(curdir, "Asking bibdocfile to fix marc") bibdocfile_bin = os.path.join(CFG_BINDIR, 'bibdocfile --yes-i-know') os.system(bibdocfile_bin + " --fix-marc --recid=" + str(sysno)) # Delete the HB BibFormat cache in the DB, so that the fulltext # links do not point to possible dead files run_sql("DELETE LOW_PRIORITY from bibfmt WHERE format='HB' AND id_bibrec=%s", (sysno,)) return ""
def create_icons_for_record(recid, icon_sizes, icon_format_mappings=None, docnames=None, add_default_icon=False, inherit_moreinfo=False): """Generate icons, if missing, for a record @param recid: the record id for which icons are being created @type recid: int @param icon_sizes: the list of icon sizes that need to be generated. Note that upscaled is not allowed @type icon_sizes: list @param icon_format_mappings: defines for each "master" format in which format the icons should be created. If the master format is not specified here, then its icons will be created in the same format, if possible (for eg. the icons of a TIFF file would be created as TIFF, while icons of a PDF or DOC file would be created in JPG) and unless a default mapping is not provided in C{CFG_ICON_CREATION_FORMAT_MAPPINGS}. @type icon_format_mappings: dict @param docnames: the list of docnames for which we want to create an icon. If not provided, consider all docnames. @type docnames: list @param add_default_icon: if a default icon (i.e. without icon size suffix, matching CFG_BIBDOCFILE_DEFAULT_ICON_SUBFORMAT) should be added or not. @type add_default_icon: bool @param inherit_moreinfo: if the added icons should also have their description and comment set to the same value as the "main" bibdoc or not. @type inherit_moreinfo: bool """ exceptions = [] # keep track of all exceptions done = 0 brd = BibRecDocs(recid) bibdocs = brd.list_bibdocs() # Override default formats from CFG_ICON_CREATION_FORMAT_MAPPINGS # with values specified in icon_format_mappings if icon_format_mappings is None: icon_format_mappings = {} icon_format_mappings = dict(CFG_ICON_CREATION_FORMAT_MAPPINGS, **icon_format_mappings) if icon_format_mappings.has_key('*') and \ not icon_format_mappings['*']: # we must override the default in order to keep the # "superformat" del icon_format_mappings['*'] for bibdoc in bibdocs: docname = brd.get_docname(bibdoc.id) if docnames and not docname in docnames: # Skip this docname continue comment, description = get_comment_and_description(bibdoc, inherit_moreinfo) default_icon_added_p = False bibfiles = bibdoc.list_latest_files() bibdoc_formats = [bibfile.get_format() for bibfile in bibfiles] for bibfile in bibfiles: if bibfile.get_subformat(): # this is a subformat, do nothing continue filepath = bibfile.get_full_path() #do not consider the dot in front of the format superformat = bibfile.get_format()[1:].lower() bibfile_icon_formats = icon_format_mappings.get(superformat, icon_format_mappings.get('*', [superformat])) if isinstance(bibfile_icon_formats, str): bibfile_icon_formats = [bibfile_icon_formats] bibfile_icon_formats = [bibfile_icon_format for bibfile_icon_format in bibfile_icon_formats \ if bibfile_icon_format in CFG_ALLOWED_FILE_EXTENSIONS] if add_default_icon and not default_icon_added_p: # add default icon try: iconpath, iconname = _create_icon(filepath, CFG_DEFAULT_ICON_SIZE, docname, icon_format=CFG_DEFAULT_ICON_EXTENSION, verbosity=9) bibdoc.add_file_new_format(os.path.join(iconpath, iconname), docformat=".%s;%s" % (CFG_DEFAULT_ICON_EXTENSION, CFG_BIBDOCFILE_DEFAULT_ICON_SUBFORMAT), comment=comment, description=description) default_icon_added_p = True write_message("Added default icon to recid: %s, format: %s" % (recid, CFG_DEFAULT_ICON_EXTENSION)) except Exception, ex: exceptions.append("Could not add new icon to recid: %s, format: %s; exc: %s" \ % (recid, CFG_DEFAULT_ICON_EXTENSION, ex)) # check if the subformat that we want to create already exists for icon_size in icon_sizes: washed_icon_size = icon_size.replace('>', '').replace('<', '').replace('^', '').replace('!', '') for icon_format in bibfile_icon_formats: new_format = '.%s;%s-%s' % (icon_format, CFG_BIBDOCFILE_DEFAULT_ICON_SUBFORMAT, washed_icon_size) if new_format in bibdoc_formats: # the subformat already exists, do nothing continue # add icon try: iconpath, iconname = _create_icon(filepath, icon_size, docname, icon_format=icon_format, verbosity=9) bibdoc.add_file_new_format(os.path.join(iconpath, iconname), docformat=new_format, comment=comment, description=description) write_message("Added icon to recid: %s, format: %s %s %s %s" % (recid, new_format, iconpath, iconname, icon_size)) done += 1 except Exception, ex: exceptions.append("Could not add new format to recid: %s, format: %s; exc: %s" \ %(recid, new_format, ex))
def create_photos_manager_interface(sysno, session_id, uid, doctype, indir, curdir, access, can_delete_photos=True, can_reorder_photos=True, can_upload_photos=True, editor_width=None, editor_height=None, initial_slider_value=100, max_slider_value=200, min_slider_value=80): """ Creates and returns the HTML of the photos manager interface for submissions. @param sysno: current record id @param session_id: user session_id (as retrieved by get_session_id(...) ) @param uid: user id @param doctype: doctype of the submission @param indir: submission "indir" @param curdir: submission "curdir" @param access: submission "access" @param can_delete_photos: if users can delete photos @param can_reorder_photos: if users can reorder photos @param can_upload_photos: if users can upload photos @param editor_width: width (in pixels) of the editor @param editor_height: height (in pixels) of the editor @param initial_slider_value: initial value of the photo size slider @param max_slider_value: max value of the photo size slider @param min_slider_value: min value of the photo size slider """ out = '' PHOTO_MANAGER_ICONS = read_param_file(curdir, 'PHOTO_MANAGER_ICONS', split_lines=True) photo_manager_icons_dict = dict([value.split('/', 1) for value in PHOTO_MANAGER_ICONS if '/' in value]) PHOTO_MANAGER_ORDER = read_param_file(curdir, 'PHOTO_MANAGER_ORDER', split_lines=True) photo_manager_order_list = [value for value in PHOTO_MANAGER_ORDER if value.strip()] PHOTO_MANAGER_DELETE = read_param_file(curdir, 'PHOTO_MANAGER_DELETE', split_lines=True) photo_manager_delete_list = [value for value in PHOTO_MANAGER_DELETE if value.strip()] PHOTO_MANAGER_NEW = read_param_file(curdir, 'PHOTO_MANAGER_NEW', split_lines=True) photo_manager_new_dict = dict([value.split('/', 1) for value in PHOTO_MANAGER_NEW if '/' in value]) photo_manager_descriptions_dict = {} # Compile a regular expression that can match the "default" icon, # and not larger version. CFG_BIBDOCFILE_ICON_SUBFORMAT_RE_DEFAULT = re.compile(CFG_BIBDOCFILE_DEFAULT_ICON_SUBFORMAT + '\Z') # Load the existing photos from the DB if we are displaying # this interface for the first time, and if a record exists if sysno and not PHOTO_MANAGER_ORDER: bibarchive = BibRecDocs(sysno) for doc in bibarchive.list_bibdocs(): if doc.get_icon() is not None: original_url = doc.list_latest_files()[0].get_url() doc_id = str(doc.get_id()) icon_url = doc.get_icon(subformat_re=CFG_BIBDOCFILE_ICON_SUBFORMAT_RE_DEFAULT).get_url() # Get "default" icon description = "" for bibdoc_file in doc.list_latest_files(): #format = bibdoc_file.get_format().lstrip('.').upper() #url = bibdoc_file.get_url() #photo_files.append((format, url)) if not description and bibdoc_file.get_comment(): description = escape(bibdoc_file.get_comment()) name = bibarchive.get_docname(doc.id) photo_manager_descriptions_dict[doc_id] = description photo_manager_icons_dict[doc_id] = icon_url photo_manager_order_list.append(doc_id) # FIXME: respect order # Prepare the list of photos to display. photos_img = [] for doc_id in photo_manager_order_list: if doc_id not in photo_manager_icons_dict: continue icon_url = photo_manager_icons_dict[doc_id] if PHOTO_MANAGER_ORDER: # Get description from disk only if some changes have been done description = escape(read_param_file(curdir, 'PHOTO_MANAGER_DESCRIPTION_' + doc_id)) else: description = escape(photo_manager_descriptions_dict[doc_id]) photos_img.append(''' <li id="%(doc_id)s" style="width:%(initial_slider_value)spx;"> <div class="imgBlock"> <div class="normalLineHeight" style="margin-left:auto;margin-right:auto;display:inline" > <img id="delete_%(doc_id)s" class="hidden" src="/img/cross_red.gif" alt="Delete" style="position:absolute;top:0;" onclick="delete_photo('%(doc_id)s');"/> <img src="%(icon_url)s" class="imgIcon"/> </div> <div class="normalLineHeight"> <textarea style="width:95%%" id="PHOTO_MANAGER_DESCRIPTION_%(doc_id)s" name="PHOTO_MANAGER_DESCRIPTION_%(doc_id)s">%(description)s</textarea> </div> </div> </li>''' % \ {'initial_slider_value': initial_slider_value, 'doc_id': doc_id, 'icon_url': icon_url, 'description': description}) out += ''' <link rel="stylesheet" href="%(CFG_SITE_URL)s/vendors/jquery-ui/themes/redmond/jquery-ui.min.css" type="text/css" charset="utf-8"/> <link rel="stylesheet" href="%(CFG_SITE_URL)s/vendors/jquery-ui/themes/redmond/theme.css" type="text/css" charset="utf-8"/> <style type="text/css"> #sortable { list-style-type: none; margin: 0; padding: 0; } #sortable li { margin: auto 3px; padding: 1px; float: left; width: 180px; font-size:small; text-align: center; position: relative;} #sortable .imgIcon {max-height:95%%;max-width:95%%;margin: 2px;max-height:130px;} #sortable li div.imgBlock {vertical-align: middle; margin: auto;display:inline;display:inline-table;display:inline-block;vertical-align:middle;text-align : center; width:100%%;position:relative} #sortable li div.imgBlock .hidden {display:none;} %(delete_hover_class)s .fileUploadQueue{text-align:left; margin: 0 auto; width:300px;} .normalLineHeight {line-height:normal} </style> <div id="uploadedFiles" style="%(hide_photo_viewer)sborder-left:1px solid #555; border-top:1px solid #555;border-right:1px solid #eee;border-bottom:1px solid #eee;overflow:auto;%(editor_height_style)s%(editor_width_style)sbackground-color:#eee;margin:3px;text-align:left;position:relative"><ul id="sortable">%(photos_img)s</ul></div> <div id="grid_slider" style="%(hide_photo_viewer)swidth:300px;"> <div class='ui-slider-handle'></div> </div> <script type="text/javascript" src="%(CFG_SITE_URL)s/vendors/uploadify/jquery.uploadify.min.js"></script> <script type="text/javascript" src="%(CFG_SITE_URL)s/vendors/swfobject/swfobject/swfobject.js"></script> <script type="text/javascript" src="%(CFG_SITE_URL)s/vendors/jquery-ui/jquery-ui.min.js"></script> <link rel="stylesheet" href="%(CFG_SITE_URL)s/vendors/uploadify/uploadify.css" type="text/css" /> <script type="text/javascript"> $(document).ready(function() { /* Uploading */ if (%(can_upload_photos)s) { $('#uploadFile').uploadify({ 'uploader': '%(CFG_SITE_URL)s/vendors/uploadify/uploadify.swf', 'script': '/submit/uploadfile', 'cancelImg': '%(CFG_SITE_URL)s/vendors/uploadify/uploadify-cancel.png', 'multi' : true, 'auto' : true, 'simUploadLimit': 2, 'scriptData' : {'type': 'File', 'uid': %(uid)s, 'session_id': '%(session_id)s', 'indir': '%(indir)s', 'doctype': '%(doctype)s', 'access': '%(access)s'}, 'displayDate': 'percentage', 'buttonText': 'Browse', 'fileDataName': 'NewFile' /* be compatible with CKEditor */, 'onSelectOnce': function(event, data) { }, 'onSelect': function(event, queueID, fileObj, response, data) { $('#loading').css("visibility","visible"); }, 'onAllComplete' : function(event, queueID, fileObj, response, data) { $('#loading').css("visibility","hidden"); }, /*'onCheck': function(event, checkScript, fileQueue, folder, single) { return false; },*/ 'onComplete': function(event, queueID, fileObj, response, data) { $('#grid_slider').css("display","block"); $('#uploadedFiles').css("display","block"); var cur_width = $("#grid_slider").slider('option', 'value'); var response_obj = parse_invenio_response(response); icon_url = '%(CFG_SITE_URL)s/img/file-icon-blank-96x128.gif' if ("NewFile" in response_obj) { filename = response_obj["NewFile"]["name"] if ('iconName' in response_obj["NewFile"]){ icon_name = response_obj["NewFile"]["iconName"] icon_url = '%(CFG_SITE_URL)s/submit/getuploadedfile?indir=%(indir)s&doctype=%(doctype)s&access=%(access)s&key=NewFile&icon=1&filename=' + icon_name } } else { return true; } $('#sortable').append('<li id="'+ queueID +'" style="width:'+cur_width+'px;"><div class="imgBlock"><div class="normalLineHeight" style="margin-left:auto;margin-right:auto;display:inline" ><img id="delete_'+ queueID +'" class="hidden" src="/img/cross_red.gif" alt="Delete" style="position:absolute;top:0;" onclick="delete_photo(\\''+ queueID +'\\');"/><img src="'+ icon_url +'" class="imgIcon"/></div><div class="normalLineHeight"><textarea style="width:95%%" id="PHOTO_MANAGER_DESCRIPTION_'+ queueID +'" name="PHOTO_MANAGER_DESCRIPTION_'+ queueID +'"></textarea></div></div></li>'); update_order_field(); $('#photo_manager_icons').val($("#photo_manager_icons").val() + '\\n' + queueID + '/' + icon_url); $('#photo_manager_new').val($("#photo_manager_new").val() + '\\n' + queueID + '/' + filename); update_CSS(); return true; } }); } /* Resizing */ $("#grid_slider").slider({ value: %(initial_slider_value)s, max: %(max_slider_value)s, min: %(min_slider_value)s, slide: function(event, ui) { update_CSS(); } }); /* Update CSS to ensure that existing photos get nicely laid out*/ update_CSS(); }); /* Ordering */ $(function() { if (%(can_reorder_photos)s) { $("#sortable").sortable(); $("#sortable").bind('sortupdate', function(event, ui) { update_order_field(); }); } }); function delete_photo(docid){ if (confirm("Are you sure you want to delete the photo? (The file will be deleted after you apply all the modifications)")) { $("#" + docid).remove(); $("#photo_manager_delete").val($("#photo_manager_delete").val() + '\\n' + docid); update_order_field(); } } /* CSS-related */ function update_CSS(){ /* Update some style according to the slider size */ var slider_value = $("#grid_slider").slider('option', 'value'); $('#uploadedFiles li').css('width', slider_value+"px"); /*$('#uploadedFiles div.floater').css('width', slider_value+"px");*/ /* Update height attr accordingly so that image get centered. First we need to get the tallest element of the list. */ var max_height = 0; $('#uploadedFiles li div').each(function() { this_height = $(this).height(); if(this_height > max_height) { max_height = this_height; } }); $('#uploadedFiles li').css('height',max_height+"px"); $('#uploadedFiles li').css('line-height',max_height+"px"); } /* Utils */ function update_order_field(){ $("#photo_manager_order").val($("#sortable").sortable('toArray').join('\\n')); } function parse_invenio_response(response){ /* Return the javascript object included in the the given Invenio message. Really dirty implementation, but ok in this very simple scenario */ /*var object_string = response.substring(response.indexOf('<![CDATA[')+9, response.lastIndexOf(']]>'));*/ object_string = response; var object = {}; eval('object=' + object_string); return object; } </script> <div style="margin: 0 auto;"> <img src="%(CFG_SITE_URL)s/img/loading.gif" style="visibility: hidden" id="loading"/> <input type="file" size="40" id="uploadFile" name="PHOTO_FILE" style="margin: 0 auto;%(upload_display)s"/> </div> <!--<a href="javascript:$('#uploadFile').fileUploadStart();">Upload Files</a> --> <textarea id="photo_manager_icons" style="display:none" name="PHOTO_MANAGER_ICONS">%(PHOTO_MANAGER_ICONS)s</textarea> <textarea id="photo_manager_order" style="display:none" name="PHOTO_MANAGER_ORDER">%(PHOTO_MANAGER_ORDER)s</textarea> <textarea id="photo_manager_new" style="display:none" name="PHOTO_MANAGER_NEW">%(PHOTO_MANAGER_NEW)s</textarea> <textarea id="photo_manager_delete" style="display:none" name="PHOTO_MANAGER_DELETE">%(PHOTO_MANAGER_DELETE)s</textarea> ''' % {'CFG_SITE_URL': CFG_SITE_URL, #'curdir': cgi.escape(quote(curdir, safe="")),#quote(curdir, safe=""), 'uid': uid, 'access': quote(access, safe=""), 'doctype': quote(doctype, safe=""), 'indir': quote(indir, safe=""), 'session_id': quote(session_id, safe=""), 'PHOTO_MANAGER_ICONS': '\n'.join([key + '/' + value for key, value in iteritems(photo_manager_icons_dict)]), 'PHOTO_MANAGER_ORDER': '\n'.join(photo_manager_order_list), 'PHOTO_MANAGER_DELETE': '\n'.join(photo_manager_delete_list), 'PHOTO_MANAGER_NEW': '\n'.join([key + '/' + value for key, value in iteritems(photo_manager_new_dict)]), 'initial_slider_value': initial_slider_value, 'max_slider_value': max_slider_value, 'min_slider_value': min_slider_value, 'photos_img': '\n'.join(photos_img), 'hide_photo_viewer': (len(photos_img) == 0 and len(photo_manager_new_dict.keys()) == 0) and 'display:none;' or '', 'delete_hover_class': can_delete_photos and "#sortable li div.imgBlock:hover .hidden {display:inline;}" or '', 'can_reorder_photos': can_reorder_photos and 'true' or 'false', 'can_upload_photos': can_upload_photos and 'true' or 'false', 'upload_display': not can_upload_photos and 'display: none' or '', 'editor_width_style': editor_width and 'width:%spx;' % editor_width or '', 'editor_height_style': editor_height and 'height:%spx;' % editor_height or ''} return out
def Move_Revised_Files_to_Storage(parameters, curdir, form, user_info=None): """ The function revises the files of a record with the newly uploaded files. This function can work only if you can define a mapping from the WebSubmit element name that uploads the file, to the doctype of the file. In most cases, the doctype is equivalent to the element name, or just map to 'Main' doctype. That is typically the case if you use the Move_Files_to_Storage.py function to upload the files at submission step. For eg. with the DEMOBOO submission of the Atlantis Demo site, a file is uploaded thanks to the DEMOBOO_FILE element/File input, which is mapped to doctype DEMOBOO_FILE. The function ignores files for which multiple files exist for a single doctype in the record, or when several files are uploaded with the same element name. If the record to revise does not have a corresponding file, the file is inserted This function is similar to Move_Uploaded_Files_to_Storage.py, excepted that Move_Uploaded_Files_to_Storage relies on files uploaded from the web interface created by Create_Upload_Files_Interface.py, while this function relies on the files uploaded by a regular WebSubmit page that you have built from WebSubmit admin: Regular WebSubmit interface --(upload file)--> Move_Revised_Files_to_Storage.py Create_Upload_Files_Interface.py --(upload file)--> Move_Uploaded_Files_to_Storage.py The main advantages of this function over the functions Create_Upload_Files_Interface.py/Move_Uploaded_Files_to_Storage is that it lets you customize the display of your submission in the way you want, which could be simpler for your users if you usually only upload a few and fixed number of files per record. The disadvantages are that this function is not capable of : deleting files, adding an alternative format to a file, add a variable number of files, does not allow to set permissions at the level of file, does not support user comments, renaming, etc. @param parameters:(dictionary) - must contain: + elementNameToDoctype: maps an element/field name to a doctype. Eg. the file uploaded from the DEMOBOO_FILE element (input file tag) should revise the file with document type (doctype) "Main": DEMOBOO_FILE=Main|DEMOBOO_FILE_2=ADDITIONAL ('=' separates element name and doctype '|' separates each doctype/element name group) In most cases, the element name == doctype: DEMOBOO_FILE=DEMOBOO_FILE|DEMOBOO_FILE_2=DEMOBOO_FILE_2 + createIconDoctypes: the list of doctypes for which an icon should be created when revising the file. Eg: Figure|Graph ('|' separated values) Use '*' for all doctypes + iconsize: size of the icon to create (when applicable) + keepPreviousVersionDoctypes: the list of doctypes for which the function should keep previous versions visible when revising a file. Eg: Main|Additional ('|' separated values) Default is all + createRelatedFormats: if uploaded files get converted to whatever format we can (1) or not (0) """ # pylint: disable=E0602 # sysno is defined in the WebSubmit functions sandbox. global sysno bibrecdocs = BibRecDocs(int(sysno)) # Wash function parameters ( element_name_and_doctype, create_icon_doctypes, iconsize, keep_previous_version_doctypes, createRelatedFormats_p, ) = wash_function_parameters(parameters, curdir) for element_name, doctype in element_name_and_doctype: _do_log(curdir, "Processing " + element_name) # Check if there is a corresponding file file_path = os.path.join(curdir, "files", element_name, read_file(curdir, element_name)) if file_path and os.path.exists(file_path): # Now identify which file to revise files_in_record = bibrecdocs.list_bibdocs(doctype) if len(files_in_record) == 1: # Ok, we can revise bibdoc_name = bibrecdocs.get_docname(files_in_record[0].id) revise( bibrecdocs, curdir, sysno, file_path, bibdoc_name, doctype, iconsize, create_icon_doctypes, keep_previous_version_doctypes, createRelatedFormats_p, ) elif len(files_in_record) == 0: # We must add the file add( bibrecdocs, curdir, sysno, file_path, doctype, iconsize, create_icon_doctypes, createRelatedFormats_p, ) else: _do_log( curdir, " %s ignored, because multiple files found for same doctype %s in record %s: %s" % (element_name, doctype, sysno, ", ".join(files_in_record)), ) else: _do_log(curdir, " No corresponding file found (%s)" % file_path) # Update the MARC bibdocfile_bin = os.path.join(CFG_BINDIR, "bibdocfile --yes-i-know") os.system(bibdocfile_bin + " --fix-marc --recid=" + sysno) # Delete the HB BibFormat cache in the DB, so that the fulltext # links do not point to possible dead files run_sql("DELETE LOW_PRIORITY from bibfmt WHERE format='HB' AND id_bibrec=%s", (sysno,))
def format_element(bfo, separator=" ", style='', img_style='', text_style='font-size:small', print_links='yes', max_photos='', show_comment='yes', img_max_width='250px', display_all_version_links='yes'): """ Lists the photos of a record. Display the icon version, linked to its original version. This element works for photos appended to a record as BibDoc files, for which a preview icon has been generated. If there are several formats for one photo, use the first one found. @param separator: separator between each photo @param print_links: if 'yes', print links to the original photo @param style: style attributes of the whole image block. Eg: "padding:2px;border:1px" @param img_style: style attributes of the images. Eg: "width:50px;border:none" @param text_style: style attributes of the text. Eg: "font-size:small" @param max_photos: the maximum number of photos to display @param show_comment: if 'yes', display the comment of each photo @param display_all_version_links: if 'yes', print links to additional (sub)formats """ photos = [] bibarchive = BibRecDocs(bfo.recID) bibdocs = bibarchive.list_bibdocs() if max_photos.isdigit(): max_photos = int(max_photos) else: max_photos = len(bibdocs) for doc in bibdocs[:max_photos]: found_icons = [] found_url = '' for docfile in doc.list_latest_files(): if docfile.is_icon(): found_icons.append( (docfile.get_size(), get_relative_url(docfile.get_url()))) else: found_url = get_relative_url(docfile.get_url()) found_icons.sort() if found_icons: additional_links = '' name = bibarchive.get_docname(doc.id) comment = doc.list_latest_files()[0].get_comment() preview_url = None if len(found_icons) > 1: preview_url = get_relative_url(found_icons[1][1]) additional_urls = [(docfile.get_size(), get_relative_url(docfile.get_url()), \ docfile.get_superformat(), docfile.get_subformat()) \ for docfile in doc.list_latest_files() if not docfile.is_icon()] additional_urls.sort() additional_links = [create_html_link(url, urlargd={}, \ linkattrd={'style': 'font-size:x-small'}, \ link_label="%s %s (%s)" % (format.strip('.').upper(), subformat, format_size(size))) \ for (size, url, format, subformat) in additional_urls] img = '<img src="%(icon_url)s" alt="%(name)s" style="max-width:%(img_max_width)s;_width:%(img_max_width)s;%(img_style)s" />' % \ {'icon_url': cgi.escape(get_relative_url(found_icons[0][1]), True), 'name': cgi.escape(name, True), 'img_style': img_style, 'img_max_width': img_max_width} if print_links.lower() == 'yes': img = '<a href="%s">%s</a>' % (cgi.escape( preview_url or found_url, True), img) if display_all_version_links.lower() == 'yes' and additional_links: img += '<br />' + ' '.join(additional_links) + '<br />' if show_comment.lower() == 'yes' and comment: img += '<div style="margin-auto;text-align:center;%(text_style)s">%(comment)s</div>' % \ {'comment': comment.replace('\n', '<br/>'), 'text_style': text_style} img = '<div style="vertical-align: middle;text-align:center;display:inline-block;display: -moz-inline-stack;zoom: 1;*display: inline;max-width:%(img_max_width)s;_width:%(img_max_width)s;text-align:center;%(style)s">%(img)s</div>' % \ {'img_max_width': img_max_width, 'style': style, 'img': img} photos.append(img) return '<div>' + separator.join(photos) + '</div>'
def getfile(req, form): args = wash_urlargd(form, bibdocfile_templates.files_default_urlargd) ln = args['ln'] _ = gettext_set_language(ln) uid = getUid(req) user_info = collect_user_info(req) verbose = args['verbose'] if verbose >= 1 and not isUserSuperAdmin(user_info): # Only SuperUser can see all the details! verbose = 0 if uid == -1 or CFG_ACCESS_CONTROL_LEVEL_SITE > 1: return page_not_authorized(req, "/%s/%s" % (CFG_SITE_RECORD, self.recid), navmenuid='submit') if record_exists(self.recid) < 1: msg = "<p>%s</p>" % _( "Requested record does not seem to exist.") return warning_page(msg, req, ln) if record_empty(self.recid): msg = "<p>%s</p>" % _( "Requested record does not seem to have been integrated.") return warning_page(msg, req, ln) (auth_code, auth_message) = check_user_can_view_record(user_info, self.recid) if auth_code and user_info['email'] == 'guest': if webjournal_utils.is_recid_in_released_issue(self.recid): # We can serve the file pass else: cookie = mail_cookie_create_authorize_action( VIEWRESTRCOLL, { 'collection': guess_primary_collection_of_a_record(self.recid) }) target = CFG_SITE_SECURE_URL + '/youraccount/login' + \ make_canonical_urlargd({'action': cookie, 'ln' : ln, 'referer' : \ CFG_SITE_SECURE_URL + user_info['uri']}, {}) return redirect_to_url(req, target, norobot=True) elif auth_code: if webjournal_utils.is_recid_in_released_issue(self.recid): # We can serve the file pass else: return page_not_authorized(req, "../", \ text = auth_message) readonly = CFG_ACCESS_CONTROL_LEVEL_SITE == 1 # From now on: either the user provided a specific file # name (and a possible version), or we return a list of # all the available files. In no case are the docids # visible. try: bibarchive = BibRecDocs(self.recid) except InvenioBibDocFileError: register_exception(req=req, alert_admin=True) msg = "<p>%s</p><p>%s</p>" % ( _("The system has encountered an error in retrieving the list of files for this document." ), _("The error has been logged and will be taken in consideration as soon as possible." )) return warning_page(msg, req, ln) if bibarchive.deleted_p(): req.status = apache.HTTP_GONE return warning_page( _("Requested record does not seem to exist."), req, ln) docname = '' docformat = '' version = '' warn = '' if filename: # We know the complete file name, guess which docid it # refers to ## TODO: Change the extension system according to ext.py from setlink ## and have a uniform extension mechanism... docname = file_strip_ext(filename) docformat = filename[len(docname):] if docformat and docformat[0] != '.': docformat = '.' + docformat if args['subformat']: docformat += ';%s' % args['subformat'] else: docname = args['docname'] if not docformat: docformat = args['format'] if args['subformat']: docformat += ';%s' % args['subformat'] if not version: version = args['version'] ## Download as attachment is_download = False if args['download']: is_download = True # version could be either empty, or all or an integer try: int(version) except ValueError: if version != 'all': version = '' display_hidden = isUserSuperAdmin(user_info) if version != 'all': # search this filename in the complete list of files for doc in bibarchive.list_bibdocs(): if docname == bibarchive.get_docname(doc.id): try: try: docfile = doc.get_file(docformat, version) except InvenioBibDocFileError as msg: req.status = apache.HTTP_NOT_FOUND if not CFG_INSPIRE_SITE and req.headers_in.get( 'referer'): ## There must be a broken link somewhere. ## Maybe it's good to alert the admin register_exception(req=req, alert_admin=True) warn += write_warning( _("The format %(x_form)s does not exist for the given version: %(x_vers)s", x_form=cgi.escape(docformat), x_vers=cgi.escape(str(msg)))) break (auth_code, auth_message) = docfile.is_restricted(user_info) if auth_code != 0 and not is_user_owner_of_record( user_info, self.recid): if CFG_BIBDOCFILE_ICON_SUBFORMAT_RE.match( get_subformat_from_format(docformat)): return stream_restricted_icon(req) if user_info['email'] == 'guest': cookie = mail_cookie_create_authorize_action( 'viewrestrdoc', {'status': docfile.get_status()}) target = CFG_SITE_SECURE_URL + '/youraccount/login' + \ make_canonical_urlargd({'action': cookie, 'ln' : ln, 'referer' : \ CFG_SITE_SECURE_URL + user_info['uri']}, {}) redirect_to_url(req, target) else: req.status = apache.HTTP_UNAUTHORIZED warn += write_warning( _("This file is restricted: ") + str(auth_message)) break if not docfile.hidden_p(): if not readonly: ip = str(req.remote_ip) doc.register_download( ip, docfile.get_version(), docformat, uid, self.recid) try: return docfile.stream(req, download=is_download) except InvenioBibDocFileError as msg: register_exception(req=req, alert_admin=True) req.status = apache.HTTP_INTERNAL_SERVER_ERROR warn += write_warning( _("An error has happened in trying to stream the request file." )) else: req.status = apache.HTTP_UNAUTHORIZED warn += write_warning( _("The requested file is hidden and can not be accessed." )) except InvenioBibDocFileError as msg: register_exception(req=req, alert_admin=True) # Prevent leaking of restricted file names req.status = apache.HTTP_NOT_FOUND return if docname and docformat and not warn: req.status = apache.HTTP_NOT_FOUND warn += write_warning( _("Requested file does not seem to exist.")) # filelist = bibarchive.display("", version, ln=ln, verbose=verbose, display_hidden=display_hidden) filelist = bibdocfile_templates.tmpl_display_bibrecdocs( bibarchive, "", version, ln=ln, verbose=verbose, display_hidden=display_hidden) t = warn + bibdocfile_templates.tmpl_filelist(ln=ln, filelist=filelist) cc = guess_primary_collection_of_a_record(self.recid) unordered_tabs = get_detailed_page_tabs(get_colID(cc), self.recid, ln) ordered_tabs_id = [(tab_id, values['order']) for (tab_id, values) in iteritems(unordered_tabs)] ordered_tabs_id.sort(lambda x, y: cmp(x[1], y[1])) link_ln = '' if ln != CFG_SITE_LANG: link_ln = '?ln=%s' % ln tabs = [ (unordered_tabs[tab_id]['label'], '%s/%s/%s/%s%s' % (CFG_SITE_URL, CFG_SITE_RECORD, self.recid, tab_id, link_ln), tab_id == 'files', unordered_tabs[tab_id]['enabled']) for (tab_id, dummy_order) in ordered_tabs_id if unordered_tabs[tab_id]['visible'] is True ] tabs_counts = get_detailed_page_tabs_counts(self.recid) top = webstyle_templates.detailed_record_container_top( self.recid, tabs, args['ln'], citationnum=tabs_counts['Citations'], referencenum=tabs_counts['References'], discussionnum=tabs_counts['Discussions']) bottom = webstyle_templates.detailed_record_container_bottom( self.recid, tabs, args['ln']) title, description, keywords = websearch_templates.tmpl_record_page_header_content( req, self.recid, args['ln']) return pageheaderonly(title=title, navtrail=create_navtrail_links(cc=cc, aas=0, ln=ln) + \ ''' > <a class="navtrail" href="%s/%s/%s">%s</a> > %s''' % \ (CFG_SITE_URL, CFG_SITE_RECORD, self.recid, title, _("Access to Fulltext")), description=description, keywords=keywords, uid=uid, language=ln, req=req, navmenuid='search', navtrail_append_title_p=0) + \ websearch_templates.tmpl_search_pagestart(ln) + \ top + t + bottom + \ websearch_templates.tmpl_search_pageend(ln) + \ pagefooteronly(language=ln, req=req)
def create_photos_manager_interface(sysno, session_id, uid, doctype, indir, curdir, access, can_delete_photos=True, can_reorder_photos=True, can_upload_photos=True, editor_width=None, editor_height=None, initial_slider_value=100, max_slider_value=200, min_slider_value=80): """ Creates and returns the HTML of the photos manager interface for submissions. @param sysno: current record id @param session_id: user session_id (as retrieved by get_session_id(...) ) @param uid: user id @param doctype: doctype of the submission @param indir: submission "indir" @param curdir: submission "curdir" @param access: submission "access" @param can_delete_photos: if users can delete photos @param can_reorder_photos: if users can reorder photos @param can_upload_photos: if users can upload photos @param editor_width: width (in pixels) of the editor @param editor_height: height (in pixels) of the editor @param initial_slider_value: initial value of the photo size slider @param max_slider_value: max value of the photo size slider @param min_slider_value: min value of the photo size slider """ out = '' PHOTO_MANAGER_ICONS = read_param_file(curdir, 'PHOTO_MANAGER_ICONS', split_lines=True) photo_manager_icons_dict = dict( [value.split('/', 1) for value in PHOTO_MANAGER_ICONS if '/' in value]) PHOTO_MANAGER_ORDER = read_param_file(curdir, 'PHOTO_MANAGER_ORDER', split_lines=True) photo_manager_order_list = [ value for value in PHOTO_MANAGER_ORDER if value.strip() ] PHOTO_MANAGER_DELETE = read_param_file(curdir, 'PHOTO_MANAGER_DELETE', split_lines=True) photo_manager_delete_list = [ value for value in PHOTO_MANAGER_DELETE if value.strip() ] PHOTO_MANAGER_NEW = read_param_file(curdir, 'PHOTO_MANAGER_NEW', split_lines=True) photo_manager_new_dict = dict( [value.split('/', 1) for value in PHOTO_MANAGER_NEW if '/' in value]) photo_manager_descriptions_dict = {} # Compile a regular expression that can match the "default" icon, # and not larger version. CFG_BIBDOCFILE_ICON_SUBFORMAT_RE_DEFAULT = re.compile( CFG_BIBDOCFILE_DEFAULT_ICON_SUBFORMAT + '\Z') # Load the existing photos from the DB if we are displaying # this interface for the first time, and if a record exists if sysno and not PHOTO_MANAGER_ORDER: bibarchive = BibRecDocs(sysno) for doc in bibarchive.list_bibdocs(): if doc.get_icon() is not None: original_url = doc.list_latest_files()[0].get_url() doc_id = str(doc.get_id()) icon_url = doc.get_icon( subformat_re=CFG_BIBDOCFILE_ICON_SUBFORMAT_RE_DEFAULT ).get_url() # Get "default" icon description = "" for bibdoc_file in doc.list_latest_files(): #format = bibdoc_file.get_format().lstrip('.').upper() #url = bibdoc_file.get_url() #photo_files.append((format, url)) if not description and bibdoc_file.get_comment(): description = escape(bibdoc_file.get_comment()) name = bibarchive.get_docname(doc.id) photo_manager_descriptions_dict[doc_id] = description photo_manager_icons_dict[doc_id] = icon_url photo_manager_order_list.append(doc_id) # FIXME: respect order # Prepare the list of photos to display. photos_img = [] for doc_id in photo_manager_order_list: if doc_id not in photo_manager_icons_dict: continue icon_url = photo_manager_icons_dict[doc_id] if PHOTO_MANAGER_ORDER: # Get description from disk only if some changes have been done description = escape( read_param_file(curdir, 'PHOTO_MANAGER_DESCRIPTION_' + doc_id)) else: description = escape(photo_manager_descriptions_dict[doc_id]) photos_img.append(''' <li id="%(doc_id)s" style="width:%(initial_slider_value)spx;"> <div class="imgBlock"> <div class="normalLineHeight" style="margin-left:auto;margin-right:auto;display:inline" > <img id="delete_%(doc_id)s" class="hidden" src="/img/cross_red.gif" alt="Delete" style="position:absolute;top:0;" onclick="delete_photo('%(doc_id)s');"/> <img src="%(icon_url)s" class="imgIcon"/> </div> <div class="normalLineHeight"> <textarea style="width:95%%" id="PHOTO_MANAGER_DESCRIPTION_%(doc_id)s" name="PHOTO_MANAGER_DESCRIPTION_%(doc_id)s">%(description)s</textarea> </div> </div> </li>''' % \ {'initial_slider_value': initial_slider_value, 'doc_id': doc_id, 'icon_url': icon_url, 'description': description}) out += ''' <link rel="stylesheet" href="%(CFG_SITE_URL)s/vendors/jquery-ui/themes/redmond/jquery-ui.min.css" type="text/css" charset="utf-8"/> <link rel="stylesheet" href="%(CFG_SITE_URL)s/vendors/jquery-ui/themes/redmond/theme.css" type="text/css" charset="utf-8"/> <style type="text/css"> #sortable { list-style-type: none; margin: 0; padding: 0; } #sortable li { margin: auto 3px; padding: 1px; float: left; width: 180px; font-size:small; text-align: center; position: relative;} #sortable .imgIcon {max-height:95%%;max-width:95%%;margin: 2px;max-height:130px;} #sortable li div.imgBlock {vertical-align: middle; margin: auto;display:inline;display:inline-table;display:inline-block;vertical-align:middle;text-align : center; width:100%%;position:relative} #sortable li div.imgBlock .hidden {display:none;} %(delete_hover_class)s .fileUploadQueue{text-align:left; margin: 0 auto; width:300px;} .normalLineHeight {line-height:normal} </style> <div id="uploadedFiles" style="%(hide_photo_viewer)sborder-left:1px solid #555; border-top:1px solid #555;border-right:1px solid #eee;border-bottom:1px solid #eee;overflow:auto;%(editor_height_style)s%(editor_width_style)sbackground-color:#eee;margin:3px;text-align:left;position:relative"><ul id="sortable">%(photos_img)s</ul></div> <div id="grid_slider" style="%(hide_photo_viewer)swidth:300px;"> <div class='ui-slider-handle'></div> </div> <script type="text/javascript" src="%(CFG_SITE_URL)s/vendors/uploadify/jquery.uploadify.min.js"></script> <script type="text/javascript" src="%(CFG_SITE_URL)s/vendors/swfobject/swfobject/swfobject.js"></script> <script type="text/javascript" src="%(CFG_SITE_URL)s/vendors/jquery-ui/jquery-ui.min.js"></script> <link rel="stylesheet" href="%(CFG_SITE_URL)s/vendors/uploadify/uploadify.css" type="text/css" /> <script type="text/javascript"> $(document).ready(function() { /* Uploading */ if (%(can_upload_photos)s) { $('#uploadFile').uploadify({ 'uploader': '%(CFG_SITE_URL)s/vendors/uploadify/uploadify.swf', 'script': '/submit/uploadfile', 'cancelImg': '%(CFG_SITE_URL)s/vendors/uploadify/uploadify-cancel.png', 'multi' : true, 'auto' : true, 'simUploadLimit': 2, 'scriptData' : {'type': 'File', 'uid': %(uid)s, 'session_id': '%(session_id)s', 'indir': '%(indir)s', 'doctype': '%(doctype)s', 'access': '%(access)s'}, 'displayDate': 'percentage', 'buttonText': 'Browse', 'fileDataName': 'NewFile' /* be compatible with CKEditor */, 'onSelectOnce': function(event, data) { }, 'onSelect': function(event, queueID, fileObj, response, data) { $('#loading').css("visibility","visible"); }, 'onAllComplete' : function(event, queueID, fileObj, response, data) { $('#loading').css("visibility","hidden"); }, /*'onCheck': function(event, checkScript, fileQueue, folder, single) { return false; },*/ 'onComplete': function(event, queueID, fileObj, response, data) { $('#grid_slider').css("display","block"); $('#uploadedFiles').css("display","block"); var cur_width = $("#grid_slider").slider('option', 'value'); var response_obj = parse_invenio_response(response); icon_url = '%(CFG_SITE_URL)s/img/file-icon-blank-96x128.gif' if ("NewFile" in response_obj) { filename = response_obj["NewFile"]["name"] if ('iconName' in response_obj["NewFile"]){ icon_name = response_obj["NewFile"]["iconName"] icon_url = '%(CFG_SITE_URL)s/submit/getuploadedfile?indir=%(indir)s&doctype=%(doctype)s&access=%(access)s&key=NewFile&icon=1&filename=' + icon_name } } else { return true; } $('#sortable').append('<li id="'+ queueID +'" style="width:'+cur_width+'px;"><div class="imgBlock"><div class="normalLineHeight" style="margin-left:auto;margin-right:auto;display:inline" ><img id="delete_'+ queueID +'" class="hidden" src="/img/cross_red.gif" alt="Delete" style="position:absolute;top:0;" onclick="delete_photo(\\''+ queueID +'\\');"/><img src="'+ icon_url +'" class="imgIcon"/></div><div class="normalLineHeight"><textarea style="width:95%%" id="PHOTO_MANAGER_DESCRIPTION_'+ queueID +'" name="PHOTO_MANAGER_DESCRIPTION_'+ queueID +'"></textarea></div></div></li>'); update_order_field(); $('#photo_manager_icons').val($("#photo_manager_icons").val() + '\\n' + queueID + '/' + icon_url); $('#photo_manager_new').val($("#photo_manager_new").val() + '\\n' + queueID + '/' + filename); update_CSS(); return true; } }); } /* Resizing */ $("#grid_slider").slider({ value: %(initial_slider_value)s, max: %(max_slider_value)s, min: %(min_slider_value)s, slide: function(event, ui) { update_CSS(); } }); /* Update CSS to ensure that existing photos get nicely laid out*/ update_CSS(); }); /* Ordering */ $(function() { if (%(can_reorder_photos)s) { $("#sortable").sortable(); $("#sortable").bind('sortupdate', function(event, ui) { update_order_field(); }); } }); function delete_photo(docid){ if (confirm("Are you sure you want to delete the photo? (The file will be deleted after you apply all the modifications)")) { $("#" + docid).remove(); $("#photo_manager_delete").val($("#photo_manager_delete").val() + '\\n' + docid); update_order_field(); } } /* CSS-related */ function update_CSS(){ /* Update some style according to the slider size */ var slider_value = $("#grid_slider").slider('option', 'value'); $('#uploadedFiles li').css('width', slider_value+"px"); /*$('#uploadedFiles div.floater').css('width', slider_value+"px");*/ /* Update height attr accordingly so that image get centered. First we need to get the tallest element of the list. */ var max_height = 0; $('#uploadedFiles li div').each(function() { this_height = $(this).height(); if(this_height > max_height) { max_height = this_height; } }); $('#uploadedFiles li').css('height',max_height+"px"); $('#uploadedFiles li').css('line-height',max_height+"px"); } /* Utils */ function update_order_field(){ $("#photo_manager_order").val($("#sortable").sortable('toArray').join('\\n')); } function parse_invenio_response(response){ /* Return the javascript object included in the the given Invenio message. Really dirty implementation, but ok in this very simple scenario */ /*var object_string = response.substring(response.indexOf('<![CDATA[')+9, response.lastIndexOf(']]>'));*/ object_string = response; var object = {}; eval('object=' + object_string); return object; } </script> <div style="margin: 0 auto;"> <img src="%(CFG_SITE_URL)s/img/loading.gif" style="visibility: hidden" id="loading"/> <input type="file" size="40" id="uploadFile" name="PHOTO_FILE" style="margin: 0 auto;%(upload_display)s"/> </div> <!--<a href="javascript:$('#uploadFile').fileUploadStart();">Upload Files</a> --> <textarea id="photo_manager_icons" style="display:none" name="PHOTO_MANAGER_ICONS">%(PHOTO_MANAGER_ICONS)s</textarea> <textarea id="photo_manager_order" style="display:none" name="PHOTO_MANAGER_ORDER">%(PHOTO_MANAGER_ORDER)s</textarea> <textarea id="photo_manager_new" style="display:none" name="PHOTO_MANAGER_NEW">%(PHOTO_MANAGER_NEW)s</textarea> <textarea id="photo_manager_delete" style="display:none" name="PHOTO_MANAGER_DELETE">%(PHOTO_MANAGER_DELETE)s</textarea> ''' % { 'CFG_SITE_URL': CFG_SITE_URL, #'curdir': cgi.escape(quote(curdir, safe="")),#quote(curdir, safe=""), 'uid': uid, 'access': quote(access, safe=""), 'doctype': quote(doctype, safe=""), 'indir': quote(indir, safe=""), 'session_id': quote(session_id, safe=""), 'PHOTO_MANAGER_ICONS': '\n'.join([ key + '/' + value for key, value in iteritems(photo_manager_icons_dict) ]), 'PHOTO_MANAGER_ORDER': '\n'.join(photo_manager_order_list), 'PHOTO_MANAGER_DELETE': '\n'.join(photo_manager_delete_list), 'PHOTO_MANAGER_NEW': '\n'.join([ key + '/' + value for key, value in iteritems(photo_manager_new_dict) ]), 'initial_slider_value': initial_slider_value, 'max_slider_value': max_slider_value, 'min_slider_value': min_slider_value, 'photos_img': '\n'.join(photos_img), 'hide_photo_viewer': (len(photos_img) == 0 and len(photo_manager_new_dict.keys()) == 0) and 'display:none;' or '', 'delete_hover_class': can_delete_photos and "#sortable li div.imgBlock:hover .hidden {display:inline;}" or '', 'can_reorder_photos': can_reorder_photos and 'true' or 'false', 'can_upload_photos': can_upload_photos and 'true' or 'false', 'upload_display': not can_upload_photos and 'display: none' or '', 'editor_width_style': editor_width and 'width:%spx;' % editor_width or '', 'editor_height_style': editor_height and 'height:%spx;' % editor_height or '' } return out
def test_BibDocs(self): """bibdocfile - BibDocs functions""" from invenio.legacy.bibdocfile.api import BibRecDocs #add file my_bibrecdoc = BibRecDocs(2) timestamp1 = datetime( *(time.strptime("2011-10-09 08:07:06", "%Y-%m-%d %H:%M:%S")[:6])) my_bibrecdoc.add_new_file(pkg_resources.resource_filename( 'invenio_demosite.testsuite.regression', 'data/test.jpg'), 'Main', 'img_test', False, 'test add new file', 'test', '.jpg', modification_date=timestamp1) my_new_bibdoc = my_bibrecdoc.get_bibdoc("img_test") value = my_bibrecdoc.list_bibdocs() self.assertEqual(len(value), 2) #get total file (bibdoc) self.assertEqual(my_new_bibdoc.get_total_size(), 91750) #get recid self.assertEqual(my_new_bibdoc.bibrec_links[0]["recid"], 2) #change name my_new_bibdoc.change_name(2, 'new_name') #get docname my_bibrecdoc = BibRecDocs(2) self.assertEqual(my_bibrecdoc.get_docname(my_new_bibdoc.id), 'new_name') #get type self.assertEqual(my_new_bibdoc.get_type(), 'Main') #get id self.assert_(my_new_bibdoc.get_id() > 80) #set status my_new_bibdoc.set_status('new status') #get status self.assertEqual(my_new_bibdoc.get_status(), 'new status') #get base directory self.assert_(my_new_bibdoc.get_base_dir().startswith( cfg['CFG_BIBDOCFILE_FILEDIR'])) #get file number self.assertEqual(my_new_bibdoc.get_file_number(), 1) #add file new version timestamp2 = datetime( *(time.strptime("2010-09-08 07:06:05", "%Y-%m-%d %H:%M:%S")[:6])) my_new_bibdoc.add_file_new_version(pkg_resources.resource_filename( 'invenio_demosite.testsuite.regression', 'data/test.jpg'), description='the new version', comment=None, docformat=None, flags=["PERFORM_HIDE_PREVIOUS"], modification_date=timestamp2) self.assertEqual(my_new_bibdoc.list_versions(), [1, 2]) #revert timestamp3 = datetime.now() time.sleep( 2 ) # so we can see a difference between now() and the time of the revert my_new_bibdoc.revert(1) self.assertEqual(my_new_bibdoc.list_versions(), [1, 2, 3]) self.assertEqual(my_new_bibdoc.get_description('.jpg', version=3), 'test add new file') #get total size latest version self.assertEqual(my_new_bibdoc.get_total_size_latest_version(), 91750) #get latest version self.assertEqual(my_new_bibdoc.get_latest_version(), 3) #list latest files self.assertEqual(len(my_new_bibdoc.list_latest_files()), 1) self.assertEqual(my_new_bibdoc.list_latest_files()[0].get_version(), 3) #list version files self.assertEqual( len(my_new_bibdoc.list_version_files(1, list_hidden=True)), 1) #display # No Display facility inside of an object ! # value = my_new_bibdoc.display(version='', ln='en', display_hidden=True) # self.assert_('>test add new file<' in value) #format already exist self.assertEqual(my_new_bibdoc.format_already_exists_p('.jpg'), True) #get file self.assertEqual( my_new_bibdoc.get_file('.jpg', version='1').get_version(), 1) #set description my_new_bibdoc.set_description('new description', '.jpg', version=1) #get description self.assertEqual(my_new_bibdoc.get_description('.jpg', version=1), 'new description') #set comment my_new_bibdoc.set_description('new comment', '.jpg', version=1) #get comment self.assertEqual(my_new_bibdoc.get_description('.jpg', version=1), 'new comment') #get history assert len(my_new_bibdoc.get_history()) > 0 #check modification date self.assertEqual( my_new_bibdoc.get_file('.jpg', version=1).md, timestamp1) self.assertEqual( my_new_bibdoc.get_file('.jpg', version=2).md, timestamp2) assert my_new_bibdoc.get_file('.jpg', version=3).md > timestamp3 #delete file my_new_bibdoc.delete_file('.jpg', 2) #list all files self.assertEqual(len(my_new_bibdoc.list_all_files()), 2) #delete file my_new_bibdoc.delete_file('.jpg', 3) #add new format timestamp4 = datetime( *(time.strptime("2012-11-10 09:08:07", "%Y-%m-%d %H:%M:%S")[:6])) my_new_bibdoc.add_file_new_format(pkg_resources.resource_filename( 'invenio_demosite.testsuite.regression', 'data/test.gif'), version=None, description=None, comment=None, docformat=None, modification_date=timestamp4) self.assertEqual(len(my_new_bibdoc.list_all_files()), 2) #check modification time self.assertEqual( my_new_bibdoc.get_file('.jpg', version=1).md, timestamp1) self.assertEqual( my_new_bibdoc.get_file('.gif', version=1).md, timestamp4) #change the format name my_new_bibdoc.change_docformat('.gif', '.gif;icon-640') self.assertEqual(my_new_bibdoc.format_already_exists_p('.gif'), False) self.assertEqual( my_new_bibdoc.format_already_exists_p('.gif;icon-640'), True) #delete file my_new_bibdoc.delete_file('.jpg', 1) #delete file my_new_bibdoc.delete_file('.gif;icon-640', 1) #empty bibdoc self.assertEqual(my_new_bibdoc.empty_p(), True) #hidden? self.assertEqual(my_new_bibdoc.hidden_p('.jpg', version=1), False) #hide my_new_bibdoc.set_flag('HIDDEN', '.jpg', version=1) #hidden? self.assertEqual(my_new_bibdoc.hidden_p('.jpg', version=1), True) #add and get icon my_new_bibdoc.add_icon(pkg_resources.resource_filename( 'invenio_demosite.testsuite.regression', 'data/icon-test.gif'), modification_date=timestamp4) my_bibrecdoc = BibRecDocs(2) value = my_bibrecdoc.get_bibdoc("new_name") self.assertEqual(value.get_icon().docid, my_new_bibdoc.get_icon().docid) self.assertEqual(value.get_icon().version, my_new_bibdoc.get_icon().version) self.assertEqual(value.get_icon().format, my_new_bibdoc.get_icon().format) #check modification time self.assertEqual(my_new_bibdoc.get_icon().md, timestamp4) #delete icon my_new_bibdoc.delete_icon() #get icon self.assertEqual(my_new_bibdoc.get_icon(), None) #delete my_new_bibdoc.delete() self.assertEqual(my_new_bibdoc.deleted_p(), True) #undelete my_new_bibdoc.undelete(previous_status='', recid=2) #expunging my_new_bibdoc.expunge() my_bibrecdoc.build_bibdoc_list() self.failIf('new_name' in my_bibrecdoc.get_bibdoc_names()) self.failUnless(my_bibrecdoc.get_bibdoc_names())
def Move_Photos_to_Storage(parameters, curdir, form, user_info=None): """ The function moves files received from the submission's form through the PHOTO_MANAGER element and its asynchronous uploads at CFG_SITE_URL/submit/uploadfile. Parameters: @iconsize - Seperate multiple sizes with commas. The ImageMagick geometry inputs are supported. Use type 'geometry' as defined in ImageMagick. (eg. 320 or 320x240 or 100> or 5%) Example: "180>,700>" will create two icons, one with maximum dimension 180px, one 700px @iconformat - Allowed extensions (as defined in websubmit_icon_creator.py) are: "pdf", "gif", "jpg", "jpeg", "ps", "png", "bmp" "eps", "epsi", "epsf" The PHOTO_MANAGER elements builds the following file organization in the directory curdir:: curdir/ | ______________________________________________________________________ | | | files/ PHOTO_MANAGER_ICONS icons/ | PHOTO_MANAGER_ORDER | (user id)/ PHOTO_MANAGER_DELETE (user id)/ | PHOTO_MANAGER_NEW | NewFile/ PHOTO_MANAGER_DESCRIPTION_X NewFile/ | | _______________________ _____________________ | | | | | | photo1.jpg myPhoto.gif ... photo1.jpg myPhoto.gif ... where the files are: - PHOTO_MANAGER_ORDER: ordered list of file IDs. One per line. - PHOTO_MANAGER_ICONS: mappings from file IDs to URL of the icons. One per line. Separator: / - PHOTO_MANAGER_NEW: mapping from file ID to filename on disk. Only applicable to files that have just been uploaded (i.e. not bibdocfiles). One per line. Separator: / - PHOTO_MANAGER_DELETE: list of files IDs that must be deleted. One per line - PHOTO_MANAGER_DESCRIPTION_X, where X is file ID: contains photos descriptions (one per file) """ global sysno icon_sizes = parameters.get('iconsize').split(',') icon_format = parameters.get('iconformat') if not icon_format: icon_format = 'gif' PHOTO_MANAGER_ICONS = read_param_file(curdir, 'PHOTO_MANAGER_ICONS', split_lines=True) photo_manager_icons_dict = dict([value.split('/', 1) \ for value in PHOTO_MANAGER_ICONS \ if '/' in value]) PHOTO_MANAGER_ORDER = read_param_file(curdir, 'PHOTO_MANAGER_ORDER', split_lines=True) photo_manager_order_list = [ value for value in PHOTO_MANAGER_ORDER if value.strip() ] PHOTO_MANAGER_DELETE = read_param_file(curdir, 'PHOTO_MANAGER_DELETE', split_lines=True) photo_manager_delete_list = [ value for value in PHOTO_MANAGER_DELETE if value.strip() ] PHOTO_MANAGER_NEW = read_param_file(curdir, 'PHOTO_MANAGER_NEW', split_lines=True) photo_manager_new_dict = dict([value.split('/', 1) \ for value in PHOTO_MANAGER_NEW \ if '/' in value]) ## Create an instance of BibRecDocs for the current recid(sysno) bibrecdocs = BibRecDocs(sysno) for photo_id in photo_manager_order_list: photo_description = read_param_file( curdir, 'PHOTO_MANAGER_DESCRIPTION_' + photo_id) # We must take different actions depending if we deal with a # file that already exists, or if it is a new file if photo_id in photo_manager_new_dict.keys(): # New file if photo_id not in photo_manager_delete_list: filename = photo_manager_new_dict[photo_id] filepath = os.path.join(curdir, 'files', str(user_info['uid']), 'NewFile', filename) icon_filename = os.path.splitext(filename)[0] + ".gif" fileiconpath = os.path.join(curdir, 'icons', str(user_info['uid']), 'NewFile', icon_filename) # Add the file if os.path.exists(filepath): _do_log(curdir, "Adding file %s" % filepath) bibdoc = bibrecdocs.add_new_file(filepath, doctype="picture", never_fail=True) has_added_default_icon_subformat_p = False for icon_size in icon_sizes: # Create icon if needed try: (icon_path, icon_name) = create_icon({ 'input-file': filepath, 'icon-name': icon_filename, 'icon-file-format': icon_format, 'multipage-icon': False, 'multipage-icon-delay': 100, 'icon-scale': icon_size, # Resize only if width > 300 'verbosity': 0, }) fileiconpath = os.path.join(icon_path, icon_name) except InvenioWebSubmitIconCreatorError as e: _do_log( curdir, "Icon could not be created to %s: %s" % (filepath, e)) pass if os.path.exists(fileiconpath): try: if not has_added_default_icon_subformat_p: bibdoc.add_icon(fileiconpath) has_added_default_icon_subformat_p = True _do_log(curdir, "Added icon %s" % fileiconpath) else: icon_suffix = icon_size.replace( '>', '').replace('<', '').replace( '^', '').replace('!', '') bibdoc.add_icon( fileiconpath, subformat= CFG_BIBDOCFILE_DEFAULT_ICON_SUBFORMAT + "-" + icon_suffix) _do_log(curdir, "Added icon %s" % fileiconpath) except InvenioBibDocFileError as e: # Most probably icon already existed. pass if photo_description and bibdoc: for file_format in [bibdocfile.get_format() \ for bibdocfile in bibdoc.list_latest_files()]: bibdoc.set_comment(photo_description, file_format) _do_log(curdir, "Added comment %s" % photo_description) else: # Existing file bibdocname = bibrecdocs.get_docname(int(photo_id)) if photo_id in photo_manager_delete_list: # In principle we should not get here. but just in case... bibrecdocs.delete_bibdoc(bibdocname) _do_log(curdir, "Deleted %s" % bibdocname) else: bibdoc = bibrecdocs.get_bibdoc(bibdocname) for file_format in [bibdocfile.get_format() \ for bibdocfile in bibdoc.list_latest_files()]: bibdoc.set_comment(photo_description, file_format) _do_log(curdir, "Added comment %s" % photo_description) # Now delete requeted files for photo_id in photo_manager_delete_list: try: bibdocname = bibrecdocs.get_docname(int(photo_id)) bibrecdocs.delete_bibdoc(bibdocname) _do_log(curdir, "Deleted %s" % bibdocname) except: # we tried to delete a photo that does not exist (maybe already deleted) pass # Update the MARC _do_log(curdir, "Asking bibdocfile to fix marc") bibdocfile_bin = os.path.join(CFG_BINDIR, 'bibdocfile --yes-i-know') os.system(bibdocfile_bin + " --fix-marc --recid=" + str(sysno)) # Delete the HB BibFormat cache in the DB, so that the fulltext # links do not point to possible dead files run_sql( "DELETE LOW_PRIORITY from bibfmt WHERE format='HB' AND id_bibrec=%s", (sysno, )) return ""
def create_icons_for_record(recid, icon_sizes, icon_format_mappings=None, docnames=None, add_default_icon=False, inherit_moreinfo=False): """Generate icons, if missing, for a record @param recid: the record id for which icons are being created @type recid: int @param icon_sizes: the list of icon sizes that need to be generated. Note that upscaled is not allowed @type icon_sizes: list @param icon_format_mappings: defines for each "master" format in which format the icons should be created. If the master format is not specified here, then its icons will be created in the same format, if possible (for eg. the icons of a TIFF file would be created as TIFF, while icons of a PDF or DOC file would be created in JPG) and unless a default mapping is not provided in C{CFG_ICON_CREATION_FORMAT_MAPPINGS}. @type icon_format_mappings: dict @param docnames: the list of docnames for which we want to create an icon. If not provided, consider all docnames. @type docnames: list @param add_default_icon: if a default icon (i.e. without icon size suffix, matching CFG_BIBDOCFILE_DEFAULT_ICON_SUBFORMAT) should be added or not. @type add_default_icon: bool @param inherit_moreinfo: if the added icons should also have their description and comment set to the same value as the "main" bibdoc or not. @type inherit_moreinfo: bool """ exceptions = [] # keep track of all exceptions done = 0 brd = BibRecDocs(recid) bibdocs = brd.list_bibdocs() # Override default formats from CFG_ICON_CREATION_FORMAT_MAPPINGS # with values specified in icon_format_mappings if icon_format_mappings is None: icon_format_mappings = {} icon_format_mappings = dict(CFG_ICON_CREATION_FORMAT_MAPPINGS, **icon_format_mappings) if icon_format_mappings.has_key('*') and \ not icon_format_mappings['*']: # we must override the default in order to keep the # "superformat" del icon_format_mappings['*'] for bibdoc in bibdocs: docname = brd.get_docname(bibdoc.id) if docnames and not docname in docnames: # Skip this docname continue comment, description = get_comment_and_description( bibdoc, inherit_moreinfo) default_icon_added_p = False bibfiles = bibdoc.list_latest_files() bibdoc_formats = [bibfile.get_format() for bibfile in bibfiles] for bibfile in bibfiles: if bibfile.get_subformat(): # this is a subformat, do nothing continue filepath = bibfile.get_full_path() #do not consider the dot in front of the format superformat = bibfile.get_format()[1:].lower() bibfile_icon_formats = icon_format_mappings.get( superformat, icon_format_mappings.get('*', [superformat])) if isinstance(bibfile_icon_formats, str): bibfile_icon_formats = [bibfile_icon_formats] bibfile_icon_formats = [bibfile_icon_format for bibfile_icon_format in bibfile_icon_formats \ if bibfile_icon_format in CFG_ALLOWED_FILE_EXTENSIONS] if add_default_icon and not default_icon_added_p: # add default icon try: iconpath, iconname = _create_icon( filepath, CFG_DEFAULT_ICON_SIZE, docname, icon_format=CFG_DEFAULT_ICON_EXTENSION, verbosity=9) bibdoc.add_file_new_format( os.path.join(iconpath, iconname), docformat=".%s;%s" % (CFG_DEFAULT_ICON_EXTENSION, CFG_BIBDOCFILE_DEFAULT_ICON_SUBFORMAT), comment=comment, description=description) default_icon_added_p = True write_message( "Added default icon to recid: %s, format: %s" % (recid, CFG_DEFAULT_ICON_EXTENSION)) except Exception, ex: exceptions.append("Could not add new icon to recid: %s, format: %s; exc: %s" \ % (recid, CFG_DEFAULT_ICON_EXTENSION, ex)) # check if the subformat that we want to create already exists for icon_size in icon_sizes: washed_icon_size = icon_size.replace('>', '').replace( '<', '').replace('^', '').replace('!', '') for icon_format in bibfile_icon_formats: new_format = '.%s;%s-%s' % ( icon_format, CFG_BIBDOCFILE_DEFAULT_ICON_SUBFORMAT, washed_icon_size) if new_format in bibdoc_formats: # the subformat already exists, do nothing continue # add icon try: iconpath, iconname = _create_icon( filepath, icon_size, docname, icon_format=icon_format, verbosity=9) bibdoc.add_file_new_format(os.path.join( iconpath, iconname), docformat=new_format, comment=comment, description=description) write_message( "Added icon to recid: %s, format: %s %s %s %s" % (recid, new_format, iconpath, iconname, icon_size)) done += 1 except Exception, ex: exceptions.append("Could not add new format to recid: %s, format: %s; exc: %s" \ %(recid, new_format, ex))
def getfile(req, form): args = wash_urlargd(form, bibdocfile_templates.files_default_urlargd) ln = args['ln'] _ = gettext_set_language(ln) uid = getUid(req) user_info = collect_user_info(req) verbose = args['verbose'] if verbose >= 1 and not isUserSuperAdmin(user_info): # Only SuperUser can see all the details! verbose = 0 if uid == -1 or CFG_ACCESS_CONTROL_LEVEL_SITE > 1: return page_not_authorized(req, "/%s/%s" % (CFG_SITE_RECORD, self.recid), navmenuid='submit') if record_exists(self.recid) < 1: msg = "<p>%s</p>" % _("Requested record does not seem to exist.") return warning_page(msg, req, ln) if record_empty(get_record(self.recid).legacy_create_recstruct()): msg = "<p>%s</p>" % _("Requested record does not seem to have been integrated.") return warning_page(msg, req, ln) (auth_code, auth_message) = check_user_can_view_record(user_info, self.recid) if auth_code and user_info['email'] == 'guest': cookie = mail_cookie_create_authorize_action(VIEWRESTRCOLL, {'collection' : guess_primary_collection_of_a_record(self.recid)}) target = CFG_SITE_SECURE_URL + '/youraccount/login' + \ make_canonical_urlargd({'action': cookie, 'ln' : ln, 'referer' : \ CFG_SITE_SECURE_URL + user_info['uri']}, {}) return redirect_to_url(req, target, norobot=True) elif auth_code: return page_not_authorized(req, "../", \ text = auth_message) readonly = CFG_ACCESS_CONTROL_LEVEL_SITE == 1 # From now on: either the user provided a specific file # name (and a possible version), or we return a list of # all the available files. In no case are the docids # visible. try: bibarchive = BibRecDocs(self.recid) except InvenioBibDocFileError: register_exception(req=req, alert_admin=True) msg = "<p>%s</p><p>%s</p>" % ( _("The system has encountered an error in retrieving the list of files for this document."), _("The error has been logged and will be taken in consideration as soon as possible.")) return warning_page(msg, req, ln) if bibarchive.deleted_p(): req.status = apache.HTTP_GONE return warning_page(_("Requested record does not seem to exist."), req, ln) docname = '' docformat = '' version = '' warn = '' if filename: # We know the complete file name, guess which docid it # refers to ## TODO: Change the extension system according to ext.py from setlink ## and have a uniform extension mechanism... docname = file_strip_ext(filename) docformat = filename[len(docname):] if docformat and docformat[0] != '.': docformat = '.' + docformat if args['subformat']: docformat += ';%s' % args['subformat'] else: docname = args['docname'] if not docformat: docformat = args['format'] if args['subformat']: docformat += ';%s' % args['subformat'] if not version: version = args['version'] ## Download as attachment is_download = False if args['download']: is_download = True # version could be either empty, or all or an integer try: int(version) except ValueError: if version != 'all': version = '' display_hidden = isUserSuperAdmin(user_info) if version != 'all': # search this filename in the complete list of files for doc in bibarchive.list_bibdocs(): if docname == bibarchive.get_docname(doc.id): try: try: docfile = doc.get_file(docformat, version) except InvenioBibDocFileError as msg: req.status = apache.HTTP_NOT_FOUND if not CFG_INSPIRE_SITE and req.headers_in.get('referer'): ## There must be a broken link somewhere. ## Maybe it's good to alert the admin register_exception(req=req, alert_admin=True) warn += write_warning(_("The format %(x_form)s does not exist for the given version: %(x_vers)s", x_form=cgi.escape(docformat), x_vers=cgi.escape(str(msg)))) break (auth_code, auth_message) = docfile.is_restricted(user_info) if auth_code != 0 and not is_user_owner_of_record(user_info, self.recid): if CFG_BIBDOCFILE_ICON_SUBFORMAT_RE.match(get_subformat_from_format(docformat)): return stream_restricted_icon(req) if user_info['email'] == 'guest': cookie = mail_cookie_create_authorize_action('viewrestrdoc', {'status' : docfile.get_status()}) target = CFG_SITE_SECURE_URL + '/youraccount/login' + \ make_canonical_urlargd({'action': cookie, 'ln' : ln, 'referer' : \ CFG_SITE_SECURE_URL + user_info['uri']}, {}) redirect_to_url(req, target) else: req.status = apache.HTTP_UNAUTHORIZED warn += write_warning(_("This file is restricted: ") + str(auth_message)) break if not docfile.hidden_p(): if not readonly: ip = str(req.remote_ip) doc.register_download(ip, docfile.get_version(), docformat, uid, self.recid) try: return docfile.stream(req, download=is_download) except InvenioBibDocFileError as msg: register_exception(req=req, alert_admin=True) req.status = apache.HTTP_INTERNAL_SERVER_ERROR warn += write_warning(_("An error has happened in trying to stream the request file.")) else: req.status = apache.HTTP_UNAUTHORIZED warn += write_warning(_("The requested file is hidden and can not be accessed.")) except InvenioBibDocFileError as msg: register_exception(req=req, alert_admin=True) if docname and docformat and not warn: req.status = apache.HTTP_NOT_FOUND warn += write_warning(_("Requested file does not seem to exist.")) # filelist = bibarchive.display("", version, ln=ln, verbose=verbose, display_hidden=display_hidden) filelist = bibdocfile_templates.tmpl_display_bibrecdocs(bibarchive, "", version, ln=ln, verbose=verbose, display_hidden=display_hidden) t = warn + bibdocfile_templates.tmpl_filelist( ln=ln, filelist=filelist) cc = guess_primary_collection_of_a_record(self.recid) cc_id = Collection.query.filter_by(name=cc).value('id') unordered_tabs = None # get_detailed_page_tabs(cc_id, self.recid, ln) ordered_tabs_id = [(tab_id, values['order']) for (tab_id, values) in iteritems(unordered_tabs)] ordered_tabs_id.sort(lambda x, y: cmp(x[1], y[1])) link_ln = '' if ln != CFG_SITE_LANG: link_ln = '?ln=%s' % ln tabs = [(unordered_tabs[tab_id]['label'], '%s/%s/%s/%s%s' % (CFG_SITE_URL, CFG_SITE_RECORD, self.recid, tab_id, link_ln), tab_id == 'files', unordered_tabs[tab_id]['enabled']) for (tab_id, dummy_order) in ordered_tabs_id if unordered_tabs[tab_id]['visible'] is True] tabs_counts = {} # get_detailed_page_tabs_counts(self.recid) top = webstyle_templates.detailed_record_container_top(self.recid, tabs, args['ln'], citationnum=tabs_counts['Citations'], referencenum=tabs_counts['References'], discussionnum=tabs_counts['Discussions']) bottom = webstyle_templates.detailed_record_container_bottom(self.recid, tabs, args['ln']) title, description, keywords = websearch_templates.tmpl_record_page_header_content(req, self.recid, args['ln']) return pageheaderonly(title=title, navtrail=create_navtrail_links(cc=cc, aas=0, ln=ln) + \ ''' > <a class="navtrail" href="%s/%s/%s">%s</a> > %s''' % \ (CFG_SITE_URL, CFG_SITE_RECORD, self.recid, title, _("Access to Fulltext")), description=description, keywords=keywords, uid=uid, language=ln, req=req, navmenuid='search', navtrail_append_title_p=0) + \ websearch_templates.tmpl_search_pagestart(ln) + \ top + t + bottom + \ websearch_templates.tmpl_search_pageend(ln) + \ pagefooteronly(language=ln, req=req)
def test_BibDocs(self): """bibdocfile - BibDocs functions""" from invenio.legacy.bibdocfile.api import BibRecDocs #add file my_bibrecdoc = BibRecDocs(2) timestamp1 = datetime(*(time.strptime("2011-10-09 08:07:06", "%Y-%m-%d %H:%M:%S")[:6])) my_bibrecdoc.add_new_file( pkg_resources.resource_filename( 'invenio_demosite.testsuite.regression', 'data/test.jpg'), 'Main', 'img_test', False, 'test add new file', 'test', '.jpg', modification_date=timestamp1) my_new_bibdoc = my_bibrecdoc.get_bibdoc("img_test") value = my_bibrecdoc.list_bibdocs() self.assertEqual(len(value), 2) #get total file (bibdoc) self.assertEqual(my_new_bibdoc.get_total_size(), 91750) #get recid self.assertEqual(my_new_bibdoc.bibrec_links[0]["recid"], 2) #change name my_new_bibdoc.change_name(2, 'new_name') #get docname my_bibrecdoc = BibRecDocs(2) self.assertEqual(my_bibrecdoc.get_docname(my_new_bibdoc.id), 'new_name') #get type self.assertEqual(my_new_bibdoc.get_type(), 'Main') #get id self.assert_(my_new_bibdoc.get_id() > 80) #set status my_new_bibdoc.set_status('new status') #get status self.assertEqual(my_new_bibdoc.get_status(), 'new status') #get base directory self.assert_(my_new_bibdoc.get_base_dir().startswith(cfg['CFG_BIBDOCFILE_FILEDIR'])) #get file number self.assertEqual(my_new_bibdoc.get_file_number(), 1) #add file new version timestamp2 = datetime(*(time.strptime("2010-09-08 07:06:05", "%Y-%m-%d %H:%M:%S")[:6])) my_new_bibdoc.add_file_new_version( pkg_resources.resource_filename( 'invenio_demosite.testsuite.regression', 'data/test.jpg'), description= 'the new version', comment=None, docformat=None, flags=["PERFORM_HIDE_PREVIOUS"], modification_date=timestamp2) self.assertEqual(my_new_bibdoc.list_versions(), [1, 2]) #revert timestamp3 = datetime.now() time.sleep(2) # so we can see a difference between now() and the time of the revert my_new_bibdoc.revert(1) self.assertEqual(my_new_bibdoc.list_versions(), [1, 2, 3]) self.assertEqual(my_new_bibdoc.get_description('.jpg', version=3), 'test add new file') #get total size latest version self.assertEqual(my_new_bibdoc.get_total_size_latest_version(), 91750) #get latest version self.assertEqual(my_new_bibdoc.get_latest_version(), 3) #list latest files self.assertEqual(len(my_new_bibdoc.list_latest_files()), 1) self.assertEqual(my_new_bibdoc.list_latest_files()[0].get_version(), 3) #list version files self.assertEqual(len(my_new_bibdoc.list_version_files(1, list_hidden=True)), 1) #display # No Display facility inside of an object ! # value = my_new_bibdoc.display(version='', ln='en', display_hidden=True) # self.assert_('>test add new file<' in value) #format already exist self.assertEqual(my_new_bibdoc.format_already_exists_p('.jpg'), True) #get file self.assertEqual(my_new_bibdoc.get_file('.jpg', version='1').get_version(), 1) #set description my_new_bibdoc.set_description('new description', '.jpg', version=1) #get description self.assertEqual(my_new_bibdoc.get_description('.jpg', version=1), 'new description') #set comment my_new_bibdoc.set_description('new comment', '.jpg', version=1) #get comment self.assertEqual(my_new_bibdoc.get_description('.jpg', version=1), 'new comment') #get history assert len(my_new_bibdoc.get_history()) > 0 #check modification date self.assertEqual(my_new_bibdoc.get_file('.jpg', version=1).md, timestamp1) self.assertEqual(my_new_bibdoc.get_file('.jpg', version=2).md, timestamp2) assert my_new_bibdoc.get_file('.jpg', version=3).md > timestamp3 #delete file my_new_bibdoc.delete_file('.jpg', 2) #list all files self.assertEqual(len(my_new_bibdoc.list_all_files()), 2) #delete file my_new_bibdoc.delete_file('.jpg', 3) #add new format timestamp4 = datetime(*(time.strptime("2012-11-10 09:08:07", "%Y-%m-%d %H:%M:%S")[:6])) my_new_bibdoc.add_file_new_format( pkg_resources.resource_filename( 'invenio_demosite.testsuite.regression', 'data/test.gif'), version=None, description=None, comment=None, docformat=None, modification_date=timestamp4) self.assertEqual(len(my_new_bibdoc.list_all_files()), 2) #check modification time self.assertEqual(my_new_bibdoc.get_file('.jpg', version=1).md, timestamp1) self.assertEqual(my_new_bibdoc.get_file('.gif', version=1).md, timestamp4) #change the format name my_new_bibdoc.change_docformat('.gif', '.gif;icon-640') self.assertEqual(my_new_bibdoc.format_already_exists_p('.gif'), False) self.assertEqual(my_new_bibdoc.format_already_exists_p('.gif;icon-640'), True) #delete file my_new_bibdoc.delete_file('.jpg', 1) #delete file my_new_bibdoc.delete_file('.gif;icon-640', 1) #empty bibdoc self.assertEqual(my_new_bibdoc.empty_p(), True) #hidden? self.assertEqual(my_new_bibdoc.hidden_p('.jpg', version=1), False) #hide my_new_bibdoc.set_flag('HIDDEN', '.jpg', version=1) #hidden? self.assertEqual(my_new_bibdoc.hidden_p('.jpg', version=1), True) #add and get icon my_new_bibdoc.add_icon( pkg_resources.resource_filename( 'invenio_demosite.testsuite.regression', 'data/icon-test.gif'), modification_date=timestamp4) my_bibrecdoc = BibRecDocs(2) value = my_bibrecdoc.get_bibdoc("new_name") self.assertEqual(value.get_icon().docid, my_new_bibdoc.get_icon().docid) self.assertEqual(value.get_icon().version, my_new_bibdoc.get_icon().version) self.assertEqual(value.get_icon().format, my_new_bibdoc.get_icon().format) #check modification time self.assertEqual(my_new_bibdoc.get_icon().md, timestamp4) #delete icon my_new_bibdoc.delete_icon() #get icon self.assertEqual(my_new_bibdoc.get_icon(), None) #delete my_new_bibdoc.delete() self.assertEqual(my_new_bibdoc.deleted_p(), True) #undelete my_new_bibdoc.undelete(previous_status='', recid=2) #expunging my_new_bibdoc.expunge() my_bibrecdoc.build_bibdoc_list() self.failIf('new_name' in my_bibrecdoc.get_bibdoc_names()) self.failUnless(my_bibrecdoc.get_bibdoc_names())
def format_element(bfo, separator=" ", style='', img_style='', text_style='font-size:small', print_links='yes', max_photos='', show_comment='yes', img_max_width='250px', display_all_version_links='yes'): """ Lists the photos of a record. Display the icon version, linked to its original version. This element works for photos appended to a record as BibDoc files, for which a preview icon has been generated. If there are several formats for one photo, use the first one found. @param separator: separator between each photo @param print_links: if 'yes', print links to the original photo @param style: style attributes of the whole image block. Eg: "padding:2px;border:1px" @param img_style: style attributes of the images. Eg: "width:50px;border:none" @param text_style: style attributes of the text. Eg: "font-size:small" @param max_photos: the maximum number of photos to display @param show_comment: if 'yes', display the comment of each photo @param display_all_version_links: if 'yes', print links to additional (sub)formats """ photos = [] bibarchive = BibRecDocs(bfo.recID) bibdocs = bibarchive.list_bibdocs() if max_photos.isdigit(): max_photos = int(max_photos) else: max_photos = len(bibdocs) for doc in bibdocs[:max_photos]: found_icons = [] found_url = '' for docfile in doc.list_latest_files(): if docfile.is_icon(): found_icons.append(( docfile.get_size(), get_relative_url(docfile.get_url()) )) else: found_url = get_relative_url(docfile.get_url()) found_icons.sort() if found_icons: additional_links = '' name = bibarchive.get_docname(doc.id) comment = doc.list_latest_files()[0].get_comment() preview_url = None if len(found_icons) > 1: preview_url = get_relative_url(found_icons[1][1]) additional_urls = [(docfile.get_size(), get_relative_url(docfile.get_url()), \ docfile.get_superformat(), docfile.get_subformat()) \ for docfile in doc.list_latest_files() if not docfile.is_icon()] additional_urls.sort() additional_links = [create_html_link(url, urlargd={}, \ linkattrd={'style': 'font-size:x-small'}, \ link_label="%s %s (%s)" % (format.strip('.').upper(), subformat, format_size(size))) \ for (size, url, format, subformat) in additional_urls] img = '<img src="%(icon_url)s" alt="%(name)s" style="max-width:%(img_max_width)s;_width:%(img_max_width)s;%(img_style)s" />' % \ {'icon_url': cgi.escape(get_relative_url(found_icons[0][1]), True), 'name': cgi.escape(name, True), 'img_style': img_style, 'img_max_width': img_max_width} if print_links.lower() == 'yes': img = '<a href="%s">%s</a>' % (cgi.escape(preview_url or found_url, True), img) if display_all_version_links.lower() == 'yes' and additional_links: img += '<br />' + ' '.join(additional_links) + '<br />' if show_comment.lower() == 'yes' and comment: img += '<div style="margin-auto;text-align:center;%(text_style)s">%(comment)s</div>' % \ {'comment': comment.replace('\n', '<br/>'), 'text_style': text_style} img = '<div style="vertical-align: middle;text-align:center;display:inline-block;display: -moz-inline-stack;zoom: 1;*display: inline;max-width:%(img_max_width)s;_width:%(img_max_width)s;text-align:center;%(style)s">%(img)s</div>' % \ {'img_max_width': img_max_width, 'style': style, 'img': img} photos.append(img) return '<div>' + separator.join(photos) + '</div>'
def Move_Revised_Files_to_Storage(parameters, curdir, form, user_info=None): """ The function revises the files of a record with the newly uploaded files. This function can work only if you can define a mapping from the WebSubmit element name that uploads the file, to the doctype of the file. In most cases, the doctype is equivalent to the element name, or just map to 'Main' doctype. That is typically the case if you use the Move_Files_to_Storage.py function to upload the files at submission step. For eg. with the DEMOBOO submission of the Atlantis Demo site, a file is uploaded thanks to the DEMOBOO_FILE element/File input, which is mapped to doctype DEMOBOO_FILE. The function ignores files for which multiple files exist for a single doctype in the record, or when several files are uploaded with the same element name. If the record to revise does not have a corresponding file, the file is inserted This function is similar to Move_Uploaded_Files_to_Storage.py, excepted that Move_Uploaded_Files_to_Storage relies on files uploaded from the web interface created by Create_Upload_Files_Interface.py, while this function relies on the files uploaded by a regular WebSubmit page that you have built from WebSubmit admin: Regular WebSubmit interface --(upload file)--> Move_Revised_Files_to_Storage.py Create_Upload_Files_Interface.py --(upload file)--> Move_Uploaded_Files_to_Storage.py The main advantages of this function over the functions Create_Upload_Files_Interface.py/Move_Uploaded_Files_to_Storage is that it lets you customize the display of your submission in the way you want, which could be simpler for your users if you usually only upload a few and fixed number of files per record. The disadvantages are that this function is not capable of : deleting files, adding an alternative format to a file, add a variable number of files, does not allow to set permissions at the level of file, does not support user comments, renaming, etc. @param parameters:(dictionary) - must contain: + elementNameToDoctype: maps an element/field name to a doctype. Eg. the file uploaded from the DEMOBOO_FILE element (input file tag) should revise the file with document type (doctype) "Main": DEMOBOO_FILE=Main|DEMOBOO_FILE_2=ADDITIONAL ('=' separates element name and doctype '|' separates each doctype/element name group) In most cases, the element name == doctype: DEMOBOO_FILE=DEMOBOO_FILE|DEMOBOO_FILE_2=DEMOBOO_FILE_2 + createIconDoctypes: the list of doctypes for which an icon should be created when revising the file. Eg: Figure|Graph ('|' separated values) Use '*' for all doctypes + iconsize: size of the icon to create (when applicable) + keepPreviousVersionDoctypes: the list of doctypes for which the function should keep previous versions visible when revising a file. Eg: Main|Additional ('|' separated values) Default is all + createRelatedFormats: if uploaded files get converted to whatever format we can (1) or not (0) """ # pylint: disable=E0602 # sysno is defined in the WebSubmit functions sandbox. global sysno bibrecdocs = BibRecDocs(int(sysno)) # Wash function parameters (element_name_and_doctype, create_icon_doctypes, iconsize, keep_previous_version_doctypes, createRelatedFormats_p) = \ wash_function_parameters(parameters, curdir) for element_name, doctype in element_name_and_doctype: _do_log(curdir, "Processing " + element_name) # Check if there is a corresponding file file_path = os.path.join(curdir, 'files', element_name, read_file(curdir, element_name)) if file_path and os.path.exists(file_path): # Now identify which file to revise files_in_record = bibrecdocs.list_bibdocs(doctype) if len(files_in_record) == 1: # Ok, we can revise bibdoc_name = bibrecdocs.get_docname(files_in_record[0].id) revise(bibrecdocs, curdir, sysno, file_path, bibdoc_name, doctype, iconsize, create_icon_doctypes, keep_previous_version_doctypes, createRelatedFormats_p) elif len(files_in_record) == 0: # We must add the file add(bibrecdocs, curdir, sysno, file_path, doctype, iconsize, create_icon_doctypes, createRelatedFormats_p) else: _do_log(curdir, " %s ignored, because multiple files found for same doctype %s in record %s: %s" %\ (element_name, doctype, sysno, ', '.join(files_in_record))) else: _do_log(curdir, " No corresponding file found (%s)" % file_path) # Update the MARC bibdocfile_bin = os.path.join(CFG_BINDIR, 'bibdocfile --yes-i-know') os.system(bibdocfile_bin + " --fix-marc --recid=" + sysno) # Delete the HB BibFormat cache in the DB, so that the fulltext # links do not point to possible dead files run_sql( "DELETE LOW_PRIORITY from bibfmt WHERE format='HB' AND id_bibrec=%s", (sysno, ))