def POST(self): form = web.input() subject = form['subject'] email_body = form['body'] to = form['to'] receivers = [] if to=="admins": receivers =[u for u in User.selectBy(admin=True, disabled=False)] elif to=="supadmins": receivers=[u for u in User.selectBy(super_admin=True).distinct()] elif to == 'contrib': id_channel=form['select_channel'] c = PluginChannel.get(id_channel) receivers = [u for u in c.get_contribs()] elif to=="channel_editor_users": pc = PluginChannel.select() for elem in pc: if elem.plugin.name=="editor": l1=[u1 for u1 in elem.get_admins()] l2=[u2 for u2 in elem.get_contribs()] list_users = l1+l2 receivers=[u for u in list_users] else: for s in Screen.select(): receivers=[u for u in s.owners] try: for u in receivers: web.sendmail(web.config.smtp_sendername, u.email, subject, email_body, headers={'Content-Type': 'text/html;charset=utf-8'}) except smtplib.SMTPException: logger.error('An error occured when sending email ', exc_info=True) return web.seeother("/")
def assert_edition(attrs=None, channel_params=channel_params, bundle_params=bundle_params, status=200): if attrs is None: attrs = [ 'name', 'description', 'enabled', 'subscription_right', 'plugin' ] assert self.testApp.post('/channels', params=channel_params, status=status).body is not None pc = PluginChannel.get(self.pc1.id) for attr in attrs: if attr in channel_params: assert get_attr(pc, attr) == channel_params[attr] assert self.testApp.post('/channels', params=bundle_params, status=status).body is not None bc = ChannelBundle.get(self.bundle.id) for attr in attrs: if attr in bundle_params: assert get_attr(bc, attr) == bundle_params[attr] if channel_params is not orig_plugin_channel_params and bundle_params is not orig_bundle_params: assert_edition(channel_params=orig_plugin_channel_params, bundle_params=orig_bundle_params) # Revert
def assert_no_edition(status=200): assert self.testApp.post('/channels', params=channel_params, status=status).body is not None assert orig_plugin_channel == repr(PluginChannel.get(self.pc1.id)) assert self.testApp.post('/channels', params=bundle_params, status=status).body is not None assert orig_bundle_channel == repr( ChannelBundle.get(self.bundle.id))
def get_content(channel_id): channel = PluginChannel.get(channel_id) logger_extra = {'channel_name': channel.name, 'channel_id': channel.id} logger = get_logger('github_reader', channel) token = channel.get_config_param('token') duration = channel.get_config_param('duration') * 1000 repo_url = channel.get_config_param('repo_url') had_organization = channel.get_config_param('had_organization') number_organizations = channel.get_config_param('number_organizations') orga_url = channel.get_config_param('orga_url') disp_commits = channel.get_config_param('disp_commits') number_commits = channel.get_config_param('number_commits') max_days_commit = channel.get_config_param('max_days_commit') disp_contributors = channel.get_config_param('disp_contributors') number_contributors = channel.get_config_param('number_contributors') disp_issues = channel.get_config_param('disp_issues') number_issues = channel.get_config_param('number_issues') disp_stat = channel.get_config_param('disp_stat') disp_releases = channel.get_config_param('disp_releases') number_releases = channel.get_config_param('number_releases') if not token or not repo_url: logger.warning('Some of the required parameters are empty', extra=logger_extra) return [] git_obj = Github(token) capsule = GithubReaderCapsule() #if disp_stat: # stat = git_obj.get_stat() if disp_issues: capsule._slides.append( GithubReaderSlideIssue(repo_url, number_issues, duration, git_obj, logger, logger_extra)) if disp_commits: capsule._slides.append( GithubReaderSlideCommit(repo_url, number_commits, duration, git_obj, max_days_commit, logger, logger_extra)) if disp_releases: capsule._slides.append( GithubReaderSlideRelease(repo_url, number_releases, duration, git_obj, logger, logger_extra)) if disp_contributors: capsule._slides.append( GithubReaderSlideContributor(repo_url, number_contributors, duration, git_obj, logger, logger_extra)) if had_organization: capsule._slides.append( GithubReaderSlideOrganization(orga_url, number_organizations, duration, git_obj, logger, logger_extra)) return [capsule]
def invalidate_cache(channel_id): channel = PluginChannel.get(channel_id) file_hash = get_file_hash(channel_id, channel.get_config_param('link')) _, full_iframe_path, _, full_inlined_page_path = get_paths(file_hash) def safe_rm(path): if os.path.exists(path): os.remove(path) safe_rm(full_iframe_path) safe_rm(full_inlined_page_path)
def render_page(self, channel_id): channel = PluginChannel.get(channel_id) con = sqlhub.threadConnection select_query = Select(['mime_type', 'SUM(file_size)'], where=Asset.q.plugin_channel == channel_id, staticTables=['asset'], groupBy='mime_type') labels = [] data = [] for type, size in con.queryAll(con.sqlrepr(select_query)): labels.append(type) data.append(int(size)) palette = [(0.86, 0.37119999999999997, 0.33999999999999997), (0.86, 0.7612000000000001, 0.33999999999999997), (0.56880000000000008, 0.86, 0.33999999999999997), (0.33999999999999997, 0.86, 0.50120000000000009), (0.33999999999999997, 0.82879999999999987, 0.86), (0.33999999999999997, 0.43879999999999986, 0.86), (0.63119999999999976, 0.33999999999999997, 0.86), (0.86, 0.33999999999999997, 0.69879999999999964)] background_color = [] border_color = [] for R,G,B in palette: background_color.append('rgba(%d, %d, %d, 0.95)' % (int(R*255), int(G*255), int(B*255))) border_color.append('rgba(%d, %d, %d, 1)' % (int(R*255), int(G*255), int(B*255))) chart_data = {'labels': labels, 'datasets': [{'data': data, 'backgroundColor': background_color}]} return self.renderer.storage_channel(channel=channel, chart_data=json.dumps(chart_data))
def wrapper(*args, **kwargs): app = flask.current_app if len(flask.g.homepath)>0: # we are in a sub-app channelid = re.findall(r'\d+', flask.g.homepath)[0] else: channelid = re.findall(r'\d+', flask.request.path)[0] channel = PluginChannel.get(channelid) u = User.get(app.session['user']['id']) if 'real_user' in app.session: real_user = User.get(app.session['real_user']['id']) # if the real user has at least the same right as the "logged as" user if u.highest_permission_level not in real_user.highest_permission_level: resp.seeother('/logas/nobody') if UserPermissions.administrator in u.highest_permission_level or permission_level in channel.get_channel_permissions_of(u): kwargs['channel'] = channel return func(*args, **kwargs) else: resp.forbidden()
def wrapper(*args, **kwargs): app = web.ctx.app_stack[0] if len(web.ctx.homepath) > 0: # We are in a sub-app channelid = re.findall(r'\d+', web.ctx.homepath)[0] else: # We are in the core app channelid = re.findall(r'\d+', web.ctx.path)[0] channel = PluginChannel.get(channelid) u = User.get(app.session['user']['id']) if 'real_user' in app.session: real_user = User.get(app.session['real_user']['id']) # if the real user has at least the same right as the "logged as" user if u.highest_permission_level not in real_user.highest_permission_level: raise web.seeother('/logas/nobody') if UserPermissions.administrator in u.highest_permission_level or permission_level in channel.get_channel_permissions_of( u): kwargs['channel'] = channel return func(*args, **kwargs) else: raise web.forbidden()
def get_content(channel_id): channel = PluginChannel.get(channel_id) logger_extra = {'channel_name': channel.name, 'channel_id': channel.id} logger = get_logger('i_like_trains', channel) departure_station = channel.get_config_param('departure_station') duration = channel.get_config_param('duration')*1000 language = channel.get_config_param('language') nb_train = channel.get_config_param('nb_train') logo_1 = channel.get_config_param('logo_1') if not departure_station: logger.warning('Problem with the departure station', extra=logger_extra) return [] else: base_url = "http://api.irail.be/" head = {'user-agent': 'ICTVbooyy/0.69 (ictv.github.con; [email protected])'} payload = {'station': departure_station, 'arrdep': 'departures', 'lang': language, 'format': 'json', 'alert': 'true'} r = requests.get(base_url + 'liveboard/', params=payload, headers=head) parsed = json.loads(r.text) return [ILikeTrainsCapsule(departure_station, duration, language, nb_train, parsed, logo_1)]
def get_content(channelid, capsuleid=None) -> Iterable[PluginCapsule]: content = [] channel = PluginChannel.get(channelid) if 0 < len(channel.get_config_param('api_key') or '') < 8: raise MisconfiguredParameters( 'api_key', channel.get_config_param('api_key'), "The key must be at least 8-character long") if capsuleid is None: now = datetime.now() capsules = EditorCapsule.selectBy(channel=channelid).filter( AND(EditorCapsule.q.validity_to > now, EditorCapsule.q.validity_from < now)).orderBy("c_order") for c in capsules: content.append(c.to_plugin_capsule()) else: content = [EditorCapsule.get(capsuleid).to_plugin_capsule()] for capsule in content: for slide in capsule.get_slides(): if channel.get_config_param( 'force_duration') or slide.duration == -1: slide.duration = int( channel.get_config_param('duration') * 1000) return content
def post(self): form = self.form subject = form['subject'] email_body = form['body'] to = form['to'] receivers = [] if to == "admins": receivers = [u for u in User.selectBy(admin=True, disabled=False)] elif to == "supadmins": receivers = [u for u in User.selectBy(super_admin=True).distinct()] elif to == 'contrib': id_channel = form['select_channel'] c = PluginChannel.get(id_channel) receivers = [u for u in c.get_contribs()] elif to == "channel_editor_users": pc = PluginChannel.select() for elem in pc: if elem.plugin.name == "editor": l1 = [u1 for u1 in elem.get_admins()] l2 = [u2 for u2 in elem.get_contribs()] list_users = l1 + l2 receivers = [u for u in list_users] else: for s in Screen.select(): receivers = [u for u in s.owners] try: mail = Mail(self.app) msg = Message( recipients=[u.email for u in receivers], subject=subject, body=email_body, extra_headers={'Content-Type': 'text/html;charset=utf-8'}) mail.send(msg) except smtplib.SMTPException: logger.error('An error occured when sending email ', exc_info=True) resp.seeother("/")
def authenticate(self): """ Authenticates the request according to the API key and returns the channel. """ if len(web.ctx.homepath) > 0: # We are in a sub-app channelid = re.findall(r'\d+', web.ctx.homepath)[0] else: # We are in the core app channelid = re.findall(r'\d+', web.ctx.path)[0] try: channel = PluginChannel.get(channelid) except SQLObjectNotFound: raise web.notfound() try: if not channel.get_config_param('enable_rest_api'): raise web.forbidden() if not (channel.get_config_param('api_key') or '').strip(): raise web.forbidden() if (channel.get_config_param('api_key') or '').strip() != web.ctx.env.get( 'HTTP_X_ICTV_EDITOR_API_KEY', '').strip(): raise web.forbidden() except KeyError: raise web.forbidden() return channel
def get_content(channel_id): channel = PluginChannel.get(channel_id) logger_extra = {'channel_name': channel.name, 'channel_id': channel.id} logger = ictv.plugin_manager.plugin_manager.get_logger('embed', channel) link = channel.get_config_param('link') file_hash = get_file_hash(channel_id, link) width = channel.get_config_param('width') height = channel.get_config_param('height') refresh_rate = channel.get_config_param('refresh_rate') duration = channel.get_config_param('duration') if link is None or height is None or width is None or duration is None: logger.warning('Some of the parameters are missing', extra=logger_extra) return [] iframe_path, full_iframe_path, inlined_page, full_inlined_page_path = get_paths( file_hash) if not os.path.exists(full_iframe_path) or os.path.getmtime( full_iframe_path) + (refresh_rate * 60 * 60) < int(time.time()): logger.debug('Rebuilding cache', extra=logger_extra) # No cache exists or it has expired scripts = [] if channel.get_config_param('jquery'): scripts.append('/static/plugins/embed/js/jquery.min.js') if channel.get_config_param('jquery_ui'): scripts.append('/static/plugins/embed/js/jquery-ui.min.js') try: inline(link, full_inlined_page_path, logger, scripts) except URLError as e: raise MisconfiguredParameters( 'link', link, 'The following error was encountered: %s.' % str(e)) iframe_path = create_iframe_page('/static/' + inlined_page, width, height, file_hash) return [EmbedCapsule(iframe_path, duration * 1000)]
def get_content(channel_id): channel = PluginChannel.get(channel_id) logger_extra = {'channel_name': channel.name, 'channel_id': channel.id} logger = get_logger('img-grabber', channel) url = channel.get_config_param('url') image_selector = channel.get_config_param('image_selector') attr = channel.get_config_param('src_attr') qrcode = channel.get_config_param('qrcode') if not url or not image_selector or not attr: logger.warning('Some of the required parameters are empty', extra=logger_extra) return [] try: doc = PyQuery(url=url) except Exception as e: raise MisconfiguredParameters( 'url', url, 'The following error was encountered: %s.' % str(e)) img = doc(image_selector).eq(0).attr(attr) if not img: message = 'Could not find img with CSS selector %s and attribute %s' % ( image_selector, attr) raise MisconfiguredParameters('image_selector', image_selector, message).add_faulty_parameter( 'src_attr', attr, message) img = urljoin(url, img) duration = channel.get_config_param('duration') * 1000 text = doc(channel.get_config_param('text_selector')).eq(0).text() alternative_text = channel.get_config_param('alternative_text') color = channel.get_config_param('color') return [ ImgGrabberCapsule(img, text if text else alternative_text, duration, color, qrcode=url if qrcode else None) ]
def runTest(self): """ Tests the Channel object. """ try: PluginChannel(name='test', plugin=Plugin(name='channel_plugin', activated='no'), subscription_right='restricted') PluginChannel( name='test2', plugin=Plugin.selectBy(name='channel_plugin').getOne(), subscription_right='restricted') c = PluginChannel.selectBy(name="test").getOne() assert_not_equal(None, c) c.set(name="testNew") assert_equal(c.name, "testNew") u = User(username='******', fullname='test test', email='*****@*****.**', super_admin=True, disabled=False) up = UserPermissions.channel_contributor c.give_permission_to_user(u, up) role = Role.selectBy(user=u, channel=c).getOne(None) assert_true(role != None) c.give_permission_to_user(u, up) role = Role.selectBy(user=u, channel=c).getOne(None) assert_true(role != None) getup = c.get_channel_permissions_of(u) assert_equal(getup, up) getupnoperm = c.get_channel_permissions_of(User.get(1)) assert_equal(getupnoperm, UserPermissions.no_permission) c.remove_permission_to_user(u) role = Role.selectBy(user=u, channel=c).getOne(None) assert_true(role == None) assert_false(c.has_admin(u)) up = UserPermissions.channel_administrator c.give_permission_to_user(u, up) assert_true(c.has_admin(u)) assert_true(c.has_contrib(u)) assert_is_not_none(c.get_admins()) assert_is_not_none(c.get_contribs()) assert_in(str(u.id), c.get_users_as_json()) c.remove_permission_to_user(u) role = Role.selectBy(user=u, channel=c).getOne(None) assert_true(role == None) c.give_permission_to_user(None, up) role = Role.selectBy(user=u).getOne(None) assert_true(role == None) tru = c.has_visible_params_for(u) assert_true(tru) u3 = User(username='******', fullname='test3 test2', email='*****@*****.**', super_admin=False, disabled=False) tru = c.has_visible_params_for(u3) assert_false(tru) t = PluginChannel.delete(c.id) assert_equal(t, None) # try to delete a channel used by a screen - Seems to work... sc = Screen(name='A', building=Building(name='A')) sc.subscribe_to(u, PluginChannel.get(2)) # t2 = PluginChannel.delete(2) c4 = PluginChannel.get(2) nbSub = c4.subscriptions.count() c4.set(enabled=False) assert_equal(nbSub, c4.subscriptions.count()) c4.set(enabled=True) c4.set(subscription_right="private") assert_equal(nbSub, c4.subscriptions.count()) c4.set(subscription_right="public") # todo seems working by bypassing the webinterface c4.set(cache_validity=-10) assert_true(c4.cache_validity < 0) sc.unsubscribe_from(u, PluginChannel.get(2)) u2 = User(username='******', fullname='test2 test2', email='*****@*****.**', super_admin=False, disabled=False) l = PluginChannel.get_screens_channels_from(u2) assert_is_not_none(l) temp = PluginChannel.get_visible_channels_of(u2) assert_is_not_none(temp) User.delete(u.id) User.delete(u2.id) User.delete(u3.id) except DuplicateEntryError: assert_true(False) return
def runTest(self): """ Tests the channels deletion through the Channels page """ pc1_id = self.pc1.id bundle_id = self.bundle.id channel_params = {'action': 'delete-channel', 'id': pc1_id} bundle_params = {'action': 'delete-bundle', 'id': bundle_id} def assert_deletion(channel_params=channel_params, bundle_params=bundle_params, status=200): assert self.testApp.post('/channels', params=channel_params, status=status).body is not None assert PluginChannel.selectBy(id=pc1_id).getOne(None) is None assert self.testApp.post('/channels', params=bundle_params, status=status).body is not None assert ChannelBundle.selectBy(id=bundle_id).getOne(None) is None return (PluginChannel(plugin=self.fake_plugin, name='PC 1', subscription_right='public').id, ChannelBundle(name='Bundle', subscription_right='public').id) def assert_no_deletion(channel_params=channel_params, bundle_params=bundle_params, status=200): assert self.testApp.post('/channels', params=channel_params, status=status).body is not None assert PluginChannel.selectBy(id=pc1_id).getOne(None) is not None assert self.testApp.post('/channels', params=bundle_params, status=status).body is not None assert ChannelBundle.selectBy( id=bundle_id).getOne(None) is not None # Test basic functionality pc1_id, bundle_id = assert_deletion() channel_params['id'] = pc1_id bundle_params['id'] = bundle_id # Test insufficient permissions for channel edition for u in [ self.user_nothing, self.user_contrib, self.user_chan_admin, self.user_screen_admin, self.user_admin ]: self.ictv_app.test_user = {'email': u.email} assert_no_deletion(status=403) # Test sufficient permissions for channel edition for u in [self.user_super_admin]: self.ictv_app.test_user = {'email': u.email} pc1_id, bundle_id = assert_deletion() channel_params['id'] = pc1_id bundle_params['id'] = bundle_id # Test invalid id channel_params['id'] = bundle_params['id'] = -1 assert_no_deletion() channel_params['id'] = bundle_params['id'] = 'invalid' assert_no_deletion() channel_params['id'] = pc1_id bundle_params['id'] = bundle_id # Test subscriptions pc1_id, bundle_id = assert_deletion() channel_params['id'] = pc1_id bundle_params['id'] = bundle_id self.pc1 = PluginChannel.get(pc1_id) self.bundle = ChannelBundle.get(bundle_id) self.screen.subscribe_to(self.user_super_admin, self.pc1) assert self.testApp.post('/channels', params=channel_params, status=200).body is not None assert PluginChannel.selectBy(id=pc1_id).getOne(None) is not None self.screen.subscribe_to(self.user_super_admin, self.bundle) assert self.testApp.post('/channels', params=bundle_params, status=200).body is not None assert ChannelBundle.selectBy(id=bundle_id).getOne(None) is not None self.screen.unsubscribe_from(self.user_super_admin, self.pc1) assert self.testApp.post('/channels', params=channel_params, status=200).body is not None assert PluginChannel.selectBy(id=pc1_id).getOne(None) is None self.screen.unsubscribe_from(self.user_super_admin, self.bundle) assert self.testApp.post('/channels', params=bundle_params, status=200).body is not None assert ChannelBundle.selectBy(id=bundle_id).getOne(None) is None
def POST(self): """ Handles channel creation, editing, deletion, configuration and user permissions. """ form = web.input() current_user = User.get(self.session['user']['id']) channel = None try: if form.action.startswith('create') or form.action.startswith( 'edit'): # Prepare creation or edition of channels/bundles name = form.name.strip() description = form.description if form.description and form.description.strip( ) else None enabled = form.get('enabled') == 'on' if form.subscription_right not in [ 'public', 'restricted', 'private' ]: raise ImmediateFeedback(form.action, 'invalid_subscription_right') if len(name) < 3: raise ImmediateFeedback(form.action, 'invalid_name') if form.action.startswith('create'): if UserPermissions.administrator not in current_user.highest_permission_level: logger.warning( 'user %s tried to create a channel without being admin', current_user.log_name) raise web.forbidden() try: if form.action == 'create-channel': try: plugin_id = int(form.plugin) except ValueError: raise ImmediateFeedback(form.action, 'invalid_plugin') p = Plugin.get(plugin_id) channel = PluginChannel( name=name, plugin=p, subscription_right=form.subscription_right, description=description, enabled=enabled) if p.webapp: self.plugin_manager.add_mapping(self.app, channel) elif form.action == 'create-bundle': channel = ChannelBundle( name=name, description=description, subscription_right=form.subscription_right, enabled=enabled) else: raise web.badrequest() except SQLObjectNotFound: raise ImmediateFeedback(form.action, 'invalid_plugin') except DuplicateEntryError: raise ImmediateFeedback(form.action, 'name_already_exists') logger.info('channel ' + channel.name + ' created by ' + current_user.log_name) elif form.action.startswith('edit'): if UserPermissions.administrator not in current_user.highest_permission_level: raise web.forbidden() try: form.id = int(form.id) channel = (PluginChannel if form.action == 'edit-channel' else Channel).get(form.id) except (SQLObjectNotFound, ValueError): raise ImmediateFeedback(form.action, 'invalid_id') previous_state = { 'name': channel.name, 'description': channel.description, 'subscription_right': channel.subscription_right, 'enabled': channel.enabled } new_state = { 'name': name, 'description': description, 'subscription_right': form.subscription_right, 'enabled': enabled } state_diff = dict( set(new_state.items()) - set(previous_state.items())) if form.action == 'edit-channel': try: plugin_id = int(form.plugin) p = Plugin.get(plugin_id) add_mapping = p.webapp and channel.plugin != p previous_state['plugin'] = channel.plugin new_state['plugin'] = p except (SQLObjectNotFound, ValueError): raise ImmediateFeedback(form.action, 'invalid_plugin') elif form.action == 'edit-bundle': pass # There is nothing more to edit for a bundle than a channel else: raise web.badrequest() try: channel.set(**new_state) except DuplicateEntryError: channel.set(**previous_state) # Rollback raise ImmediateFeedback(form.action, 'name_already_exists') logger.info( '[Channel %s (%d)] ' % (channel.name, channel.id) + current_user.log_name + ' edited the channel.\n' 'Previous state: %s\n' % str({ k: v for k, v in previous_state.items() if k in state_diff }) + 'New state: %s' % str(state_diff)) if form.action == 'edit-channel' and add_mapping: self.plugin_manager.add_mapping(self.app, channel) elif form.action.startswith('delete'): if not current_user.super_admin: logger.warning( 'the user %s tried to delete a channel without having the rights to do it', current_user.log_name) raise web.forbidden() try: form.id = int(form.id) channel = Channel.get(form.id) if channel.subscriptions.count( ) > 0 and 'confirm-delete' not in form: raise ImmediateFeedback( form.action, 'channel_has_subscriptions', { 'channel': { 'name': channel.name, 'id': channel.id, 'description': channel.description, 'subscription_right': channel.subscription_right }, 'plugin_id': channel.plugin.id if form.action == 'delete-channel' else None, 'subscriptions': [(s.screen.id, s.screen.name, s.screen.building.name) for s in channel.subscriptions] }) form.name = channel.name channel_name = channel.name channel.destroySelf() logger.info('the channel %s has been deleted by user %s', channel_name, current_user.log_name) except (SQLObjectNotFound, ValueError) as e: print(e) raise ImmediateFeedback(form.action, 'invalid_id') elif form.action == 'add-users-channel': try: if 'users' not in form: raise web.badrequest() form.users = json.loads(form.users) form.id = int(form.id) channel = PluginChannel.get(form.id) if not channel.has_admin( current_user ) and UserPermissions.administrator not in current_user.highest_permission_level: raise web.forbidden() form.name = channel.name for user_id, diff in form.users.items(): user_id = int(user_id) user = User.get(user_id) if 'permission' in diff: permission_level = diff['permission'] new_permission_level = UserPermissions( permission_level) old_permission_level = channel.get_channel_permissions_of( user) if new_permission_level == UserPermissions.no_permission \ and (UserPermissions.administrator in current_user.highest_permission_level or old_permission_level == UserPermissions.channel_contributor): channel.remove_permission_to_user(user) logger.info( 'permissions of user %s concerning channel %s have been removed by user %s', user.log_name, channel.name, current_user.log_name) elif (new_permission_level == UserPermissions.channel_contributor and channel.has_admin( current_user) and old_permission_level == UserPermissions.no_permission) \ or (new_permission_level in UserPermissions.channel_administrator and UserPermissions.administrator in current_user.highest_permission_level): channel.give_permission_to_user( user, new_permission_level) logger.info( 'permissions of user %s concerning channel %s have been set to %s by user %s', user.log_name, channel.name, UserPermissions.get_permission_string( new_permission_level), current_user.log_name) if 'authorized_subscriber' in diff: authorized_subscriber = diff[ 'authorized_subscriber'] if authorized_subscriber and ( user not in channel.authorized_subscribers): channel.addUser(user) logger.info( 'the user %s has been added to channel %s as authorized subscriber by user %s', user.log_name, channel.name, current_user.log_name) elif not authorized_subscriber and ( user in channel.authorized_subscribers): channel.removeUser(user) logger.info( 'the user %s has been removed from channel %s as authorized subscriber by user %s', user.log_name, channel.name, current_user.log_name) except (SQLObjectNotFound, ValueError): raise ImmediateFeedback(form.action, 'invalid_id') except (KeyError, json.JSONDecodeError): raise ImmediateFeedback(form.action, 'invalid_users') elif form.action == 'configure': try: form.id = int(form.id) channel = PluginChannel.get(form.id) pattern = re.compile(r'list\[.*\]') if UserPermissions.administrator in current_user.highest_permission_level or UserPermissions.channel_administrator in channel.get_channel_permissions_of( current_user) or channel.has_contrib(current_user): for k, v in [(k, v) for k, v in channel.plugin.channels_params.items() if channel.get_access_rights_for( k, current_user)[1]]: # Iterates on the parameters the current user can write to if v['type'] == 'bool': value = k in form and form[k] == 'on' elif v['type'] == 'int': value = int(form[k]) if not (v.get('min', float('-inf')) <= value <= v.get('max', float('inf'))): continue elif pattern.match(v['type']): inner_type = v['type'][5:-1] if inner_type == 'string': value = web.input(**{k: ['']})[k] elif pattern.match(inner_type): inner_type = inner_type[5:-1] if inner_type == 'string': delimiter = form[k + '-delimiter'] values = web.input(**{k: ['']})[k] lists = [] l = [] for v in values: if v == delimiter: lists.append(l) l = [] else: l.append(v) value = lists elif k in form: if v['type'] == 'template' and form[k] == '~': value = None else: value = form[k] else: continue if channel.get_config_param(k) != value: channel.plugin_config[k] = value logger.info( 'the %s parameter of channel %s has been changed to %s by user %s', k, channel.name, value, current_user.log_name) if current_user.super_admin: channel.cache_activated = 'cache-activated' in form and form[ 'cache-activated'] == 'on' channel.cache_validity = int( form['cache-validity'] ) if 'cache-validity' in form and form[ 'cache-validity'] else channel.cache_validity channel.keep_noncomplying_capsules = 'keep-capsules' in form and form[ 'keep-capsules'] == 'on' channel.plugin_config = channel.plugin_config # Force SQLObject update try: self.plugin_manager.invalidate_cache( channel.plugin.name, channel.id) self.plugin_manager.get_plugin( channel.plugin.name).get_content(channel.id) except MisconfiguredParameters as e: for faulty_param in e: add_feedback(form.action, faulty_param[0], faulty_param) raise web.seeother('/channels/%d' % channel.id) except Exception as e: add_feedback(form.action, 'general_error', str(e)) raise web.seeother('/channels/%d' % channel.id) else: raise web.forbidden() form.name = channel.name except (SQLObjectNotFound, ValueError): raise ImmediateFeedback(form.action, 'invalid_id') if channel: form.name = channel.name add_feedback(form.action, 'ok') except ImmediateFeedback: if channel is not None and channel.enabled: form.enabled = 'on' store_form(form) return self.render_page(current_user)
def get_content(channel_id): channel = PluginChannel.get(channel_id) logger_extra = {'channel_name': channel.name, 'channel_id': channel.id} logger = get_logger('github', channel) token = channel.get_config_param('token') duration = channel.get_config_param('duration') * 1000 repo_url = channel.get_config_param('repo_url') had_organization = channel.get_config_param('had_organization') number_organizations = channel.get_config_param('number_organizations') orga_url = channel.get_config_param('orga_url') disp_commits = channel.get_config_param('disp_commits') number_commits = channel.get_config_param('number_commits') max_days_commit = channel.get_config_param('max_days_commit') disp_contributors = channel.get_config_param('disp_contributors') number_contributors = channel.get_config_param('number_contributors') disp_issues = channel.get_config_param('disp_issues') number_issues = channel.get_config_param('number_issues') disp_stat = channel.get_config_param('disp_stat') disp_releases = channel.get_config_param('disp_releases') number_releases = channel.get_config_param('number_releases') if not token or not repo_url: logger.warning('Some of the required parameters are empty', extra=logger_extra) return [] git_obj = GithubAPI(token) capsule = GithubReaderCapsule() if disp_issues: try: capsule.slides.append( GithubReaderSlideIssue(repo_url, number_issues, duration, git_obj, logger, logger_extra)) except NoContentError: pass except: logger.info( 'An exception occurred when generating the issues slide', exc_info=True, extra=logger_extra) if disp_commits: try: capsule.slides.append( GithubReaderSlideCommit(repo_url, number_commits, duration, git_obj, max_days_commit, logger, logger_extra)) except NoContentError: pass except: logger.info( 'An exception occurred when generating the commits slide', exc_info=True, extra=logger_extra) if disp_releases: try: capsule.slides.append( GithubReaderSlideRelease(repo_url, number_releases, duration, git_obj, logger, logger_extra)) except NoContentError: pass except: logger.info( 'An exception occurred when generating the releases slide', exc_info=True, extra=logger_extra) if disp_contributors: try: capsule.slides.append( GithubReaderSlideContributor(repo_url, number_contributors, duration, git_obj, logger, logger_extra)) except NoContentError: pass except: logger.info( 'An exception occurred when generating the contributors slide', exc_info=True, extra=logger_extra) if had_organization: try: capsule.slides.append( GithubReaderSlideOrganization(orga_url, number_organizations, duration, git_obj, logger, logger_extra)) except NoContentError: pass except: logger.info( 'An exception occurred when generating the organisation slide', exc_info=True, extra=logger_extra) return [capsule]
def runTest(self): """ Tests the channels edition through the Channels page """ channel_params = { 'action': 'edit-channel', 'name': 'Plugin Channel test edition', 'description': 'Descr.', 'subscription_right': 'public', 'plugin': self.fake_plugin.id, 'id': self.pc1.id } bundle_params = dict(**channel_params) bundle_params.update({ 'action': 'edit-bundle', 'name': 'Channel Bundle test edition', 'id': self.bundle.id }) bundle_params.pop('plugin') def get_attr(o, a): if a == 'plugin': return o.plugin.id if a == 'enabled': return 'on' if o.enabled else '' return getattr(o, a) def assert_edition(attrs=None, channel_params=channel_params, bundle_params=bundle_params, status=200): if attrs is None: attrs = [ 'name', 'description', 'enabled', 'subscription_right', 'plugin' ] assert self.testApp.post('/channels', params=channel_params, status=status).body is not None pc = PluginChannel.get(self.pc1.id) for attr in attrs: if attr in channel_params: assert get_attr(pc, attr) == channel_params[attr] assert self.testApp.post('/channels', params=bundle_params, status=status).body is not None bc = ChannelBundle.get(self.bundle.id) for attr in attrs: if attr in bundle_params: assert get_attr(bc, attr) == bundle_params[attr] if channel_params is not orig_plugin_channel_params and bundle_params is not orig_bundle_params: assert_edition(channel_params=orig_plugin_channel_params, bundle_params=orig_bundle_params) # Revert def assert_no_edition(status=200): assert self.testApp.post('/channels', params=channel_params, status=status).body is not None assert orig_plugin_channel == repr(PluginChannel.get(self.pc1.id)) assert self.testApp.post('/channels', params=bundle_params, status=status).body is not None assert orig_bundle_channel == repr( ChannelBundle.get(self.bundle.id)) orig_plugin_channel_params = { 'action': 'edit-channel', 'name': 'Plugin Channel', 'description': 'Original descr.', 'subscription_right': 'public', 'plugin': self.fake_plugin.id, 'id': self.pc1.id } orig_bundle_params = dict(**orig_plugin_channel_params) orig_bundle_params.update({ 'action': 'edit-bundle', 'name': 'Channel Bundle test edition', 'id': self.bundle.id }) orig_bundle_params.pop('plugin') assert_edition(channel_params=orig_plugin_channel_params, bundle_params=orig_bundle_params) orig_plugin_channel = repr(PluginChannel.get(self.pc1.id)) orig_bundle_channel = repr(ChannelBundle.get(self.bundle.id)) # Test basic functionality assert_edition() # Test insufficient permissions for channel edition for u in [ self.user_nothing, self.user_contrib, self.user_chan_admin, self.user_screen_admin ]: self.ictv_app.test_user = {'email': u.email} assert_no_edition(403) # Test sufficient permissions for channel edition for u in [self.user_admin, self.user_super_admin]: self.ictv_app.test_user = {'email': u.email} assert_edition() # Test invalid id channel_params['id'] = bundle_params['id'] = -1 assert_no_edition() channel_params['id'] = bundle_params['id'] = 'invalid' assert_no_edition() channel_params['id'] = self.pc1.id bundle_params['id'] = self.bundle.id # Test invalid plugin channel_params['plugin'] = -1 assert self.testApp.post('/channels', params=channel_params, status=200).body is not None assert orig_plugin_channel == repr(PluginChannel.get(self.pc1.id)) channel_params['plugin'] = 'invalid' assert self.testApp.post('/channels', params=channel_params, status=200).body is not None assert orig_plugin_channel == repr(PluginChannel.get(self.pc1.id)) channel_params['plugin'] = self.fake_plugin.id # Test invalid action channel_params['action'] = bundle_params['action'] = 'edit-invalid' assert_no_edition(400) channel_params['action'] = 'edit-channel' bundle_params['action'] = 'edit-bundle' # Test duplicate name Channel(name='already taken', subscription_right='public') channel_params['name'] = bundle_params['name'] = 'already taken' assert_no_edition()