fisharebest /
webtrees
These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more
| 1 | <?php |
||
| 2 | /** |
||
| 3 | * webtrees: online genealogy |
||
| 4 | * Copyright (C) 2018 webtrees development team |
||
| 5 | * This program is free software: you can redistribute it and/or modify |
||
| 6 | * it under the terms of the GNU General Public License as published by |
||
| 7 | * the Free Software Foundation, either version 3 of the License, or |
||
| 8 | * (at your option) any later version. |
||
| 9 | * This program is distributed in the hope that it will be useful, |
||
| 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of |
||
| 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||
| 12 | * GNU General Public License for more details. |
||
| 13 | * You should have received a copy of the GNU General Public License |
||
| 14 | * along with this program. If not, see <http://www.gnu.org/licenses/>. |
||
| 15 | */ |
||
| 16 | namespace Fisharebest\Webtrees; |
||
| 17 | |||
| 18 | use DateTimeZone; |
||
| 19 | use Fisharebest\Webtrees\Controller\PageController; |
||
| 20 | use Fisharebest\Webtrees\Functions\FunctionsEdit; |
||
| 21 | |||
| 22 | /** @global Tree $WT_TREE */ |
||
| 23 | global $WT_TREE; |
||
| 24 | |||
| 25 | require 'includes/session.php'; |
||
| 26 | |||
| 27 | // Need to be logged in |
||
| 28 | if (!Auth::check()) { |
||
| 29 | header('Location: index.php'); |
||
| 30 | |||
| 31 | return; |
||
| 32 | } |
||
| 33 | |||
| 34 | // Extract form variables |
||
| 35 | $action = Filter::post('action', 'update|delete', ''); |
||
| 36 | $username = Filter::post('username'); |
||
| 37 | $real_name = Filter::post('real-name'); |
||
| 38 | $password_1 = Filter::post('password-1', WT_REGEX_PASSWORD); |
||
| 39 | $password_2 = Filter::post('password-2', WT_REGEX_PASSWORD); |
||
| 40 | $email = Filter::post('email'); |
||
| 41 | $root_id = Filter::post('root-id', WT_REGEX_XREF); |
||
| 42 | $theme = Filter::post('theme', implode('|', array_keys(Theme::themeNames())), ''); |
||
| 43 | $language = Filter::post('language', null, ''); |
||
| 44 | $time_zone = Filter::post('time-zone', null, 'UTC'); |
||
| 45 | $contact_method = Filter::post('contact-method', null, ''); |
||
| 46 | $visible_online = Filter::postBool('visible-online'); |
||
| 47 | |||
| 48 | // Respond to form action |
||
| 49 | if ($action !== '' && Filter::checkCsrf()) { |
||
| 50 | switch ($action) { |
||
| 51 | case 'update': |
||
| 52 | if ($username !== Auth::user()->getUserName() && User::findByUserName($username)) { |
||
| 53 | FlashMessages::addMessage(I18N::translate('Duplicate username. A user with that username already exists. Please choose another username.')); |
||
| 54 | } elseif ($email !== Auth::user()->getEmail() && User::findByEmail($email)) { |
||
| 55 | FlashMessages::addMessage(I18N::translate('Duplicate email address. A user with that email already exists.')); |
||
| 56 | } else { |
||
| 57 | // Change username |
||
| 58 | if ($username !== Auth::user()->getUserName()) { |
||
| 59 | Log::addAuthenticationLog('User ' . Auth::user()->getUserName() . ' renamed to ' . $username); |
||
| 60 | Auth::user()->setUserName($username); |
||
| 61 | } |
||
| 62 | |||
| 63 | // Change password |
||
| 64 | if ($password_1 !== '' && $password_1 === $password_2) { |
||
| 65 | Auth::user()->setPassword($password_1); |
||
| 66 | } |
||
| 67 | |||
| 68 | // Change other settings |
||
| 69 | Auth::user() |
||
| 70 | ->setRealName($real_name) |
||
| 71 | ->setEmail($email) |
||
| 72 | ->setPreference('language', $language) |
||
| 73 | ->setPreference('TIMEZONE', $time_zone) |
||
| 74 | ->setPreference('contactmethod', $contact_method) |
||
| 75 | ->setPreference('visibleonline', $visible_online ? '1' : '0'); |
||
| 76 | |||
| 77 | Auth::user()->setPreference('theme', $theme); |
||
| 78 | |||
| 79 | $WT_TREE->setUserPreference(Auth::user(), 'rootid', $root_id); |
||
| 80 | } |
||
| 81 | break; |
||
| 82 | |||
| 83 | case 'delete': |
||
| 84 | // An administrator can only be deleted by another administrator |
||
| 85 | if (!Auth::user()->getPreference('canadmin')) { |
||
| 86 | $currentUser = Auth::user(); |
||
| 87 | Auth::logout(); |
||
| 88 | $currentUser->delete(); |
||
| 89 | } |
||
| 90 | break; |
||
| 91 | } |
||
| 92 | |||
| 93 | header('Location: edituser.php'); |
||
| 94 | |||
| 95 | return; |
||
| 96 | } |
||
| 97 | |||
| 98 | $controller = new PageController; |
||
| 99 | $controller |
||
| 100 | ->setPageTitle(I18N::translate('My account')) |
||
| 101 | ->pageHeader(); |
||
| 102 | |||
| 103 | $my_individual_record = Individual::getInstance($WT_TREE->getUserPreference(Auth::user(), 'gedcomid'), $WT_TREE); |
||
| 104 | $default_individual = Individual::getInstance($WT_TREE->getUserPreference(Auth::user(), 'rootid'), $WT_TREE); |
||
| 105 | |||
| 106 | // Form validation |
||
| 107 | ?> |
||
| 108 | <script> |
||
| 109 | function checkform(frm) { |
||
| 110 | if (frm.form_pass1.value!=frm.form_pass2.value) { |
||
| 111 | alert("<?= I18N::translate('The passwords do not match.') ?>"); |
||
| 112 | frm.form_pass1.focus(); |
||
| 113 | return false; |
||
| 114 | } |
||
| 115 | if (frm.form_pass1.value.length > 0 && frm.form_pass1.value.length < 6) { |
||
| 116 | alert("<?= I18N::translate('Passwords must contain at least 6 characters.') ?>"); |
||
| 117 | frm.form_pass1.focus(); |
||
| 118 | return false; |
||
| 119 | } |
||
| 120 | return true; |
||
| 121 | } |
||
| 122 | </script> |
||
| 123 | |||
| 124 | <h2><?= $controller->getPageTitle() ?></h2> |
||
| 125 | |||
| 126 | <form name="editform" method="post" onsubmit="return checkform(this);"> |
||
| 127 | <input type="hidden" name="action" value="update"> |
||
| 128 | <?= Filter::getCsrf() ?> |
||
| 129 | |||
| 130 | <div class="row form-group"> |
||
| 131 | <label class="col-sm-3 col-form-label" for="username"> |
||
| 132 | <?= I18N::translate('Username') ?> |
||
| 133 | </label> |
||
| 134 | <div class="col-sm-9"> |
||
| 135 | <input type="text" class="form-control" id="username" name="username" value="<?= e(Auth::user()->getUserName()) ?>" dir="auto" aria-describedby="username-description" required> |
||
| 136 | <p class="small text-muted" id="username-description"> |
||
| 137 | <?= I18N::translate('Usernames are case-insensitive and ignore accented letters, so that āchloeā, āchloĆ«ā, and āChloeā are considered to be the same.') ?> |
||
| 138 | </p> |
||
| 139 | </div> |
||
| 140 | </div> |
||
| 141 | |||
| 142 | <div class="row form-group"> |
||
| 143 | <label class="col-sm-3 col-form-label" for="real-name"> |
||
| 144 | <?= I18N::translate('Real name') ?> |
||
| 145 | </label> |
||
| 146 | <div class="col-sm-9"> |
||
| 147 | <input type="text" class="form-control" id="real-name" name="real-name" value="<?= e(Auth::user()->getRealName()) ?>" dir="auto" aria-describedby="real-name-description" required> |
||
| 148 | <p class="small text-muted" id="username-description"> |
||
| 149 | <?= I18N::translate('This is your real name, as you would like it displayed on screen.') ?> |
||
| 150 | </p> |
||
| 151 | </div> |
||
| 152 | </div> |
||
| 153 | |||
| 154 | <div class="row form-group"> |
||
| 155 | <label class="col-sm-3 col-form-label" for="gedcom-id"> |
||
| 156 | <?= I18N::translate('Individual record') ?> |
||
| 157 | </label> |
||
| 158 | <div class="col-sm-9"> |
||
| 159 | <select class="form-control" id="gedcom-id" aria-describedby="gedcom-id-description" disabled> |
||
| 160 | <?php if ($my_individual_record instanceof Individual): ?> |
||
| 161 | <option value=""><?= $my_individual_record->getFullName() ?></option> |
||
| 162 | <?php else: ?> |
||
| 163 | <option value=""><?= I18N::translateContext('unknown people', 'Unknown') ?></option> |
||
| 164 | <?php endif ?> |
||
| 165 | </select> |
||
| 166 | <p class="small text-muted" id="gedcom-id-description"> |
||
| 167 | <?= I18N::translate('This is a link to your own record in the family tree. If this is the wrong individual, contact an administrator.') ?> |
||
| 168 | </p> |
||
| 169 | </div> |
||
| 170 | </div> |
||
| 171 | |||
| 172 | <div class="row form-group"> |
||
| 173 | <label class="col-sm-3 col-form-label" for="root-id"> |
||
| 174 | <?= I18N::translate('Default individual') ?> |
||
| 175 | </label> |
||
| 176 | <div class="col-sm-9"> |
||
| 177 | <?= FunctionsEdit::formControlIndividual($default_individual, ['id' => 'root-id', 'name' => 'root-id', 'aria-describedby' => 'root-id-description']) ?> |
||
|
0 ignored issues
–
show
|
|||
| 178 | <p class="small text-muted" id="root-id-description"> |
||
| 179 | <?= I18N::translate('This individual will be selected by default when viewing charts and reports.') ?> |
||
| 180 | </p> |
||
| 181 | </div> |
||
| 182 | </div> |
||
| 183 | |||
| 184 | <div class="row form-group"> |
||
| 185 | <label class="col-sm-3 col-form-label" for="password-1"> |
||
| 186 | <?= I18N::translate('Password') ?> |
||
| 187 | </label> |
||
| 188 | <div class="col-sm-9"> |
||
| 189 | <input class="form-control" type="password" id="password-1" name="password-1" aria-describedby="password-1-description" autocomplete="new-password"> |
||
| 190 | <p class="small text-muted" id="password-1-description"> |
||
| 191 | <?= I18N::translate('Passwords must be at least 6 characters long and are case-sensitive, so that āsecretā is different from āSECRETā.') ?> |
||
| 192 | <br> |
||
| 193 | <?= I18N::translate('Leave the password blank if you want to keep the current password.') ?> |
||
| 194 | </p> |
||
| 195 | </div> |
||
| 196 | </div> |
||
| 197 | |||
| 198 | <div class="row form-group"> |
||
| 199 | <label class="col-sm-3 col-form-label" for="password-2"> |
||
| 200 | <?= I18N::translate('Confirm password') ?> |
||
| 201 | </label> |
||
| 202 | <div class="col-sm-9"> |
||
| 203 | <input class="form-control" type="password" id="password-2" name="password-2" aria-describedby="password-2-description" autocomplete="new-password"> |
||
| 204 | <p class="small text-muted" id="password-2-description"> |
||
| 205 | <?= I18N::translate('Type your password again, to make sure you have typed it correctly.') ?> |
||
| 206 | </p> |
||
| 207 | </div> |
||
| 208 | </div> |
||
| 209 | |||
| 210 | <div class="row form-group"> |
||
| 211 | <label class="col-sm-3 col-form-label" for="language"> |
||
| 212 | <?= I18N::translate('Language') ?> |
||
| 213 | </label> |
||
| 214 | <div class="col-sm-9"> |
||
| 215 | <?= Bootstrap4::select(FunctionsEdit::optionsInstalledLanguages(), Auth::user()->getPreference('language'), ['id' => 'language', 'name' => 'language']) ?> |
||
| 216 | </div> |
||
| 217 | </div> |
||
| 218 | |||
| 219 | <div class="row form-group"> |
||
| 220 | <label class="col-sm-3 col-form-label" for="time-zone"> |
||
| 221 | <?= I18N::translate('Time zone') ?> |
||
| 222 | </label> |
||
| 223 | <div class="col-sm-9"> |
||
| 224 | <?= Bootstrap4::select(array_combine(DateTimeZone::listIdentifiers(), DateTimeZone::listIdentifiers()), Auth::user()->getPreference('TIMEZONE', 'UTC'), ['id' => 'time-zone', 'name', 'time-zone', 'aria-describedby' => 'time-zone-description']) ?> |
||
| 225 | <p class="small text-muted" id="time-zone-description"> |
||
| 226 | <?= I18N::translate('The time zone is required for date calculations, such as knowing todayās date.') ?> |
||
| 227 | </p> |
||
| 228 | </div> |
||
| 229 | </div> |
||
| 230 | |||
| 231 | <div class="row form-group"> |
||
| 232 | <label class="col-sm-3 col-form-label" for="email"> |
||
| 233 | <?= I18N::translate('Email address') ?> |
||
| 234 | </label> |
||
| 235 | <div class="col-sm-9"> |
||
| 236 | <input class="form-control" type="email" id="email" name="email" value="<?= e(Auth::user()->getEmail()) ?>" aria-describedby="email-description"> |
||
| 237 | <p class="small text-muted" id="email-description"> |
||
| 238 | <?= I18N::translate('This email address will be used to send password reminders, website notifications, and messages from other family members who are registered on the website.') ?> |
||
| 239 | </p> |
||
| 240 | </div> |
||
| 241 | </div> |
||
| 242 | |||
| 243 | <?php if (Site::getPreference('ALLOW_USER_THEMES') === '1'): ?> |
||
| 244 | <div class="row form-group"> |
||
| 245 | <label class="col-sm-3 col-form-label" for="theme"> |
||
| 246 | <?= I18N::translate('Theme') ?> |
||
| 247 | </label> |
||
| 248 | <div class="col-sm-9"> |
||
| 249 | <select class="form-control" id="theme" name="theme" aria-describedby="theme-description"> |
||
| 250 | <option value=""> |
||
| 251 | <?= e(/* I18N: default option in list of themes */ I18N::translate('<default theme>')) ?> |
||
| 252 | </option> |
||
| 253 | <?php foreach (Theme::themeNames() as $theme_id => $theme_name): ?> |
||
| 254 | <option value="<?= $theme_id ?>" <?= $theme_id === Auth::user()->getPreference('theme') ? 'selected' : '' ?>> |
||
|
0 ignored issues
–
show
|
|||
| 255 | <?= $theme_name ?> |
||
| 256 | </option> |
||
| 257 | <?php endforeach ?> |
||
| 258 | </select> |
||
| 259 | <p class="small text-muted" id="theme-description"> |
||
| 260 | <?= /* I18N: Help text for the "Default theme" site configuration setting */ I18N::translate('You can change the appearance of webtrees using āthemesā. Each theme has a different style, layout, color scheme, etc.') ?> |
||
| 261 | </p> |
||
| 262 | </div> |
||
| 263 | </div> |
||
| 264 | <?php endif ?> |
||
| 265 | |||
| 266 | <div class="row form-group"> |
||
| 267 | <label class="col-sm-3 col-form-label" for="contact-method"> |
||
| 268 | <?= I18N::translate('Contact method') ?> |
||
| 269 | </label> |
||
| 270 | <div class="col-sm-9"> |
||
| 271 | <?= Bootstrap4::select(FunctionsEdit::optionsContactMethods(), Auth::user()->getPreference('contactmethod'), ['id' => 'contact-method', 'name' => 'contact-method', 'aria-describedby' => 'contact-method-description']) ?> |
||
| 272 | <p class="small text-muted" id="contact-method-description"> |
||
| 273 | <?= I18N::translate('Site members can send each other messages. You can choose to how these messages are sent to you, or choose not receive them at all.') ?> |
||
| 274 | </p> |
||
| 275 | </div> |
||
| 276 | </div> |
||
| 277 | |||
| 278 | <fieldset class="form-group"> |
||
| 279 | <div class="row"> |
||
| 280 | <legend class="col-sm-3 col-form-label"> |
||
| 281 | <?= I18N::translate('Visible online') ?> |
||
| 282 | </legend> |
||
| 283 | <div class="col-sm-9"> |
||
| 284 | <?= Bootstrap4::checkbox(I18N::translate('Visible to other users when online'), false, ['name' => 'visible-online', 'checked' => (bool) Auth::user()->getPreference('visibleonline'), 'aria-describedby' => 'visible-online-description']) ?> |
||
|
0 ignored issues
–
show
array('name' => 'visible...le-online-description') is of type array<string,string|bool...describedby":"string"}>, but the function expects a array<integer,string>.
It seems like the type of the argument is not accepted by the function/method which you are calling. In some cases, in particular if PHP’s automatic type-juggling kicks in this might be fine. In other cases, however this might be a bug. We suggest to add an explicit type cast like in the following example: function acceptsInteger($int) { }
$x = '123'; // string "123"
// Instead of
acceptsInteger($x);
// we recommend to use
acceptsInteger((integer) $x);
Loading history...
|
|||
| 285 | <p class="small text-muted" id="visible-online-description"> |
||
| 286 | <?= I18N::translate('You can choose whether to appear in the list of users who are currently signed-in.') ?> |
||
| 287 | </p> |
||
| 288 | </div> |
||
| 289 | </div> |
||
| 290 | </fieldset> |
||
| 291 | |||
| 292 | <div class="row form-group"> |
||
| 293 | <div class="col-sm-9 offset-sm-3"> |
||
| 294 | <input class="btn btn-primary" type="submit" value="<?= I18N::translate('save') ?>"> |
||
| 295 | </div> |
||
| 296 | </div> |
||
| 297 | </form> |
||
| 298 | |||
| 299 | <?php if (!Auth::user()->getPreference('canadmin')): ?> |
||
| 300 | <form method="post"> |
||
| 301 | <input type="hidden" name="action" value="delete"> |
||
| 302 | <?= Filter::getCsrf() ?> |
||
| 303 | <div class="row form-group"> |
||
| 304 | <div class="col-sm-9 offset-sm-3"> |
||
| 305 | <input class="btn btn-danger" type="submit" value="<?= I18N::translate('Delete your account') ?>" data-confirm="<?= I18N::translate('Are you sure you want to delete ā%sā?', e(Auth::user()->getUserName())) ?>" onclick="return confirm(this.dataset.confirm);"> |
||
| 306 | </div> |
||
| 307 | </div> |
||
| 308 | </form> |
||
| 309 | <?php endif ?> |
||
| 310 |
If a method or function can return multiple different values and unless you are sure that you only can receive a single value in this context, we recommend to add an additional type check:
If this a common case that PHP Analyzer should handle natively, please let us know by opening an issue.