CMS:USER_PW

Prepares the resetting of a password.

(CMS:USER_PW [parameter=value …])

Method: Modules\Record\RecordUser::cmsPw()
PHP snippet: include_and_stop (after)

Parameters

Parameter Value Default Required Description
successtemplate – – yes Detail template that is included if “uniquevalue” could be assigned to a profile in the field “uniquefield”.
errortemplate – – yes Detail template that is included if “uniquevalue” was given but could not be assigned to a profile.
container container ID or name – yes ID or name of the profile container in which the profiles to be matched are stored.
uniquefield field name – yes Name of the field to search by (field type chars, text or encrypted, e.g. “email”). The value must match exactly one profile.
uniquevalue text – Value sought in the field “uniquefield”, e.g. $_POST[email].
submit text value – yes The command runs only if this field contains a text.
message[…] text – Error message. In the index: use case; in the value: message text (see table).
csrf true / false true true: The request must contain a valid token from CMS:USER_TOKEN (protection against CSRF). false switches off the check for this command – only with good reason.
formguard true / false / seconds false true: form protection against robots – the form must contain the fields from (CMS:USER_TOKEN formguard=true) and may not be submitted earlier than 3 seconds (user.formguard_min_seconds). A number sets the minimum time for this form (formguard=5), 0 switches it off. Otherwise the message throttled.

[…] – the parameter accepts sub-keys, e.g. name[key]=value.

Usage

First step of “Forgot password”: searches for the profile via a unique field (usually the email address) and creates a one-time token in $set['hash']. The successtemplate sends the link. The target page signs the frontend user in with (CMS:USER_LOGIN hash=…); afterwards, the user sets a new password with CMS:USER_INPUT:

<?php $submit = $_POST['submit'] ?? ''; ?>
(CMS:USER_PW container=members uniquefield=email uniquevalue="{$_POST['data']['email']}"
  submit="$submit" successtemplate=u_pwsent errortemplate=u_pwfail)
<h1>Forgot password</h1>
<form method="post">
  (CMS:USER_TOKEN)
  <input name="data[email]" type="email">
  <button name="submit" value="1">Request link</button>
</form>

u_pwsent sends the link with CMS:EMAIL:

<?php $link = 'https://www.example.com/0,u_hashlogin?hash=' . rawurlencode($set['hash']); ?>
(CMS:EMAIL submit="1" to="{$set['user']['email']}" subject="New password"
  body="Link (valid for one hour): $link")
(CMS:MESSAGE)
<p>We have sent you a link.</p>

Message indexes: notfound, container, throttled, token.

Throttling and form protection

Each request sends an email to an address that someone has typed in. So that nobody can flood foreign mailboxes through your form, camindo counts the requests (throttling): at most three per entered address and hour, ten per origin (IP address) and 200 per website (system administrator: user.throttle). What is counted is the entered value – whether an account exists does not matter. Once a limit is reached, no link is created, and the command includes the errortemplate, with $set['throttled'] = 1 and the message throttled. If you show the same text there as in the success case, the page reveals neither whether an account exists nor that throttling took place.

Against robots that fill in every form blindly, the form protection helps additionally: formguard=true on the command and (CMS:USER_TOKEN formguard=true) in the form. Anyone who submits the form faster than three seconds, or fills the invisible honeypot field, receives the same response as with throttling:

(CMS:USER_PW container=members formguard=true uniquefield=email uniquevalue="{$_POST['data']['email']}"
  submit="$submit" successtemplate=u_pwsent errortemplate=u_pwfail)
…
<form method="post">
  (CMS:USER_TOKEN formguard=true)
  …
</form>

The link is valid for one hour and only once (setting user.password_token_expiration). It works on any device – someone who has forgotten their password is often sitting at a new device. If the sign-in via the link comes from an unknown device, CMS:USER_LOGIN reports it like any other sign-in.

Show the same text in the errortemplate as in the successtemplate (“If an account exists for this address, we have sent a link.”). Otherwise anyone can try out which email addresses have an account with you.

Parameters in detail

successtemplate

Included if a profile was found. In it, $set['hash'] and $set['user'] are available, and the profile is the current record:

(CMS:USER_PW container=members uniquefield=email uniquevalue="$email" submit="$submit" successtemplate=u_pwsent errortemplate=u_pwfail)

errortemplate

Included if uniquevalue was given but no profile matches:

(CMS:USER_PW … errortemplate=u_pwfail)

container

(CMS:USER_PW container=members …)

uniquefield

Field to search by (field type chars, text or encrypted). The comparison is literal and not case-sensitive. If the value matches more than one profile, that counts as “not found”. Therefore, mark the field as unique in the area:

(CMS:USER_PW container=members uniquefield=email …)
(CMS:USER_PW container=members uniquefield=nickname …)

uniquevalue

Value sought, usually from the form. If empty, the command does nothing:

(CMS:USER_PW container=members uniquefield=email uniquevalue="{$_POST['data']['email']}" …)

submit

<?php $submit = $_POST['submit'] ?? ''; ?>
(CMS:USER_PW … submit="$submit")

message

(CMS:USER_PW … message[notfound]="There is no account for this address.")

← Overview

As of camindo CMS 9.1.3