You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@allura.apache.org by br...@apache.org on 2016/09/01 16:08:18 UTC
[1/4] allura git commit: [#8117] make all 2FA pages look nicer;
increase pwd reconfirm timeout
Repository: allura
Updated Branches:
refs/heads/db/8117 57b425241 -> a8d198013
[#8117] make all 2FA pages look nicer; increase pwd reconfirm timeout
Project: http://git-wip-us.apache.org/repos/asf/allura/repo
Commit: http://git-wip-us.apache.org/repos/asf/allura/commit/56fa52cc
Tree: http://git-wip-us.apache.org/repos/asf/allura/tree/56fa52cc
Diff: http://git-wip-us.apache.org/repos/asf/allura/diff/56fa52cc
Branch: refs/heads/db/8117
Commit: 56fa52ccab3c1e45f7cc4f93ddfbb5c77b3cc722
Parents: 57b4252
Author: Dave Brondsema <da...@brondsema.net>
Authored: Wed Aug 31 17:14:16 2016 -0400
Committer: Dave Brondsema <da...@brondsema.net>
Committed: Thu Sep 1 10:29:10 2016 -0400
----------------------------------------------------------------------
Allura/allura/templates/login_multifactor.html | 7 ++-
Allura/allura/templates/reconfirm_auth.html | 7 ++-
Allura/allura/templates/user_account_base.html | 2 +
Allura/allura/templates/user_totp.html | 62 ++++++++++++++++-----
Allura/allura/tests/functional/test_auth.py | 4 +-
Allura/development.ini | 2 +-
6 files changed, 62 insertions(+), 22 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/allura/blob/56fa52cc/Allura/allura/templates/login_multifactor.html
----------------------------------------------------------------------
diff --git a/Allura/allura/templates/login_multifactor.html b/Allura/allura/templates/login_multifactor.html
index 07eaa80..3edb53c 100644
--- a/Allura/allura/templates/login_multifactor.html
+++ b/Allura/allura/templates/login_multifactor.html
@@ -25,15 +25,18 @@
{% block content %}
<form method="post" action="/auth/do_multifactor">
- <h2>Please enter your Multifactor Authentication Code</h2>
+ <h2>Enter your Multifactor Authentication Code</h2>
+ <p>
+ Please enter the {{ config['auth.multifactor.totp.length'] }}-digit code from your authenticator app:<br>
{% if c.form_errors['code'] %}
- <div class="fielderror">{{ c.form_errors['code'] }}</div>
+ <span class="fielderror">{{ c.form_errors['code'] }}</span><br>
{% endif %}
<input type="text" name="code" autofocus autocomplete="off"/>
<input type="hidden" name="return_to" value="{{ return_to }}"/>
<br>
<input type="submit" value="Log In">
{{ lib.csrf_token() }}
+ </p>
</form>
{% endblock %}
http://git-wip-us.apache.org/repos/asf/allura/blob/56fa52cc/Allura/allura/templates/reconfirm_auth.html
----------------------------------------------------------------------
diff --git a/Allura/allura/templates/reconfirm_auth.html b/Allura/allura/templates/reconfirm_auth.html
index f44be2d..26d6fd2 100644
--- a/Allura/allura/templates/reconfirm_auth.html
+++ b/Allura/allura/templates/reconfirm_auth.html
@@ -26,8 +26,10 @@
{% block content %}
<form method="post">
<h2>Password Confirmation</h2>
- <p>To access this account security page, you must reconfirm your password:</p>
- <div class="fielderror">{{ c.form_errors['password'] }}</div>
+ <p>To access this account security page, you must reconfirm your password:<br>
+ {% if c.form_errors['password'] %}
+ <span class="fielderror">{{ c.form_errors['password'] }}</span><br>
+ {% endif %}
<input type="password" name="password" autofocus>
<br>
<input type="submit" value="Submit">
@@ -40,5 +42,6 @@
{% endfor %}
{{ lib.csrf_token() }}
+ </p>
</form>
{% endblock %}
http://git-wip-us.apache.org/repos/asf/allura/blob/56fa52cc/Allura/allura/templates/user_account_base.html
----------------------------------------------------------------------
diff --git a/Allura/allura/templates/user_account_base.html b/Allura/allura/templates/user_account_base.html
index eb68667..71442ee 100644
--- a/Allura/allura/templates/user_account_base.html
+++ b/Allura/allura/templates/user_account_base.html
@@ -20,6 +20,7 @@
{% extends g.theme.master %}
{% block content %}
+{% if menu %}
<ul id="account-nav-menu" class="b-hornav droppy">
{% for item in menu -%}
<li id="{{ item.tabid }}">
@@ -30,4 +31,5 @@
</li>
{%- endfor %}
</ul>
+{% endif %}
{% endblock %}
http://git-wip-us.apache.org/repos/asf/allura/blob/56fa52cc/Allura/allura/templates/user_totp.html
----------------------------------------------------------------------
diff --git a/Allura/allura/templates/user_totp.html b/Allura/allura/templates/user_totp.html
index 4dce799..241ff42 100644
--- a/Allura/allura/templates/user_totp.html
+++ b/Allura/allura/templates/user_totp.html
@@ -30,26 +30,58 @@
{% if c.user.get_pref('multifactor') %}
<h3>Warning: this will invalidate your previous multifactor configuration.</h3>
{% endif %}
- <h2>Install App</h2>
- <p>To use two-factor authentication, you will need to install an app on your phone.
- You can use Duo Mobile, Authy, Google Authenticator, or Authenticator for Windows phones.</p>
+ <h2>Install App</h2>
+ <p>To use two-factor authentication, you will need to install an app on your phone.<br>
+ Install Google Authenticator for
+ <a href="https://play.google.com/store/apps/details?id=com.google.android.apps.authenticator2"><b>Android</b></a>
+ or <a href="https://itunes.apple.com/us/app/google-authenticator/id388497605"><b>iOS</b></a>.
+ <br>
+ Or use another app like Duo Mobile, Authy, or Authenticator for Windows phones.
+ </p>
{% endif %}
<h2>Scan this barcode with your app</h2>
- <img src="{{ h.base64uri(qr) }}"/>
+ <img class="qrcode" src="{{ h.base64uri(qr) }}"/>
{% if setup %}
- <h2>Enter the code</h2>
- <p>
- Enter the 6-digit code to confirm it is set up correctly:
- <form method="POST" action="totp_set">
- <div class="fielderror">{{ c.form_errors['code'] }}</div>
- <input type="text" name="code" autofocus autocomplete="off"/>
- {{ lib.csrf_token() }}
- <br>
- <input type="submit" value="Submit">
- </form>
- </p>
+ <h2>Enter the code</h2>
+ <form method="POST" action="totp_set">
+ <p>
+ Enter the {{ config['auth.multifactor.totp.length'] }}-digit code to confirm it is set up correctly:<br>
+ {% if c.form_errors['code'] %}
+ <span class="fielderror">{{ c.form_errors['code'] }}</span><br>
+ {% endif %}
+ <input type="text" name="code" autofocus autocomplete="off"/>
+ {{ lib.csrf_token() }}
+ <br>
+ <input type="submit" value="Submit">
+ <a class="cancel" href="/auth/preferences/">Cancel</a>
+ </p>
+ </form>
+ {% else %}
+ <p>
+ You may use this to set up additional devices with the same two-factor key.<br>
+ <br>
+ If you are replacing a device, please <a href="totp_new">regenerate a brand new key</a>.<br>
+ <br>
+ <a href="/auth/preferences/">Back</a>
+ </p>
{% endif %}
</div>
{% endblock %}
+
+{% block extra_css %}
+<style type="text/css">
+ .qrcode {
+ /* compensate for whitespace on QR code image */
+ position: relative;
+ top: -15px;
+ margin-bottom: -15px;
+ }
+ a.cancel {
+ /* align with floated button */
+ display: inline-block;
+ margin: 6px 10px;
+ }
+</style>
+{% endblock %}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/allura/blob/56fa52cc/Allura/allura/tests/functional/test_auth.py
----------------------------------------------------------------------
diff --git a/Allura/allura/tests/functional/test_auth.py b/Allura/allura/tests/functional/test_auth.py
index 3483e6f..e203869 100644
--- a/Allura/allura/tests/functional/test_auth.py
+++ b/Allura/allura/tests/functional/test_auth.py
@@ -2037,12 +2037,12 @@ class TestTwoFactor(TestController):
assert_not_in('Password Confirmation', r)
# still not required
- datetime.utcnow.return_value = real_datetime(2016, 1, 1, 0, 0, 45)
+ datetime.utcnow.return_value = real_datetime(2016, 1, 1, 0, 1, 45)
r = self.app.get('/auth/preferences/totp_new')
assert_not_in('Password Confirmation', r)
# required later
- datetime.utcnow.return_value = real_datetime(2016, 1, 1, 0, 1, 3)
+ datetime.utcnow.return_value = real_datetime(2016, 1, 1, 0, 2, 3)
r = self.app.get('/auth/preferences/totp_new')
assert_in('Password Confirmation', r)
http://git-wip-us.apache.org/repos/asf/allura/blob/56fa52cc/Allura/development.ini
----------------------------------------------------------------------
diff --git a/Allura/development.ini b/Allura/development.ini
index a72f9fd..31ad42f 100644
--- a/Allura/development.ini
+++ b/Allura/development.ini
@@ -191,7 +191,7 @@ auth.upload_ssh_url = /auth/preferences/
auth.recovery_hash_expiry_period = 600
; Some pages require users to reconfirm their password. This controls how long that lasts for
-auth.reconfirm.seconds = 60
+auth.reconfirm.seconds = 120
; TOTP stands for Time-based One Time Password
; it is the most common two-factor auth protocol, used with Google Authenticator and other phone apps
[2/4] allura git commit: [#8117] add email notifications to 2FA;
add helper with nice From: address
Posted by br...@apache.org.
[#8117] add email notifications to 2FA; add helper with nice From: address
Project: http://git-wip-us.apache.org/repos/asf/allura/repo
Commit: http://git-wip-us.apache.org/repos/asf/allura/commit/b8562071
Tree: http://git-wip-us.apache.org/repos/asf/allura/tree/b8562071
Diff: http://git-wip-us.apache.org/repos/asf/allura/diff/b8562071
Branch: refs/heads/db/8117
Commit: b85620717fb7a727a6a727c9f5f4dea0eb75e8a7
Parents: 56fa52c
Author: Dave Brondsema <da...@brondsema.net>
Authored: Wed Aug 31 18:29:39 2016 -0400
Committer: Dave Brondsema <da...@brondsema.net>
Committed: Thu Sep 1 10:54:05 2016 -0400
----------------------------------------------------------------------
Allura/allura/controllers/auth.py | 13 ++++++--
Allura/allura/lib/multifactor.py | 2 +-
Allura/allura/tasks/mail_tasks.py | 33 +++++++++++++++++++-
.../allura/templates/mail/twofactor_disabled.md | 26 +++++++++++++++
.../allura/templates/mail/twofactor_enabled.md | 26 +++++++++++++++
Allura/allura/tests/functional/test_auth.py | 11 +++++++
6 files changed, 107 insertions(+), 4 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/allura/blob/b8562071/Allura/allura/controllers/auth.py
----------------------------------------------------------------------
diff --git a/Allura/allura/controllers/auth.py b/Allura/allura/controllers/auth.py
index 7dbfa1b..42840d2 100644
--- a/Allura/allura/controllers/auth.py
+++ b/Allura/allura/controllers/auth.py
@@ -50,6 +50,7 @@ from allura.lib.widgets import forms, form_fields as ffw
from allura.lib import mail_util
from allura.lib.multifactor import TotpService
from allura.controllers import BaseController
+from allura.tasks.mail_tasks import send_system_mail_to_user
log = logging.getLogger(__name__)
@@ -685,7 +686,6 @@ class PreferencesController(BaseController):
@reconfirm_auth
@require_post()
def totp_set(self, code, **kw):
- # TODO: email notification
key = session['totp_new_key']
totp_service = TotpService.get()
totp = totp_service.Totp(key)
@@ -702,18 +702,27 @@ class PreferencesController(BaseController):
del session['totp_new_key']
session.save()
tg.flash('Two factor authentication has now been set up.')
+ email_body = g.jinja2_env.get_template('allura:templates/mail/twofactor_enabled.md').render(dict(
+ user=c.user,
+ config=config,
+ ))
+ send_system_mail_to_user(c.user, u'Two-Factor Authentication Enabled', email_body)
redirect('.')
@expose()
@require_post()
@reconfirm_auth
def multifactor_disable(self, **kw):
- # TODO: email notification
h.auditlog_user('Disabled multifactor TOTP')
totp_service = TotpService.get()
totp_service.set_secret_key(c.user, None)
c.user.set_pref('multifactor', False)
tg.flash('Multifactor authentication has now been disabled.')
+ email_body = g.jinja2_env.get_template('allura:templates/mail/twofactor_disabled.md').render(dict(
+ user=c.user,
+ config=config,
+ ))
+ send_system_mail_to_user(c.user, u'Two-Factor Authentication Disabled', email_body)
redirect('.')
http://git-wip-us.apache.org/repos/asf/allura/blob/b8562071/Allura/allura/lib/multifactor.py
----------------------------------------------------------------------
diff --git a/Allura/allura/lib/multifactor.py b/Allura/allura/lib/multifactor.py
index 9970893..56827a4 100644
--- a/Allura/allura/lib/multifactor.py
+++ b/Allura/allura/lib/multifactor.py
@@ -117,7 +117,7 @@ class TotpService(object):
def set_secret_key(self, user, key):
'''
:param user: a :class:`User <allura.model.auth.User>`
- :param bytes key: may be `None` to clear out a key
+ :param bytes|None key: may be `None` to clear out a key
'''
raise NotImplementedError('set_secret_key')
http://git-wip-us.apache.org/repos/asf/allura/blob/b8562071/Allura/allura/tasks/mail_tasks.py
----------------------------------------------------------------------
diff --git a/Allura/allura/tasks/mail_tasks.py b/Allura/allura/tasks/mail_tasks.py
index 963555f..ce0f98a 100644
--- a/Allura/allura/tasks/mail_tasks.py
+++ b/Allura/allura/tasks/mail_tasks.py
@@ -18,7 +18,7 @@
import logging
import HTMLParser
-from pylons import tmpl_context as c, app_globals as g
+from pylons import tmpl_context as c, app_globals as g, config
from bson import ObjectId
from allura.lib import helpers as h
@@ -30,6 +30,7 @@ log = logging.getLogger(__name__)
smtp_client = mail_util.SMTPClient()
+
def mail_meta_content(metalink):
'''
Helper function used to include a view action button in your email client
@@ -47,6 +48,7 @@ def mail_meta_content(metalink):
<meta itemprop="description" content="View"></meta>
</div>""" % metalink)
+
@task
def route_email(
peer, mailfrom, rcpttos, data):
@@ -223,3 +225,32 @@ def sendsimplemail(
smtp_client.sendmail(
[toaddr], fromaddr, reply_to, subject, message_id,
in_reply_to, multi_msg, sender=sender, references=references, cc=cc, to=toaddr)
+
+
+def send_system_mail_to_user(user_or_emailaddr, subject, text):
+ '''
+ Sends a standard email from the Allura system itself, to a user.
+ This is a helper function around sendsimplemail() that generates a new task
+
+ :param user_or_emailaddr: an email addres (str) or a User object
+ :param subject: subject of the email
+ :param text: text of the email (markdown)
+ '''
+ if isinstance(user_or_emailaddr, basestring):
+ toaddr = user_or_emailaddr
+ else:
+ toaddr = user_or_emailaddr._id
+
+ email = {
+ 'toaddr': toaddr,
+ 'fromaddr': u'"{}" <{}>'.format(
+ config['site_name'],
+ config['forgemail.return_path']
+ ),
+ 'sender': unicode(config['forgemail.return_path']),
+ 'reply_to': unicode(config['forgemail.return_path']),
+ 'message_id': h.gen_message_id(),
+ 'subject': subject,
+ 'text': text,
+ }
+ sendsimplemail.post(**email)
http://git-wip-us.apache.org/repos/asf/allura/blob/b8562071/Allura/allura/templates/mail/twofactor_disabled.md
----------------------------------------------------------------------
diff --git a/Allura/allura/templates/mail/twofactor_disabled.md b/Allura/allura/templates/mail/twofactor_disabled.md
new file mode 100644
index 0000000..3e4e619
--- /dev/null
+++ b/Allura/allura/templates/mail/twofactor_disabled.md
@@ -0,0 +1,26 @@
+{#
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements. See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership. The ASF licenses this file
+ to you under the Apache License, Version 2.0 (the
+ "License"); you may not use this file except in compliance
+ with the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing,
+ software distributed under the License is distributed on an
+ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ KIND, either express or implied. See the License for the
+ specific language governing permissions and limitations
+ under the License.
+-#}
+
+Hello {{ user.username }},
+
+You have recently disabled two-factor authentication on {{ config['site_name'] }}. :(
+
+{% block footer %}
+If you did not do this, please contact us immediately.
+{% endblock %}
http://git-wip-us.apache.org/repos/asf/allura/blob/b8562071/Allura/allura/templates/mail/twofactor_enabled.md
----------------------------------------------------------------------
diff --git a/Allura/allura/templates/mail/twofactor_enabled.md b/Allura/allura/templates/mail/twofactor_enabled.md
new file mode 100644
index 0000000..e2d0ca0
--- /dev/null
+++ b/Allura/allura/templates/mail/twofactor_enabled.md
@@ -0,0 +1,26 @@
+{#
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements. See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership. The ASF licenses this file
+ to you under the Apache License, Version 2.0 (the
+ "License"); you may not use this file except in compliance
+ with the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing,
+ software distributed under the License is distributed on an
+ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ KIND, either express or implied. See the License for the
+ specific language governing permissions and limitations
+ under the License.
+-#}
+
+Hello {{ user.username }},
+
+You have recently set up new two-factor authentication on {{ config['site_name'] }}. This is a confirmation email, you are all set.
+
+{% block footer %}
+If you did not do this, please contact us immediately.
+{% endblock %}
http://git-wip-us.apache.org/repos/asf/allura/blob/b8562071/Allura/allura/tests/functional/test_auth.py
----------------------------------------------------------------------
diff --git a/Allura/allura/tests/functional/test_auth.py b/Allura/allura/tests/functional/test_auth.py
index e203869..a50a13a 100644
--- a/Allura/allura/tests/functional/test_auth.py
+++ b/Allura/allura/tests/functional/test_auth.py
@@ -2072,6 +2072,11 @@ class TestTwoFactor(TestController):
assert_equal('Two factor authentication has now been set up.', json.loads(self.webflash(r))['message'],
self.webflash(r))
+ tasks = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendsimplemail')).all()
+ assert_equal(len(tasks), 1)
+ assert_equal(tasks[0].kwargs['subject'], 'Two-Factor Authentication Enabled')
+ assert_in('new two-factor authentication', tasks[0].kwargs['text'])
+
def test_reset_totp(self):
self._init_totp()
@@ -2137,6 +2142,12 @@ class TestTwoFactor(TestController):
assert_equal(user.get_pref('multifactor'), False)
assert_equal(TotpService().get().get_secret_key(user), None)
+ # email confirmation
+ tasks = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendsimplemail')).all()
+ assert_equal(len(tasks), 1)
+ assert_equal(tasks[0].kwargs['subject'], 'Two-Factor Authentication Disabled')
+ assert_in('disabled two-factor authentication', tasks[0].kwargs['text'])
+
def test_login_totp(self):
self._init_totp()
[3/4] allura git commit: [#8117] apply new mail helper to other
places, so they get nicer From address display
Posted by br...@apache.org.
[#8117] apply new mail helper to other places, so they get nicer From address display
Project: http://git-wip-us.apache.org/repos/asf/allura/repo
Commit: http://git-wip-us.apache.org/repos/asf/allura/commit/62aa90b9
Tree: http://git-wip-us.apache.org/repos/asf/allura/tree/62aa90b9
Diff: http://git-wip-us.apache.org/repos/asf/allura/diff/62aa90b9
Branch: refs/heads/db/8117
Commit: 62aa90b99a4ab21e4e0cdffb28e4500468b3fdde
Parents: b856207
Author: Dave Brondsema <da...@brondsema.net>
Authored: Thu Sep 1 10:30:45 2016 -0400
Committer: Dave Brondsema <da...@brondsema.net>
Committed: Thu Sep 1 10:54:05 2016 -0400
----------------------------------------------------------------------
Allura/allura/controllers/auth.py | 9 +--------
Allura/allura/model/auth.py | 10 +++-------
Allura/allura/tasks/export_tasks.py | 14 +++-----------
Allura/allura/tests/functional/test_auth.py | 3 ++-
Allura/allura/tests/functional/test_site_admin.py | 3 ++-
Allura/allura/tests/test_tasks.py | 2 +-
6 files changed, 12 insertions(+), 29 deletions(-)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/allura/blob/62aa90b9/Allura/allura/controllers/auth.py
----------------------------------------------------------------------
diff --git a/Allura/allura/controllers/auth.py b/Allura/allura/controllers/auth.py
index 42840d2..669f81f 100644
--- a/Allura/allura/controllers/auth.py
+++ b/Allura/allura/controllers/auth.py
@@ -214,14 +214,7 @@ class AuthController(BaseController):
config=config,
hash=hash,
))
-
- allura.tasks.mail_tasks.sendsimplemail.post(
- toaddr=email_record.email,
- fromaddr=config['forgemail.return_path'],
- reply_to=config['forgemail.return_path'],
- subject=subject,
- message_id=h.gen_message_id(),
- text=text)
+ send_system_mail_to_user(email_record.email, subject, text)
h.auditlog_user('Password recovery link sent to: %s', email, user=user_record)
flash(message)
redirect('/')
http://git-wip-us.apache.org/repos/asf/allura/blob/62aa90b9/Allura/allura/model/auth.py
----------------------------------------------------------------------
diff --git a/Allura/allura/model/auth.py b/Allura/allura/model/auth.py
index c1c8235..32b419a 100644
--- a/Allura/allura/model/auth.py
+++ b/Allura/allura/model/auth.py
@@ -188,13 +188,9 @@ class EmailAddress(MappedClass):
config=config
))
- allura.tasks.mail_tasks.sendsimplemail.post(
- toaddr=self.email,
- fromaddr=config['forgemail.return_path'],
- reply_to=config['forgemail.return_path'],
- subject=u'%s - Email address claim attempt' % config['site_name'],
- message_id=h.gen_message_id(),
- text=text)
+ allura.tasks.mail_tasks.send_system_mail_to_user(self.email,
+ u'%s - Email address claim attempt' % config['site_name'],
+ text)
def set_nonce_hash(self):
self.nonce = sha256(os.urandom(10)).hexdigest()
http://git-wip-us.apache.org/repos/asf/allura/blob/62aa90b9/Allura/allura/tasks/export_tasks.py
----------------------------------------------------------------------
diff --git a/Allura/allura/tasks/export_tasks.py b/Allura/allura/tasks/export_tasks.py
index 9e2d73e..87fcc8b 100644
--- a/Allura/allura/tasks/export_tasks.py
+++ b/Allura/allura/tasks/export_tasks.py
@@ -84,17 +84,9 @@ class BulkExport(object):
'not_exported_tools': list(set(tools) - set(exported_names)),
}
- email = {
- 'toaddr': unicode(user._id),
- 'fromaddr': unicode(tg.config['forgemail.return_path']),
- 'sender': unicode(tg.config['forgemail.return_path']),
- 'reply_to': unicode(tg.config['forgemail.return_path']),
- 'message_id': h.gen_message_id(),
- 'subject': u'Bulk export for project %s completed' % project.shortname,
- 'text': tmpl.render(tmpl_context)
- }
-
- mail_tasks.sendsimplemail.post(**email)
+ mail_tasks.send_system_mail_to_user(user,
+ u'Bulk export for project %s completed' % project.shortname,
+ tmpl.render(tmpl_context))
def get_export_path(self, export_base_path, export_filename):
"""Create temporary directory for export files"""
http://git-wip-us.apache.org/repos/asf/allura/blob/62aa90b9/Allura/allura/tests/functional/test_auth.py
----------------------------------------------------------------------
diff --git a/Allura/allura/tests/functional/test_auth.py b/Allura/allura/tests/functional/test_auth.py
index a50a13a..828d207 100644
--- a/Allura/allura/tests/functional/test_auth.py
+++ b/Allura/allura/tests/functional/test_auth.py
@@ -1368,8 +1368,9 @@ To reset your password on %s, please visit the following URL:
%s/auth/forgotten_password/%s''' % (config['site_name'], config['base_url'], hash)
sendmail.post.assert_called_once_with(
+ sender='noreply@localhost',
toaddr=email.email,
- fromaddr=config['forgemail.return_path'],
+ fromaddr=u'"{}" <{}>'.format(config['site_name'], config['forgemail.return_path']),
reply_to=config['forgemail.return_path'],
subject='Allura Password recovery',
message_id=gen_message_id(),
http://git-wip-us.apache.org/repos/asf/allura/blob/62aa90b9/Allura/allura/tests/functional/test_site_admin.py
----------------------------------------------------------------------
diff --git a/Allura/allura/tests/functional/test_site_admin.py b/Allura/allura/tests/functional/test_site_admin.py
index d4e96a0..64c2dbb 100644
--- a/Allura/allura/tests/functional/test_site_admin.py
+++ b/Allura/allura/tests/functional/test_site_admin.py
@@ -709,8 +709,9 @@ To reset your password on %s, please visit the following URL:
%s/auth/forgotten_password/%s''' % (config['site_name'], config['base_url'], hash)
sendmail.post.assert_called_once_with(
+ sender='noreply@localhost',
toaddr='test-user@example.org',
- fromaddr=config['forgemail.return_path'],
+ fromaddr=u'"{}" <{}>'.format(config['site_name'], config['forgemail.return_path']),
reply_to=config['forgemail.return_path'],
subject='Allura Password recovery',
message_id=gen_message_id(),
http://git-wip-us.apache.org/repos/asf/allura/blob/62aa90b9/Allura/allura/tests/test_tasks.py
----------------------------------------------------------------------
diff --git a/Allura/allura/tests/test_tasks.py b/Allura/allura/tests/test_tasks.py
index abf22c2..525e7e3 100644
--- a/Allura/allura/tests/test_tasks.py
+++ b/Allura/allura/tests/test_tasks.py
@@ -567,7 +567,7 @@ class TestExportTasks(unittest.TestCase):
assert_equal(len(tasks), 1)
assert_equal(tasks[0].kwargs['subject'],
'Bulk export for project test completed')
- assert_equal(tasks[0].kwargs['fromaddr'], g.noreply)
+ assert_equal(tasks[0].kwargs['fromaddr'], '"Allura" <no...@localhost>')
assert_equal(tasks[0].kwargs['reply_to'], g.noreply)
text = tasks[0].kwargs['text']
assert_in('The bulk export for project test is completed.', text)
[4/4] allura git commit: [#8117] option to send app links by email
Posted by br...@apache.org.
[#8117] option to send app links by email
Project: http://git-wip-us.apache.org/repos/asf/allura/repo
Commit: http://git-wip-us.apache.org/repos/asf/allura/commit/a8d19801
Tree: http://git-wip-us.apache.org/repos/asf/allura/tree/a8d19801
Diff: http://git-wip-us.apache.org/repos/asf/allura/diff/a8d19801
Branch: refs/heads/db/8117
Commit: a8d198013973e1e236c8ca9d76df9bd0e08e3884
Parents: 62aa90b
Author: Dave Brondsema <da...@brondsema.net>
Authored: Thu Sep 1 12:07:56 2016 -0400
Committer: Dave Brondsema <da...@brondsema.net>
Committed: Thu Sep 1 12:07:56 2016 -0400
----------------------------------------------------------------------
Allura/allura/controllers/auth.py | 9 +++++++
Allura/allura/templates/mail/twofactor_apps.md | 28 +++++++++++++++++++++
Allura/allura/templates/user_totp.html | 22 ++++++++++++++++
Allura/allura/tests/functional/test_auth.py | 13 ++++++++++
4 files changed, 72 insertions(+)
----------------------------------------------------------------------
http://git-wip-us.apache.org/repos/asf/allura/blob/a8d19801/Allura/allura/controllers/auth.py
----------------------------------------------------------------------
diff --git a/Allura/allura/controllers/auth.py b/Allura/allura/controllers/auth.py
index 669f81f..382f4b1 100644
--- a/Allura/allura/controllers/auth.py
+++ b/Allura/allura/controllers/auth.py
@@ -718,6 +718,15 @@ class PreferencesController(BaseController):
send_system_mail_to_user(c.user, u'Two-Factor Authentication Disabled', email_body)
redirect('.')
+ @expose()
+ @require_post()
+ def totp_send_link(self, **kw):
+ email_body = g.jinja2_env.get_template('allura:templates/mail/twofactor_apps.md').render(dict(
+ user=c.user,
+ config=config,
+ ))
+ send_system_mail_to_user(c.user, u'Two-Factor Authentication Apps', email_body)
+
class UserInfoController(BaseController):
http://git-wip-us.apache.org/repos/asf/allura/blob/a8d19801/Allura/allura/templates/mail/twofactor_apps.md
----------------------------------------------------------------------
diff --git a/Allura/allura/templates/mail/twofactor_apps.md b/Allura/allura/templates/mail/twofactor_apps.md
new file mode 100644
index 0000000..b5e80bd
--- /dev/null
+++ b/Allura/allura/templates/mail/twofactor_apps.md
@@ -0,0 +1,28 @@
+{#
+ Licensed to the Apache Software Foundation (ASF) under one
+ or more contributor license agreements. See the NOTICE file
+ distributed with this work for additional information
+ regarding copyright ownership. The ASF licenses this file
+ to you under the Apache License, Version 2.0 (the
+ "License"); you may not use this file except in compliance
+ with the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing,
+ software distributed under the License is distributed on an
+ "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ KIND, either express or implied. See the License for the
+ specific language governing permissions and limitations
+ under the License.
+-#}
+
+Hello,
+
+Here are links to install Google Authenticator, which you'll need to use for two-factor authentication:
+
+[Google Authenticator for Android](https://play.google.com/store/apps/details?id=com.google.android.apps.authenticator2)
+
+[Google Authenticator for iOS](https://itunes.apple.com/us/app/google-authenticator/id388497605)
+
+Other authenticator apps work too, like Duo Mobile, Authy, and more.
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/allura/blob/a8d19801/Allura/allura/templates/user_totp.html
----------------------------------------------------------------------
diff --git a/Allura/allura/templates/user_totp.html b/Allura/allura/templates/user_totp.html
index 241ff42..53bc928 100644
--- a/Allura/allura/templates/user_totp.html
+++ b/Allura/allura/templates/user_totp.html
@@ -31,13 +31,17 @@
<h3>Warning: this will invalidate your previous multifactor configuration.</h3>
{% endif %}
<h2>Install App</h2>
+ <form action="totp_send_link" id="totp_send_link" method="post">
<p>To use two-factor authentication, you will need to install an app on your phone.<br>
Install Google Authenticator for
<a href="https://play.google.com/store/apps/details?id=com.google.android.apps.authenticator2"><b>Android</b></a>
or <a href="https://itunes.apple.com/us/app/google-authenticator/id388497605"><b>iOS</b></a>.
+ <a href="#" class="ajax-submit-form">Email me these links.</a>
<br>
Or use another app like Duo Mobile, Authy, or Authenticator for Windows phones.
</p>
+ {{ lib.csrf_token() }}
+ </form>
{% endif %}
<h2>Scan this barcode with your app</h2>
@@ -84,4 +88,22 @@
margin: 6px 10px;
}
</style>
+{% endblock %}
+
+{% block extra_js %}
+<script type="text/javascript">
+$(function() {
+ $('a.ajax-submit-form').click(function(e){
+ e.preventDefault();
+ $form = $(this).closest('form');
+ $.post($form.attr('action'), $form.serialize())
+ .done(function() {
+ $('#messages').notify({message: 'Email sent!'});
+ })
+ .fail(function() {
+ $('#messages').notify({message: 'Error sending email', status: 'error'});
+ });
+ });
+});
+</script>
{% endblock %}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/allura/blob/a8d19801/Allura/allura/tests/functional/test_auth.py
----------------------------------------------------------------------
diff --git a/Allura/allura/tests/functional/test_auth.py b/Allura/allura/tests/functional/test_auth.py
index 828d207..0e0da43 100644
--- a/Allura/allura/tests/functional/test_auth.py
+++ b/Allura/allura/tests/functional/test_auth.py
@@ -2221,3 +2221,16 @@ class TestTwoFactor(TestController):
r.form['password'] = 'foo'
r = r.form.submit()
assert_in('Scan this barcode', r)
+
+ def test_send_links(self):
+ r = self.app.get('/auth/preferences/totp_new')
+ r.form['password'] = 'foo'
+ r = r.form.submit()
+
+ r = r.forms['totp_send_link'].submit()
+
+ tasks = M.MonQTask.query.find(dict(task_name='allura.tasks.mail_tasks.sendsimplemail')).all()
+ assert_equal(len(tasks), 1)
+ assert_equal(tasks[0].kwargs['subject'], 'Two-Factor Authentication Apps')
+ assert_in('itunes.apple.com', tasks[0].kwargs['text'])
+ assert_in('play.google.com', tasks[0].kwargs['text'])