def sort_key(obj): attr = getattr(obj, p_attr, None) if isinstance(attr, basestring): if lower: return force_to_unicode(attr).lower() else: return force_to_unicode(attr) else: return attr
def edit_message(self, msgid, lang, translation): """Edits or adds message with `translation` in `lang` language""" # input type sanitize logger = logging.getLogger(__name__) if isinstance(msgid, str): msgid = force_to_unicode(msgid) if isinstance(translation, str): translation = force_to_unicode(translation) # language existance test if lang not in self.get_languages(): return # Add-by-edit functionality if not self._messages.has_key(msgid): self.gettext(msgid, lang) self._messages[msgid][lang] = collapse_whitespace(translation)
def get_local_user_info(self, user): user_roles = self.get_local_user_roles(user) firstname = force_to_unicode(user.firstname) lastname = force_to_unicode(user.lastname) name = firstname + u' ' + lastname return { 'userid': user.name, 'firstname': force_to_unicode(user.firstname), 'lastname': force_to_unicode(user.lastname), 'name': name, 'email': user.email, 'access_level': self.get_user_access_level(user_roles), 'organisation': 'N/A', 'postal_address': 'N/A', }
def create_message(text, addr_to, addr_from, subject): if isinstance(addr_to, basestring): addr_to = (addr_to,) addr_to = ', '.join(addr_to) subject = force_to_unicode(subject) text = force_to_unicode(text) message = create_plain_message(text.encode('utf-8')) hack_to_use_quopri(message) message['To'] = safe_header(addr_to) message['From'] = safe_header(addr_from) message['Subject'] = safe_header(subject) message['Date'] = email_utils.formatdate() return message
def slugify(s, maxlen=80, removelist=None): ''' Converts unicode to ascii string ready for use in urls/zope id-s You can use the returned value as a param for uniqueId(id,exists) to get an available valid id in context. * `s`: unicode string. However, if a `str` is provided, it's decoded to `unicode` using the "ascii" encoding. * `maxlen`: maximum length of string * `removelist`: list of words to be removed from id. If None, a common En. wordlist will be used (default_remove_words) Uses unidecode, converts group of spaces/unacceptable chars to single hyphens. Strips leading/trailing hyphens, lowers case, returns random 5-digit word if id can not be constructed from input. ''' if maxlen <= 0: raise ValueError("Illegal value for @param maxlen") if type(s) is str: s = force_to_unicode(s) # raises UnicodeDecodeError if non-ascii # coder should take notice `s` must be unicode / ascii str s = str(unidecode(s)) if removelist is None: if s.lower() in default_remove_words: # if the id as a whole is already in default_remove_words # it should be kept removelist = [] else: removelist = default_remove_words ignore_words = '|'.join([r for r in removelist]) ignore_words_pat = re.compile(r'\b(' + ignore_words + r')\b', re.I) ignore_chars_pat = re.compile(r'[^-_\.A-Z0-9\s]', re.I) outside_space_pat = re.compile(r'^[-\s]+|[-\s]+$') inside_space_pat = re.compile(r'[-\s]+') s = ignore_words_pat.sub('', s) # remove unimportant words s = ignore_chars_pat.sub('-', s) # change unneeded chars to hyphens s = outside_space_pat.sub('', s) # trim leading/trailing spaces/hyphens # convert spaces or group of s = inside_space_pat.sub('-', s) wordlist = s.split('-') picked_words = [] for w in wordlist: if (sum([len(x) for x in picked_words]) + len(picked_words) + len(w)) <= maxlen: picked_words.append(w) else: break # join with hyphens, convert to lowercase s = '-'.join(picked_words).lower() if not s: # empty string unnacceptable # for backwards compat., but also take in mind maxlen return genRandomId(p_length=min(5, maxlen)) return s
def tmpl_version(context, version, ver_id): """ """ # Try to get the adapter for this version and set viewable viewable = False if get_view_adapter(version) is not None: viewable = True pretty_version_size = None url = None icon_url = None if not version.removed: pretty_version_size = pretty_size(version.size) url = "%s/download/%s/%s" % (context.absolute_url(), ver_id, urllib.quote(version.filename, safe="")) icon_url = icon_for_content_type(version.content_type)["url"] return { "contributor": getattr(version, "contributor", ""), "filename": force_to_unicode(version.filename), "content_type": version.content_type, "pretty_size": pretty_version_size, "removed": version.removed, "url": url, "icon_url": icon_url, "pretty_timestamp": version.timestamp.strftime("%d %b %Y"), "timestamp": DateTime(version.timestamp.replace(tzinfo=None)), "id": ver_id, "is_current": False, "viewable": viewable, "ob": context, }
def slugify(s, maxlen=80, removelist=None): ''' Converts unicode to ascii string ready for use in urls/zope id-s You can use the returned value as a param for uniqueId(id,exists) to get an available valid id in context. * `s`: unicode string. However, if a `str` is provided, it's decoded to `unicode` using the "ascii" encoding. * `maxlen`: maximum length of string * `removelist`: list of words to be removed from id. If None, a common En. wordlist will be used (default_remove_words) Uses unidecode, converts group of spaces/unacceptable chars to single hyphens. Strips leading/trailing hyphens, lowers case, returns random 5-digit word if id can not be constructed from input. ''' if maxlen <= 0: raise ValueError("Illegal value for @param maxlen") if type(s) is str: s = force_to_unicode(s) # raises UnicodeDecodeError if non-ascii # coder should take notice `s` must be unicode / ascii str s = str(unidecode(s)) if removelist is None: if s.lower() in default_remove_words: # if the id as a whole is already in default_remove_words # it should be kept removelist = [] else: removelist = default_remove_words ignore_words = '|'.join([r for r in removelist]) ignore_words_pat = re.compile(r'\b('+ignore_words+r')\b', re.I) ignore_chars_pat = re.compile(r'[^-_\.A-Z0-9\s]', re.I) outside_space_pat = re.compile(r'^[-\s]+|[-\s]+$') inside_space_pat = re.compile(r'[-\s]+') s = ignore_words_pat.sub('', s) # remove unimportant words s = ignore_chars_pat.sub('-', s) # change unneeded chars to hyphens s = outside_space_pat.sub('', s) # trim leading/trailing spaces/hyphens # convert spaces or group of s = inside_space_pat.sub('-', s) wordlist = s.split('-') picked_words = [] for w in wordlist: if (sum([len(x) for x in picked_words]) + len(picked_words) + len(w)) <= maxlen: picked_words.append(w) else: break # join with hyphens, convert to lowercase s = '-'.join(picked_words).lower() if not s: # empty string unnacceptable # for backwards compat., but also take in mind maxlen return genRandomId(p_length=min(5, maxlen)) return s
def gettext(self, msgid, lang=None, default=None): """Returns the corresponding translation of msgid in Catalog.""" if not isinstance(msgid, basestring): raise TypeError('Only strings can be translated.') # saving everything unicode, utf-8 elif isinstance(msgid, str): msgid = force_to_unicode(msgid) if not lang: raise ValueError("No language provided for gettext") msgid = msgid.strip() # empty message is translated as empty message, regardless of lang if not msgid: return msgid # default `default translation` is the msgid itself if default is None: default = msgid if lang not in self.get_languages(): # we don't have that lang, thus we can't translate and won't add msg return default # Add it if it's not in the dictionary if not self._messages.has_key(msgid): self._messages[msgid] = PersistentMapping() notify(MessageAddEvent(self, msgid, lang, default)) if not self._messages[msgid].has_key(self._default_language): default_translation = collapse_whitespace(default) self._messages[msgid][self._default_language] = default_translation # translation may be blank (supposition), then-> default (usually msgid) in_catalog = self._messages[msgid].get(lang, '') return in_catalog or default
def _update(self, portal): if 'title' not in portal.aq_base.__dict__: self.log.debug('no need to update') return True lang = portal.gl_get_default_language() self.log.debug('default lang is %s' % lang) self.log.debug('portal.title = %r' % portal.title) localized_title_not_exists = 'title' not in portal._local_properties localized_title_empty = not portal.getLocalAttribute('title', lang) if localized_title_not_exists: self.log.debug("title localized property doesn't exist") if localized_title_empty: self.log.debug("title property empty for default lang") if localized_title_not_exists or localized_title_empty: portal.set_localpropvalue('title', lang, force_to_unicode(portal.title)) self.log.debug("updated title localized property") delattr(portal.aq_base, 'title') self.log.debug('removed portal title attr') return True
def tmpl_version(context, version, ver_id): """ """ # Try to get the adapter for this version and set viewable viewable = False if get_view_adapter(version) is not None: viewable = True pretty_version_size = None url = None icon_url = None language = context.REQUEST.form.get( 'lang', context.get_selected_language() or 'en') if not version.removed: pretty_version_size = pretty_size(version.size) url = ('%s/download/%s/%s/%s' % (context.absolute_url(), language, ver_id, urllib.quote(strip_leading_underscores(version.filename), safe=''))) icon_url = (icon_for_content_type(version.content_type)['url']) return { 'contributor': getattr(version, 'contributor', ''), 'filename': force_to_unicode(version.filename), 'content_type': version.content_type, 'pretty_size': pretty_version_size, 'removed': version.removed, 'url': url, 'icon_url': icon_url, 'pretty_timestamp': version.timestamp.strftime('%d %b %Y'), 'timestamp': DateTime(version.timestamp.replace(tzinfo=None)), 'id': ver_id, 'is_current': False, 'viewable': viewable, 'ob': context, }
def _name_and_email(self, obj): # First look for the user in Nayaa's acl_users site = obj.getSite() auth_tool = site.getAuthenticationTool() user_obj = auth_tool.getUser(self.user_id) if user_obj is not None: full_name = u'%s %s' % ( auth_tool.getUserFirstName(user_obj), auth_tool.getUserLastName(user_obj)) email = auth_tool.getUserEmail(user_obj) return (full_name, email) # The user is not in Naaya's acl_users, so let's look deeper parent_acl_users = site.restrictedTraverse('/').acl_users if parent_acl_users.meta_type == 'LDAPUserFolder': # TODO: what if parent_acl_users is not an LDAPUserFolder? # Note: EIONET LDAP data is encoded with latin-1 ldap_user_data = parent_acl_users.getUserById(self.user_id) if ldap_user_data: full_name = ldap_user_data.cn email = ldap_user_data.mail return (force_to_unicode(full_name), email) # Didn't find the user anywhere; return a placeholder notif_logger.warn('Could not find email for user %r (context: %r)', self.user_id, obj) return (u'[not found]', None)
def _name_and_email(self, obj): # First look for the user in Nayaa's acl_users site = obj.getSite() auth_tool = site.getAuthenticationTool() user_obj = auth_tool.getUser(self.user_id) if user_obj is not None: try: full_name = u'%s %s' % ( auth_tool.getUserFirstName(user_obj).decode('utf-8'), auth_tool.getUserLastName(user_obj).decode('utf-8')) except UnicodeEncodeError: full_name = u'%s %s' % ( auth_tool.getUserFirstName(user_obj), auth_tool.getUserLastName(user_obj)) email = auth_tool.getUserEmail(user_obj) return (full_name, email) # The user is not in Naaya's acl_users, so let's look deeper parent_acl_users = site.restrictedTraverse('/').acl_users if parent_acl_users.meta_type == 'LDAPUserFolder': # TODO: what if parent_acl_users is not an LDAPUserFolder? # Note: EIONET LDAP data is encoded with latin-1 ldap_user_data = parent_acl_users.getUserById(self.user_id) if ldap_user_data: full_name = ldap_user_data.cn email = ldap_user_data.mail return (force_to_unicode(full_name), email) # Didn't find the user anywhere; return a placeholder notif_logger.warn('Could not find email for user %r (context: %r)', self.user_id, obj) return (u'[not found]', None)
def get_external_user_info(self, source, user, user_roles=None): user_id = user.get('uid', user.get('id')) # user_roles are precalculated for the member search (perfomance) if user_roles is None: user_roles = self.get_external_user_roles(source, user_id) return { 'userid': user_id, 'firstname': force_to_unicode(user['first_name']), 'lastname': force_to_unicode(user['last_name']), 'name': force_to_unicode(user['full_name']), 'email': user['email'], 'access_level': self.get_user_access_level(user_roles), 'organisation': force_to_unicode(user.get('organisation', 'N/A')), 'postal_address': force_to_unicode(user.get('postal_address', 'N/A')), }
def get_external_user_info(self, source, user, user_roles=None): user_id = user.get('uid', user.get('id')) # user_roles are precalculated for the member search (perfomance) if user_roles is None: user_roles = self.get_external_user_roles(source, user_id) return { 'userid': user_id, 'firstname': force_to_unicode(user['first_name']), 'lastname': force_to_unicode(user['last_name']), 'name': force_to_unicode(user['full_name']), 'email': user['email'], 'access_level': self.get_user_access_level(user_roles), 'organisation': force_to_unicode( user.get('organisation', 'N/A')), 'postal_address': force_to_unicode( user.get('postal_address', 'N/A')), }
def saveProperties(self, REQUEST=None, **kwargs): """ """ if not self.checkPermissionEditObject(): raise EXCEPTION_NOTAUTHORIZED, EXCEPTION_NOTAUTHORIZED_MSG if self.hasVersion(): obj = self.version if self.checkout_user != self.REQUEST.AUTHENTICATED_USER.getUserName(): raise EXCEPTION_NOTAUTHORIZED, EXCEPTION_NOTAUTHORIZED_MSG else: obj = self if REQUEST is not None: schema_raw_data = dict(REQUEST.form) else: schema_raw_data = kwargs _lang = schema_raw_data.pop('_lang', schema_raw_data.pop('lang', None)) _releasedate = self.process_releasedate(schema_raw_data.pop('releasedate', ''), obj.releasedate) _subtitle = schema_raw_data.pop('subtitle', '') _subtitle_file = schema_raw_data.pop('subtitle_file', None) _startup_image = schema_raw_data.pop('startup_image', '') _delete_startup_image = schema_raw_data.pop('delete_startup_image', '') _source = schema_raw_data.pop('source', None) _file = schema_raw_data.pop('file', '') form_errors = self.process_submitted_form(schema_raw_data, _lang, _override_releasedate=_releasedate) # TODO: check if video file is good video file if form_errors: if REQUEST is not None: self._prepare_error_response(REQUEST, form_errors, schema_raw_data) REQUEST.RESPONSE.redirect('%s/edit_html?lang=%s' % (self.absolute_url(), _lang)) return else: raise ValueError(form_errors.popitem()[1]) # pick a random error if _subtitle_file: _subtitle = force_to_unicode(_subtitle_file.read()) self._setLocalPropValue('subtitle', _lang, _subtitle) if _delete_startup_image: self.startup_image = None if _startup_image: self.startup_image = make_blobfile(_startup_image) if _source: self.saveUpload(file=_file, lang=_lang) self._p_changed = 1 self.recatalogNyObject(self) #log date contributor = self.REQUEST.AUTHENTICATED_USER.getUserName() auth_tool = self.getAuthenticationTool() auth_tool.changeLastPost(contributor) notify(NyContentObjectEditEvent(self, contributor)) if REQUEST: self.setSessionInfoTrans(MESSAGE_SAVEDCHANGES, date=self.utGetTodayDate()) REQUEST.RESPONSE.redirect('%s/edit_html?lang=%s' % (self.absolute_url(), _lang))
def getFailPercentage(self, link): """Returns the link fail percentage based on the last 5 logs""" logs = self.getLogEntries() logs.sort(lambda x, y: cmp(y.bobobase_modification_time(), x.bobobase_modification_time())) logs = logs[:5] failed = 0 for log in logs: for entry in log.url_list: for url in entry[4]: try: if force_to_unicode(url[0]) == force_to_unicode(link): failed += 1 continue except UnicodeDecodeError: continue rate = int(((failed * 1.0) / len(logs)) * 100) if rate > 100: return 100 return rate
def create_message(text, addr_to, addr_from, subject, addr_cc=[]): if isinstance(addr_to, basestring): addr_to = (addr_to,) addr_to = ", ".join(addr_to) if isinstance(addr_cc, basestring): addr_cc = (addr_cc,) addr_cc = ", ".join(addr_cc) subject = force_to_unicode(subject) text = force_to_unicode(text) message = create_plain_message(text.encode("utf-8")) hack_to_use_quopri(message) message["To"] = safe_header(addr_to) if addr_cc: message["Cc"] = safe_header(addr_cc) message["From"] = safe_header(addr_from) message["Subject"] = safe_header(subject) message["Date"] = email_utils.formatdate() return message
def create_message(text, addr_to, addr_from, subject, addr_cc=[]): if isinstance(addr_to, basestring): addr_to = (addr_to, ) addr_to = ', '.join(addr_to) if isinstance(addr_cc, basestring): addr_cc = (addr_cc, ) addr_cc = ', '.join(addr_cc) subject = force_to_unicode(subject) text = force_to_unicode(text) message = create_plain_message(text.encode('utf-8')) hack_to_use_quopri(message) message['To'] = safe_header(addr_to) if addr_cc: message['Cc'] = safe_header(addr_cc) message['From'] = safe_header(addr_from) message['Subject'] = safe_header(subject) message['Date'] = email_utils.formatdate() return message
def set_translations(self, node, ob, languages): lang_names = self.lang_names(ob) name_node = node.xpath('./name')[0] name_translations = self.get_translations(name_node) for lang in languages: lang_name = lang_names[lang] translation = name_translations.get(lang, u'') translation = force_to_unicode(translation) self.set_translation(ob, translation, lang_name, lang_name, 'set_translations_list') definition_node = node.xpath('./definition')[0] definition_translations = self.get_translations(definition_node) for lang in languages: lang_name = lang_names[lang] def_lang = ob.definition_lang(lang_name) translation = definition_translations.get(lang, u'') translation = force_to_unicode(translation) self.set_translation(ob, translation, lang_name, def_lang, 'set_def_trans_list')
def get_choice_mapping(survey, widget_name): cache_name = '_v_aoa_choice_map_' + widget_name if hasattr(survey, cache_name): return getattr(survey, cache_name) mapping = {} widget = survey[widget_name] en_values = widget.getLocalProperty('choices', 'en') for idx, label in list(enumerate(en_values)): mapping[idx] = force_to_unicode(label) setattr(survey, cache_name, mapping) return mapping
def convert_values_to_unicode(self, element, languages): title = getattr(element, 'title', u'') if not isinstance(title, unicode): self.log.debug('%s title: %s', element.absolute_url(), title) element.title = force_to_unicode(title) for language in languages: value = getattr(element, language, u'') if isinstance(value, unicode): continue self.log.debug('%s %s: %s', element.absolute_url(), language, value) setattr(element, language, force_to_unicode(value)) for language in languages: def_attr = 'def_' + language value = getattr(element, def_attr, u'') if isinstance(value, unicode): continue self.log.debug('%s %s: %s', element.absolute_url(), def_attr, value) setattr(element, def_attr, force_to_unicode(value))
def get_all_portlets(self): output = [] names = set() for portlet_id in self.getPortletsIds(): output.append(self.getPortletById(portlet_id)) names.add(portlet_id) site = self.getSite() for portlet_id, portlet in component.getAdapters((site,), INyPortlet): if portlet_id not in names: output.append(LegacyPortletWrapper(portlet, portlet_id)) names.add(portlet_id) output.sort(key=lambda portlet: force_to_unicode(portlet.title_or_id().lower())) return output
def get_all_portlets(self): output = [] names = set() for portlet_id in self.getPortletsIds(): output.append(self.getPortletById(portlet_id)) names.add(portlet_id) site = self.getSite() for portlet_id, portlet in component.getAdapters((site, ), INyPortlet): if portlet_id not in names: output.append(LegacyPortletWrapper(portlet, portlet_id)) names.add(portlet_id) output.sort(key=lambda portlet: force_to_unicode(portlet.title_or_id(). lower())) return output
def gettext(self, msgid, lang=None, default=None): """Returns the corresponding translation of msgid in Catalog. """ msgstr = None if not isinstance(msgid, basestring): raise TypeError('Only strings can be translated.') # saving everything unicode, utf-8 elif isinstance(msgid, str): msgstr = msgid msgid = force_to_unicode(msgid) if not lang: raise ValueError("No language provided for gettext") msgid = msgid.strip() # empty message is translated as empty message, regardless of lang if not msgid: return msgid # default `default translation` is the msgid itself if default is None: default = msgid if lang not in self.get_languages(): # we don't have that lang, thus we can't translate and won't add msg return default # Add it if it's not in the dictionary if not self._message_exists(msgid): if msgstr is not None: import logging logger = logging.getLogger(__name__) logger.warn('Got str "%s" in gettext, expecting unicode' % msgstr) self._messages[msgid] = PersistentMapping() update_transaction_note() if not self._messages[msgid].has_key(self._default_language): self._messages[msgid][self._default_language] = default # translation may be blank (supposition), then-> default (usually msgid) in_catalog = self._messages[msgid].get(lang, '') return in_catalog or default
def exorcize_local_properties(obj): """ remove any data set by LocalPropertyManager, recover plain (non-localized) string values, and set them as simple properties. Returns `None` if nothing was touched, or a list of extracted property names (which may be empty if we only removed empty LocalPropertyManager data structures). """ obj.getId() # make sure it's loaded from zodb changed = False names = [] default_lang = obj.__dict__.get('_default_lang', 'en') if '_local_properties' in obj.__dict__: for name, localdata in obj.__dict__['_local_properties'].items(): if default_lang in localdata: value = localdata[default_lang][0] else: value = localdata.values()[0][0] obj.__dict__[name] = force_to_unicode(value) changed = True names.append(name) for attrname in [ '_default_language', '_languages', '_local_properties', '_local_properties_metadata' ]: if attrname in obj.__dict__: del obj.__dict__[attrname] changed = True if changed: obj._p_changed = True return names else: return None
def tmpl_version(context, version, ver_id): """ """ #Try to get the adapter for this version and set viewable viewable = False if get_view_adapter(version) is not None: viewable = True return { 'contributor': getattr(version, 'contributor', ''), 'filename': force_to_unicode(version.filename), 'content_type': version.content_type, 'pretty_size': pretty_size(version.size), 'removed': version.removed, 'url': ('%s/download/%s/%s' % (context.absolute_url(), ver_id, urllib.quote(version.filename, safe=''))), 'icon_url': (icon_for_content_type(version.content_type)['url']), 'pretty_timestamp': version.timestamp.strftime('%d %b %Y'), 'id': ver_id, 'is_current': False, 'viewable': viewable, }
def tmpl_version(context, version, ver_id, language=None): """ """ # Try to get the adapter for this version and set viewable viewable = False if get_view_adapter(version) is not None: viewable = True pretty_version_size = None url = None icon_url = None if not language: language = context.REQUEST.form.get( 'lang', context.get_selected_language() or 'en') if not version.removed: pretty_version_size = pretty_size(version.size) url = ('%s/download/%s/%s/%s' % (context.absolute_url(), language, ver_id, urllib.quote(strip_leading_underscores(version.filename), safe=''))) icon_url = (icon_for_content_type(version.content_type)['url']) return { 'contributor': getattr(version, 'contributor', ''), 'filename': force_to_unicode(version.filename), 'content_type': version.content_type, 'pretty_size': pretty_version_size, 'removed': version.removed, 'url': url, 'icon_url': icon_url, 'pretty_timestamp': version.timestamp.strftime('%d %b %Y'), 'timestamp': DateTime(version.timestamp.replace(tzinfo=None)), 'id': ver_id, 'is_current': False, 'viewable': viewable, 'ob': context, }
def exorcize_local_properties(obj): """ remove any data set by LocalPropertyManager, recover plain (non-localized) string values, and set them as simple properties. Returns `None` if nothing was touched, or a list of extracted property names (which may be empty if we only removed empty LocalPropertyManager data structures). """ obj.getId() # make sure it's loaded from zodb changed = False names = [] default_lang = obj.__dict__.get('_default_lang', 'en') if '_local_properties' in obj.__dict__: for name, localdata in obj.__dict__['_local_properties'].items(): if default_lang in localdata: value = localdata[default_lang][0] else: value = localdata.values()[0][0] obj.__dict__[name] = force_to_unicode(value) changed = True names.append(name) for attrname in ['_default_language', '_languages', '_local_properties', '_local_properties_metadata']: if attrname in obj.__dict__: del obj.__dict__[attrname] changed = True if changed: obj._p_changed = True return names else: return None
def _update(self, portal): if "title" not in portal.aq_base.__dict__: self.log.debug("no need to update") return True lang = portal.gl_get_default_language() self.log.debug("default lang is %s" % lang) self.log.debug("portal.title = %r" % portal.title) localized_title_not_exists = "title" not in portal._local_properties localized_title_empty = not portal.getLocalAttribute("title", lang) if localized_title_not_exists: self.log.debug("title localized property doesn't exist") if localized_title_empty: self.log.debug("title property empty for default lang") if localized_title_not_exists or localized_title_empty: portal.set_localpropvalue("title", lang, force_to_unicode(portal.title)) self.log.debug("updated title localized property") delattr(portal.aq_base, "title") self.log.debug("removed portal title attr") return True
def saveProperties(self, REQUEST=None, **kwargs): """ """ if not self.checkPermissionEditObject(): raise EXCEPTION_NOTAUTHORIZED, EXCEPTION_NOTAUTHORIZED_MSG if self.hasVersion(): obj = self.version if self.checkout_user != self.REQUEST.AUTHENTICATED_USER.getUserName( ): raise EXCEPTION_NOTAUTHORIZED, EXCEPTION_NOTAUTHORIZED_MSG else: obj = self if REQUEST is not None: schema_raw_data = dict(REQUEST.form) else: schema_raw_data = kwargs _lang = schema_raw_data.pop('_lang', schema_raw_data.pop('lang', None)) _releasedate = self.process_releasedate( schema_raw_data.pop('releasedate', ''), obj.releasedate) _subtitle = schema_raw_data.pop('subtitle', '') _subtitle_file = schema_raw_data.pop('subtitle_file', None) _startup_image = schema_raw_data.pop('startup_image', '') _delete_startup_image = schema_raw_data.pop('delete_startup_image', '') _source = schema_raw_data.pop('source', None) _file = schema_raw_data.pop('file', '') form_errors = self.process_submitted_form( schema_raw_data, _lang, _override_releasedate=_releasedate) # TODO: check if video file is good video file if form_errors: if REQUEST is not None: self._prepare_error_response(REQUEST, form_errors, schema_raw_data) REQUEST.RESPONSE.redirect('%s/edit_html?lang=%s' % (self.absolute_url(), _lang)) return else: raise ValueError( form_errors.popitem()[1]) # pick a random error if _subtitle_file: _subtitle = force_to_unicode(_subtitle_file.read()) self._setLocalPropValue('subtitle', _lang, _subtitle) if _delete_startup_image: self.startup_image = None if _startup_image: self.startup_image = make_blobfile(_startup_image) if _source: self.saveUpload(file=_file, lang=_lang) self._p_changed = 1 self.recatalogNyObject(self) #log date contributor = self.REQUEST.AUTHENTICATED_USER.getUserName() auth_tool = self.getAuthenticationTool() auth_tool.changeLastPost(contributor) notify(NyContentObjectEditEvent(self, contributor)) if REQUEST: self.setSessionInfoTrans(MESSAGE_SAVEDCHANGES, date=self.utGetTodayDate()) REQUEST.RESPONSE.redirect('%s/edit_html?lang=%s' % (self.absolute_url(), _lang))
def sanitize_xml_data(data): return RE_SANITIZE_XML.sub('', force_to_unicode(data)).encode( 'utf-8', 'xmlcharrefreplace').decode('utf-8')
assert file_container_path in folder_map try: file_container = folder_map[file_container_path] if overwrite: filename = slugify(file_name).rsplit('.', 1)[0] if file_container._getOb(filename, None): file_container.manage_delObjects([filename]) file_ob_id = add_file(file_container, file_name, file_data) file_ob = file_container[file_ob_id] except Exception, e: errors.append(( (u"Error while creating file ${file_path}: " "${error}"), {'file_path': file_path, 'error': force_to_unicode(str(e))})) else: p = relative_object_path(file_ob, container) created_file_paths.add(p) if errors: if REQUEST is not None: transaction.abort() self.setSessionErrorsTrans(errors) return self.index_html(REQUEST) else: return errors else: notify(ZipImportEvent(container, sorted(created_file_paths)))
def sanitize_xml_data(data): return RE_SANITIZE_XML.sub('', force_to_unicode(data)).encode('utf-8', 'xmlcharrefreplace').decode('utf-8')
folder_map[''] = container for file_path, file_data in zip_files: if '/' in file_path: file_container_path, file_name = file_path.rsplit('/', 1) else: file_container_path, file_name = '', file_path file_name = file_name.encode('utf-8') assert file_container_path in folder_map try: file_container = folder_map[file_container_path] file_ob_id = add_file(file_container, file_name, file_data) file_ob = file_container[file_ob_id] except Exception, e: errors.append((u"Error while creating file ${file_path}: ${error}", {'file_path': file_path, 'error': force_to_unicode(str(e))})) else: p = relative_object_path(file_ob, container) created_file_paths.add(p) if errors: if REQUEST is not None: transaction.abort() self.setSessionErrorsTrans(errors) return self.index_html(REQUEST) else: return errors else: notify(ZipImportEvent(container, sorted(created_file_paths)))
assert file_container_path in folder_map try: file_container = folder_map[file_container_path] if overwrite: filename = slugify(file_name).rsplit('.', 1)[0] if file_container._getOb(filename, None): file_container.manage_delObjects([filename]) file_ob_id = add_file(file_container, file_name, file_data) file_ob = file_container[file_ob_id] except Exception, e: errors.append( ((u"Error while creating file ${file_path}: " "${error}"), { 'file_path': file_path, 'error': force_to_unicode(str(e)) })) else: p = relative_object_path(file_ob, container) created_file_paths.add(p) if errors: if REQUEST is not None: transaction.abort() self.setSessionErrorsTrans(errors) return self.index_html(REQUEST) else: return errors else:
def _update(self, portal): """ Summary of update: * test for portal_i18n existance, if true, skip portal * get languages and default language * create portal_i18n, place it in portal * copy message translations * fix localized properties * delete Localizer and portal_translations """ #if Localizer is None: # self.log.error('Migration unavailable when edw-localizer' # ' not installed') # return False if isinstance(portal.getPortalI18n(), NaayaI18n): self.log.debug( "Portal already uses naaya.i18n, skipping i18n init") localizer = None else: self.log.debug( "Creating portal_i18n and copying message catalog data") localizer = portal._getOb('Localizer', None) portal_trans = portal._getOb('portal_translations') if localizer is None: self.log.error("Localizer not found") return False if portal_trans is None: self.log.error("Portal Translations not found") return False languages = [(x, localizer.get_language_name(x)) for x in localizer.get_languages()] def_lang = localizer.get_default_language() self.log.debug('Found languages: %r, default: %s', languages, def_lang) manage_addNaayaI18n(portal, languages) portal.getPortalI18n().manage_changeDefaultLang(def_lang) message_cat = portal.getPortalI18n().get_message_catalog() (msg_cnt, trans_cnt) = (0, 0) for (msgid, trans) in portal_trans._messages.items(): if isinstance(msgid, str): msgid = force_to_unicode(msgid) # one call to gettext, to add 'en' identical translation, if missing message_cat.gettext(msgid, def_lang) msg_cnt += 1 for lang in trans: found = message_cat.gettext(msgid, lang, '') if lang != 'note': trans_cnt += 1 if isinstance(trans[lang], unicode): translation = trans[lang] elif isinstance(trans[lang], str): translation = force_to_unicode(trans[lang]) else: self.log.error(("Unacceptable type '%s' found for " "translation") % type(trans[lang])) self.log.error("Migration cancelled") return False if translation != found: message_cat.edit_message(msgid, lang, translation) self.log.debug('%d iterated, a total of %d translation mappings.' % (msg_cnt, trans_cnt)) self.log.debug('Message Catalog now counts %d entries (msgid-s).' % len(message_cat._messages.keys())) # Clean up and delete localizer localizer.manage_beforeDelete(localizer, portal) portal._delObject('Localizer') portal._delObject('portal_translations') self.log.debug('Localizer and Portal translations removed') # Fix local properties: # * remove translations with None-index (instead of language code) # * add existent properties in _local_properties_metadata # * remove blank/emptystring translations # Clean up any LocalAttribute-s on instances, if attribute not # present in class and superclasses or present but is LocalAttribute # key: class, value: attrs on class that are not LocalAttribute # their overrides need to be kept lookup_cache = {} localprops_del_cnt = 0 localprops_keep_cnt = 0 total_cnt = 0 all_objects = itertools.chain([portal], ofs_walk(portal)) # this class is not used anymore: for obj in all_objects: # Part 0.0: remove unused contenttype classes on sites: if INySite.providedBy(obj): if '_contenttypes_tool__contenttype_dictionary' in obj.__dict__: del obj.__dict__[ '_contenttypes_tool__contenttype_dictionary'] obj._p_changed = 1 # Part 0.1: if broken, report it # if other localizer in NySite child, skip it if isinstance(obj, BrokenClass): self.log.error(("Object %r is broken! Unable to fix local" " properties, if any ") % obj) continue if isinstance(obj, Localizer) and obj != localizer: continue # Part 1: delete unnecessary LocalAttributes on instances if obj.__dict__.get('_languages') is not None: del obj._languages if obj.__dict__.get('_default_language') is not None: del obj._default_language for (key, value) in obj.__dict__.items(): if isinstance(value, LocalAttribute): if not requires_localproperty(obj, key): self.log.debug("Deleting LocalAttribute: %r.%s", obj, key) delattr(obj, key) localprops_del_cnt += 1 else: self.log.debug("Keeping LocalAttribute: %r.%s", obj, key) setattr(obj, key, NewLocalAttribute(key)) localprops_keep_cnt += 1 # Part 2: normalize representation of local properties _local_properties = getattr(obj, '_local_properties', None) if _local_properties is not None: for (property, trans) in _local_properties.items(): if property not in obj._local_properties_metadata: obj.set_localproperty(property, 'string') delete_keys = set() for (lang, translation) in trans.items(): if not translation[0]: delete_keys.add(lang) if len(delete_keys): for key in delete_keys: del trans[key] obj._p_changed = 1 self.log.debug("%d LocalAttribute-s deleted from OFS" % localprops_del_cnt) self.log.debug("%d LocalAttribute-s kept in OFS" % localprops_keep_cnt) self.log.debug('Migration is complete!') return True
def utSortObjsListByAttr(self, p_list, p_attr, p_desc=1): """Sort a list of objects by an attribute values""" return sorted(p_list, key=lambda obj: isinstance(obj, str) and \ force_to_unicode(getattr(obj, p_attr, '')) or \ getattr(obj, p_attr, None), reverse=bool(p_desc))
created_file_paths.add) folder_map[''] = container for file_path, file_data in zip_files: if '/' in file_path: file_container_path, file_name = file_path.rsplit('/', 1) else: file_container_path, file_name = '', file_path assert file_container_path in folder_map try: file_container = folder_map[file_container_path] file_ob_id = add_file(file_container, file_name, file_data) file_ob = file_container[file_ob_id] except Exception, e: errors.append((u"Error while creating file ${file_path}: ${error}", {'file_path': file_path, 'error': force_to_unicode(str(e))})) else: p = relative_object_path(file_ob, container) created_file_paths.add(p) if errors: if REQUEST is not None: transaction.abort() self.setSessionErrorsTrans(errors) return self.index_html(REQUEST) else: return errors else: notify(ZipImportEvent(container, sorted(created_file_paths)))
def _update(self, portal): """ Summary of update: * test for portal_i18n existance, if true, skip portal * get languages and default language * create portal_i18n, place it in portal * copy message translations * fix localized properties * delete Localizer and portal_translations """ #if Localizer is None: # self.log.error('Migration unavailable when edw-localizer' # ' not installed') # return False if isinstance(portal.getPortalI18n(), NaayaI18n): self.log.debug("Portal already uses naaya.i18n, skipping i18n init") localizer = None else: self.log.debug("Creating portal_i18n and copying message catalog data") localizer = portal._getOb('Localizer', None) portal_trans = portal._getOb('portal_translations') if localizer is None: self.log.error("Localizer not found") return False if portal_trans is None: self.log.error("Portal Translations not found") return False languages = [ (x, localizer.get_language_name(x)) for x in localizer.get_languages() ] def_lang = localizer.get_default_language() self.log.debug('Found languages: %r, default: %s', languages, def_lang) manage_addNaayaI18n(portal, languages) portal.getPortalI18n().manage_changeDefaultLang(def_lang) message_cat = portal.getPortalI18n().get_message_catalog() (msg_cnt, trans_cnt) = (0, 0) for (msgid, trans) in portal_trans._messages.items(): if isinstance(msgid, str): msgid = force_to_unicode(msgid) # one call to gettext, to add 'en' identical translation, if missing message_cat.gettext(msgid, def_lang) msg_cnt += 1 for lang in trans: found = message_cat.gettext(msgid, lang, '') if lang != 'note': trans_cnt += 1 if isinstance(trans[lang], unicode): translation = trans[lang] elif isinstance(trans[lang], str): translation = force_to_unicode(trans[lang]) else: self.log.error(("Unacceptable type '%s' found for " "translation") % type(trans[lang])) self.log.error("Migration cancelled") return False if translation != found: message_cat.edit_message(msgid, lang, translation) self.log.debug('%d iterated, a total of %d translation mappings.' % (msg_cnt, trans_cnt)) self.log.debug('Message Catalog now counts %d entries (msgid-s).' % len(message_cat._messages.keys())) # Clean up and delete localizer localizer.manage_beforeDelete(localizer, portal) portal._delObject('Localizer') portal._delObject('portal_translations') self.log.debug('Localizer and Portal translations removed') # Fix local properties: # * remove translations with None-index (instead of language code) # * add existent properties in _local_properties_metadata # * remove blank/emptystring translations # Clean up any LocalAttribute-s on instances, if attribute not # present in class and superclasses or present but is LocalAttribute # key: class, value: attrs on class that are not LocalAttribute # their overrides need to be kept lookup_cache = {} localprops_del_cnt = 0 localprops_keep_cnt = 0 total_cnt = 0 all_objects = itertools.chain([portal], ofs_walk(portal)) # this class is not used anymore: for obj in all_objects: # Part 0.0: remove unused contenttype classes on sites: if INySite.providedBy(obj): if '_contenttypes_tool__contenttype_dictionary' in obj.__dict__: del obj.__dict__['_contenttypes_tool__contenttype_dictionary'] obj._p_changed = 1 # Part 0.1: if broken, report it # if other localizer in NySite child, skip it if isinstance(obj, BrokenClass): self.log.error(("Object %r is broken! Unable to fix local" " properties, if any ") % obj) continue if isinstance(obj, Localizer) and obj != localizer: continue # Part 1: delete unnecessary LocalAttributes on instances if obj.__dict__.get('_languages') is not None: del obj._languages if obj.__dict__.get('_default_language') is not None: del obj._default_language for (key, value) in obj.__dict__.items(): if isinstance(value, LocalAttribute): if not requires_localproperty(obj, key): self.log.debug("Deleting LocalAttribute: %r.%s", obj, key) delattr(obj, key) localprops_del_cnt += 1 else: self.log.debug("Keeping LocalAttribute: %r.%s", obj, key) setattr(obj, key, NewLocalAttribute(key)) localprops_keep_cnt += 1 # Part 2: normalize representation of local properties _local_properties = getattr(obj, '_local_properties', None) if _local_properties is not None: for (property, trans) in _local_properties.items(): if property not in obj._local_properties_metadata: obj.set_localproperty(property, 'string') delete_keys = set() for (lang, translation) in trans.items(): if not translation[0]: delete_keys.add(lang) if len(delete_keys): for key in delete_keys: del trans[key] obj._p_changed = 1 self.log.debug("%d LocalAttribute-s deleted from OFS" % localprops_del_cnt) self.log.debug("%d LocalAttribute-s kept in OFS" % localprops_keep_cnt) self.log.debug('Migration is complete!') return True