no actual template functionality yet - just the ability for services
that have letters enabled to edit a 10 line block that will go on the
top right hand side of their letters with contact information
Right now we have separate pages for email and text message templates.
In the future we will also have a separate page for letter templates.
This commit changes Notify to only have one page for all templates.
What is the problem?
---
The left-hand navigation is getting quite crowded, at 8 items for a
service that can send letters. Research suggests that the number of
objects an average human can hold in working memory is 7 ± 2 [1]. So
we’re at the limit of how many items the navigation should have.
In the future we will need to search/sort/filter templates by attributes
other than type, for example:
- show me the ‘confirmation’ templates
- show me the most recently used templates
- show me all templates containing the placeholder `((ref_no))`
These are hypothetical for now, but these needs (or others) may become
real in the future. At this point pre-filtering the list of templates
by type would restrict what searches a user could do. So by making this
change now we’re in a better position to iterate the design in the
future.
What’s the change?
---
This commit replaces the ‘Email templates’, ‘Text message templates’ and
‘Letter templates’ pages with one page called ‘Templates’.
This new templates page shows all the templates for the service, sorted
by most recently created first (as before).
To add a new template there is a new page with a form asking you what
kind of template you want to create. This is necessary because in the
past we knew what kind of template you wanted to create based on the
kind you were looking at.
What’s the impact of this change on new users?
---
This change alters the onboarding process slightly. We still want to
take people through the empty templates page from the call-to-action on
the dashboard because it helps them understand that to send a message
using Notify you need a template. But because we don’t have separate
pages for emails/text messages we will have to send users through the
extra step of choosing what kind of template to create. This is a bit
clunkier on first use but:
- it still gets the point across
- it takes them through the actual flow they will be using to create new
templates in the future (ie they’re learning how to use Notify, not
just being taken through a special onboarding route)
I’m not too worried about this change in terms of the experience for new
users. Furthermore, by making it now we get to validate whether it’s
causing any problems in the lab research booked for next week.
What’s the impact of this change on current services?
---
Looking at the top 15 services by number of templates[2], most are using
either text messages or emails. So this change would not have a
significant impact on these services because the page will not get any
longer. In other words we wouldn’t be making it worse for them.
Those services who do use both are not using as many templates. The
worst-case scenario is SSCS, who have 16 templates, evenly split between
email and text messages. So they would go from having 8 templates per
page to 16, which is still less than half the number that HMPO or
Digital Marketplace are managing.
References
---
1. https://en.wikipedia.org/wiki/The_Magical_Number_Seven,_Plus_or_Minus_Two
2. Template usage by service
Service name | Template count | Template types
---------------------------------------|----------------|---------------
Her Majesty's Passport Office | 40 | sms
Digital Marketplace | 40 | email
GovWifi-Staging | 19 | sms
GovWifi | 18 | sms
Digital Apprenticeship Service | 16 | email
SSCS | 16 | both
Crown Commercial Service MI Collection | 15 | email
Help with Prison Visits | 12 | both
Digital Future | 12 | email
Export Licensing Service | 11 | email
Civil Money Claims | 9 | both
DVLA Drivers Medical Service | 9 | sms
GOV.UK Notify | 8 | both
Manage your benefit overpayments | 8 | both
Tax Renewals | 8 | both
The user has 10 tries at the password, after which the account is locked.
The same is true for the verify code, the user will have 10 tries before the user account is locked.
> When the CSV is missing the header row, we get an error and the user
> will see "Sorry, we are experiencing technical difficulties..."
>
> We should return a better error message for the user.
– https://www.pivotaltracker.com/story/show/140668615
This was caused by an attempt to access the `first_recipient` variable
before it was assigned. It would only be assigned when there was at
least one row in the file.
Fixing this means doing two things:
- defaulting `first_recipient` to be `None` before looking in the file
- adding an error message for when we can’t extract any rows out of the
file (which is more nuanced than the file just being completely empty)
(There’s a nasty `sort` in the Jinja template because when there are no
rows in the file the order of the required column headers is not
deterministic.)
specifically, the 2FA page when you first create an account is different to the login 2FA page
and also the 2FA page when you change your phone number is different as well
Not sure why we had a non-breaking space in here because it didn’t wrap
onto two lines anyway. And it wasn’t working because it was showing up
encoded, rather than as a raw entity.
when a user enters their 2FA code, the API will store a random UUID
against them in the database - this code is then stored on the cookie
on the front end.
At the beginning of each authenticated request, we do the following
steps:
* Retrieve the user's cookie, and get the user_id from it
* Request that user's details from the database
* populate current_user with the DB model
* run the login_required decorator, which calls
current_user.is_authenticated
is_authenticated now also checks that the database model matches the
cookie for session_id. The potential states and meanings are as follows:
database | cookie | meaning
----------+--------+---------
None | None | New user, or system just been deployed.
| | Redirect to start page.
----------+--------+---------
'abc' | None | New browser (or cleared cookies). Redirect to
| | start page.
----------+--------+---------
None | 'abc' | Invalid state (cookie is set from user obj, so
| | would only happen if DB is cleared)
----------+--------+---------
'abc' | 'abc' | Same browser. Business as usual
----------+--------+---------
'abc' | 'def' | Different browser in cookie - db has been changed
| | since then. Redirect to start
Use `it`/`they` depending on how many different characters you've used
Also don't wrap the message with quotes, as it looks confusing and
potentialy implies that you can't use apostrophes
> Users that allow their session to expire, or access a bookmarked link
> are told they need to "Sign in to access this page" - we should
> explain that it's because they've been away a while, so that they
> understand why they're being asked to log in again.
– https://www.pivotaltracker.com/story/show/140016919
The message we were showing before (Please log in to access this page is
the default message from Flask Login).
In order to stop this flash message from appearing, we need to override
the default handler for when a user is unauthorised. We’re overriding it
with the same behaviour, minus the flash message.
If you navigate deliberately to the sign in page it’s unchanged.
Content is Sheryll-approved.
Matches what we do on the usage page. No need to see months in the
future because there’s no way you’ll have sent any messages in those
months, unless you’re Marty McFly.
The previous, weekly activity breakdown was what we reckoned might be
useful. But now that we have people using the platform it feels like
aggregating a service’s usage by month is:
- matches the timeframe users report on within their organisation
- is consistent with the usage page
And like the usage page this commit also limits the page to only show
one financial year’s worth of data at once (rather than data for all
time).
This commit also makes some changes to the jobs view code so that our
aggregation of failure states is consistent between the dashboard pages
and the jobs pages.
Right now we tell people that the usage page is for the current
financial year. This is a lie – it’s for all time.
So this commit calls through to the API to get the stats for (by
default) the current financial year.
We already do this for the monthly breakdown, this just does the same
thing for the yearly totals.
It also adds navigation to show the data for other financial years:
- previous so you can go back and see your usage and verify that the
bill you’re about to pay is correct
- next so that you can check what your SMS allowance is going to be
before you actually get into it
`severe` can mean one of three things:
- `yes` – user has told us this is an emergency
- `no` – user has told us this isn’t an emergency
- Anything else – user hasn’t been asked the question or has
hacked/mangled the URL
This commit adds some stricter sanitisation of the `severe` query
parameter and does so up front, rather than spreading it across multiple
functions.
`replace` doesn’t convert a time from one timezone to another. It just
changes the label that says what timezone a time is in 😬
`.localize` is how we handle these kind of issues in the API (see
d0b467b2fb/app/utils.py (L42-L44) )
So this commit changes the calculation to use `.localize`, and makes the
tests timezone aware to check we’re doing this right.
Using and/or over any/all has a couple of advantages:
- it's a bit quicker
- it won't evaluate the second half at all if the first half fails – if
it is in business hours, and convert_to_boolean would raise, with your
use of all we'd throw a 500, whereas if we had or, business_hours
would trip and we'd skip over the second half without worrying about
exceptions
any and all are designed for use with variable length args eg
`any(x for x in thing())`
If you report a problem we want to be able to get back to you to find
out more information, or to update you on the status of a fix. So it
shouldn’t be possible to report a problem without providing an email
address.
This commit makes `email_address` a required field when `ticket_type` is
problem.
This requires a bit of fiddling with the tests which weren’t expecting
to have to provide an email address. So the tests now either:
- pass an email address
- check for an error when they don’t pass an email address
This is a real edge case, but it seems worth handling.
How you’d get to this case:
- it’s 5:29pm and you start to describe the problem you’re having
- it’s 5:31pm and you click ‘submit’
- you’re redirected to the triage page because we’re now out of hours
- you click ‘this is a serious problem’
What would be bad thing to happen:
- you’re back on the message page and all the stuff you’ve written is
gone
What would be a good thing to happen:
- we save the message in a session so that you can check it again before
sending it
Generally I prefer confirmation pages to the flash message thing
(they’re harder to miss). So this commit adds one.
It also adds some logic to this page, so that, depending what the user
has told us about the thing they’ve submitted, we can tell them how
quickly to expect a response.
TL;DR, as much as possible we should work out how to prioritise tickets
and not put that burden on the user. However, there are some cases where
we can’t.
In business hours all tickets are high priority, ie we will at least
acknowledge them within 30 mins.
If we are not in business hours then we need to know if a ticket is
serious enough to get someone out of bed. Only the user can tell us
this, but we can give them some examples to help them decide.
In addition, out-of-hours tickets are only a priority if the user has
live services. Normally we can determine this and do the
priority-setting in the background.
If they can’t log in then we can’t determine what services they have. So
in this case they will need to use the emergency email address, which
only users with live services will have.
The logic for this gets fairly complex. It might be to easier to
understand what’s going on by walking through the test cases, which are
a bit more declarative.
N.B. Deskpro’s ‘urgency’ is descending, eg 10 is the most urgent and 1
is the least.
If a user is logged in then we already know their name and email
address. So there’s no need for them to fill them again on the support
form.
One concern we might have about this is the user not realising we’re
doing this, and the feedback form looking like a bit of a black hole.
So we’re replaying their email address on this page to reassure them
that:
- we know who they are
- and that they’ll get a reply
The kind of communications we’re getting at the moment can broadly be
broken down into:
- problems
- questions and feedback
We will need to triage problems differently, because they could
potentially be urgent/severe/emergency/P1/whatever language we use.
Questions or feedback will never be P1.
Two reasons for making the user categorise their tickets themselves:
- Outside of hours we can’t get someone out of bed in order to decide if
a ticket is a problem or just feedback
- We can tailor the subsequent pages to whether it’s a problem or
feedback (eg showing a link to the status page if the user is having
a problem)
This commit let’s users make the choice with a pair of radio buttons.
It also cleans up a bunch of the tests and parameterizes them so we’re
testing the flow for both ticket types.
Our support process is about to get more fully fledged so we’ll need
an index page to route people properly.
We reckon that users will also want to know what the support process is,
so let’s explain it on this page.