def profile_update(user_id): ucontr = None if admin_permission.can(): ucontr = UserController() elif Permission(UserNeed(user_id)).can(): ucontr = UserController(user_id) else: flash(gettext('You do not have rights on this user'), 'danger') raise Forbidden(gettext('You do not have rights on this user')) user = ucontr.get(id=user_id) profile_form, pass_form = ProfileForm(obj=user), PasswordModForm() if profile_form.validate(): values = { 'login': profile_form.login.data, 'email': profile_form.email.data } if admin_permission.can(): values['is_active'] = profile_form.is_active.data values['is_admin'] = profile_form.is_admin.data values['is_api'] = profile_form.is_api.data ucontr.update({'id': user_id}, values) flash(gettext('User %(login)s successfully updated', login=user.login), 'success') return redirect(url_for('user.profile', user_id=user.id)) return render_template('profile.html', user=user, admin_permission=admin_permission, form=profile_form, pass_form=pass_form)
def test_api_creation(self): resp = self._api('post', self.urn, user='******', data={'feed_id': 1}) self.assertEquals(403, resp.status_code) UserController().update({'login': '******'}, {'is_api': True}) resp = self._api('post', self.urn, user='******', data={'feed_id': 1}) self.assertEquals(201, resp.status_code) self.assertEquals(2, resp.json()['user_id']) resp = self._api('post', self.urn, user='******', data={'feed_id': 1}) self.assertEquals(2, resp.json()['user_id']) self.assertEquals(201, resp.status_code) resp = self._api('post', self.urn, user='******', data={ 'user_id': 2, 'feed_id': 1 }) self.assertEquals(403, resp.status_code) UserController().update({'login': '******'}, {'is_api': True}) resp = self._api('post', self.urn, user='******', data={ 'user_id': 2, 'feed_id': 1 }) self.assertEquals(404, resp.status_code) resp = self._api('post', self.urns, user='******', data=[{ 'feed_id': 1 }, { 'feed_id': 5 }]) self.assertEquals(206, resp.status_code) self.assertTrue(isinstance(resp.json()[0], dict)) self.assertEquals('404: Not Found', resp.json()[1]) resp = self._api('post', self.urns, user='******', data=[{ 'user_id': 1, 'feed_id': 6 }, { 'feed_id': 5 }]) self.assertEquals(500, resp.status_code) self.assertEquals(['404: Not Found', '404: Not Found'], resp.json())
def delete(user_id): ucontr = None if admin_permission.can(): ucontr = UserController() elif Permission(UserNeed(user_id)).can(): ucontr = UserController(user_id) logout_user() else: flash(gettext('You do not have rights on this user'), 'danger') raise Forbidden(gettext('You do not have rights on this user')) ucontr.delete(user_id) flash(gettext('Deletion successful'), 'success') if admin_permission.can(): return redirect(url_for('admin.dashboard')) return redirect(url_for('login'))
def profile(): """ Edit the profile of the currently logged user. """ user_contr = UserController(current_user.id) user = user_contr.get(id=current_user.id) form = ProfileForm() if request.method == 'POST': if form.validate(): try: user_contr.update({'id': current_user.id}, {'nickname': form.nickname.data, 'email': form.email.data, 'password': form.password.data, 'automatic_crawling': form.automatic_crawling.data, 'is_public_profile': form.is_public_profile.data, 'bio': form.bio.data, 'webpage': form.webpage.data, 'twitter': form.twitter.data}) except Exception as error: flash(gettext('Problem while updating your profile: ' '%(error)s', error=error), 'danger') else: flash(gettext('User %(nick)s successfully updated', nick=user.nickname), 'success') return redirect(url_for('user.profile')) else: return render_template('profile.html', user=user, form=form) if request.method == 'GET': form = ProfileForm(obj=user) return render_template('profile.html', user=user, form=form)
def fetch_asyncio(user_id, feed_id): "Crawl the feeds with asyncio." import asyncio with application.app_context(): from flask.ext.login import current_user from crawler import classic_crawler ucontr = UserController() users = [] try: users = [ucontr.get(user_id)] except: users = ucontr.read() finally: if users == []: users = ucontr.read() try: feed_id = int(feed_id) except: feed_id = None loop = asyncio.get_event_loop() for user in users: if user.is_active: logger.warn("Fetching articles for " + user.login) classic_crawler.retrieve_feed(loop, current_user, feed_id) loop.close()
def process_user_form(user_id=None): """ Create or edit a user. """ form = UserForm() user_contr = UserController() if not form.validate(): return render_template('/admin/create_user.html', form=form, message=gettext('Some errors were found')) if user_id is not None: # Edit a user user_contr.update({'id': user_id}, { 'nickname': form.nickname.data, 'password': form.password.data, 'automatic_crawling': form.automatic_crawling.data }) user = user_contr.get(id=user_id) flash( gettext('User %(nick)s successfully updated', nick=user.nickname), 'success') else: # Create a new user (by the admin) user = user_contr.create( nickname=form.nickname.data, pwdhash=generate_password_hash(form.password.data), automatic_crawling=form.automatic_crawling.data, is_admin=False, is_active=True) flash( gettext('User %(nick)s successfully created', nick=user.nickname), 'success') return redirect(url_for('admin.user_form', user_id=user.id))
def fetch_asyncio(user_id=None, feed_id=None): "Crawl the feeds with asyncio." import asyncio with application.app_context(): from crawler import default_crawler filters = {} filters['is_active'] = True filters['automatic_crawling'] = True if None is not user_id: filters['id'] = user_id users = UserController().read(**filters).all() try: feed_id = int(feed_id) except: feed_id = None logger.info('Starting crawler.') start = datetime.now() loop = asyncio.get_event_loop() for user in users: default_crawler.retrieve_feed(loop, user, feed_id) loop.close() end = datetime.now() logger.info('Crawler finished in {} seconds.' \ .format((end - start).seconds))
def test_feed_list_fetchable(self): resp = self._api('get', 'feeds/fetchable', user='******') self.assertEquals(403, resp.status_code) UserController().update({'login__in': ['admin', 'user1']}, {'is_api': True}) resp = self._api('get', 'feeds/fetchable', user='******') self.assertEquals(3, len(resp.json())) self.assertEquals(200, resp.status_code) resp = self._api('get', 'feeds/fetchable', user='******') self.assertEquals(204, resp.status_code) resp = self._api('get', 'feeds/fetchable', user='******') self.assertEquals(3, len(resp.json())) self.assertEquals(200, resp.status_code) resp = self._api('get', 'feeds/fetchable', user='******') self.assertEquals(204, resp.status_code) resp = self._api('get', 'feeds/fetchable', user='******', data={'refresh_rate': 0}) self.assertEquals(3, len(resp.json())) resp = self._api('get', 'feeds/fetchable', user='******', data={'refresh_rate': 0}) self.assertEquals(5, len(resp.json()))
def delete_account(): """ Delete the account of the user (with all its data). """ UserController(current_user.id).delete(current_user.id) flash(gettext("Your account has been deleted."), "success") return redirect(url_for("login"))
def export_articles(): """ Export all articles to HTML or JSON. """ user = UserController(g.user.id).get(id=g.user.id) if request.args.get('format') == "HTML": # Export to HTML try: archive_file, archive_file_name = export.export_html(user) except: flash(gettext("Error when exporting articles."), 'danger') return redirect(redirect_url()) response = make_response(archive_file) response.headers['Content-Type'] = 'application/x-compressed' response.headers['Content-Disposition'] = 'attachment; filename=%s' \ % archive_file_name elif request.args.get('format') == "JSON": # Export to JSON try: json_result = export.export_json(user) except: flash(gettext("Error when exporting articles."), 'danger') return redirect(redirect_url()) response = make_response(json_result) response.mimetype = 'application/json' response.headers["Content-Disposition"] \ = 'attachment; filename=account.json' else: flash(gettext('Export format not supported.'), 'warning') return redirect(redirect_url()) return response
def populate_db(): db_create() ucontr = UserController() ccontr = CategoryController() fcontr = FeedController() acontr = ArticleController() ccontr = CategoryController() user1, user2 = [ ucontr.create(login=name, email="*****@*****.**" % name, password=name) for name in ["user1", "user2"] ] article_total = 0 for user in (user1, user2): for i in range(3): cat_id = None if i: cat_id = ccontr.create(user_id=user.id, name="category%d" % i).id feed = fcontr.create(link="feed%d" % i, user_id=user.id, category_id=cat_id, title="%s feed%d" % (user.login, i)) for j in range(3): entry = "%s %s article%d" % (user.login, feed.title, j) article_total += 1 acontr.create(entry_id=entry, link='http://test.te/%d' % article_total, feed_id=feed.id, user_id=user.id, category_id=cat_id, title=entry, content="content %d" % article_total)
def toggle_user(user_id=None): """ Enable or disable the account of a user. """ user_contr = UserController() user = user_contr.get(id=user_id) if user is None: flash(gettext('This user does not exist.'), 'danger') return redirect(url_for('admin.dashboard')) if user.activation_key != "": # Send the confirmation email try: notifications.new_account_activation(user) user_contr.unset_activation_key(user.id) message = gettext( 'Account of the user %(nick)s successfully ' 'activated.', nick=user.nickname) except Exception as error: flash( gettext('Problem while sending activation email %(error)s:', error=error), 'danger') return redirect(url_for('admin.dashboard')) else: user_contr.set_activation_key(user.id) message = gettext('Account of the user %(nick)s successfully disabled', nick=user.nickname) flash(message, 'success') return redirect(url_for('admin.dashboard'))
def fetch_asyncio(user_id=None, feed_id=None): "Crawl the feeds with asyncio." import asyncio with application.app_context(): from crawler import default_crawler filters = {} filters["is_active"] = True filters["automatic_crawling"] = True if None is not user_id: filters["id"] = user_id users = UserController().read(**filters).all() try: feed_id = int(feed_id) except: feed_id = None loop = asyncio.get_event_loop() queue = asyncio.Queue(maxsize=3, loop=loop) producer_coro = default_crawler.retrieve_feed(queue, users, feed_id) consumer_coro = default_crawler.insert_articles(queue, 1) logger.info("Starting crawler.") start = datetime.now() loop.run_until_complete(asyncio.gather(producer_coro, consumer_coro)) end = datetime.now() loop.close() logger.info("Crawler finished in {} seconds.".format( (end - start).seconds))
def signup(): if not conf.SELF_REGISTRATION: flash(gettext("Self-registration is disabled."), "warning") return redirect(url_for("home")) if current_user.is_authenticated: return redirect(url_for("home")) form = SignupForm() if form.validate_on_submit(): user = UserController().create( nickname=form.nickname.data, pwdhash=generate_password_hash(form.password.data), ) # Send the confirmation email try: notifications.new_account_notification(user, form.email.data) except Exception as error: flash( gettext("Problem while sending activation email: %(error)s", error=error), "danger", ) return redirect(url_for("home")) flash( gettext("Your account has been created. " "Check your mail to confirm it."), "success", ) return redirect(url_for("home")) return render_template("signup.html", form=form)
def validate(self): ucontr = UserController() validated = super().validate() if not ucontr.read(email=self.email.data).count(): self.email.errors.append('No user with that email') validated = False return validated
def recover(): """ Enables the user to recover its account when he has forgotten its password. """ form = RecoverPasswordForm() user_contr = UserController() if request.method == 'POST': if form.validate(): user = user_contr.get(email=form.email.data) characters = string.ascii_letters + string.digits password = "".join( random.choice(characters) for x in range(random.randint(8, 16))) user.set_password(password) user_contr.update({'id': user.id}, {'password': password}) # Send the confirmation email try: notifications.new_password_notification(user, password) flash(gettext('New password sent to your address.'), 'success') except Exception as error: flash( gettext( 'Problem while sending your new password: '******'%(error)s', error=error), 'danger') return redirect(url_for('login')) return render_template('recover.html', form=form) if request.method == 'GET': return render_template('recover.html', form=form)
def signup(): if not conf.SELF_REGISTRATION: flash(gettext('Self-registration is disabled.'), 'warning') return redirect(url_for('home')) if current_user.is_authenticated: return redirect(url_for('home')) form = SignupForm() if form.validate_on_submit(): user = UserController().create(nickname=form.nickname.data, email=form.email.data, pwdhash=generate_password_hash( form.password.data)) # Send the confirmation email try: notifications.new_account_notification(user) except Exception as error: flash( gettext('Problem while sending activation email: %(error)s', error=error), 'danger') return redirect(url_for('home')) flash( gettext('Your account has been created. ' 'Check your mail to confirm it.'), 'success') return redirect(url_for('home')) return render_template('signup.html', form=form)
def profile(): """ Edit the profile of the currently logged user. """ user_contr = UserController(g.user.id) user = user_contr.get(id=g.user.id) form = ProfileForm() if request.method == 'POST': if form.validate(): user_contr.update({'id': g.user.id}, { 'nickname': form.nickname.data, 'email': form.email.data, 'password': form.password.data, 'refresh_rate': form.refresh_rate.data }) flash( gettext('User %(nick)s successfully updated', nick=user.nickname), 'success') return redirect(url_for('user.profile')) else: return render_template('profile.html', user=user, form=form) if request.method == 'GET': form = ProfileForm(obj=user) return render_template('profile.html', user=user, form=form)
def validate(self): ucontr = UserController() validated = super().validate() if ucontr.read(nickname=self.nickname.data).count(): self.nickname.errors.append('Nickname already taken') validated = False return validated
def delete_account(): """ Delete the account of the user (with all its data). """ UserController(g.user.id).delete(g.user.id) flash(gettext('Your account has been deleted.'), 'success') return redirect(url_for('login'))
def export(): """ Export to OPML or JSON. """ user = UserController(current_user.id).get(id=current_user.id) if request.args.get('format') == "JSON": # Export to JSON for the export of account. try: json_result = export_json(user) except Exception as e: flash(gettext("Error when exporting articles."), 'danger') return redirect(redirect_url()) response = make_response(json_result) response.mimetype = 'application/json' response.headers["Content-Disposition"] \ = 'attachment; filename=account.json' elif request.args.get('format') == "OPML": # Export to the OPML format. categories = { cat.id: cat.dump() for cat in CategoryController(user.id).read() } response = make_response( render_template('opml.xml', user=user, categories=categories, now=datetime.now())) response.headers['Content-Type'] = 'application/xml' response.headers[ 'Content-Disposition'] = 'attachment; filename=feeds.opml' else: flash(gettext('Export format not supported.'), 'warning') return redirect(redirect_url()) return response
def export(): """ Export feeds to OPML. """ include_disabled = request.args.get('includedisabled', '') == 'on' include_private = request.args.get('includeprivate', '') == 'on' include_exceeded_error_count = request.args. \ get('includeexceedederrorcount', '') == 'on' filter = {} if not include_disabled: filter['enabled'] = True if not include_private: filter['private'] = False if not include_exceeded_error_count: filter['error_count__lt'] = conf.DEFAULT_MAX_ERROR user = UserController(current_user.id).get(id=current_user.id) feeds = FeedController(current_user.id).read(**filter) categories = { cat.id: cat.dump() for cat in CategoryController(user.id).read() } response = make_response( render_template('opml.xml', user=user, feeds=feeds, categories=categories, now=datetime.now())) response.headers['Content-Type'] = 'application/xml' response.headers['Content-Disposition'] = 'attachment; filename=feeds.opml' return response
def export(): """ Export feeds to OPML. """ include_disabled = request.args.get("includedisabled", "") == "on" include_private = request.args.get("includeprivate", "") == "on" include_exceeded_error_count = (request.args.get( "includeexceedederrorcount", "") == "on") filter = {} if not include_disabled: filter["enabled"] = True if not include_private: filter["private"] = False if not include_exceeded_error_count: filter["error_count__lt"] = conf.DEFAULT_MAX_ERROR user = UserController(current_user.id).get(id=current_user.id) feeds = FeedController(current_user.id).read(**filter) categories = { cat.id: cat.dump() for cat in CategoryController(user.id).read() } response = make_response( render_template( "opml.xml", user=user, feeds=feeds, categories=categories, now=datetime.now(), )) response.headers["Content-Type"] = "application/xml" response.headers["Content-Disposition"] = "attachment; filename=feeds.opml" return response
def about_more(): return render_template( "about_more.html", newspipe_version=__version__.split()[1], registration=[conf.SELF_REGISTRATION and "Open" or "Closed"][0], python_version="{}.{}.{}".format(*sys.version_info[:3]), nb_users=UserController().read().count(), )
def about_more(): return render_template( 'about_more.html', newspipe_version=__version__.split()[1], on_heroku=[conf.ON_HEROKU and 'Yes' or 'No'][0], registration=[conf.SELF_REGISTRATION and 'Open' or 'Closed'][0], python_version="{}.{}.{}".format(*sys.version_info[:3]), nb_users=UserController().read().count())
def test_feed_rights(self): cat = CategoryController(2).read()[0].dump() self.assertTrue(3, ArticleController().read(category_id=cat['id']).count()) self.assertTrue(3, FeedController().read(category_id=cat['id']).count()) self._test_controller_rights(cat, UserController().get(id=cat['user_id']))
def profile(user_id=None): ucontr = None if user_id and admin_permission.can(): ucontr = UserController() elif user_id and Permission(UserNeed(user_id)).can(): ucontr = UserController(user_id) elif user_id: flash(gettext('You do not have rights on this user'), 'danger') raise Forbidden(gettext('You do not have rights on this user')) else: ucontr = UserController(current_user.id) user_id = current_user.id user = ucontr.get(id=user_id) profile_form, pass_form = ProfileForm(obj=user), PasswordModForm() return render_template('profile.html', user=user, admin_permission=admin_permission, form=profile_form, pass_form=pass_form)
def validate(self): ucontr = UserController() validated = super().validate() if ucontr.read(login=self.login.data).count(): self.login.errors.append('Login already taken') validated = False if self.password.data != self.password_conf.data: self.password_conf.errors.append("Passwords don't match") validated = False return validated
def user_form(user_id=None): if user_id is not None: user = UserController().get(id=user_id) form = UserForm(obj=user) message = gettext("Edit the user <i>%(nick)s</i>", nick=user.nickname) else: form = UserForm() message = gettext("Add a new user") return render_template("/admin/create_user.html", form=form, message=message)
def create_admin(nickname, password): "Will create an admin user." admin = { "is_admin": True, "is_api": True, "is_active": True, "nickname": nickname, "pwdhash": generate_password_hash(password), } with application.app_context(): UserController(ignore_context=True).create(**admin)