Skip to content
This repository was archived by the owner on Aug 29, 2023. It is now read-only.

Commit 7d415ef

Browse files
committed
feat: add user creation and editing
1 parent ccb5192 commit 7d415ef

8 files changed

Lines changed: 301 additions & 13 deletions

File tree

br/templates/backend/_layout.html

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -34,7 +34,7 @@ <h4>Rapid<strong>SMS</strong></h4>
3434
{% if perms.ipd.change_report %}<li><a class="dropdown-item" href="{% url 'mnchw:campaign_list' %}">MNCHW campaigns</a></li>{% endif %}
3535
<div class="dropdown-divider"></div>
3636
{% if perms.auth.change_user %}
37-
<li><a href="{% url 'users:user_list' %}" class="dropdown-item">Users</a></li>
37+
<li><a href="{% url 'users:users_list' %}" class="dropdown-item">Users</a></li>
3838
<div class="dropdown-divider"></div>
3939
{% endif %}
4040
<li><a class="dropdown-item" href="{% url 'messaging:message_list' %}">Messages</a></li>
Lines changed: 124 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
{% extends 'backend/_layout.html' %}
2+
{% block content %}
3+
<div class="row">
4+
<div class="col">
5+
<div class="d-flex justify-content-between flex-wrap flex-md-nowrap align-items-center pt-1 pb-1 mb-1 border-bottom">
6+
<h3>{{ page_title }}</h3>
7+
</div>
8+
</div>
9+
</div>
10+
<div class="row">
11+
<div class="col-sm-10 offset-sm-1 col-md-8 offset-md-2 py-3">
12+
<form method="post">
13+
{% csrf_token %}
14+
<div class="card">
15+
<div class="card-body">
16+
<div class="row mb-3">
17+
<label for="{{ form.username.id_for_label }}" class="col-sm-4 col-form-label">Username</label>
18+
<div class="col-sm-8">
19+
<input type="text" class="form-control" name="{{ form.username.name }}" id="{{ form.username.id_for_label }}">
20+
</div>
21+
</div>
22+
<div class="row mb-3">
23+
<label for="{{ form.email.id_for_label }}" class="col-sm-4 col-form-label">Email</label>
24+
<div class="col-sm-8">
25+
<input type="email" class="form-control" name="{{ form.email.name }}" id="{{ form.email.id_for_label }}">
26+
</div>
27+
</div>
28+
<div class="row mb-3">
29+
<label for="{{ form.first_name.id_for_label }}" class="col-sm-4 col-form-label">First name</label>
30+
<div class="col-sm-8">
31+
<input type="text" class="form-control" name="{{ form.first_name.name }}" id="{{ form.first_name.id_for_label }}">
32+
</div>
33+
</div>
34+
<div class="row mb-3">
35+
<label for="{{ form.password_confirm.id_for_label }}" class="col-sm-4 col-form-label">Surname</label>
36+
<div class="col-sm-8">
37+
<input type="text" class="form-control" name="{{ form.last_name.name }}" id="{{ form.last_name.id_for_label }}">
38+
</div>
39+
</div>
40+
<div class="row mb-3">
41+
<label for="{{ form.password.id_for_label }}" class="col-sm-4 col-form-label">Password</label>
42+
<div class="col-sm-8">
43+
<input type="password" class="form-control" name="{{ form.password.name }}" id="{{ form.password.id_for_label }}">
44+
<p class="form-text">Enter a new password to change the current password</p>
45+
</div>
46+
</div>
47+
<div class="row mb-3">
48+
<label for="{{ form.password_confirm.id_for_label }}" class="col-sm-4 col-form-label">Confirm password</label>
49+
<div class="col-sm-8">
50+
<input type="password" class="form-control" name="{{ form.password_confirm.name }}" id="{{ form.password_confirm.id_for_label }}">
51+
<p class="form-text">Repeat the password entered above</p>
52+
</div>
53+
</div>
54+
<div class="row mb-3">
55+
<div class="col-sm-8 offset-sm-4">
56+
<div class="form-check">
57+
<input type="checkbox" name="{{ form.is_active.name }}" id="{{ form.is_active.id_for_label }}" class="form-check-input">
58+
<label for="{{ form.is_active.id_for_label }}" class="form-check-label">Active?</label>
59+
<p class="form-text">An inactive user will not be able to use the system.</p>
60+
</div>
61+
</div>
62+
</div>
63+
<fieldset>
64+
<legend>Permissions</legend>
65+
<div class="row mb-3">
66+
<div class="col-sm-8 offset-sm-4">
67+
<div class="form-check">
68+
<input type="checkbox" name="{{ form.can_add_locations.name }}" id="{{ form.can_add_locations.id_for_label }}" class="form-check-input">
69+
<label for="{{ form.can_add_locations.id_for_label }}" class="form-check-label">Can manage BR centres</label>
70+
</div>
71+
</div>
72+
</div>
73+
<div class="row mb-3">
74+
<div class="col-sm-8 offset-sm-4">
75+
<div class="form-check">
76+
<input type="checkbox" name="{{ form.can_change_br_reports.name }}" id="{{ form.can_change_br_reports.id_for_label }}" class="form-check-input">
77+
<label for="{{ form.can_change_br_reports.id_for_label }}" class="form-check-label">Can manage BR reports</label>
78+
</div>
79+
</div>
80+
</div>
81+
<div class="row mb-3">
82+
<div class="col-sm-8 offset-sm-4">
83+
<div class="form-check">
84+
<input type="checkbox" name="{{ form.can_change_dr_reports.name }}" id="{{ form.can_change_dr_reports.id_for_label }}" class="form-check-input">
85+
<label for="{{ form.can_change_dr_reports.id_for_label }}" class="form-check-label">Can manage DR reports</label>
86+
</div>
87+
</div>
88+
</div>
89+
<div class="row mb-3">
90+
<div class="col-sm-8 offset-sm-4">
91+
<div class="form-check">
92+
<input type="checkbox" name="{{ form.can_change_mnchw_reports.name }}" id="{{ form.can_change_mnchw_reports.id_for_label }}" class="form-check-input">
93+
<label for="{{ form.can_change_mnchw_reports.id_for_label }}" class="form-check-label">Can manage MNCHW reports</label>
94+
</div>
95+
</div>
96+
</div>
97+
<div class="row mb-3">
98+
<div class="col-sm-8 offset-sm-4">
99+
<div class="form-check">
100+
<input type="checkbox" name="{{ form.can_change_reporters.name }}" id="{{ form.can_change_reporters.id_for_label }}" class="form-check-input">
101+
<label for="{{ form.can_change_reporters.id_for_label }}" class="form-check-label">Can manage users</label>
102+
</div>
103+
</div>
104+
</div>
105+
<div class="row mb-3">
106+
<div class="col-sm-8 offset-sm-4">
107+
<div class="form-check">
108+
<input type="checkbox" name="{{ form.is_superuser.name }}" id="{{ form.is_superuser.id_for_label }}" class="form-check-input">
109+
<label for="{{ form.is_superuser.id_for_label }}" class="form-check-label">Superuser?</label>
110+
<p class="form-text">A superuser has access to everything without needing specific access to anything. <span class="text-danger">Use with caution.</span></p>
111+
</div>
112+
</div>
113+
</div>
114+
</fieldset>
115+
</div>
116+
<div class="card-footer">
117+
<button type="submit" class="btn btn-primary">Save Changes</button>
118+
<a href="{% url 'users:users_list' %}" class="btn btn-secondary">Cancel</a>
119+
</div>
120+
</div>
121+
</form>
122+
</div>
123+
</div>
124+
{% endblock content %}

br/templates/backend/user_edit.html

Lines changed: 77 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -32,11 +32,86 @@ <h3>{{ page_title }}</h3>
3232
</div>
3333
</div>
3434
<div class="row mb-3">
35-
<label for="{{ form.last_name.id_for_label }}" class="col-sm-4 col-form-label">Surname</label>
35+
<label for="{{ form.password_confirm.id_for_label }}" class="col-sm-4 col-form-label">Surname</label>
3636
<div class="col-sm-8">
37-
<input type="number" class="form-control" name="{{ form.last_name.name }}" id="{{ form.last_name.id_for_label }}" value="{{ form.last_name.value }}">
37+
<input type="text" class="form-control" name="{{ form.last_name.name }}" id="{{ form.last_name.id_for_label }}" value="{{ form.last_name.value }}">
3838
</div>
3939
</div>
40+
<div class="row mb-3">
41+
<label for="{{ form.password.id_for_label }}" class="col-sm-4 col-form-label">Password</label>
42+
<div class="col-sm-8">
43+
<input type="password" class="form-control" name="{{ form.password.name }}" id="{{ form.password.id_for_label }}">
44+
<p class="form-text">Enter a new password to change the current password</p>
45+
</div>
46+
</div>
47+
<div class="row mb-3">
48+
<label for="{{ form.password_confirm.id_for_label }}" class="col-sm-4 col-form-label">Confirm password</label>
49+
<div class="col-sm-8">
50+
<input type="password" class="form-control" name="{{ form.password_confirm.name }}" id="{{ form.password_confirm.id_for_label }}">
51+
<p class="form-text">Repeat the password entered above</p>
52+
</div>
53+
</div>
54+
<div class="row mb-3">
55+
<div class="col-sm-8 offset-sm-4">
56+
<div class="form-check">
57+
<input type="checkbox" name="{{ form.is_active.name }}" id="{{ form.is_active.id_for_label }}" class="form-check-input" {% if form.is_active.value %}checked{% endif %}>
58+
<label for="{{ form.is_active.id_for_label }}" class="form-check-label">Active?</label>
59+
<p class="form-text">An inactive user will not be able to use the system.</p>
60+
</div>
61+
</div>
62+
</div>
63+
<fieldset>
64+
<legend>Permissions</legend>
65+
<div class="row mb-3">
66+
<div class="col-sm-8 offset-sm-4">
67+
<div class="form-check">
68+
<input type="checkbox" name="{{ form.can_add_locations.name }}" id="{{ form.can_add_locations.id_for_label }}" class="form-check-input" {% if form.can_add_locations.value %}checked{% endif %}>
69+
<label for="{{ form.can_add_locations.id_for_label }}" class="form-check-label">Can manage BR centres</label>
70+
</div>
71+
</div>
72+
</div>
73+
<div class="row mb-3">
74+
<div class="col-sm-8 offset-sm-4">
75+
<div class="form-check">
76+
<input type="checkbox" name="{{ form.can_change_br_reports.name }}" id="{{ form.can_change_br_reports.id_for_label }}" class="form-check-input" {% if form.can_change_br_reports.value %}checked{% endif %}>
77+
<label for="{{ form.can_change_br_reports.id_for_label }}" class="form-check-label">Can manage BR reports</label>
78+
</div>
79+
</div>
80+
</div>
81+
<div class="row mb-3">
82+
<div class="col-sm-8 offset-sm-4">
83+
<div class="form-check">
84+
<input type="checkbox" name="{{ form.can_change_dr_reports.name }}" id="{{ form.can_change_dr_reports.id_for_label }}" class="form-check-input" {% if form.can_change_dr_reports.value %}checked{% endif %}>
85+
<label for="{{ form.can_change_dr_reports.id_for_label }}" class="form-check-label">Can manage DR reports</label>
86+
</div>
87+
</div>
88+
</div>
89+
<div class="row mb-3">
90+
<div class="col-sm-8 offset-sm-4">
91+
<div class="form-check">
92+
<input type="checkbox" name="{{ form.can_change_mnchw_reports.name }}" id="{{ form.can_change_mnchw_reports.id_for_label }}" class="form-check-input" {% if form.can_change_mnchw_reports.value %}checked{% endif %}>
93+
<label for="{{ form.can_change_mnchw_reports.id_for_label }}" class="form-check-label">Can manage MNCHW reports</label>
94+
</div>
95+
</div>
96+
</div>
97+
<div class="row mb-3">
98+
<div class="col-sm-8 offset-sm-4">
99+
<div class="form-check">
100+
<input type="checkbox" name="{{ form.can_change_reporters.name }}" id="{{ form.can_change_reporters.id_for_label }}" class="form-check-input" {% if form.can_change_reporters.value %}checked{% endif %}>
101+
<label for="{{ form.can_change_reporters.id_for_label }}" class="form-check-label">Can manage users</label>
102+
</div>
103+
</div>
104+
</div>
105+
<div class="row mb-3">
106+
<div class="col-sm-8 offset-sm-4">
107+
<div class="form-check">
108+
<input type="checkbox" name="{{ form.is_superuser.name }}" id="{{ form.is_superuser.id_for_label }}" class="form-check-input" {% if form.is_superuser.value %}checked{% endif %}>
109+
<label for="{{ form.is_superuser.id_for_label }}" class="form-check-label">Superuser?</label>
110+
<p class="form-text">A superuser has access to everything without needing specific access to anything. <span class="text-danger">Use with caution.</span></p>
111+
</div>
112+
</div>
113+
</div>
114+
</fieldset>
40115
</div>
41116
<div class="card-footer">
42117
<button type="submit" class="btn btn-primary">Save Changes</button>

br/templates/backend/user_list.html

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ <h3>{{ page_title }}</h3>
1414
<div class="card-body">
1515
<div class="row g-3">
1616
<div class="col">
17-
<a href="#" class="btn btn-success mt-3">
17+
<a href="{% url 'users:user_create' %}" class="btn btn-success mt-3">
1818
<svg xmlns="http://www.w3.org/2000/svg" class="h-5 w-5" viewBox="0 0 20 20" fill="currentColor" width="20" height="20">
1919
<path fill-rule="evenodd" d="M10 3a1 1 0 011 1v5h5a1 1 0 110 2h-5v5a1 1 0 11-2 0v-5H4a1 1 0 110-2h5V4a1 1 0 011-1z" clip-rule="evenodd" />
2020
</svg>
@@ -45,7 +45,7 @@ <h3>{{ page_title }}</h3>
4545
{% for user in users %}
4646
<tr>
4747
<td>
48-
<a href="">
48+
<a href="{% url 'users:user_edit' pk=user.pk %}">
4949
<svg xmlns="http://www.w3.org/2000/svg" class="h-5 w-5" viewBox="0 0 20 20" fill="currentColor" width="20" height="20">
5050
<title>Edit this user</title>
5151
<path d="M13.586 3.586a2 2 0 112.828 2.828l-.793.793-2.828-2.828.793-.793zM11.379 5.793L3 14.172V17h2.828l8.38-8.379-2.83-2.828z" />

profiles/forms.py

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,12 +18,15 @@ class Meta:
1818

1919
class UserForm(forms.ModelForm):
2020
locations = forms.ModelMultipleChoiceField(
21-
queryset=Location.objects.filter(type__name=u'State'))
21+
queryset=Location.objects.filter(type__name=u'State'), required=False)
2222
can_add_locations = forms.BooleanField(required=False)
2323
can_change_br_reports = forms.BooleanField(required=False)
2424
can_change_dr_reports = forms.BooleanField(required=False)
2525
can_change_mnchw_reports = forms.BooleanField(required=False)
2626
can_change_reporters = forms.BooleanField(required=False)
27+
can_change_users = forms.BooleanField(required=False)
28+
password = forms.CharField(required=False, widget=forms.PasswordInput())
29+
password_confirm = forms.CharField(required=False, widget=forms.PasswordInput())
2730

2831
class Meta:
2932
model = User
@@ -52,7 +55,17 @@ def __init__(self, *args, **kwargs):
5255
initial_data['can_change_dr_reports'] = user.has_perm('dr.change_deathreport')
5356
initial_data['can_change_mnchw_reports'] = user.has_perm('ipd.change_report')
5457
initial_data['can_change_reporters'] = user.has_perm('reporters.change_reporter')
58+
initial_data['can_change_users'] = user.has_perm('auth.change_user')
5559

5660
kwargs['initial'] = initial_data
5761

5862
super(UserForm, self).__init__(*args, **kwargs)
63+
64+
def clean(self):
65+
cleaned_data = super(UserForm, self).clean()
66+
password = cleaned_data.get('password')
67+
password_confirm = cleaned_data.get('password_confirm')
68+
if password != password_confirm:
69+
self.add_error('password', 'Passwords do not match')
70+
71+
return cleaned_data

profiles/urls.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
11
# -*- coding: utf-8 -*-
22
from django.conf.urls import url
33

4-
from profiles.views import UserListView
4+
from profiles.views import UserCreateView, UserListView, UserUpdateView
55

66
urlpatterns = [
77
url(r'^$', UserListView.as_view(), name='users_list'),
8-
# url(r'^new/?$', UserCreateView.as_view(), name='user_create'),
9-
# url(r'^(?P<pk>\d+)/?$', UserUpdateView.as_view(), name='user_edit'),
8+
url(r'^new/?$', UserCreateView.as_view(), name='user_create'),
9+
url(r'^(?P<pk>\d+)/?$', UserUpdateView.as_view(), name='user_edit'),
1010
]

0 commit comments

Comments
 (0)