def wrapper(username, id, **kwds): print "id is", id worksheet_filename = username + "/" + id try: worksheet = kwds['worksheet'] = g.notebook.get_worksheet_with_filename(worksheet_filename) except KeyError: return current_app.message(_("You do not have permission to access this worksheet")) with worksheet_locks[worksheet]: owner = worksheet.owner() if owner != '_sage_' and g.username != owner: if not worksheet.is_published(): if (not g.username in worksheet.collaborators() and not g.notebook.user_manager().user_is_admin(g.username)): return current_app.message(_("You do not have permission to access this worksheet")) if not worksheet.is_published(): worksheet.set_active(g.username) #This was in twist.Worksheet.childFactory from base import notebook_updates notebook_updates() return f(username, id, **kwds)
def wrapper(username, id, **kwds): worksheet_filename = username + "/" + id try: worksheet = kwds[ 'worksheet'] = g.notebook.get_worksheet_with_filename( worksheet_filename) except KeyError: return current_app.message( _("You do not have permission to access this worksheet"), username=g.username) with worksheet_locks[worksheet]: owner = worksheet.owner() if owner != '_sage_' and g.username != owner: if not worksheet.is_published(): if (not g.username in worksheet.collaborators() and not g.notebook.user_manager().user_is_admin( g.username)): return current_app.message(_( "You do not have permission to access this worksheet" ), username=g.username) if not worksheet.is_published(): worksheet.set_active(g.username) #This was in twist.Worksheet.childFactory from .base import notebook_updates notebook_updates() return f(username, id, **kwds)
def upload_worksheet(): from sage.misc.misc import tmp_filename, tmp_dir from werkzeug import secure_filename import zipfile #XXX: i18n backlinks = """ Return to <a href="/upload" title="Upload a worksheet"><strong>Upload File</strong></a>.""" url = request.values['url'].strip() dir = '' if url: #Downloading a file from the internet import urllib filename = tmp_filename() + ('.zip' if url.endswith('.zip') else '.sws') urllib.urlretrieve(url, filename) else: #Uploading a file from the user's computer dir = tmp_dir() file = request.files['file'] if file.filename == '': return current_app.message( "Please specify a worksheet to load.%s" % backlinks) filename = secure_filename(file.filename) filename = os.path.join(dir, filename) file.save(filename) new_name = request.values.get('name', None) try: try: if filename.endswith('.zip'): # Extract all the .sws files from a zip file. zip_file = zipfile.ZipFile(filename) sws_file = os.path.join(dir, "tmp.sws") for sws in zip_file.namelist(): if sws.endswith('.sws'): open(sws_file, 'w').write(zip_file.read( sws)) # 2.6 zip_file.extract(sws, sws_file) W = g.notebook.import_worksheet(sws_file, g.username) if new_name: W.set_name("%s - %s" % (new_name, W.name())) return redirect(url_for('home', username=g.username)) else: W = g.notebook.import_worksheet(filename, g.username) except Exception, msg: s = 'There was an error uploading the worksheet. It could be an old unsupported format or worse. If you desperately need its contents contact the <a href="http://groups.google.com/group/sage-support">sage-support group</a> and post a link to your worksheet. Alternatively, an sws file is just a bzip2 tarball; take a look inside!%s' % backlinks return current_app.message(s, url_for('home', username=g.username)) finally: # Clean up the temporarily uploaded filename. os.unlink(filename) # if a temp directory was created, we delete it now. if dir: import shutil shutil.rmtree(dir)
def worksheet_jsmol_data(worksheet): """ Jmol/JSmol callback The jmol applet does not take the data inline, but calls back at this URI to get one or more base64-encoded data files. """ # Defaults taken from upstream jsmol.php query = request.values.get('query', "http://cactus.nci.nih.gov/chemical/structure/ethanol/file?format=sdf&get3d=True") call = request.values.get('call', u'getRawDataFromDatabase') database = request.values.get('database', '_') encoding = request.values.get('encoding', None) current_app.logger.debug('JSmol call: %s', call) current_app.logger.debug('JSmol query: %s', query) if encoding == None: def encoder(x): return x elif encoding == u'base64': import base64 def encoder(x): # JSmol expects the magic ';base64,' in front of output return ';base64,' + base64.encodestring(x) else: current_app.logger.error('Invalid JSmol encoding %s', encoding) return current_app.message(_('Invalid JSmol encoding: ' + str(encoding)), username=g.username) if call == u'getRawDataFromDatabase': # Annoyingly, JMol prepends the worksheet url (not: the # request url) to the query. Strip off: worksheet_url = request.base_url[:-len('/jsmol')] pattern = worksheet_url + '/cells/(?P<cell_id>[0-9]*)/(?P<filename>.*)' match = re.match(pattern, query) if match is None: current_app.logger.error('Invalid JSmol query %s, does not match %s', query, pattern) return current_app.message(_('Invalid JSmol query: ' + query), username=g.username) cell_id = match.group('cell_id') filename = match.group('filename') filename = filename.rsplit('?',1)[0] # appended query is only for cache busting filename = secure_filename(filename) # never trust input filename = os.path.join(worksheet.cells_directory(), cell_id, filename) with open(filename, 'r') as f: data = f.read() response = make_response(encoder(data)) else: current_app.logger.error('Invalid JSmol request %s', call) return current_app.message(_('Invalid JSmol request: ' + str(call)), username=g.username) # Taken from upstream jsmol.php is_binary = '.gz' in query # Non-standard Content-Type taken from upstream jsmol.php if is_binary: response.headers['Content-Type'] = 'Content-Type: text/plain; charset=x-user-defined'; else: response.headers['Content-Type'] = 'Content-Type: application/json'; return response
def worksheet_do_upload_data(worksheet): from werkzeug import secure_filename worksheet_url = url_for_worksheet(worksheet) upload_url = worksheet_upload_data.url_for(worksheet) #XXX: i18n backlinks = """ Return to <a href="%s" title="Upload or create a data file in a wide range of formats"><strong>Upload or Create Data File</strong></a> or <a href="%s" title="Interactively use the worksheet"><strong>%s</strong></a>.""" % (upload_url, worksheet_url, worksheet.name()) if 'file' not in request.files: #XXX: i18n return current_app.message('Error uploading file (missing field "file").%s' % backlinks, worksheet_url) else: file = request.files['file'] text_fields = ['url', 'new', 'name'] for field in text_fields: if field not in request.values: #XXX: i18n return current_app.message('Error uploading file (missing %s arg).%s' % (field, backlinks), worksheet_url) name = request.values.get('name', '').strip() new_field = request.values.get('new', '').strip() url = request.values.get('url', '').strip() name = name or file.filename or new_field if url and not name: name = url.split('/')[-1] name = secure_filename(name) if not name: #XXX: i18n return current_app.message('Error uploading file (missing filename).%s' % backlinks, worksheet_url) #XXX: disk access dest = os.path.join(worksheet.data_directory(), name) if os.path.exists(dest): if not os.path.isfile(dest): #XXX: i18n return current_app.message('Suspicious filename "%s" encountered uploading file.%s' % (name, backlinks), worksheet_url) os.unlink(dest) response = redirect(worksheet_datafile.url_for(worksheet, name=name)) if url != '': #XXX: Finish me! pass elif new_field: open(dest, 'w').close() return response else: file.save(dest) return response
def upload_worksheet(): from sage.misc.misc import tmp_filename, tmp_dir from werkzeug import secure_filename import zipfile #XXX: i18n backlinks = """ Return to <a href="/upload" title="Upload a worksheet"><strong>Upload File</strong></a>.""" url = request.values['url'].strip() dir = '' if url: #Downloading a file from the internet import urllib filename = tmp_filename() + ('.zip' if url.endswith('.zip') else '.sws') urllib.urlretrieve(url, filename) else: #Uploading a file from the user's computer dir = tmp_dir() file = request.files['file'] if file.filename == '': return current_app.message("Please specify a worksheet to load.%s" % backlinks) filename = secure_filename(file.filename) filename = os.path.join(dir, filename) file.save(filename) new_name = request.values.get('name', None) try: try: if filename.endswith('.zip'): # Extract all the .sws files from a zip file. zip_file = zipfile.ZipFile(filename) sws_file = os.path.join(dir, "tmp.sws") for sws in zip_file.namelist(): if sws.endswith('.sws'): open(sws_file, 'w').write(zip_file.read(sws)) # 2.6 zip_file.extract(sws, sws_file) W = g.notebook.import_worksheet(sws_file, g.username) if new_name: W.set_name("%s - %s" % (new_name, W.name())) return redirect(url_for('home', username=g.username)) else: W = g.notebook.import_worksheet(filename, g.username) except Exception, msg: s = 'There was an error uploading the worksheet. It could be an old unsupported format or worse. If you desperately need its contents contact the <a href="http://groups.google.com/group/sage-support">sage-support group</a> and post a link to your worksheet. Alternatively, an sws file is just a bzip2 tarball; take a look inside!%s' % backlinks return current_app.message(s, url_for('home', username=g.username)) finally: # Clean up the temporarily uploaded filename. os.unlink(filename) # if a temp directory was created, we delete it now. if dir: import shutil shutil.rmtree(dir)
def forgot_pass(): if not g.notebook.conf()['email']: return current_app.message( _('The account recovery system is not active.')) username = request.values.get('username', '').strip() if not username: return render_template( os.path.join('html', 'accounts', 'account_recovery.html')) def error(msg): return current_app.message(msg, url_for('forgot_pass')) try: user = g.notebook.user(username) except KeyError: return error(_('Username is invalid.')) if not user.is_email_confirmed(): return error(_("The e-mail address hasn't been confirmed.")) #XXX: some of this could be factored out into a random passowrd #function. There are a few places in admin.py that also use it. from random import choice import string chara = string.letters + string.digits old_pass = user.password() password = ''.join([choice(chara) for i in range(8)]) from sagenb.notebook.smtpsend import send_mail from sagenb.notebook.register import build_password_msg # TODO: make this come from the server settings listenaddr = g.notebook.interface port = g.notebook.port fromaddr = 'no-reply@%s' % listenaddr body = build_password_msg(password, username, listenaddr, port, g.notebook.secure) destaddr = user.get_email() try: send_mail(fromaddr, destaddr, _("Sage Notebook Account Recovery"), body) except ValueError: # the email address is invalid return error( _("The new password couldn't be sent to %(dest)s.", dest=destaddr)) else: g.notebook.user_manager().set_password(username, password) return current_app.message( _("A new password has been sent to your e-mail address."), url_for('base.index'))
def worksheet_link_datafile(worksheet): target_worksheet_filename = request.values['target'] data_filename = request.values['filename'] src = os.path.abspath(os.path.join( worksheet.data_directory(), data_filename)) target_ws = g.notebook.get_worksheet_with_filename(target_worksheet_filename) target = os.path.abspath(os.path.join( target_ws.data_directory(), data_filename)) if target_ws.owner() != g.username and not target_ws.is_collaborator(g.username): return current_app.message(_("illegal link attempt!"), worksheet_datafile.url_for(worksheet, name=data_filename), username=g.username) if os.path.exists(target): return current_app.message(_("The data filename already exists in other worksheet\nDelete the file in the other worksheet before creating a link."), worksheet_datafile.url_for(worksheet, name=data_filename), username=g.username) os.link(src,target) return redirect(worksheet_datafile.url_for(worksheet, name=data_filename))
def worksheet_link_datafile(worksheet): target_worksheet_filename = request.values['target'] data_filename = request.values['filename'] src = os.path.abspath(os.path.join( worksheet.data_directory(), data_filename)) target_ws = g.notebook.get_worksheet_with_filename(target_worksheet_filename) target = os.path.abspath(os.path.join( target_ws.data_directory(), data_filename)) if target_ws.owner() != g.username and not target_ws.is_collaborator(g.username): return current_app.message(_("illegal link attempt!"), worksheet_datafile.url_for(worksheet, name=data_filename)) if os.path.exists(target): return current_app.message(_("The data filename already exists in other worksheet\nDelete the file in the other worksheet before creating a link."), worksheet_datafile.url_for(worksheet, name=data_filename)) os.link(src,target) return redirect(worksheet_datafile.url_for(worksheet, name=data_filename))
def worksheet_invite_collab(worksheet): owner = worksheet.owner() id_number = worksheet.id_number() old_collaborators = set(worksheet.collaborators()) collaborators = set([u.strip() for u in request.values.get('collaborators', '').split(',') if u!=owner]) if len(collaborators-old_collaborators)>500: # to prevent abuse, you can't add more than 500 collaborators at a time return current_app.message(_("Error: can't add more than 500 collaborators at a time"), cont=url_for_worksheet(worksheet)) worksheet.set_collaborators(collaborators) user_manager = g.notebook.user_manager() # add worksheet to new collaborators for u in collaborators-old_collaborators: try: user_manager.user(u).viewable_worksheets().add((owner, id_number)) except KeyError: # user doesn't exist pass # remove worksheet from ex-collaborators for u in old_collaborators-collaborators: try: user_manager.user(u).viewable_worksheets().discard((owner, id_number)) except KeyError: # user doesn't exist pass return redirect(url_for_worksheet(worksheet))
def worksheet_file(path): # Create a live Sage worksheet from the given path. if not os.path.exists(path): return current_app.message(_('Document does not exist.')) doc_page_html = open(path).read() from sagenb.notebook.docHTMLProcessor import SphinxHTMLProcessor doc_page = SphinxHTMLProcessor().process_doc_html(doc_page_html) title = (extract_title(doc_page_html).replace('—', '--') or 'Live Sage Documentation') W = doc_worksheet() W.edit_save(doc_page) W.set_system('sage') W.set_name(title) W.save() W.quit() # FIXME: For some reason, an extra cell gets added so we # remove it here. W.cell_list().pop() return g.notebook.html(worksheet_filename=W.filename(), username=g.username)
def wrapper(*args, **kwds): if not g.notebook.user_manager().user_is_admin(g.username): return current_app.message( _("You do not have permission to access this location"), cont=url_for('base.index'), username=g.username) return f(*args, **kwds)
def add_user(): from sagenb.notebook.misc import is_valid_username from sagenb.misc.misc import SAGE_VERSION template_dict = {'admin': g.notebook.user_manager().user(g.username).is_admin(), 'username': g.username, 'sage_version': SAGE_VERSION} if 'username' in request.values: if request.values['cancel']: return redirect(url_for('users')) username = request.values['username'] if not is_valid_username(username): return render_template(os.path.join('html', 'settings', 'admin_add_user.html'), error='username_invalid', username_input=username, **template_dict) from random import choice import string chara = string.letters + string.digits password = ''.join([choice(chara) for i in range(8)]) if username in g.notebook.user_manager().usernames(): return render_template(os.path.join('html', 'settings', 'admin_add_user.html'), error='username_taken', username_input=username, **template_dict) g.notebook.user_manager().add_user(username, password, '', force=True) message = _('The temporary password for the new user <em>%(username)s</em> is <em>%(password)s</em>', username=username, password=password) return current_app.message(message, cont='/adduser', title=_('New User')) else: return render_template(os.path.join('html', 'settings', 'admin_add_user.html'), **template_dict)
def add_user(): from sagenb.notebook.misc import is_valid_username template_dict = {'admin': g.notebook.user_manager().user(g.username).is_admin(), 'username': g.username} if 'username' in request.values: username = request.values['username'] if not is_valid_username(username): return render_template(os.path.join('html', 'settings', 'admin_add_user.html'), error='username_invalid', username=username, **template_dict) from random import choice import string chara = string.letters + string.digits password = ''.join([choice(chara) for i in range(8)]) if username in g.notebook.user_manager().usernames(): return render_template(os.path.join('html', 'settings', 'admin_add_user.html'), error='username_taken', username_input=username, **template_dict) g.notebook.user_manager().add_user(username, password, '', force=True) message = _('The temporary password for the new user <em>%(username)s</em> is <em>%(password)s</em>', username=username, password=password) return current_app.message(message, cont='/adduser', title=_('New User')) else: return render_template(os.path.join('html', 'settings', 'admin_add_user.html'), **template_dict)
def worksheet_file(path): # Create a live Sage worksheet from the given path. if not os.path.exists(path): return current_app.message(_('Document does not exist.'), username=g.username) doc_page_html = open(path).read() from sagenb.notebook.docHTMLProcessor import SphinxHTMLProcessor doc_page = SphinxHTMLProcessor().process_doc_html(doc_page_html) title = (extract_title(doc_page_html).replace('—', '--') or 'Live Sage Documentation') W = doc_worksheet() W.edit_save(doc_page) W.set_system('sage') W.set_name(title) W.save() W.quit() # FIXME: For some reason, an extra cell gets added so we # remove it here. W.cell_list().pop() return g.notebook.html(worksheet_filename=W.filename(), username=g.username)
def worksheet_revisions(worksheet): """ Show a list of revisions of this worksheet. """ if 'action' not in request.values: if 'rev' in request.values: return g.notebook.html_specific_revision(g.username, worksheet, request.values['rev']) else: return g.notebook.html_worksheet_revision_list(g.username, worksheet) else: rev = request.values['rev'] action = request.values['action'] if action == 'revert': import bz2 worksheet.save_snapshot(g.username) #XXX: Requires access to filesystem txt = bz2.decompress(open(worksheet.get_snapshot_text_filename(rev)).read()) worksheet.delete_cells_directory() worksheet.edit_save(txt) return redirect(url_for_worksheet(worksheet)) elif action == 'publish': import bz2 W = g.notebook.publish_worksheet(worksheet, g.username) txt = bz2.decompress(open(worksheet.get_snapshot_text_filename(rev)).read()) W.delete_cells_directory() W.edit_save(txt) return redirect(url_for_worksheet(W)) else: return current_app.message(_('Error'))
def wrapper(*args, **kwds): # We remove the first two arguments corresponding to the # username and the worksheet id username_id = args[:2] args = args[2:] ##################### # Public worksheets # ##################### # _sage_ is used by live docs and published interacts if username_id and username_id[0] in ["_sage_"]: if target.split("/")[0] not in published_commands_allowed: raise NotImplementedError("User _sage_ can not access URL %s" % target) if g.notebook.readonly_user(g.username): if target.split("/")[0] not in readonly_commands_allowed: return current_app.message( _("Account is in read-only mode"), cont=url_for("worksheet_listing.home", username=g.username) ) # Make worksheet a non-keyword argument appearing before the # other non-keyword arguments. worksheet = kwds.pop("worksheet", None) if worksheet is not None: args = (worksheet,) + args return f(*args, **kwds)
def worksheet_data(worksheet, filename): dir = os.path.abspath(worksheet.data_directory()) if not os.path.exists(dir): return current_app.message(_('No data files')) else: from flask.helpers import send_from_directory return send_from_directory(worksheet.data_directory(), filename)
def wrapper(*args, **kwds): #We remove the first two arguments corresponding to the #username and the worksheet id username_id = args[:2] args = args[2:] ##################### # Public worksheets # ##################### #_sage_ is used by live docs and published interacts if username_id and username_id[0] in ['_sage_']: if target.split('/')[0] not in published_commands_allowed: raise NotImplementedError( "User _sage_ can not access URL %s" % target) if g.notebook.readonly_user(g.username): if target.split('/')[0] not in readonly_commands_allowed: return current_app.message( _("Account is in read-only mode"), cont=url_for('worksheet_listing.home', username=g.username)) #Make worksheet a non-keyword argument appearing before the #other non-keyword arguments. worksheet = kwds.pop('worksheet', None) if worksheet is not None: args = (worksheet, ) + args return f(*args, **kwds)
def worksheet_invite_collab(worksheet): owner = worksheet.owner() id_number = worksheet.id_number() old_collaborators = set(worksheet.collaborators()) collaborators = set([ u.strip() for u in request.values.get('collaborators', '').split(',') if u != owner ]) if len(collaborators - old_collaborators) > 500: # to prevent abuse, you can't add more than 500 collaborators at a time return current_app.message( _("Error: can't add more than 500 collaborators at a time"), cont=url_for_worksheet(worksheet), username=g.username) worksheet.set_collaborators(collaborators) user_manager = g.notebook.user_manager() # add worksheet to new collaborators for u in collaborators - old_collaborators: try: user_manager.user(u).viewable_worksheets().add((owner, id_number)) except (ValueError, LookupError): # user doesn't exist pass # remove worksheet from ex-collaborators for u in old_collaborators - collaborators: try: user_manager.user(u).viewable_worksheets().discard( (owner, id_number)) except (ValueError, LookupError): # user doesn't exist pass return redirect(url_for_worksheet(worksheet))
def worksheet_revisions(worksheet): """ Show a list of revisions of this worksheet. """ if 'action' not in request.values: if 'rev' in request.values: return g.notebook.html_specific_revision(g.username, worksheet, request.values['rev']) else: return g.notebook.html_worksheet_revision_list( g.username, worksheet) else: rev = request.values['rev'] action = request.values['action'] if action == 'revert': import bz2 worksheet.save_snapshot(g.username) #XXX: Requires access to filesystem txt = bz2.decompress( open(worksheet.get_snapshot_text_filename(rev)).read()) worksheet.delete_cells_directory() worksheet.edit_save(txt) return redirect(url_for_worksheet(worksheet)) elif action == 'publish': import bz2 W = g.notebook.publish_worksheet(worksheet, g.username) txt = bz2.decompress( open(worksheet.get_snapshot_text_filename(rev)).read()) W.delete_cells_directory() W.edit_save(txt) return redirect(url_for_worksheet(W)) else: return current_app.message(_('Error'), username=g.username)
def worksheet_data(worksheet, filename): dir = os.path.abspath(worksheet.data_directory()) if not os.path.exists(dir): return current_app.message(_('No data files'), username=g.username) else: from flask.helpers import send_from_directory return send_from_directory(worksheet.data_directory(), filename)
def forgot_pass(): if not g.notebook.conf()["email"]: return current_app.message(_("The account recovery system is not active.")) username = request.values.get("username", "").strip() if not username: return render_template(os.path.join("html", "accounts", "account_recovery.html")) def error(msg): return current_app.message(msg, url_for("forgot_pass")) try: user = g.notebook.user(username) except KeyError: return error(_("Username is invalid.")) if not user.is_email_confirmed(): return error(_("The e-mail address hasn't been confirmed.")) # XXX: some of this could be factored out into a random passowrd # function. There are a few places in admin.py that also use it. from random import choice import string chara = string.letters + string.digits old_pass = user.password() password = "".join([choice(chara) for i in range(8)]) from sagenb.notebook.smtpsend import send_mail from sagenb.notebook.register import build_password_msg # TODO: make this come from the server settings listenaddr = g.notebook.interface port = g.notebook.port fromaddr = "no-reply@%s" % listenaddr body = build_password_msg(password, username, listenaddr, port, g.notebook.secure) destaddr = user.get_email() try: send_mail(fromaddr, destaddr, _("Sage Notebook Account Recovery"), body) except ValueError: # the email address is invalid return error(_("The new password couldn't be sent to %(dest)s.", dest=destaddr)) else: g.notebook.user_manager().set_password(username, password) return current_app.message(_("A new password has been sent to your e-mail address."), url_for("base.index"))
def public_worksheet_download(id, title): from worksheet import unconditional_download worksheet_filename = "pub" + "/" + id try: worksheet = g.notebook.get_worksheet_with_filename(worksheet_filename) except KeyError: return current_app.message(_("You do not have permission to access this worksheet")) return unconditional_download(worksheet, title)
def public_worksheet_cells(id, filename): worksheet_filename = "pub" + "/" + id try: worksheet = g.notebook.get_worksheet_with_filename(worksheet_filename) except KeyError: return current_app.message("You do not have permission to access this worksheet") #XXX: i18n from flask.helpers import send_from_directory return send_from_directory(worksheet.cells_directory(), filename)
def upload(): from sagenb.misc.misc import SAGE_VERSION if g.notebook.readonly_user(g.username): return current_app.message(_("Account is in read-only mode"), cont=url_for('home', username=g.username)) return render_template(os.path.join('html', 'upload.html'), username=g.username, sage_version=SAGE_VERSION)
def new_worksheet(): if g.notebook.readonly_user(g.username): return current_app.message( _("Account is in read-only mode"), cont=url_for("worksheet_listing.home", username=g.username) ) W = g.notebook.create_new_worksheet(gettext("Untitled"), g.username) return redirect(url_for_worksheet(W))
def new_worksheet(): if g.notebook.readonly_user(g.username): return current_app.message(_("Account is in read-only mode"), cont=url_for('worksheet_listing.home', username=g.username)) W = g.notebook.create_new_worksheet(gettext("Untitled"), g.username) return redirect(url_for_worksheet(W))
def forgot_pass(): if not g.notebook.conf()['email']: return current_app.message('The account recovery system is not active.') username = request.values.get('username', '').strip() if not username: return render_template(os.path.join('html', 'accounts', 'account_recovery.html')) def error(msg): return current_app.message(msg, url_for('forgot_pass')) try: user = g.notebook.user(request.values[username]) except KeyError: return error('Username is invalid.') if not user.is_email_confirmed(): return error("The e-mail address hasn't been confirmed.") #XXX: some of this could be factored out into a random passowrd #function. There are a few places in admin.py that also use it. from random import choice import string chara = string.letters + string.digits old_pass = user.password() password = ''.join([choice(chara) for i in range(8)]) user.set_password(password) from sagenb.notebook.smtpsend import send_mail from sagenb.notebook.register import build_password_msg # TODO: make this come from the server settings listenaddr = g.notebook.interface port = g.notebook.port fromaddr = 'no-reply@%s' % listenaddr body = build_password_msg(password, username, listenaddr, port, g.notebook.secure) destaddr = user.get_email() try: send_mail(fromaddr, destaddr, "Sage Notebook Account Recovery", body) except ValueError: # the email address is invalid user.set_password(old_pass) return error("The new password couldn't be sent."%destaddr) return current_app.message("A new password has been sent to your e-mail address.", url_for('base.index'))
def worksheet_rate(worksheet): ## if user_type(self.username) == "guest": ## return HTMLResponse(stream = message( ## 'You must <a href="/">login first</a> in order to rate this worksheet.', ret)) rating = int(request.values['rating']) if rating < 0 or rating >= 5: return current_app.message(_("Gees -- You can't fool the rating system that easily!"), url_for_worksheet(worksheet), username=g.username) comment = request.values['comment'] worksheet.rate(rating, comment, g.username) s = _(""" Thank you for rating the worksheet <b><i>%(worksheet_name)s</i></b>! You can <a href="rating_info">see all ratings of this worksheet.</a> """, worksheet_name=worksheet.name()) #XXX: Hardcoded url return current_app.message(s.strip(), '/pub/', title=_('Rating Accepted'), username=g.username)
def render_worksheet_list(args, pub, username): """ Returns a rendered worksheet listing. INPUT: - ``args`` - ctx.args where ctx is the dict passed into a resource's render method - ``pub`` - boolean, True if this is a listing of public worksheets - ``username`` - the user whose worksheets we are listing - ``kwds`` - additional info for template rendering OUTPUT: a string """ from sagenb.notebook.notebook import sort_worksheet_list from sagenb.misc.misc import unicode_str, SAGE_VERSION typ = args['typ'] if 'typ' in args else 'active' search = unicode_str(args['search']) if 'search' in args else None sort = args['sort'] if 'sort' in args else 'last_edited' reverse = (args['reverse'] == 'True') if 'reverse' in args else False readonly = g.notebook.readonly_user(g.username) try: if not pub: worksheets = g.notebook.worksheet_list_for_user(username, typ=typ, sort=sort, search=search, reverse=reverse) else: worksheets = g.notebook.worksheet_list_for_public(username, sort=sort, search=search, reverse=reverse) except ValueError as E: # for example, the sort key was not valid print "Error displaying worksheet listing: ", E return current_app.message(_("Error displaying worksheet listing.")) worksheet_filenames = [x.filename() for x in worksheets] if pub and (not username or username == tuple([])): username = '******' accounts = g.notebook.user_manager().get_accounts() sage_version = SAGE_VERSION site_name = g.site_name return render_template('html/worksheet_listing.html', **locals())
def confirm(): if not g.notebook.conf()['email']: return current_app.message(_('The confirmation system is not active.')) key = int(request.values.get('key', '-1')) invalid_confirm_key = _("""\ <h1>Invalid confirmation key</h1> <p>You are reporting a confirmation key that has not been assigned by this server. Please <a href="/register">register</a> with the server.</p> """) try: username = waiting[key] user = g.notebook.user(username) user.set_email_confirmation(True) except KeyError: return current_app.message(invalid_confirm_key, '/register') success = _("""<h1>Email address confirmed for user %(username)s</h1>""", username=username) del waiting[key] return current_app.message(success, title=_('Email Confirmed'))
def home(username): if not g.notebook.user_manager().user_is_admin( g.username) and username != g.username: return current_app.message( _("User '%(user)s' does not have permission to view the home page of '%(name)s'.", user=g.username, name=username)) else: return render_worksheet_list(request.args, pub=False, username=username)
def worksheet_datafile(worksheet): #XXX: This requires that the worker filesystem be accessible from #the server. dir = os.path.abspath(worksheet.data_directory()) filename = request.values['name'] if request.values.get('action', '') == 'delete': path = os.path.join(dir, filename) os.unlink(path) return current_app.message("Successfully deleted '%s'"%filename) #XXX: i18n else: return g.notebook.html_download_or_delete_datafile(worksheet, g.username, filename)
def worksheet_datafile(worksheet): #XXX: This requires that the worker filesystem be accessible from #the server. dir = os.path.abspath(worksheet.data_directory()) filename = request.values['name'] if request.values.get('action', '') == 'delete': path = os.path.join(dir, filename) os.unlink(path) return current_app.message(_("Successfully deleted '%(filename)s'", filename=filename), cont=url_for_worksheet(worksheet), username=g.username) else: return g.notebook.html_download_or_delete_datafile(worksheet, g.username, filename)
def worksheet_link_datafile(worksheet): target_worksheet_filename = request.values['target'] data_filename = request.values['filename'] src = os.path.abspath(os.path.join( worksheet.data_directory(), data_filename)) target_ws = g.notebook.get_worksheet_with_filename(target_worksheet_filename) target = os.path.abspath(os.path.join( target_ws.data_directory(), data_filename)) if target_ws.owner() != g.username and not target_ws.is_collaborator(g.username): return current_app.message("illegal link attempt!") #XXX: i18n os.system('ln "%s" "%s"'%(src, target)) return redirect(worksheet_link_datafile.url_for(worksheet, name=data_filename))
def worksheet_list(): """ Returns a worksheet listing. INPUT: - ``args`` - ctx.args where ctx is the dict passed into a resource's render method - ``pub`` - boolean, True if this is a listing of public worksheets - ``username`` - the user whose worksheets we are listing OUTPUT: a string """ from sagenb.notebook.notebook import sort_worksheet_list from sagenb.misc.misc import unicode_str, SAGE_VERSION from sagenb.notebook.misc import encode_response r = {} pub = 'pub' in request.args readonly = g.notebook.readonly_user(g.username) typ = request.args['type'] if 'type' in request.args else 'active' search = unicode_str(request.args['search']) if 'search' in request.args else None sort = request.args['sort'] if 'sort' in request.args else 'last_edited' reverse = (request.args['reverse'] == 'True') if 'reverse' in request.args else False try: if not pub: r['worksheets'] = [x.basic() for x in g.notebook.worksheet_list_for_user(g.username, typ=typ, sort=sort, search=search, reverse=reverse)] else: r['worksheets'] = [x.basic() for x in g.notebook.worksheet_list_for_public(g.username, sort=sort, search=search, reverse=reverse)] except ValueError as E: # for example, the sort key was not valid print "Error displaying worksheet listing: ", E return current_app.message(_("Error displaying worksheet listing.")) #if pub and (not g.username or g.username == tuple([])): # r['username'] = '******' r['accounts'] = g.notebook.user_manager().get_accounts() r['sage_version'] = SAGE_VERSION # r['pub'] = pub return encode_response(r)
def worksheet_link_datafile(worksheet): target_worksheet_filename = request.values['target'] data_filename = request.values['filename'] src = os.path.abspath( os.path.join(worksheet.data_directory(), data_filename)) target_ws = g.notebook.get_worksheet_with_filename( target_worksheet_filename) target = os.path.abspath( os.path.join(target_ws.data_directory(), data_filename)) if target_ws.owner() != g.username and not target_ws.is_collaborator( g.username): return current_app.message("illegal link attempt!") #XXX: i18n os.system('ln "%s" "%s"' % (src, target)) return redirect( worksheet_link_datafile.url_for(worksheet, name=data_filename))
def render_worksheet_list(args, pub, username): """ Returns a rendered worksheet listing. INPUT: - ``args`` - ctx.args where ctx is the dict passed into a resource's render method - ``pub`` - boolean, True if this is a listing of public worksheets - ``username`` - the user whose worksheets we are listing OUTPUT: a string """ from sagenb.notebook.notebook import sort_worksheet_list from sagenb.misc.misc import unicode_str, SAGE_VERSION typ = args['typ'] if 'typ' in args else 'active' search = unicode_str(args['search']) if 'search' in args else None sort = args['sort'] if 'sort' in args else 'last_edited' reverse = (args['reverse'] == 'True') if 'reverse' in args else False readonly = g.notebook.readonly_user(g.username) try: if not pub: worksheets = g.notebook.worksheet_list_for_user(username, typ=typ, sort=sort, search=search, reverse=reverse) else: worksheets = g.notebook.worksheet_list_for_public(username, sort=sort, search=search, reverse=reverse) except ValueError as E: # for example, the sort key was not valid print "Error displaying worksheet listing: ", E return current_app.message(_("Error displaying worksheet listing.")) worksheet_filenames = [x.filename() for x in worksheets] if pub and (not username or username == tuple([])): username = '******' accounts = g.notebook.user_manager().get_accounts() sage_version = SAGE_VERSION return render_template('html/worksheet_listing.html', **locals())
def unconditional_download(worksheet, title): from sagenb.misc.misc import tmp_filename from flask.helpers import send_file filename = tmp_filename() + '.sws' if title.endswith('.sws'): title = title[:-4] try: #XXX: Accessing the hard disk. g.notebook.export_worksheet(worksheet.filename(), filename, title) except KeyError: return current_app.message(_('No such worksheet.')) from flask.helpers import send_file return send_file(filename, mimetype='application/sage')
def add_user(): from sagenb.notebook.misc import is_valid_username from sagenb.misc.misc import SAGE_VERSION template_dict = { "admin": g.notebook.user_manager().user(g.username).is_admin(), "username": g.username, "sage_version": SAGE_VERSION, } if "username" in request.values: if request.values["cancel"]: return redirect(url_for("users")) username = request.values["username"] if not is_valid_username(username): return render_template( os.path.join("html", "settings", "admin_add_user.html"), error="username_invalid", username_input=username, **template_dict ) from random import choice import string chara = string.letters + string.digits password = "".join([choice(chara) for i in range(8)]) if username in g.notebook.user_manager().usernames(): return render_template( os.path.join("html", "settings", "admin_add_user.html"), error="username_taken", username_input=username, **template_dict ) g.notebook.user_manager().add_user(username, password, "", force=True) message = _( "The temporary password for the new user <em>%(username)s</em> is <em>%(password)s</em>", username=username, password=password, ) return current_app.message(message, cont="/adduser", title=_("New User")) else: return render_template(os.path.join("html", "settings", "admin_add_user.html"), **template_dict)
def worksheet_file(path): # Create a live Sage worksheet out of path and render it. if not os.path.exists(path): return current_app.message('Document does not exist.') doc_page_html = open(path).read() from sagenb.notebook.docHTMLProcessor import SphinxHTMLProcessor doc_page = SphinxHTMLProcessor().process_doc_html(doc_page_html) title = extract_title(doc_page_html).replace('—', '--') doc_page = title + '\nsystem:sage\n\n' + doc_page W = doc_worksheet() W.edit_save(doc_page) #FIXME: For some reason, an extra cell gets added #so we remove it here. cells = W.cell_list() cells.pop() return g.notebook.html(worksheet_filename=W.filename(), username=g.username)
def worksheet_file(path): # Create a live Sage worksheet out of path and render it. if not os.path.exists(path): return current_app.message('Document does not exist.') doc_page_html = open(path).read() from sagenb.notebook.docHTMLProcessor import SphinxHTMLProcessor doc_page = SphinxHTMLProcessor().process_doc_html(doc_page_html) title = extract_title(doc_page_html).replace('—','--') doc_page = title + '\nsystem:sage\n\n' + doc_page W = doc_worksheet() W.edit_save(doc_page) #FIXME: For some reason, an extra cell gets added #so we remove it here. cells = W.cell_list() cells.pop() return g.notebook.html(worksheet_filename=W.filename(), username=g.username)
def add_user(): from sagenb.notebook.twist import is_valid_username template_dict = { 'admin': g.notebook.user_manager().user(g.username).is_admin(), 'username': g.username } if 'username' in request.values: username = request.values['username'] if not is_valid_username(username): return render_template(os.path.join('html', 'settings', 'admin_add_user.html'), error='username_invalid', username=username, **template_dict) from random import choice import string chara = string.letters + string.digits password = ''.join([choice(chara) for i in range(8)]) if username in g.notebook.user_manager().usernames(): return render_template(os.path.join('html', 'settings', 'admin_add_user.html'), error='username_taken', username_input=username, **template_dict) g.notebook.user_manager().add_user(username, password, '', force=True) #XXX: i18n return current_app.message( 'The temporary password for the new user <em>%s</em> is <em>%s</em>' % (username, password), '/adduser', title=u'New User') else: return render_template( os.path.join('html', 'settings', 'admin_add_user.html'), **template_dict)
def upload_worksheet(): from sage.misc.misc import tmp_filename, tmp_dir from werkzeug.utils import secure_filename import zipfile if g.notebook.readonly_user(g.username): return current_app.message(_("Account is in read-only mode"), cont=url_for('home', username=g.username)) backlinks = _("""Return to <a href="/upload" title="Upload a worksheet"><strong>Upload File</strong></a>.""") url = request.values['url'].strip() dir = '' if url != '': #Downloading a file from the internet # The file will be downloaded from the internet and saved # to a temporary file with the same extension path = urlparse.urlparse(url).path extension = os.path.splitext(path)[1].lower() if extension not in ["", ".txt", ".sws", ".zip", ".html", ".rst"]: # Or shall we try to import the document as an sws when in doubt? return current_app.message("Unknown worksheet extension: %s. %s" % (extension, backlinks)) filename = tmp_filename()+extension try: import re matches = re.match("file://(?:localhost)?(/.+)", url) if matches: if g.notebook.interface != 'localhost': return current_app.message(_("Unable to load file URL's when not running on localhost.\n%(backlinks)s",backlinks=backlinks)) import shutil shutil.copy(matches.group(1),filename) else: my_urlretrieve(url, filename, backlinks=backlinks) except RetrieveError as err: return current_app.message(str(err)) else: #Uploading a file from the user's computer dir = tmp_dir() file = request.files['file'] if file.filename is None: return current_app.message(_("Please specify a worksheet to load.\n%(backlinks)s",backlinks=backlinks)) filename = secure_filename(file.filename) if len(filename)==0: return current_app.message(_("Invalid filename.\n%(backlinks)s",backlinks=backlinks)) filename = os.path.join(dir, filename) file.save(filename) new_name = request.values.get('name', None) try: try: if filename.endswith('.zip'): # Extract all the .sws files from a zip file. zip_file = zipfile.ZipFile(filename) for subfilename in zip_file.namelist(): prefix, extension = os.path.splitext(subfilename) # Mac zip files contain files like __MACOSX/._worksheet.sws # which are metadata files, so we skip those as # well as any other files we won't understand if extension in ['.sws', '.html', '.txt', '.rst'] and not prefix.startswith('__MACOSX/'): tmpfilename = os.path.join(dir, "tmp" + extension) try: tmpfilename = zip_file.extract(subfilename, tmpfilename) except AttributeError: open(tmpfilename, 'w').write(zip_file.read(subfilename)) W = g.notebook.import_worksheet(tmpfilename, g.username) if new_name: W.set_name("%s - %s" % (new_name, W.name())) else: print "Unknown extension, file %s is ignored" % subfilename return redirect(url_for('home', username=g.username)) else: if url and extension in ['', '.html']: linked_sws = parse_link_rel(url, filename) if linked_sws: # just grab 1st URL; perhaps later add interface for # downloading multiple linked .sws try: filename = my_urlretrieve(linked_sws[0]['url'], backlinks=backlinks)[0] print 'Importing {0}, linked to from {1}'.format(linked_sws[0]['url'], url) except RetrieveError as err: return current_app.message(str(err)) W = g.notebook.import_worksheet(filename, g.username) except Exception, msg: print 'error uploading worksheet', msg s = _('There was an error uploading the worksheet. It could be an old unsupported format or worse. If you desperately need its contents contact the <a href="http://groups.google.com/group/sage-support">sage-support group</a> and post a link to your worksheet. Alternatively, an sws file is just a bzip2 tarball; take a look inside!\n%(backlinks)s', backlinks=backlinks) return current_app.message(s, url_for('home', username=g.username)) finally: # Clean up the temporarily uploaded filename. os.unlink(filename) # if a temp directory was created, we delete it now. if dir: import shutil shutil.rmtree(dir)
def upload(): if g.notebook.readonly_user(g.username): return current_app.message(_("Account is in read-only mode"), cont=url_for('home', username=g.username)) return render_template(os.path.join('html', 'upload.html'), username=g.username)
def worksheet_do_upload_data(worksheet): worksheet_url = url_for_worksheet(worksheet) upload_url = worksheet_upload_data.url_for(worksheet) backlinks = _( """ Return to <a href="%(upload_url)s" title="Upload or create a data file in a wide range of formats"><strong>Upload or Create Data File</strong></a> or <a href="%(worksheet_url)s" title="Interactively use the worksheet"><strong>%(worksheet_name)s</strong></a>.""", upload_url=upload_url, worksheet_url=worksheet_url, worksheet_name=worksheet.name()) if 'file' not in request.files: return current_app.message(_( 'Error uploading file (missing field "file"). %(backlinks)s', backlinks=backlinks), worksheet_url, username=g.username) else: file = request.files['file'] text_fields = ['url', 'new', 'name'] for field in text_fields: if field not in request.values: return current_app.message(_( 'Error uploading file (missing %(field)s arg).%(backlinks)s', field=field, backlinks=backlinks), worksheet_url, username=g.username) name = request.values.get('name', '').strip() new_field = request.values.get('new', '').strip() url = request.values.get('url', '').strip() name = name or file.filename or new_field if url and not name: name = url.split('/')[-1] name = secure_filename(name) if not name: return current_app.message( _('Error uploading file (missing filename).%(backlinks)s', backlinks=backlinks), worksheet_url) if url != '': import urllib2 from urlparse import urlparse # we normalize the url by parsing it first parsedurl = urlparse(url) if not parsedurl[0] in ('http', 'https', 'ftp'): return current_app.message(_( 'URL must start with http, https, or ftp.%(backlinks)s', backlinks=backlinks), worksheet_url, username=g.username) download = urllib2.urlopen(parsedurl.geturl()) #XXX: disk access dest = os.path.join(worksheet.data_directory(), name) if os.path.exists(dest): if not os.path.isfile(dest): return current_app.message(_( 'Suspicious filename "%(filename)s" encountered uploading file.%(backlinks)s', filename=filename, backlinks=backlinks), worksheet_url, username=g.username) os.unlink(dest) response = redirect(worksheet_datafile.url_for(worksheet, name=name)) matches = re.match("file://(?:localhost)?(/.+)", url) if matches: f = file(dest, 'wb') f.write(open(matches.group(1)).read()) f.close() return response elif url != '': with open(dest, 'w') as f: f.write(download.read()) return response elif new_field: open(dest, 'w').close() return response else: file.save(dest) return response
print 'Importing {0}, linked to from {1}'.format( linked_sws[0]['url'], url) except RetrieveError as err: return current_app.message(str(err)) W = g.notebook.import_worksheet(filename, g.username) except Exception, msg: print 'error uploading worksheet', msg s = _( 'There was an error uploading the worksheet. It could be an old unsupported format or worse. If you desperately need its contents contact the <a href="http://groups.google.com/group/sage-support">sage-support group</a> and post a link to your worksheet. Alternatively, an sws file is just a bzip2 tarball; take a look inside!\n%(backlinks)s', backlinks=backlinks) return current_app.message(s, url_for('home', username=g.username)) finally: # Clean up the temporarily uploaded filename. os.unlink(filename) # if a temp directory was created, we delete it now. if dir: import shutil shutil.rmtree(dir) except ValueError, msg: s = _("Error uploading worksheet '%(msg)s'.%(backlinks)s", msg=msg, backlinks=backlinks) return current_app.message(s, url_for('home', username=g.username)) if new_name: W.set_name(new_name) from worksheet import url_for_worksheet return redirect(url_for_worksheet(W))
def upload_worksheet(): from sage.misc.all import tmp_filename, tmp_dir from werkzeug.utils import secure_filename import zipfile if g.notebook.readonly_user(g.username): return current_app.message(_("Account is in read-only mode"), cont=url_for('home', username=g.username)) backlinks = _( """Return to <a href="/upload" title="Upload a worksheet"><strong>Upload File</strong></a>.""" ) url = request.values['url'].strip() dir = '' if url != '': #Downloading a file from the internet # The file will be downloaded from the internet and saved # to a temporary file with the same extension path = urlparse.urlparse(url).path extension = os.path.splitext(path)[1].lower() if extension not in ["", ".txt", ".sws", ".zip", ".html", ".rst"]: # Or shall we try to import the document as an sws when in doubt? return current_app.message( _("Unknown worksheet extension: %(ext)s. %(links)s", ext=extension, links=backlinks)) filename = tmp_filename() + extension try: import re matches = re.match("file://(?:localhost)?(/.+)", url) if matches: if g.notebook.interface != 'localhost': return current_app.message( _("Unable to load file URL's when not running on localhost.\n%(backlinks)s", backlinks=backlinks)) import shutil shutil.copy(matches.group(1), filename) else: my_urlretrieve(url, filename, backlinks=backlinks) except RetrieveError as err: return current_app.message(str(err)) else: #Uploading a file from the user's computer dir = tmp_dir() file = request.files['file'] if file.filename is None: return current_app.message( _("Please specify a worksheet to load.\n%(backlinks)s", backlinks=backlinks)) filename = secure_filename(file.filename) if len(filename) == 0: return current_app.message( _("Invalid filename.\n%(backlinks)s", backlinks=backlinks)) filename = os.path.join(dir, filename) file.save(filename) new_name = request.values.get('name', None) try: try: if filename.endswith('.zip'): # Extract all the .sws files from a zip file. zip_file = zipfile.ZipFile(filename) for subfilename in zip_file.namelist(): prefix, extension = os.path.splitext(subfilename) # Mac zip files contain files like __MACOSX/._worksheet.sws # which are metadata files, so we skip those as # well as any other files we won't understand if extension in ['.sws', '.html', '.txt', '.rst' ] and not prefix.startswith('__MACOSX/'): tmpfilename = os.path.join(dir, "tmp" + extension) try: tmpfilename = zip_file.extract( subfilename, tmpfilename) except AttributeError: open(tmpfilename, 'w').write(zip_file.read(subfilename)) W = g.notebook.import_worksheet( tmpfilename, g.username) if new_name: W.set_name("%s - %s" % (new_name, W.name())) else: print "Unknown extension, file %s is ignored" % subfilename return redirect(url_for('home', username=g.username)) else: if url and extension in ['', '.html']: linked_sws = parse_link_rel(url, filename) if linked_sws: # just grab 1st URL; perhaps later add interface for # downloading multiple linked .sws try: filename = my_urlretrieve(linked_sws[0]['url'], backlinks=backlinks)[0] print 'Importing {0}, linked to from {1}'.format( linked_sws[0]['url'], url) except RetrieveError as err: return current_app.message(str(err)) W = g.notebook.import_worksheet(filename, g.username) except Exception, msg: print 'error uploading worksheet', msg s = _( 'There was an error uploading the worksheet. It could be an old unsupported format or worse. If you desperately need its contents contact the <a href="http://groups.google.com/group/sage-support">sage-support group</a> and post a link to your worksheet. Alternatively, an sws file is just a bzip2 tarball; take a look inside!\n%(backlinks)s', backlinks=backlinks) return current_app.message(s, url_for('home', username=g.username)) finally: # Clean up the temporarily uploaded filename. os.unlink(filename) # if a temp directory was created, we delete it now. if dir: import shutil shutil.rmtree(dir)
def home(username): if not g.notebook.user_manager().user_is_admin(g.username) and username != g.username: #XXX: i18n return current_app.message("User '%s' does not have permission to view the home page of '%s'."%(g.username, username)) else: return render_worksheet_list(request.args, pub=False, username=username)
def settings_page(): error = None redirect_to_home = None redirect_to_logout = None nu = g.notebook.user_manager().user(g.username) autosave = int(request.values.get('autosave', 0))*60 if autosave: nu['autosave_interval'] = autosave redirect_to_home = True old = request.values.get('old-pass', None) new = request.values.get('new-pass', None) two = request.values.get('retype-pass', None) if new or two: if not old: error = 'Old password not given' elif not g.notebook.user_manager().check_password(g.username, old): error = 'Incorrect password given' elif not new: error = 'New password not given' elif not two: error = 'Please type in new password again.' elif new != two: error = 'The passwords you entered do not match.' if not error: # The browser may auto-fill in "old password," even # though the user may not want to change her password. g.notebook.user_manager().set_password(g.username, new) redirect_to_logout = True if g.notebook.conf()['email']: newemail = request.values.get('new-email', None) if newemail: nu.set_email(newemail) ##nu.set_email_confirmation(False) redirect_to_home = True if error: return current_app.message(error, url_for('settings_page')) if redirect_to_logout: return redirect(url_for('authentication.logout')) if redirect_to_home: return redirect(url_for('worksheet_listing.home', username=g.username)) td = {} td['username'] = g.username td['autosave_intervals'] = ((i, ' selected') if nu['autosave_interval']/60 == i else (i, '') for i in range(1, 10, 2)) td['email'] = g.notebook.conf()['email'] if td['email']: td['email_address'] = nu.get_email() or 'None' if nu.is_email_confirmed(): td['email_confirmed'] = 'Confirmed' else: td['email_confirmed'] = 'Not confirmed' td['admin'] = nu.is_admin() return render_template(os.path.join('html', 'settings', 'account_settings.html'), **td)
def error(msg): return current_app.message(msg, url_for('forgot_pass'))
def error(msg): return current_app.message(msg, url_for("forgot_pass"))
def doc_live_base(): return current_app.message('nothing to see.', username=g.username)