Undid last commit
- Legacy-Id: 12792
This commit is contained in:
parent
15628c698f
commit
db1cc15f1f
|
@ -15,8 +15,7 @@
|
|||
"respond": "~1",
|
||||
"select2": "~3",
|
||||
"select2-bootstrap-css": "~1",
|
||||
"spin.js": "~2",
|
||||
"zxcvbn": "~4"
|
||||
"spin.js": "~2"
|
||||
},
|
||||
"devDependencies": {},
|
||||
"overrides": {
|
||||
|
|
|
@ -1,5 +1,4 @@
|
|||
import re
|
||||
from unidecode import unidecode
|
||||
|
||||
from django import forms
|
||||
from django.conf import settings
|
||||
|
@ -9,7 +8,7 @@ from django.contrib.auth.models import User
|
|||
from django.utils.html import mark_safe
|
||||
from django.core.urlresolvers import reverse as urlreverse
|
||||
|
||||
from django_password_strength.widgets import PasswordStrengthInput, PasswordConfirmationInput
|
||||
from unidecode import unidecode
|
||||
|
||||
import debug # pyflakes:ignore
|
||||
|
||||
|
@ -32,8 +31,8 @@ class RegistrationForm(forms.Form):
|
|||
|
||||
|
||||
class PasswordForm(forms.Form):
|
||||
password = forms.CharField(widget=PasswordStrengthInput)
|
||||
password_confirmation = forms.CharField(widget=PasswordConfirmationInput,
|
||||
password = forms.CharField(widget=forms.PasswordInput)
|
||||
password_confirmation = forms.CharField(widget=forms.PasswordInput,
|
||||
help_text="Enter the same password as above, for verification.")
|
||||
|
||||
def clean_password_confirmation(self):
|
||||
|
@ -167,28 +166,3 @@ class WhitelistForm(forms.ModelForm):
|
|||
exclude = ['by', 'time' ]
|
||||
|
||||
|
||||
from django import forms
|
||||
|
||||
|
||||
class ChangePasswordForm(forms.Form):
|
||||
current_password = forms.CharField(widget=forms.PasswordInput)
|
||||
|
||||
|
||||
new_password = forms.CharField(widget=PasswordStrengthInput)
|
||||
new_password_confirmation = forms.CharField(widget=PasswordConfirmationInput)
|
||||
|
||||
def __init__(self, user, data=None):
|
||||
self.user = user
|
||||
super(ChangePasswordForm, self).__init__(data)
|
||||
|
||||
def clean_current_password(self):
|
||||
password = self.cleaned_data.get('current_password', None)
|
||||
if not self.user.check_password(password):
|
||||
raise ValidationError('Invalid password')
|
||||
|
||||
def clean(self):
|
||||
new_password = self.cleaned_data.get('new_password', None)
|
||||
conf_password = self.cleaned_data.get('new_password_confirmation', None)
|
||||
if not new_password == conf_password:
|
||||
raise ValidationError("The password confirmation is different than the new password")
|
||||
|
||||
|
|
|
@ -3,20 +3,23 @@
|
|||
from django.conf.urls import url
|
||||
from django.contrib.auth.views import login, logout
|
||||
|
||||
from ietf.ietfauth import views
|
||||
from ietf.ietfauth.views import add_account_whitelist
|
||||
|
||||
urlpatterns = [
|
||||
url(r'^$', views.index),
|
||||
url(r'^confirmnewemail/(?P<auth>[^/]+)/$', views.confirm_new_email),
|
||||
url(r'^create/$', views.create_account),
|
||||
url(r'^create/confirm/(?P<auth>[^/]+)/$', views.confirm_account),
|
||||
url(r'^$', 'ietf.ietfauth.views.index'),
|
||||
# url(r'^login/$', 'ietf.ietfauth.views.ietf_login'),
|
||||
url(r'^login/$', login),
|
||||
url(r'^logout/$', logout),
|
||||
url(r'^password/$', views.change_password),
|
||||
url(r'^profile/$', views.profile),
|
||||
url(r'^reset/$', views.password_reset),
|
||||
url(r'^reset/confirm/(?P<auth>[^/]+)/$', views.confirm_password_reset),
|
||||
url(r'^review/$', views.review_overview),
|
||||
url(r'^testemail/$', views.test_email),
|
||||
url(r'whitelist/add/?$', views.add_account_whitelist),
|
||||
# url(r'^loggedin/$', 'ietf.ietfauth.views.ietf_loggedin'),
|
||||
# url(r'^loggedout/$', 'ietf.ietfauth.views.logged_out'),
|
||||
url(r'^profile/$', 'ietf.ietfauth.views.profile'),
|
||||
# (r'^login/(?P<user>[a-z0-9.@]+)/(?P<passwd>.+)$', 'ietf.ietfauth.views.url_login'),
|
||||
url(r'^testemail/$', 'ietf.ietfauth.views.test_email'),
|
||||
url(r'^create/$', 'ietf.ietfauth.views.create_account'),
|
||||
url(r'^create/confirm/(?P<auth>[^/]+)/$', 'ietf.ietfauth.views.confirm_account'),
|
||||
url(r'^reset/$', 'ietf.ietfauth.views.password_reset'),
|
||||
url(r'^reset/confirm/(?P<auth>[^/]+)/$', 'ietf.ietfauth.views.confirm_password_reset'),
|
||||
url(r'^confirmnewemail/(?P<auth>[^/]+)/$', 'ietf.ietfauth.views.confirm_new_email'),
|
||||
url(r'whitelist/add/?$', add_account_whitelist),
|
||||
url(r'^review/$', 'ietf.ietfauth.views.review_overview'),
|
||||
]
|
||||
|
|
|
@ -32,27 +32,24 @@
|
|||
|
||||
# Copyright The IETF Trust 2007, All Rights Reserved
|
||||
|
||||
import importlib
|
||||
|
||||
from datetime import datetime as DateTime, timedelta as TimeDelta, date as Date
|
||||
from collections import defaultdict
|
||||
|
||||
import django.core.signing
|
||||
from django import forms
|
||||
from django.contrib import messages
|
||||
from django.conf import settings
|
||||
from django.contrib.auth import update_session_auth_hash
|
||||
from django.contrib.auth.decorators import login_required
|
||||
from django.contrib.auth.models import User
|
||||
from django.contrib.sites.models import Site
|
||||
from django.core.urlresolvers import reverse as urlreverse
|
||||
from django.http import Http404, HttpResponseRedirect #, HttpResponse,
|
||||
from django.http import Http404 #, HttpResponse, HttpResponseRedirect
|
||||
from django.shortcuts import render, redirect, get_object_or_404
|
||||
#from django.contrib.auth import REDIRECT_FIELD_NAME, authenticate, login
|
||||
from django.contrib.auth.decorators import login_required
|
||||
#from django.utils.http import urlquote
|
||||
import django.core.signing
|
||||
from django.contrib.sites.models import Site
|
||||
from django.contrib.auth.models import User
|
||||
from django import forms
|
||||
|
||||
import debug # pyflakes:ignore
|
||||
|
||||
from ietf.group.models import Role, Group
|
||||
from ietf.ietfauth.forms import RegistrationForm, PasswordForm, ResetPasswordForm, TestEmailForm, WhitelistForm, ChangePasswordForm
|
||||
from ietf.ietfauth.forms import RegistrationForm, PasswordForm, ResetPasswordForm, TestEmailForm, WhitelistForm
|
||||
from ietf.ietfauth.forms import get_person_form, RoleEmailForm, NewEmailForm
|
||||
from ietf.ietfauth.htpasswd import update_htpasswd_file
|
||||
from ietf.ietfauth.utils import role_required
|
||||
|
@ -468,46 +465,3 @@ def review_overview(request):
|
|||
'review_wishes': review_wishes,
|
||||
'review_wish_form': review_wish_form,
|
||||
})
|
||||
|
||||
@login_required
|
||||
def change_password(request):
|
||||
success = False
|
||||
person = None
|
||||
|
||||
try:
|
||||
person = request.user.person
|
||||
except Person.DoesNotExist:
|
||||
return render(request, 'registration/missing_person.html')
|
||||
|
||||
emails = Email.objects.filter(person=person, active=True).order_by('-primary','-time').first
|
||||
|
||||
if request.method == 'POST':
|
||||
user = request.user
|
||||
form = ChangePasswordForm(user, request.POST)
|
||||
if form.is_valid():
|
||||
new_password = form.cleaned_data["new_password"]
|
||||
|
||||
user.set_password(new_password)
|
||||
user.save()
|
||||
# password is also stored in htpasswd file
|
||||
update_htpasswd_file(user.username, new_password)
|
||||
# keep the session
|
||||
update_session_auth_hash(request, user)
|
||||
|
||||
messages.success(request, "Your password was successfully changed")
|
||||
return HttpResponseRedirect(urlreverse('ietf.ietfauth.views.profile'))
|
||||
|
||||
else:
|
||||
form = ChangePasswordForm(request.user)
|
||||
|
||||
hlibname, hashername = settings.PASSWORD_HASHERS[0].rsplit('.',1)
|
||||
|
||||
hlib = importlib.import_module(hlibname)
|
||||
hasher = getattr(hlib, hashername)
|
||||
return render(request, 'registration/change_password.html', {
|
||||
'form': form,
|
||||
'success': success,
|
||||
'hasher': hasher,
|
||||
})
|
||||
|
||||
|
||||
|
|
|
@ -32,7 +32,6 @@ from ietf.ipr.utils import (get_genitive, get_ipr_summary,
|
|||
iprs_from_docs, related_docs)
|
||||
from ietf.message.models import Message
|
||||
from ietf.message.utils import infer_message
|
||||
from ietf.name.models import IprLicenseTypeName
|
||||
from ietf.person.models import Person
|
||||
from ietf.secr.utils.document import get_rfc_num, is_draft
|
||||
from ietf.utils.draft_search import normalize_draftname
|
||||
|
@ -704,7 +703,6 @@ def get_details_tabs(ipr, selected):
|
|||
('History', urlreverse('ipr_history', kwargs={ 'id': ipr.pk }))
|
||||
]]
|
||||
|
||||
@debug.trace
|
||||
def show(request, id):
|
||||
"""View of individual declaration"""
|
||||
ipr = get_object_or_404(IprDisclosureBase, id=id).get_child()
|
||||
|
@ -719,7 +717,6 @@ def show(request, id):
|
|||
return render(request, "ipr/details_view.html", {
|
||||
'ipr': ipr,
|
||||
'tabs': get_details_tabs(ipr, 'Disclosure'),
|
||||
'choices_abc': [ i.desc for i in IprLicenseTypeName.objects.filter(slug__in=['no-license', 'royalty-free', 'reasonable', ]) ],
|
||||
'updates_iprs': ipr.relatedipr_source_set.all(),
|
||||
'updated_by_iprs': ipr.relatedipr_target_set.filter(source__state="posted")
|
||||
})
|
||||
|
|
|
@ -54,13 +54,6 @@ ADMINS = (
|
|||
('Ryan Cross', 'rcross@amsl.com'),
|
||||
)
|
||||
|
||||
PASSWORD_HASHERS = [
|
||||
'django.contrib.auth.hashers.BCryptSHA256PasswordHasher',
|
||||
'django.contrib.auth.hashers.PBKDF2PasswordHasher',
|
||||
'django.contrib.auth.hashers.SHA1PasswordHasher',
|
||||
'django.contrib.auth.hashers.CryptPasswordHasher',
|
||||
]
|
||||
|
||||
ALLOWED_HOSTS = [".ietf.org", ".ietf.org.", "209.208.19.216", "4.31.198.44", ]
|
||||
|
||||
|
||||
|
@ -303,12 +296,11 @@ INSTALLED_APPS = (
|
|||
'django.contrib.staticfiles',
|
||||
# External apps
|
||||
'bootstrap3',
|
||||
'django_markup',
|
||||
'django_password_strength',
|
||||
'djangobwr',
|
||||
'form_utils',
|
||||
'tastypie',
|
||||
'widget_tweaks',
|
||||
'django_markup',
|
||||
# IETF apps
|
||||
'ietf.api',
|
||||
'ietf.community',
|
||||
|
@ -790,6 +782,7 @@ SILENCED_SYSTEM_CHECKS = [
|
|||
"fields.W342", # Setting unique=True on a ForeignKey has the same effect as using a OneToOneField.
|
||||
]
|
||||
|
||||
|
||||
# Put the production SECRET_KEY in settings_local.py, and also any other
|
||||
# sensitive or site-specific changes. DO NOT commit settings_local.py to svn.
|
||||
from settings_local import * # pyflakes:ignore pylint: disable=wildcard-import
|
||||
|
|
|
@ -1,130 +0,0 @@
|
|||
// Taken from django-password-strength, with changes to use the bower-managed zxcvbn.js The
|
||||
// bower-managed zxcvbn.js is kept up-to-date to a larger extent than the copy packaged with
|
||||
// the django-password-strength component.
|
||||
(function($, window, document, undefined){
|
||||
window.djangoPasswordStrength = {
|
||||
config: {
|
||||
passwordClass: 'password_strength',
|
||||
confirmationClass: 'password_confirmation'
|
||||
},
|
||||
|
||||
init: function (config) {
|
||||
var self = this;
|
||||
// Setup configuration
|
||||
if ($.isPlainObject(config)) {
|
||||
$.extend(self.config, config);
|
||||
}
|
||||
|
||||
self.initListeners();
|
||||
},
|
||||
|
||||
initListeners: function() {
|
||||
var self = this;
|
||||
var body = $('body');
|
||||
|
||||
$('.' + self.config.passwordClass).on('keyup', function() {
|
||||
var password_strength_bar = $(this).parent().find('.password_strength_bar');
|
||||
var password_strength_info = $(this).parent().find('.password_strength_info');
|
||||
|
||||
if( $(this).val() ) {
|
||||
var result = zxcvbn( $(this).val() );
|
||||
|
||||
if( result.score < 3 ) {
|
||||
password_strength_bar.removeClass('progress-bar-success').addClass('progress-bar-warning');
|
||||
password_strength_info.find('.label').removeClass('hidden');
|
||||
} else {
|
||||
password_strength_bar.removeClass('progress-bar-warning').addClass('progress-bar-success');
|
||||
password_strength_info.find('.label').addClass('hidden');
|
||||
}
|
||||
|
||||
password_strength_bar.width( ((result.score+1)/5)*100 + '%' ).attr('aria-valuenow', result.score + 1);
|
||||
// henrik@levkowetz.com -- this is the only changed line:
|
||||
password_strength_info.find('.password_strength_time').html(result.crack_times_display.online_no_throttling_10_per_second);
|
||||
password_strength_info.removeClass('hidden');
|
||||
} else {
|
||||
password_strength_bar.removeClass('progress-bar-success').addClass('progress-bar-warning');
|
||||
password_strength_bar.width( '0%' ).attr('aria-valuenow', 0);
|
||||
password_strength_info.addClass('hidden');
|
||||
}
|
||||
self.match_passwords($(this));
|
||||
});
|
||||
|
||||
var timer = null;
|
||||
$('.' + self.config.confirmationClass).on('keyup', function() {
|
||||
var password_field;
|
||||
var confirm_with = $(this).data('confirm-with');
|
||||
|
||||
if( confirm_with ) {
|
||||
password_field = $('#' + confirm_with);
|
||||
} else {
|
||||
password_field = $('.' + self.config.passwordClass);
|
||||
}
|
||||
|
||||
if (timer !== null) clearTimeout(timer);
|
||||
|
||||
timer = setTimeout(function(){
|
||||
self.match_passwords(password_field);
|
||||
}, 400);
|
||||
});
|
||||
},
|
||||
|
||||
display_time: function(seconds) {
|
||||
var minute = 60;
|
||||
var hour = minute * 60;
|
||||
var day = hour * 24;
|
||||
var month = day * 31;
|
||||
var year = month * 12;
|
||||
var century = year * 100;
|
||||
|
||||
// Provide fake gettext for when it is not available
|
||||
if( typeof gettext !== 'function' ) { gettext = function(text) { return text; }; };
|
||||
|
||||
if( seconds < minute ) return gettext('only an instant');
|
||||
if( seconds < hour) return (1 + Math.ceil(seconds / minute)) + ' ' + gettext('minutes');
|
||||
if( seconds < day) return (1 + Math.ceil(seconds / hour)) + ' ' + gettext('hours');
|
||||
if( seconds < month) return (1 + Math.ceil(seconds / day)) + ' ' + gettext('days');
|
||||
if( seconds < year) return (1 + Math.ceil(seconds / month)) + ' ' + gettext('months');
|
||||
if( seconds < century) return (1 + Math.ceil(seconds / year)) + ' ' + gettext('years');
|
||||
|
||||
return gettext('centuries');
|
||||
},
|
||||
|
||||
match_passwords: function(password_field, confirmation_fields) {
|
||||
var self = this;
|
||||
// Optional parameter: if no specific confirmation field is given, check all
|
||||
if( confirmation_fields === undefined ) { confirmation_fields = $('.' + self.config.confirmationClass) }
|
||||
if( confirmation_fields === undefined ) { return; }
|
||||
|
||||
var password = password_field.val();
|
||||
|
||||
confirmation_fields.each(function(index, confirm_field) {
|
||||
var confirm_value = $(confirm_field).val();
|
||||
var confirm_with = $(confirm_field).data('confirm-with');
|
||||
|
||||
if( confirm_with && confirm_with == password_field.attr('id')) {
|
||||
if( confirm_value && password ) {
|
||||
if (confirm_value === password) {
|
||||
$(confirm_field).parent().find('.password_strength_info').addClass('hidden');
|
||||
} else {
|
||||
$(confirm_field).parent().find('.password_strength_info').removeClass('hidden');
|
||||
}
|
||||
} else {
|
||||
$(confirm_field).parent().find('.password_strength_info').addClass('hidden');
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
// If a password field other than our own has been used, add the listener here
|
||||
if( !password_field.hasClass(self.config.passwordClass) && !password_field.data('password-listener') ) {
|
||||
password_field.on('keyup', function() {
|
||||
self.match_passwords($(this));
|
||||
});
|
||||
password_field.data('password-listener', true);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
// Call the init for backwards compatibility
|
||||
djangoPasswordStrength.init();
|
||||
|
||||
})(jQuery, window, document);
|
|
@ -16,16 +16,14 @@
|
|||
{% else %}
|
||||
{% if user.is_authenticated %}
|
||||
<li><a rel="nofollow" href="/accounts/logout/" >Sign out</a></li>
|
||||
<li><a rel="nofollow" href="/accounts/profile/">Account info</a></li>
|
||||
<li><a rel="nofollow" href="/accounts/profile/">Edit profile</a></li>
|
||||
{% else %}
|
||||
<li><a rel="nofollow" href="/accounts/login/?next={{request.get_full_path|urlencode}}">Sign in</a></li>
|
||||
<li><a rel="nofollow" href="/accounts/reset/">Password reset</a></li>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
|
||||
{% if not request.user.is_authenticated %}
|
||||
<li><a href="{% url "ietf.ietfauth.views.create_account" %}">New account</a></li>
|
||||
{% endif %}
|
||||
<li><a href="{% url "ietf.ietfauth.views.create_account" %}">{% if request.user.is_authenticated %}Manage account{% else %}New account{% endif %}</a></li>
|
||||
<li><a href="{%url "ietf.cookies.views.preferences" %}" rel="nofollow">Preferences</a></li>
|
||||
|
||||
{% if user|has_role:"Reviewer" %}
|
||||
|
|
|
@ -200,19 +200,9 @@
|
|||
specification, is as follows(select one licensing declaration option only):
|
||||
</p>
|
||||
|
||||
{% if ipr.licensing.slug == "provided-later" %}
|
||||
<div>
|
||||
Possible licencing choices a), b), and c) when Licencing Declaration to be Provided Later:
|
||||
<ul style="list-style: none">
|
||||
{% for desc in choices_abc %}
|
||||
<li>{{ desc}}</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</p>
|
||||
{% endif %}
|
||||
<dl class="dl-horizontal">
|
||||
<dt>Licensing</dt>
|
||||
<dd>{% if ipr.licensing.slug == "provided-later" %}{{ ipr.licensing.desc|slice:"2:"|slice:":117" }}){% else %}{{ ipr.licensing.desc|slice:"2:" }}{% endif %}</dd>
|
||||
<dd>{% if ipr.licensing.slug == "later" %}{{ ipr.licensing.desc|slice:"2:"|slice:":43" }}{% else %}{{ ipr.licensing.desc|slice:"2:" }}{% endif %}</dd>
|
||||
|
||||
<dt>Licensing information, comments, notes, or URL for further information</dt>
|
||||
<dd>{{ ipr.licensing_comments|default:"(No information submitted)"|linebreaks }}</dd>
|
||||
|
|
|
@ -3,56 +3,30 @@
|
|||
{% load origin %}
|
||||
|
||||
{% load bootstrap3 %}
|
||||
{% load staticfiles %}
|
||||
|
||||
{% block title %}Account creation{% endblock %}
|
||||
|
||||
{% block js %}
|
||||
{{ block.super }}
|
||||
<script type="text/javascript" src="{% static 'zxcvbn/zxcvbn.js' %}"></script>
|
||||
<script type="text/javascript" src="{% static 'ietf/js/password_strength.js' %}"></script>
|
||||
{% endblock %}
|
||||
{% block title %}Change password{% endblock %}
|
||||
|
||||
{% block content %}
|
||||
{% origin %}
|
||||
|
||||
{% if success %}
|
||||
<h1>Your password was successfully changed.</h1>
|
||||
<h1>Password change successful</h1>
|
||||
|
||||
<p>Your password has been updated.</p>
|
||||
<a type="a" class="btn btn-primary" href="/accounts/login/" rel="nofollow">Sign in</a>
|
||||
|
||||
{% else %}
|
||||
<div class="row">
|
||||
<div class="col-md-2 col-sm-0"></div>
|
||||
<div class="col-md-8 col-sm-12">
|
||||
<h1>Change password</h1>
|
||||
<h1>Change password</h1>
|
||||
|
||||
<form method="post">
|
||||
{% csrf_token %}
|
||||
{% bootstrap_form form %}
|
||||
<p>You can change the password below for your user {{ username }} below.</p>
|
||||
<form method="post">
|
||||
{% csrf_token %}
|
||||
{% bootstrap_form form %}
|
||||
|
||||
{% buttons %}
|
||||
<button type="submit" class="btn btn-primary">Change password</button>
|
||||
{% endbuttons %}
|
||||
</form>
|
||||
|
||||
<div class="help-block">
|
||||
This password change form uses the
|
||||
<a href="https://blogs.dropbox.com/tech/2012/04/zxcvbn-realistic-password-strength-estimation/">zxcvbn</a>
|
||||
password strength estimator to give an indication of password strength.
|
||||
The crack times given assume online attack without rate limiting,
|
||||
at a rate of 10 attempts per second.
|
||||
</div>
|
||||
|
||||
<div class="help-block">
|
||||
The datatracker currently uses a <b>{{ hasher.algorithm }}</b>-based
|
||||
password hasher with
|
||||
<b>{% if hasher.iterations %}{{ hasher.iterations }} iterations{% else %}{{ hasher.rounds }} rounds{% endif %}</b>.
|
||||
Calculating offline attack time if password hashes wouldleak is left
|
||||
as an excercise for the reader.
|
||||
</div>
|
||||
|
||||
</div>
|
||||
<div class="col-md-2 col-sm-0"></div>
|
||||
</div>
|
||||
{% buttons %}
|
||||
<button type="submit" class="btn btn-primary">Change password</button>
|
||||
{% endbuttons %}
|
||||
</form>
|
||||
|
||||
{% endif %}
|
||||
{% endblock %}
|
||||
|
|
|
@ -18,9 +18,22 @@
|
|||
|
||||
{% else %}
|
||||
<div class="row">
|
||||
<div class="col-md-2 col-sm-0"></div>
|
||||
<div class="col-md-8 col-sm-12">
|
||||
<div class="col-md-6">
|
||||
<h1>Account creation</h1>
|
||||
<p>Please enter your email address in order to create a new datatracker account.</p>
|
||||
<form method="post">
|
||||
{% csrf_token %}
|
||||
{% bootstrap_form form %}
|
||||
|
||||
{% buttons %}
|
||||
<button type="submit" class="btn btn-primary">Create account</button>
|
||||
{% endbuttons %}
|
||||
</form>
|
||||
</div>
|
||||
|
||||
<div class="col-md-6">
|
||||
<h1>Other options</h1>
|
||||
|
||||
<p>
|
||||
<b>If you already have an account and want to use a new email address,</b>
|
||||
please go to your account profile page and
|
||||
|
@ -36,20 +49,7 @@
|
|||
<p>
|
||||
<a class="btn btn-warning" href="{% url "ietf.ietfauth.views.password_reset" %}">Reset your password</a>
|
||||
</p>
|
||||
|
||||
<hr>
|
||||
|
||||
<p>Please enter your email address in order to create your datatracker account.</p>
|
||||
<form method="post">
|
||||
{% csrf_token %}
|
||||
{% bootstrap_form form %}
|
||||
|
||||
{% buttons %}
|
||||
<button type="submit" class="btn btn-primary">Create account</button>
|
||||
{% endbuttons %}
|
||||
</form>
|
||||
</div>
|
||||
<div class="col-md-2 col-sm-0"></div>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% endblock %}
|
||||
|
|
|
@ -22,13 +22,6 @@
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<label class="col-sm-2 control-label">Password</label>
|
||||
<div class="col-sm-10">
|
||||
<p class="form-control-static"><a href="{% url 'ietf.ietfauth.views.change_password' %}">Password change form</a></p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="form-group">
|
||||
<label class="col-sm-2 control-label">Email addresses</label>
|
||||
<div class="col-sm-10">
|
||||
|
|
|
@ -8,27 +8,24 @@
|
|||
|
||||
{% block content %}
|
||||
{% origin %}
|
||||
<div class="col-md-2 col-sm-0"></div>
|
||||
<div class="col-md-8 col-sm-12">
|
||||
<h1>Sign in</h1>
|
||||
<h1>Sign in</h1>
|
||||
|
||||
<form method="post">
|
||||
{% csrf_token %}
|
||||
{% bootstrap_form form %}
|
||||
<form method="post">
|
||||
{% csrf_token %}
|
||||
{% bootstrap_form form %}
|
||||
|
||||
{% buttons %}
|
||||
<table class="col-md-12">
|
||||
<tr>
|
||||
<td >
|
||||
<button type="submit" class="btn btn-primary">Sign in</button>
|
||||
</td>
|
||||
<td >
|
||||
Forgot your password? <a href="{% url 'ietf.ietfauth.views.password_reset' %}">Request a reset</a>.
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
{% endbuttons %}
|
||||
</form>
|
||||
|
||||
{% buttons %}
|
||||
<table class="col-md-12">
|
||||
<tr>
|
||||
<td >
|
||||
<button type="submit" class="btn btn-primary">Sign in</button>
|
||||
</td>
|
||||
<td >
|
||||
Forgot your password? <a href="{% url 'ietf.ietfauth.views.password_reset' %}">Request a reset</a>.
|
||||
</td>
|
||||
</tr>
|
||||
</table>
|
||||
{% endbuttons %}
|
||||
</form>
|
||||
</div>
|
||||
<div class="col-md-2 col-sm-0"></div>
|
||||
{% endblock %}
|
||||
|
|
|
@ -8,11 +8,9 @@ coverage>=4.0.1,!=4.0.2
|
|||
decorator>=3.4.0
|
||||
defusedxml>=0.4.1 # for TastyPie when ussing xml; not a declared dependency
|
||||
Django>=1.9,<1.10
|
||||
django-bcrypt>=0.9.2
|
||||
django-bootstrap3>=7.0
|
||||
django-formtools>=1.0 # instead of django.contrib.formtools in 1.8
|
||||
django-markup>=1.1
|
||||
django-password-strength>=1.2.1
|
||||
django-tastypie>=0.13.1
|
||||
django-widget-tweaks>=1.3
|
||||
docutils>=0.12
|
||||
|
@ -45,4 +43,3 @@ Unidecode>=0.4.18
|
|||
#wsgiref>=0.1.2
|
||||
xml2rfc>=2.5.
|
||||
xym>=0.1.2,!=0.3
|
||||
zxcvbn-python>=4.4.14
|
||||
|
|
Loading…
Reference in a new issue