Beispiel #1
0
 def _process_css(self, css, event):
     stylesheet = css._localFile
     path = get_archived_file(stylesheet, self.archive_dirs)[1]
     if path is None:
         self.print_error(
             cformat('%{red!}CSS file not found on disk; skipping it'),
             event_id=event.id)
         return
     with open(path, 'rb') as f:
         stylesheet_content = convert_to_unicode(f.read())
     event.stylesheet_metadata = {
         'size':
         len(stylesheet_content),
         'hash':
         crc32(stylesheet_content),
         'filename':
         secure_filename(convert_to_unicode(stylesheet.fileName),
                         'stylesheet.css'),
         'content_type':
         'text/css'
     }
     event.stylesheet = stylesheet_content
     if not self.quiet:
         self.print_success(cformat('- %{cyan}[CSS] {}').format(
             stylesheet.fileName),
                            event_id=event.id)
Beispiel #2
0
    def _process_logo(self, logo, event):
        path = get_archived_file(logo, self.archive_dirs)[1]
        if path is None:
            self.print_error(cformat('%{red!}Logo not found on disk; skipping it'), event_id=event.id)
            return

        try:
            logo_image = Image.open(path)
        except IOError as e:
            self.print_warning("Cannot open {}: {}".format(path, e), event_id=event.id)
            return

        if logo_image.mode == 'CMYK':
            self.print_warning("Logo is a CMYK {}; converting to RGB".format(logo_image.format),
                               event_id=event.id)
            # this may result in wrong colors, but there's not much we can do...
            logo_image = logo_image.convert('RGB')

        logo_bytes = BytesIO()
        logo_image.save(logo_bytes, 'PNG')
        logo_bytes.seek(0)
        logo_content = logo_bytes.read()
        logo_filename = secure_filename(convert_to_unicode(logo.fileName), 'logo')
        logo_filename = os.path.splitext(logo_filename)[0] + '.png'
        event.logo_metadata = {
            'size': len(logo_content),
            'hash': crc32(logo_content),
            'filename': logo_filename,
            'content_type': 'image/png'
        }
        event.logo = logo_content
        if not self.quiet:
            self.print_success(cformat('- %{cyan}[Logo] {}').format(logo.fileName), event_id=event.id)
Beispiel #3
0
 def _process_POST(self):
     f = request.files[self.IMAGE_TYPE]
     try:
         img = Image.open(f)
     except IOError:
         flash(_('You cannot upload this file as an icon/logo.'), 'error')
         return jsonify_data(content=None)
     if img.format.lower() not in {'jpeg', 'png', 'gif'}:
         flash(_('The file has an invalid format ({format})').format(format=img.format), 'error')
         return jsonify_data(content=None)
     if img.mode == 'CMYK':
         flash(_('The image you uploaded is using the CMYK colorspace and has been converted to RGB.  '
                 'Please check if the colors are correct and convert it manually if necessary.'), 'warning')
         img = img.convert('RGB')
     img = self._resize(img)
     image_bytes = BytesIO()
     img.save(image_bytes, 'PNG')
     image_bytes.seek(0)
     content = image_bytes.read()
     metadata = {
         'hash': crc32(content),
         'size': len(content),
         'filename': os.path.splitext(secure_filename(f.filename, self.IMAGE_TYPE))[0] + '.png',
         'content_type': 'image/png'
     }
     self._set_image(content, metadata)
     flash(self.SAVED_FLASH_MSG, 'success')
     logger.info("New {} '%s' uploaded by %s (%s)".format(self.IMAGE_TYPE), f.filename, session.user, self.category)
     return jsonify_data(content=get_image_data(self.IMAGE_TYPE, self.category))
Beispiel #4
0
def build_rooms_spritesheet():
    image_width, image_height = ROOM_PHOTO_DIMENSIONS
    rooms = Room.query.filter(Room.photo).all()
    room_count = len(rooms)
    sprite_width = (image_width * (room_count + 1))  # +1 for the placeholder
    sprite_height = image_height
    sprite = Image.new(mode='RGB', size=(sprite_width, sprite_height), color=(0, 0, 0))
    # Placeholder image at position 0
    no_photo_path = 'web/static/images/rooms/large_photos/NoPhoto.jpg'
    no_photo_image = Image.open(os.path.join(current_app.root_path, no_photo_path))
    image = no_photo_image.resize(ROOM_PHOTO_DIMENSIONS, Image.ANTIALIAS)
    sprite.paste(image, (0, 0))
    mapping = {}
    for count, room in enumerate(rooms, start=1):
        location = image_width * count
        image = Image.open(BytesIO(room.photo.data)).resize(ROOM_PHOTO_DIMENSIONS, Image.ANTIALIAS)
        sprite.paste(image, (location, 0))
        mapping[room.id] = count

    output = BytesIO()
    sprite.save(output, 'JPEG')
    value = output.getvalue()
    _cache.set('rooms-sprite', value)
    _cache.set('rooms-sprite-mapping', mapping)
    _cache.set('rooms-sprite-token', crc32(value))
Beispiel #5
0
 def build_storage_path(
     self,
     obj,
     _new_path_re=re.compile(
         r'^(event/\d+/registrations/\d+/\d+/\d+-)(\d+)(-.*)$')):
     if isinstance(obj, File):
         # ``File``` was added in 2.3 and thus always has the correct paths
         # we cannot re-generate the storage path for it since it uses
         # a __context attribute which is only present during the initial
         # `save()` call and not stored anywhere.
         return obj.storage_file_id, obj.filename
     old_filename = obj.filename
     new_filename = secure_filename(obj.filename, None)
     assert new_filename
     obj.filename = new_filename
     new_storage_path = obj._build_storage_path()[1]
     obj.filename = old_filename
     assert new_storage_path
     if not isinstance(obj, RegistrationData):
         return new_storage_path, new_filename
     match = _new_path_re.match(obj.storage_file_id)
     if match:
         # already in the current format
         assert obj.storage_file_id == new_storage_path.replace(
             '-0-', '-{}-'.format(match.group(2)))
         return obj.storage_file_id, new_filename
     else:
         match = _new_path_re.match(new_storage_path)
         return '{}{}{}'.format(match.group(1), crc32(obj.storage_file_id),
                                match.group(3)), new_filename
Beispiel #6
0
def build_rooms_spritesheet():
    image_width, image_height = ROOM_PHOTO_DIMENSIONS
    rooms = Room.query.filter(Room.photo).all()
    room_count = len(rooms)
    sprite_width = (image_width * (room_count + 1))  # +1 for the placeholder
    sprite_height = image_height
    sprite = Image.new(mode='RGB',
                       size=(sprite_width, sprite_height),
                       color=(0, 0, 0))
    # Placeholder image at position 0
    no_photo_path = 'web/static/images/rooms/large_photos/NoPhoto.jpg'
    no_photo_image = Image.open(
        os.path.join(current_app.root_path, no_photo_path))
    image = no_photo_image.resize(ROOM_PHOTO_DIMENSIONS, Image.ANTIALIAS)
    sprite.paste(image, (0, 0))
    mapping = {}
    for count, room in enumerate(rooms, start=1):
        location = image_width * count
        image = Image.open(BytesIO(room.photo.data)).resize(
            ROOM_PHOTO_DIMENSIONS, Image.ANTIALIAS)
        sprite.paste(image, (location, 0))
        mapping[room.id] = count

    output = BytesIO()
    sprite.save(output, 'JPEG')
    value = output.getvalue()
    _cache.set('rooms-sprite', value)
    _cache.set('rooms-sprite-mapping', mapping)
    _cache.set('rooms-sprite-token', crc32(value))
Beispiel #7
0
 def _process_POST(self):
     f = request.files[self.IMAGE_TYPE]
     try:
         img = Image.open(f)
     except IOError:
         flash(_('You cannot upload this file as an icon/logo.'), 'error')
         return jsonify_data(content=None)
     if img.format.lower() not in {'jpeg', 'png', 'gif'}:
         flash(_('The file has an invalid format ({format})').format(format=img.format), 'error')
         return jsonify_data(content=None)
     if img.mode == 'CMYK':
         flash(_('The image you uploaded is using the CMYK colorspace and has been converted to RGB.  '
                 'Please check if the colors are correct and convert it manually if necessary.'), 'warning')
         img = img.convert('RGB')
     img = self._resize(img)
     image_bytes = BytesIO()
     img.save(image_bytes, 'PNG')
     image_bytes.seek(0)
     content = image_bytes.read()
     metadata = {
         'hash': crc32(content),
         'size': len(content),
         'filename': os.path.splitext(secure_filename(f.filename, self.IMAGE_TYPE))[0] + '.png',
         'content_type': 'image/png'
     }
     self._set_image(content, metadata)
     flash(self.SAVED_FLASH_MSG, 'success')
     logger.info("New {} '%s' uploaded by %s (%s)".format(self.IMAGE_TYPE), f.filename, session.user, self.category)
     return jsonify_data(content=get_image_data(self.IMAGE_TYPE, self.category))
Beispiel #8
0
 def _process(self):
     f = request.files['logo']
     try:
         img = Image.open(f)
     except IOError:
         flash(_('You cannot upload this file as a logo.'), 'error')
         return jsonify_data(content=None)
     if img.format.lower() not in {'jpeg', 'png', 'gif'}:
         flash(
             _('The file has an invalid format ({format})').format(
                 format=img.format), 'error')
         return jsonify_data(content=None)
     if img.mode == 'CMYK':
         flash(
             _('The logo you uploaded is using the CMYK colorspace and has been converted to RGB. Please check if '
               'the colors are correct and convert it manually if necessary.'
               ), 'warning')
         img = img.convert('RGB')
     image_bytes = BytesIO()
     img.save(image_bytes, 'PNG')
     image_bytes.seek(0)
     content = image_bytes.read()
     self.event_new.logo = content
     self.event_new.logo_metadata = {
         'hash': crc32(content),
         'size': len(content),
         'filename':
         os.path.splitext(secure_filename(f.filename, 'logo'))[0] + '.png',
         'content_type': 'image/png'
     }
     flash(_('New logo saved'), 'success')
     logger.info("New logo '%s' uploaded by %s (%s)", f.filename,
                 session.user, self.event_new)
     return jsonify_data(content=get_logo_data(self.event_new))
Beispiel #9
0
 def _process(self):
     f = request.files['logo']
     try:
         img = Image.open(f)
     except IOError:
         flash(_('You cannot upload this file as a logo.'), 'error')
         return jsonify_data(content=None)
     if img.format.lower() not in {'jpeg', 'png', 'gif'}:
         flash(_('The file has an invalid format ({format})').format(format=img.format), 'error')
         return jsonify_data(content=None)
     if img.mode == 'CMYK':
         flash(_('The logo you uploaded is using the CMYK colorspace and has been converted to RGB. Please check if '
                 'the colors are correct and convert it manually if necessary.'), 'warning')
         img = img.convert('RGB')
     image_bytes = BytesIO()
     img.save(image_bytes, 'PNG')
     image_bytes.seek(0)
     content = image_bytes.read()
     self.event.logo = content
     self.event.logo_metadata = {
         'hash': crc32(content),
         'size': len(content),
         'filename': os.path.splitext(secure_filename(f.filename, 'logo'))[0] + '.png',
         'content_type': 'image/png'
     }
     flash(_('New logo saved'), 'success')
     logger.info("New logo '%s' uploaded by %s (%s)", f.filename, session.user, self.event)
     return jsonify_data(content=get_logo_data(self.event))
Beispiel #10
0
 def _process(self):
     f = request.files["file"]
     try:
         img = Image.open(f)
     except IOError:
         flash(_("You cannot upload this file as a logo."), "error")
         return jsonify_data(content=None)
     if img.format.lower() not in {"jpeg", "png", "gif"}:
         flash(_("The file has an invalid format ({format})").format(format=img.format), "error")
         return jsonify_data(content=None)
     if img.mode == "CMYK":
         flash(
             _(
                 "The logo you uploaded is using the CMYK colorspace and has been converted to RGB. Please check if "
                 "the colors are correct and convert it manually if necessary."
             ),
             "warning",
         )
         img = img.convert("RGB")
     image_bytes = BytesIO()
     img.save(image_bytes, "PNG")
     image_bytes.seek(0)
     content = image_bytes.read()
     self.event.logo = content
     self.event.logo_metadata = {
         "hash": crc32(content),
         "size": len(content),
         "filename": os.path.splitext(secure_filename(f.filename, "logo"))[0] + ".png",
         "content_type": "image/png",
     }
     flash(_("New logo saved"), "success")
     logger.info("New logo '%s' uploaded by %s (%s)", f.filename, session.user, self.event)
     return jsonify_data(content=_logo_data(self.event))
Beispiel #11
0
 def _process(self):
     f = request.files['picture']
     try:
         pic = Image.open(f)
     except IOError:
         raise UserValueError(
             _('You cannot upload this file as profile picture.'))
     if pic.format.lower() not in {'jpeg', 'png', 'gif'}:
         raise UserValueError(
             _('The file has an invalid format ({format}).').format(
                 format=pic.format))
     if pic.mode not in {'RGB', 'RGBA'}:
         pic = pic.convert('RGB')
     image_bytes = BytesIO()
     pic = square(pic)
     if pic.height > 256:
         pic = pic.resize((256, 256), resample=Image.BICUBIC)
     pic.save(image_bytes, 'PNG')
     image_bytes.seek(0)
     content = image_bytes.read()
     self.user.picture = content
     self.user.picture_metadata = {
         'hash': crc32(content),
         'size': len(content),
         'filename':
         os.path.splitext(secure_filename(f.filename, 'user'))[0] + '.png',
         'content_type': 'image/png'
     }
     flash(_('Profile picture uploaded'), 'success')
     logger.info('Profile picture of user %s uploaded by %s', self.user,
                 session.user)
     return jsonify_data(content=get_picture_data(self.user))
Beispiel #12
0
    def _process_logo(self, logo, event):
        path = get_archived_file(logo, self.archive_dirs)[1]
        if path is None:
            self.print_error(cformat('%{red!}Logo not found on disk; skipping it'), event_id=event.id)
            return

        try:
            logo_image = Image.open(path)
        except IOError as e:
            self.print_warning("Cannot open {}: {}".format(path, e), event_id=event.id)
            return

        if logo_image.mode == 'CMYK':
            self.print_warning("Logo is a CMYK {}; converting to RGB".format(logo_image.format),
                               event_id=event.id)
            # this may result in wrong colors, but there's not much we can do...
            logo_image = logo_image.convert('RGB')

        logo_bytes = BytesIO()
        logo_image.save(logo_bytes, 'PNG')
        logo_bytes.seek(0)
        logo_content = logo_bytes.read()
        logo_filename = secure_filename(convert_to_unicode(logo.fileName), 'logo')
        logo_filename = os.path.splitext(logo_filename)[0] + '.png'
        event.logo_metadata = {
            'size': len(logo_content),
            'hash': crc32(logo_content),
            'filename': logo_filename,
            'content_type': 'image/png'
        }
        event.logo = logo_content
        if not self.quiet:
            self.print_success(cformat('- %{cyan}[Logo] {}').format(logo.fileName), event_id=event.id)
Beispiel #13
0
def get_color_for_user_id(user_id: t.Union[int, str]):
    """Calculate a unique color for a user based on their id.

    :param user_id: the user ID (int), or otherwise a string (external search results)
    """
    if isinstance(user_id, int):
        return user_colors[user_id % len(user_colors)]
    else:
        return user_colors[crc32(user_id) % len(user_colors)]
Beispiel #14
0
 def _getBody(self, params):
     api_key = rb_settings.get('google_maps_api_key')
     cache_key = str(sorted(dict(request.args, lang=session.lang).items())) + str(crc32(api_key))
     html = self.cache.get(cache_key)
     if html is None:
         params.update(self._get_widget_params())
         params['api_key'] = api_key
         html = WTemplated('RoomBookingMapOfRoomsWidget').getHTML(params)
         self.cache.set(cache_key, html, 3600)
     return html
Beispiel #15
0
def menu_entries_for_event(event):
    from indico.core.plugins import plugin_engine

    custom_menu_enabled = layout_settings.get(event, 'use_custom_menu')
    entries = MenuEntry.get_for_event(event) if custom_menu_enabled else []
    signal_entries = get_menu_entries_from_signal()

    cache_key = unicode(event.id)
    plugin_hash = crc32(','.join(sorted(plugin_engine.get_active_plugins())))
    cache_version = '{}:{}'.format(MaKaC.__version__, plugin_hash)
    processed = entries and _cache.get(cache_key) == cache_version

    if not processed:
        # menu entries from signal
        pos_gen = count(start=(entries[-1].position + 1) if entries else 0)
        entry_names = {entry.name for entry in entries}

        # Keeping only new entries from the signal
        new_entry_names = signal_entries.viewkeys() - entry_names

        # Mapping children data to their parent
        children = defaultdict(list)
        for name, data in signal_entries.iteritems():
            if name in new_entry_names and data.parent is not None:
                children[data.parent].append(data)

        # Building the entries
        new_entries = [_build_menu_entry(event, custom_menu_enabled, data, next(pos_gen),
                                         children=children.get(data.name))
                       for (name, data) in sorted(signal_entries.iteritems(),
                                                  key=lambda (name, data): _menu_entry_key(data))
                       if name in new_entry_names and data.parent is None]

        if custom_menu_enabled:
            with db.tmp_session() as sess:
                sess.add_all(new_entries)
                try:
                    sess.commit()
                except IntegrityError as e:
                    # If there are two parallel requests trying to insert a new menu
                    # item one of them will fail with an error due to the unique index.
                    # If the IntegrityError involves that index, we assume it's just the
                    # race condition and ignore it.
                    sess.rollback()
                    if 'ix_uq_menu_entries_event_id_name' not in unicode(e.message):
                        raise
                else:
                    _cache.set(cache_key, cache_version)
            entries = MenuEntry.get_for_event(event)
        else:
            entries = new_entries

    return entries
Beispiel #16
0
 def _process(self):
     f = request.files['css_file']
     self.event.stylesheet = to_unicode(f.read()).strip()
     self.event.stylesheet_metadata = {
         'hash': crc32(self.event.stylesheet),
         'size': len(self.event.stylesheet),
         'filename': secure_filename(f.filename, 'stylesheet.css')
     }
     db.session.flush()
     flash(_('New CSS file saved. Do not forget to enable it ("Use custom CSS") after verifying that it is correct '
             'using the preview.'), 'success')
     logger.info('CSS file for %s uploaded by %s', self.event, session.user)
     return jsonify_data(content=get_css_file_data(self.event))
Beispiel #17
0
 def _process(self):
     f = request.files['css_file']
     self.event.stylesheet = to_unicode(f.read()).strip()
     self.event.stylesheet_metadata = {
         'hash': crc32(self.event.stylesheet),
         'size': len(self.event.stylesheet),
         'filename': secure_filename(f.filename, 'stylesheet.css')
     }
     db.session.flush()
     flash(_('New CSS file saved. Do not forget to enable it ("Use custom CSS") after verifying that it is correct '
             'using the preview.'), 'success')
     logger.info('CSS file for %s uploaded by %s', self.event, session.user)
     return jsonify_data(content=get_css_file_data(self.event))
Beispiel #18
0
def set_user_avatar(user, avatar, filename, lastmod=None):
    if lastmod is None:
        lastmod = http_date(now_utc())
    elif isinstance(lastmod, datetime):
        lastmod = http_date(lastmod)
    user.picture = avatar
    user.picture_metadata = {
        'hash': crc32(avatar),
        'size': len(avatar),
        'filename': os.path.splitext(secure_filename(filename, 'avatar'))[0] + '.png',
        'content_type': 'image/png',
        'lastmod': lastmod,
    }
Beispiel #19
0
def js_vars_global():
    """
    Provides a JS file with global definitions (all users)
    Useful for server-wide config options, URLs, etc...
    """
    config = Config.getInstance()
    config_hash = crc32(repr(make_hashable(sorted(config._configVars.items()))))
    cache_file = os.path.join(config.getXMLCacheDir(), 'assets_global_{}.js'.format(config_hash))

    if not os.path.exists(cache_file):
        data = generate_global_file(config)
        with open(cache_file, 'wb') as f:
            f.write(data)

    return send_file('global.js', cache_file,
                     mimetype='application/x-javascript', no_cache=False, conditional=True)
Beispiel #20
0
 def _process_css(self, css, event):
     stylesheet = css._localFile
     path = get_archived_file(stylesheet, self.archive_dirs)[1]
     if path is None:
         self.print_error(cformat('%{red!}CSS file not found on disk; skipping it'), event_id=event.id)
         return
     with open(path, 'rb') as f:
         stylesheet_content = convert_to_unicode(f.read())
     event.stylesheet_metadata = {
         'size': len(stylesheet_content),
         'hash': crc32(stylesheet_content),
         'filename': secure_filename(convert_to_unicode(stylesheet.fileName), 'stylesheet.css'),
         'content_type': 'text/css'
     }
     event.stylesheet = stylesheet_content
     if not self.quiet:
         self.print_success(cformat('- %{cyan}[CSS] {}').format(stylesheet.fileName), event_id=event.id)
Beispiel #21
0
def i18n_locale(locale_name):
    """
    Retrieve a locale in a Jed-compatible format
    """
    config = Config.getInstance()
    root_path = os.path.join(current_app.root_path, 'translations')
    plugin_key = ','.join(sorted(plugin_engine.get_active_plugins()))
    cache_file = os.path.join(
        config.getXMLCacheDir(),
        'assets_i18n_{}_{}.js'.format(locale_name, crc32(plugin_key)))

    if not os.path.exists(cache_file):
        i18n_data = locale_data(root_path, locale_name, 'indico')
        if not i18n_data:
            # Dummy data, not having the indico domain would cause lots of failures
            i18n_data = {
                'indico': {
                    '': {
                        'domain': 'indico',
                        'lang': locale_name
                    }
                }
            }

        for pid, plugin in plugin_engine.get_active_plugins().iteritems():
            data = {}
            if plugin.translation_path:
                data = locale_data(plugin.translation_path, locale_name, pid)
            if not data:
                # Dummy entry so we can still load the domain
                data = {pid: {'': {'domain': pid, 'lang': locale_name}}}
            i18n_data.update(data)

        if not i18n_data:
            raise NotFound(
                "Translation for language '{}' not found".format(locale_name))

        with open(cache_file, 'wb') as f:
            f.write("window.TRANSLATIONS = {};".format(json.dumps(i18n_data)))

    return send_file('{}.js'.format(locale_name),
                     cache_file,
                     mimetype='application/x-javascript',
                     no_cache=False,
                     conditional=True)
Beispiel #22
0
 def build_storage_path(self, obj, _new_path_re=re.compile(r'^(event/\d+/registrations/\d+/\d+/\d+-)(\d+)(-.*)$')):
     old_filename = obj.filename
     new_filename = secure_filename(obj.filename, None)
     assert new_filename
     obj.filename = new_filename
     new_storage_path = obj._build_storage_path()[1]
     obj.filename = old_filename
     assert new_storage_path
     if not isinstance(obj, RegistrationData):
         return new_storage_path, new_filename
     match = _new_path_re.match(obj.storage_file_id)
     if match:
         # already in the current format
         assert obj.storage_file_id == new_storage_path.replace('-0-', '-{}-'.format(match.group(2)))
         return obj.storage_file_id, new_filename
     else:
         match = _new_path_re.match(new_storage_path)
         return '{}{}{}'.format(match.group(1), crc32(obj.storage_file_id), match.group(3)), new_filename
Beispiel #23
0
 def _process(self):
     f = request.files["file"]
     self.event.stylesheet = to_unicode(f.read()).strip()
     self.event.stylesheet_metadata = {
         "hash": crc32(self.event.stylesheet),
         "size": len(self.event.stylesheet),
         "filename": secure_filename(f.filename, "stylesheet.css"),
     }
     db.session.flush()
     flash(
         _(
             'New CSS file saved. Do not forget to enable it ("Use custom CSS") after verifying that it is correct '
             "using the preview."
         ),
         "success",
     )
     logger.info("CSS file for %s uploaded by %s", self.event, session.user)
     return jsonify_data(content=_css_file_data(self.event))
Beispiel #24
0
    def _process_icon(self, cat, icon):
        path = get_archived_file(icon, self.archive_dirs)[1]
        if path is None:
            self.print_error(
                cformat('%{red!}Icon not found on disk; skipping it'),
                event_id=cat.id)
            return

        try:
            icon_image = Image.open(path)
        except IOError as e:
            self.print_warning("Cannot open {}: {}".format(path, e),
                               event_id=cat.id)
            return

        if icon_image.mode == 'CMYK':
            self.print_warning("Icon is a CMYK {}; converting to RGB".format(
                icon_image.format),
                               always=False,
                               event_id=cat.id)
            # this may result in wrong colors, but there's not much we can do...
            icon_image = icon_image.convert('RGB')

        if icon_image.size != (16, 16):
            self.print_warning(
                "Icon is {}x{}; resizing to 16x16".format(*icon_image.size),
                always=False,
                event_id=cat.id)
            icon_image = icon_image.resize((16, 16), Image.ANTIALIAS)

        icon_bytes = BytesIO()
        icon_image.save(icon_bytes, 'PNG')
        icon_bytes.seek(0)
        icon_content = icon_bytes.read()
        icon_filename = secure_filename(convert_to_unicode(icon.fileName),
                                        'icon')
        icon_filename = os.path.splitext(icon_filename)[0] + '.png'
        cat.icon_metadata = {
            'size': len(icon_content),
            'hash': crc32(icon_content),
            'filename': icon_filename,
            'content_type': 'image/png'
        }
        cat.icon = icon_content
Beispiel #25
0
def update_gravatars(user=None):
    if user is not None:
        # explicitly scheduled update (after an email change)
        if user.picture_source not in (ProfilePictureSource.gravatar, ProfilePictureSource.identicon):
            return
        users = [user]
    else:
        users = User.query.filter(~User.is_deleted, User.picture_source == ProfilePictureSource.gravatar).all()
    for user in committing_iterator(users):
        gravatar, lastmod = get_gravatar_for_user(user, identicon=False, lastmod=user.picture_metadata['lastmod'])
        if gravatar is None:
            logger.debug('Gravatar for %r did not change (not modified)', user)
            continue
        if crc32(gravatar) == user.picture_metadata['hash']:
            logger.debug('Gravatar for %r did not change (same hash)', user)
            user.picture_metadata['lastmod'] = lastmod
            flag_modified(user, 'picture_metadata')
            continue
        set_user_avatar(user, gravatar, 'gravatar', lastmod)
        logger.info('Gravatar of user %s updated', user)
Beispiel #26
0
    def _migrate_resource(self, old_contrib, contribution, revision, resource,
                          created_dt, ignored_checksums):
        storage_backend, storage_path, size = self._get_local_file_info(
            resource)
        content_type = mimetypes.guess_type(
            resource.fileName)[0] or 'application/octet-stream'

        paper_file = PaperFile(filename=resource.fileName,
                               content_type=content_type,
                               size=size,
                               storage_backend=storage_backend,
                               storage_file_id=storage_path,
                               created_dt=created_dt,
                               paper_revision=revision)

        # check whether the same file has been uploaded to a subsequent revision
        try:
            with paper_file.open() as f:
                checksum = crc32(f.read())
            self.checksum_map[checksum] = paper_file
            collision = self.file_checksums.get(checksum)
            if collision:
                ignored_checksums.add(checksum)
                self.print_warning(
                    '%[yellow!]File {} (rev. {}) already in revision {}'.
                    format(resource.filename,
                           revision.id if revision else None, collision.id))
                return
            else:
                self.file_checksums[checksum] = revision
        except (RuntimeError, StorageError):
            self.print_error(
                "%[red!]File not accessible; can't CRC it [{}]".format(
                    convert_to_unicode(paper_file.filename)))

        paper_file._contribution = contribution
        db.session.add(paper_file)
        return paper_file
 def build_storage_path(
     self,
     obj,
     _new_path_re=re.compile(
         r'^(event/\d+/registrations/\d+/\d+/\d+-)(\d+)(-.*)$')):
     old_filename = obj.filename
     new_filename = secure_filename(obj.filename, None)
     assert new_filename
     obj.filename = new_filename
     new_storage_path = obj._build_storage_path()[1]
     obj.filename = old_filename
     assert new_storage_path
     if not isinstance(obj, RegistrationData):
         return new_storage_path, new_filename
     match = _new_path_re.match(obj.storage_file_id)
     if match:
         # already in the current format
         assert obj.storage_file_id == new_storage_path.replace(
             '-0-', '-{}-'.format(match.group(2)))
         return obj.storage_file_id, new_filename
     else:
         match = _new_path_re.match(new_storage_path)
         return '{}{}{}'.format(match.group(1), crc32(obj.storage_file_id),
                                match.group(3)), new_filename
Beispiel #28
0
    def _process_icon(self, cat, icon):
        path = get_archived_file(icon, self.archive_dirs)[1]
        if path is None:
            self.print_error(cformat('%{red!}Icon not found on disk; skipping it'), event_id=cat.id)
            return

        try:
            icon_image = Image.open(path)
        except IOError as e:
            self.print_warning("Cannot open {}: {}".format(path, e), event_id=cat.id)
            return

        if icon_image.mode == 'CMYK':
            self.print_warning("Icon is a CMYK {}; converting to RGB".format(icon_image.format), always=False,
                               event_id=cat.id)
            # this may result in wrong colors, but there's not much we can do...
            icon_image = icon_image.convert('RGB')

        if icon_image.size != (16, 16):
            self.print_warning("Icon is {}x{}; resizing to 16x16".format(*icon_image.size), always=False,
                               event_id=cat.id)
            icon_image = icon_image.resize((16, 16), Image.ANTIALIAS)

        icon_bytes = BytesIO()
        icon_image.save(icon_bytes, 'PNG')
        icon_bytes.seek(0)
        icon_content = icon_bytes.read()
        icon_filename = secure_filename(convert_to_unicode(icon.fileName), 'icon')
        icon_filename = os.path.splitext(icon_filename)[0] + '.png'
        cat.icon_metadata = {
            'size': len(icon_content),
            'hash': crc32(icon_content),
            'filename': icon_filename,
            'content_type': 'image/png'
        }
        cat.icon = icon_content
Beispiel #29
0
    def _migrate_paper_files(self):
        n = 0
        # we look for paper files in increasing order, so that we can detect file reuse
        q = (LegacyPaperFile.query.filter(
            Contribution.event_new == self.event).join(Contribution).order_by(
                Contribution.id, LegacyPaperFile.revision_id))

        for contribution_id, revision in itertools.groupby(
                q, attrgetter('contribution_id')):
            for revision_id, files in itertools.groupby(
                    revision, attrgetter('revision_id')):
                ignored_checksums = set()
                checksum_map = {}
                if revision_id is None:
                    # Two types of `LegacyPaperFile`s with `revision=None`:
                    #   - files uploaded whose revision was not yet submitted
                    #   - files within the latest revision
                    last_revision = self.legacy_contrib_last_revision_map[
                        contribution_id]
                    if last_revision._isAuthorSubmitted:
                        revision = self.legacy_contrib_revision_map[(
                            contribution_id, last_revision._version)]
                    else:
                        revision = None
                else:
                    revision = self.legacy_contrib_revision_map[(
                        contribution_id, revision_id)]

                for lpf in files:
                    # check whether the same file has been uploaded to a subsequent revision
                    try:
                        with lpf.open() as f:
                            checksum = crc32(f.read())
                        checksum_map[checksum] = lpf
                        collision = self.file_checksums.get(checksum)
                        if collision:
                            ignored_checksums.add(checksum)
                            self.importer.print_warning(cformat(
                                '%{yellow!}File {} (rev. {}) already in revision {}'
                            ).format(lpf.filename,
                                     revision.id if revision else None,
                                     collision.id),
                                                        event_id=self.event.id)
                            continue
                        else:
                            self.file_checksums[checksum] = revision
                    except (RuntimeError, StorageError):
                        self.importer.print_error(cformat(
                            "%{red!}File not accessible; can't CRC it [{}]").
                                                  format(lpf.filename),
                                                  event_id=self.event.id)

                    if revision:
                        revision.files.append(_paper_file_from_legacy(lpf))
                    n += 1

                # if a revision has no files (because they've all been ignored), then keep around a copy of each
                if revision and not revision.files and ignored_checksums:
                    for checksum in ignored_checksums:
                        lpf = checksum_map[checksum]
                        revision.files.append(_paper_file_from_legacy(lpf))
                        self.importer.print_warning(cformat(
                            '%{yellow!}File {} (rev. {}) reinstated').format(
                                lpf.filename, revision.id),
                                                    event_id=self.event.id)
                        n += 1

        self.importer.print_info('{} paper files migrated'.format(n))
Beispiel #30
0
def test_crc32():
    assert crc32(u"m\xf6p") == 2575016153
    assert crc32(u"m\xf6p".encode("utf-8")) == 2575016153
    assert crc32(b"") == 0
    assert crc32(b"hello world\0\1\2\3\4") == 140159631
Beispiel #31
0
def get_color_for_username(username):
    return user_colors[crc32(username) % len(user_colors)]
Beispiel #32
0
def _get_menu_cache_data(event):
    from indico.core.plugins import plugin_engine
    cache_key = unicode(event.id)
    plugin_hash = crc32(','.join(sorted(plugin_engine.get_active_plugins())))
    cache_version = '{}:{}'.format(MaKaC.__version__, plugin_hash)
    return cache_key, cache_version
Beispiel #33
0
 def hash(self):
     return crc32(repr(make_hashable(sorted(self.data.items()))))
Beispiel #34
0
def _get_menu_cache_data(event):
    from indico.core.plugins import plugin_engine
    cache_key = unicode(event.id)
    plugin_hash = crc32(','.join(sorted(plugin_engine.get_active_plugins())))
    cache_version = '{}:{}'.format(indico.__version__, plugin_hash)
    return cache_key, cache_version
Beispiel #35
0
def get_color_for_username(username):
    return user_colors[crc32(username) % len(user_colors)]
Beispiel #36
0
def menu_entries_for_event(event):
    from indico.core.plugins import plugin_engine

    custom_menu_enabled = layout_settings.get(event, 'use_custom_menu')
    entries = MenuEntry.get_for_event(event) if custom_menu_enabled else []
    signal_entries = get_menu_entries_from_signal()

    cache_key = unicode(event.id)
    plugin_hash = crc32(','.join(sorted(plugin_engine.get_active_plugins())))
    cache_version = '{}:{}'.format(MaKaC.__version__, plugin_hash)
    processed = entries and _cache.get(cache_key) == cache_version

    if not processed:
        # menu entries from signal
        pos_gen = count(start=(entries[-1].position + 1) if entries else 0)
        entry_names = {entry.name for entry in entries}

        # Keeping only new entries from the signal
        new_entry_names = signal_entries.viewkeys() - entry_names

        # Mapping children data to their parent
        children = defaultdict(list)
        for name, data in signal_entries.iteritems():
            if name in new_entry_names and data.parent is not None:
                children[data.parent].append(data)

        # Building the entries
        new_entries = [
            _build_menu_entry(event,
                              custom_menu_enabled,
                              data,
                              next(pos_gen),
                              children=children.get(data.name))
            for (
                name,
                data) in sorted(signal_entries.iteritems(),
                                key=lambda (name, data): _menu_entry_key(data))
            if name in new_entry_names and data.parent is None
        ]

        if custom_menu_enabled:
            with db.tmp_session() as sess:
                sess.add_all(new_entries)
                try:
                    sess.commit()
                except IntegrityError as e:
                    # If there are two parallel requests trying to insert a new menu
                    # item one of them will fail with an error due to the unique index.
                    # If the IntegrityError involves that index, we assume it's just the
                    # race condition and ignore it.
                    sess.rollback()
                    if 'ix_uq_menu_entries_event_id_name' not in unicode(
                            e.message):
                        raise
                else:
                    _cache.set(cache_key, cache_version)
            entries = MenuEntry.get_for_event(event)
        else:
            entries = new_entries

    return entries
Beispiel #37
0
def test_crc32():
    assert crc32(u'm\xf6p') == 2575016153
    assert crc32(u'm\xf6p'.encode('utf-8')) == 2575016153
    assert crc32(b'') == 0
    assert crc32(b'hello world\0\1\2\3\4') == 140159631
Beispiel #38
0
def test_crc32():
    assert crc32(u'm\xf6p') == 2575016153
    assert crc32(u'm\xf6p'.encode('utf-8')) == 2575016153
    assert crc32(b'') == 0
    assert crc32(b'hello world\0\1\2\3\4') == 140159631
Beispiel #39
0
 def hash(self):
     return crc32(repr(make_hashable(sorted(self.data.items()))))
Beispiel #40
0
def i18n_locale(locale_name):
    """
    Retrieve a locale in a Jed-compatible format
    """
    config = Config.getInstance()
    root_path = os.path.join(current_app.root_path, 'translations')
    plugin_key = ','.join(sorted(plugin_engine.get_active_plugins()))
    cache_file = os.path.join(config.getXMLCacheDir(), 'assets_i18n_{}_{}.js'.format(locale_name, crc32(plugin_key)))

    if not os.path.exists(cache_file):
        i18n_data = locale_data(root_path, locale_name, 'indico')
        if not i18n_data:
            # Dummy data, not having the indico domain would cause lots of failures
            i18n_data = {'indico': {'': {'domain': 'indico',
                                         'lang': locale_name}}}

        for pid, plugin in plugin_engine.get_active_plugins().iteritems():
            data = {}
            if plugin.translation_path:
                data = locale_data(plugin.translation_path, locale_name, pid)
            if not data:
                # Dummy entry so we can still load the domain
                data = {pid: {'': {'domain': pid,
                                   'lang': locale_name}}}
            i18n_data.update(data)

        if not i18n_data:
            raise NotFound("Translation for language '{}' not found".format(locale_name))

        with open(cache_file, 'wb') as f:
            f.write("window.TRANSLATIONS = {};".format(json.dumps(i18n_data)))

    return send_file('{}.js'.format(locale_name), cache_file, mimetype='application/x-javascript',
                     no_cache=False, conditional=True)
Beispiel #41
0
def _get_menu_cache_data(event):
    from indico.core.plugins import plugin_engine
    cache_key = str(event.id)
    plugin_hash = crc32(','.join(sorted(plugin_engine.get_active_plugins())))
    cache_version = f'{indico.__version__}:{plugin_hash}'
    return cache_key, cache_version