Skip to content

Commit 971938e

Browse files
committed
Release v1.1.2: Username Handling, and Email Template Update
- Implemented a unique username creation mechanism to handle conflicts when usernames are based on email addresses. - Updated the email template sent for appointment confirmations, providing a more concise and user-centric message. - Added specific tests to reproduce and verify the slot availability and unique username issues, enhancing code robustness. - Bumped version to 1.1.2. Signed-off-by: @adamspd
1 parent 843b3f6 commit 971938e

File tree

11 files changed

+343
-94
lines changed

11 files changed

+343
-94
lines changed

MANIFEST.in

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ recursive-include appointment/templates/base_templates *.html
55
recursive-include appointment/templates/email_sender *.html
66
recursive-include appointment/static/css *.css
77
recursive-include appointment/static/js *.js
8+
recursive-include appointment/static/img *.jpg
89
recursive-include appointment/email_sender *.py
910
recursive-include appointment/tests *.py
1011
recursive-include appointment *.py

appointment/operations/database_operations.py

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,14 @@ def create_new_user(client_data):
7171
Version: 1.1.0
7272
Since: 1.1.0
7373
"""
74-
username = client_data['email'].split('@')[0]
74+
username_base = client_data['email'].split('@')[0]
75+
username = username_base
76+
suffix = 1
77+
while CLIENT_MODEL.objects.filter(username=username).exists():
78+
# convert suffix to string and format it to have 2 digits
79+
suffix_str = f"{suffix:02}"
80+
username = f"{username_base}{suffix_str}"
81+
suffix += 1
7582
user = CLIENT_MODEL.objects.create_user(first_name=client_data['name'], email=client_data['email'],
7683
username=username)
7784
password = f"{Utility.get_website_name()}{Utility.get_current_year()}"

appointment/operations/email_operations.py

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,8 @@ def get_thank_you_message(ar: AppointmentRequest) -> str:
3636
return message
3737

3838

39-
def send_thank_you_email(ar: AppointmentRequest, first_name: str, email: str, appointment_details=None):
39+
def send_thank_you_email(ar: AppointmentRequest, first_name: str, email: str, appointment_details=None,
40+
account_details=None):
4041
"""
4142
Send a thank-you email to the client for booking an appointment.
4243
@@ -45,19 +46,29 @@ def send_thank_you_email(ar: AppointmentRequest, first_name: str, email: str, ap
4546
first_name (str): The first name of the client.
4647
email (str): The email address of the client.
4748
appointment_details (str, optional): Additional details about the appointment (default None).
49+
account_details (str, optional): Additional details about the account (default None).
4850
4951
Returns: None
5052
5153
Author: Adams Pierre David
5254
Version: 1.1.0
5355
Since: 1.1.0
5456
"""
57+
message = f"We've created an account for you to manage your appointment for the requested service " \
58+
f"{ar.get_service_name()}. Your password is temporary. Please change it on your first login."
59+
# Month and year like "J A N 2 0 2 1"
60+
month_year = ar.date.strftime("%b %Y").upper()
61+
day = ar.date.strftime("%d")
5562
email_context = {
5663
'first_name': first_name,
5764
'message': get_thank_you_message(ar),
5865
'current_year': datetime.datetime.now().year,
5966
'company': Utility.get_website_name(),
60-
'appointment_details': appointment_details,
67+
'more_details': appointment_details,
68+
'account_details': account_details,
69+
'account_message': message if account_details is not None else None,
70+
'month_year': month_year,
71+
'day': day,
6172
}
6273
send_email(
6374
recipient_list=[email], subject="Thank you for booking us.",
117 KB
Loading
Lines changed: 244 additions & 61 deletions
Original file line numberDiff line numberDiff line change
@@ -1,81 +1,264 @@
11
{% load i18n %}
2+
{% load static %}
23
<!DOCTYPE html>
34
<html lang="en">
45
<head>
5-
<meta charset="UTF-8">
6-
<meta name="viewport" content="width=device-width, initial-scale=1.0">
7-
<style>
8-
body {
9-
font-family: Arial, sans-serif;
10-
background-color: #f5f5f5;
11-
margin: 0;
12-
padding: 0;
6+
<title></title>
7+
<style type="text/css">
8+
/* CLIENT-SPECIFIC STYLES */
9+
body, table, td, a {
10+
-webkit-text-size-adjust: 100%;
11+
-ms-text-size-adjust: 100%;
12+
}
13+
14+
table, td {
15+
mso-table-lspace: 0;
16+
mso-table-rspace: 0;
1317
}
1418

15-
.email-container {
16-
max-width: 600px;
17-
margin: 0 auto;
18-
padding: 20px;
19-
background-color: #ffffff;
20-
border-radius: 4px;
19+
img {
20+
-ms-interpolation-mode: bicubic;
2121
}
2222

23-
.header {
24-
text-align: center;
25-
padding: 20px;
23+
/* RESET STYLES */
24+
img {
25+
border: 0;
26+
height: auto;
27+
line-height: 100%;
28+
outline: none;
29+
text-decoration: none;
2630
}
2731

28-
.header h1 {
29-
font-size: 24px;
30-
color: #333333;
31-
margin: 0;
32+
table {
33+
border-collapse: collapse !important;
34+
}
35+
36+
body {
37+
height: 100% !important;
38+
margin: 0 !important;
39+
padding: 0 !important;
40+
width: 100% !important;
3241
}
3342

34-
.content {
35-
padding: 20px;
36-
line-height: 1.5;
37-
color: #333333;
43+
/* iOS BLUE LINKS */
44+
a[x-apple-data-detectors] {
45+
color: inherit !important;
46+
text-decoration: none !important;
47+
font-size: inherit !important;
48+
font-family: inherit !important;
49+
font-weight: inherit !important;
50+
line-height: inherit !important;
51+
}
52+
53+
.appointment-details li {
54+
padding: 0 !important; /* Add padding left to the details */
55+
}
56+
57+
/* MOBILE STYLES */
58+
@media screen and (max-width: 500px) {
59+
.img-max {
60+
width: 100% !important;
61+
max-width: 100% !important;
62+
height: auto !important;
63+
}
64+
65+
.max-width {
66+
max-width: 100% !important;
67+
}
68+
69+
.mobile-wrapper {
70+
width: 85% !important;
71+
max-width: 85% !important;
72+
}
73+
74+
.mobile-padding {
75+
padding-left: 5% !important;
76+
padding-right: 5% !important;
77+
}
3878
}
3979

40-
.footer {
41-
text-align: center;
42-
padding: 20px;
43-
font-size: 12px;
44-
color: #999999;
80+
/* ANDROID CENTER FIX */
81+
div[style*="margin: 16px 0;"] {
82+
margin: 0 !important;
4583
}
4684
</style>
4785
</head>
48-
<body>
49-
<div class="email-container">
50-
<div class="header">
51-
<h1>{% trans "Your booking session request has been accepted" %}!</h1>
52-
</div>
53-
<div class="content">
54-
<p>{% trans "Hello" %} {{ first_name }},</p>
55-
<p>
56-
{{ message }}
57-
</p>
58-
{% if appointment_details %}
59-
<div class="main-content">
60-
<p class="appointment-details-title">{% trans "Appointment Details" %}:</p>
61-
<ul class="appointment-details">
62-
{% for key, value in appointment_details.items %}
63-
<li>{{ key }}: {{ value }}</li>
64-
{% endfor %}
65-
</ul>
66-
</div>
67-
{% endif %}
68-
<p>
69-
{% blocktranslate %}
70-
If you have any questions or need assistance, please don't hesitate to reach out to our support team.
71-
{% endblocktranslate %}
72-
</p>
73-
<p>{% trans "Best regards" %},</p>
74-
<p>{% trans "The Team" %}</p>
75-
</div>
76-
<div class="footer">
77-
&copy; {{ current_year }} {{ company }}. {% trans "All rights reserved" %}.
78-
</div>
86+
<body style="margin: 0 !important; padding: 0; !important background-color: #ffffff;" bgcolor="#ffffff">
87+
88+
<!-- HIDDEN PRE-HEADER TEXT -->
89+
<div style="display: none; font-size: 1px; color: #fefefe; line-height: 1px; font-family: Open Sans, Helvetica, Arial, sans-serif; max-height: 0; max-width: 0; opacity: 0; overflow: hidden;">
90+
Booking session successfully saved.
7991
</div>
92+
93+
<table border="0" cellpadding="0" cellspacing="0" width="100%">
94+
<tr>
95+
<td align="center" valign="top" width="100%" bgcolor="#3b4a69"
96+
style="background: #3b4a69 url('{% static 'img/email_hd_bg.jpg' %}'); background-size: cover; padding: 50px 15px;"
97+
class="mobile-padding">
98+
<!--[if (gte mso 9)|(IE)]>
99+
<table align="center" border="0" cellspacing="0" cellpadding="0" width="600">
100+
<tr>
101+
<td align="center" valign="top" width="600">
102+
<![endif]-->
103+
<table align="center" border="0" cellpadding="0" cellspacing="0" width="100%" style="max-width:600px;">
104+
<tr>
105+
<td align="center" valign="top" style="padding: 0 0 20px 0;">
106+
{% comment %}<!--Add a logo img in future-->{% endcomment %}
107+
</td>
108+
</tr>
109+
<tr>
110+
<td align="center" valign="top"
111+
style="padding: 0; font-family: Open Sans, Helvetica, Arial, sans-serif;">
112+
<h1 style="font-size: 40px; color: #ffffff;">Booking Session Registered</h1>
113+
</td>
114+
</tr>
115+
<tr>
116+
<td align="center" valign="top"
117+
style="padding: 0 0 35px 0; font-family: Open Sans, Helvetica, Arial, sans-serif;">
118+
<table align="center" border="0" cellpadding="0" cellspacing="0" width="80%"
119+
style="max-width: 200px;">
120+
<tr>
121+
<td align="center" bgcolor="red"
122+
style="color: #ffffff; font-family: Open Sans, Helvetica, Arial, sans-serif; font-size: 14px; padding: 10px; border-radius: 3px 3px 0 0;">
123+
{{ month_year }}
124+
</td>
125+
</tr>
126+
<tr>
127+
<td align="center" bgcolor="#ffffff"
128+
style="color: #444444; font-family: Open Sans, Helvetica, Arial, sans-serif; font-size: 48px; padding: 15px; border-radius: 0 0 3px 3px;">
129+
{{ day }}
130+
</td>
131+
</tr>
132+
</table>
133+
</td>
134+
</tr>
135+
<tr>
136+
<td align="center" valign="top"
137+
style="font-family: Open Sans, Helvetica, Arial, sans-serif; padding-bottom: 30px;">
138+
139+
<p style="color: #ffffff; font-size: 16px; line-height: 24px; margin: 0;">
140+
Hi {{ first_name }}, <br> {{ message }}
141+
</p>
142+
</td>
143+
</tr>
144+
145+
</table>
146+
<!--[if (gte mso 9)|(IE)]>
147+
</td>
148+
</tr>
149+
</table>
150+
<![endif]-->
151+
</td>
152+
</tr>
153+
<tr style="max-width: 600px !important;">
154+
<td align="center" valign="top" width="100%" bgcolor="#ffffff" style="padding: 50px 15px;"
155+
class="mobile-padding">
156+
<!--[if (gte mso 9)|(IE)]>
157+
<table align="center" border="0" cellspacing="0" cellpadding="0" width="500">
158+
<tr>
159+
<td align="center" valign="top" width="500">
160+
<![endif]-->
161+
<table align="center" border="0" cellpadding="0" cellspacing="0" width="100%" style="max-width:500px;">
162+
{% if account_details %}
163+
<tr>
164+
<td align="left" valign="top"
165+
style="padding: 0; font-family: Open Sans, Helvetica, Arial, sans-serif;">
166+
<p style="font-size: 16px; margin-top: 15px !important;">{{ account_message }}</p>
167+
</td>
168+
</tr>
169+
<tr>
170+
<td align="left" valign="top"
171+
style="padding: 0; font-family: Open Sans, Helvetica, Arial, sans-serif;">
172+
<h2 style="color: #000000; font-size: 25px">{% trans "Account Details" %}</h2>
173+
</td>
174+
</tr>
175+
<tr>
176+
<td align="left" valign="top"
177+
style="font-family: Open Sans, Helvetica, Arial, sans-serif; padding-top: 0;">
178+
179+
<div style="color: #000000; font-size: 16px; line-height: 24px; margin-top: -30px !important;">
180+
<ul>
181+
{% for key, value in account_details.items %}
182+
<li>{{ key }}: {{ value }}</li>
183+
{% endfor %}
184+
</ul>
185+
</div>
186+
187+
</td>
188+
</tr>
189+
{% endif %}
190+
{% if more_details %}
191+
<tr>
192+
<td align="left" valign="top"
193+
style="padding: 0; font-family: Open Sans, Helvetica, Arial, sans-serif;">
194+
<p style="font-size: 16px; margin-top: 15px !important;">{{ message }}</p>
195+
</td>
196+
</tr>
197+
<tr>
198+
<td align="left" valign="top"
199+
style="padding: 0; font-family: Open Sans, Helvetica, Arial, sans-serif;">
200+
<h2 style="color: #000000; font-size: 25px">{% trans "Appointment Details" %}</h2>
201+
</td>
202+
</tr>
203+
<tr>
204+
<td align="left" valign="top"
205+
style="font-family: Open Sans, Helvetica, Arial, sans-serif; padding-top: 0;">
206+
207+
<div style="color: #000000; font-size: 16px; line-height: 24px; margin-top: -30px !important;">
208+
<ul>
209+
{% for key, value in more_details.items %}
210+
<li>{{ key }}: {{ value }}</li>
211+
{% endfor %}
212+
</ul>
213+
</div>
214+
215+
</td>
216+
</tr>
217+
{% endif %}
218+
<tr>
219+
<td align="left" valign="top"
220+
style="padding: 0; font-family: Open Sans, Helvetica, Arial, sans-serif; font-size: 16px">
221+
<p style="margin-top: 15px !important;">
222+
{% blocktranslate %}
223+
If you have any questions or need assistance, please don't hesitate to reach out to our
224+
support team.
225+
{% endblocktranslate %}
226+
</p>
227+
<p>{% trans "Best regards" %},</p>
228+
<p>{% trans "The Team" %}</p>
229+
</td>
230+
</tr>
231+
</table>
232+
<!--[if (gte mso 9)|(IE)]>
233+
</td>
234+
</tr>
235+
</table>
236+
<![endif]-->
237+
</td>
238+
</tr>
239+
<tr>
240+
<td align="center" height="100%" valign="top" width="100%" bgcolor="#f6f6f6" style="padding: 40px 15px;">
241+
<!--[if (gte mso 9)|(IE)]>
242+
<table align="center" border="0" cellspacing="0" cellpadding="0" width="600">
243+
<tr>
244+
<td align="center" valign="top" width="600">
245+
<![endif]-->
246+
<table align="center" border="0" cellpadding="0" cellspacing="0" width="100%" style="max-width:600px;">
247+
<tr>
248+
<td align="center" valign="top"
249+
style="padding: 0; font-family: Open Sans, Helvetica, Arial, sans-serif; color: #999999;">
250+
&copy; {{ current_year }} {{ company }}. {% trans "All rights reserved" %}.
251+
</td>
252+
</tr>
253+
</table>
254+
<!--[if (gte mso 9)|(IE)]>
255+
</td>
256+
</tr>
257+
</table>
258+
<![endif]-->
259+
</td>
260+
</tr>
261+
</table>
262+
80263
</body>
81264
</html>

appointment/tests/operations/__init__.py

Whitespace-only changes.

0 commit comments

Comments
 (0)