<?php
/**
- * @copyright Copyright (C) 2010-2022, the Friendica project
+ * @copyright Copyright (C) 2010-2023, the Friendica project
*
* @license GNU AGPL version 3 or any later version
*
use Friendica\Security\TwoFactor\Model\AppSpecificPassword;
use Friendica\Network\HTTPException;
use Friendica\Object\Image;
+use Friendica\Protocol\Delivery;
use Friendica\Util\Crypto;
use Friendica\Util\DateTimeFormat;
use Friendica\Util\Images;
use Friendica\Util\Network;
use Friendica\Util\Proxy;
use Friendica\Util\Strings;
-use Friendica\Worker\Delivery;
use ImagickException;
use LightOpenID;
$system['publish'] = false;
$system['net-publish'] = false;
$system['hide-friends'] = true;
+ $system['hidewall'] = true;
$system['prv_keywords'] = '';
$system['pub_keywords'] = '';
$system['address'] = '';
// List of possible actor names
$possible_accounts = ['friendica', 'actor', 'system', 'internal'];
foreach ($possible_accounts as $name) {
- if (!DBA::exists('user', ['nickname' => $name, 'account_removed' => false, 'expire' => false]) &&
+ if (!DBA::exists('user', ['nickname' => $name, 'account_removed' => false, 'account_expired' => false]) &&
!DBA::exists('userd', ['username' => $name])) {
DI::config()->set('system', 'actor_name', $name);
return $name;
*
* @param array $fields
* @return array user
+ * @throws Exception
*/
public static function getFirstAdmin(array $fields = []) : array
{
if (!empty(DI::config()->get('config', 'admin_nickname'))) {
return self::getByNickname(DI::config()->get('config', 'admin_nickname'), $fields);
- } elseif (!empty(DI::config()->get('config', 'admin_email'))) {
- $adminList = explode(',', str_replace(' ', '', DI::config()->get('config', 'admin_email')));
- return self::getByEmail($adminList[0], $fields);
- } else {
- return [];
}
+
+ return self::getAdminList()[0] ?? [];
}
/**
return $user;
}
+ /**
+ * Update the day of the last activity of the given user
+ *
+ * @param integer $uid
+ * @return void
+ */
+ public static function updateLastActivity(int $uid)
+ {
+ $user = User::getById($uid, ['last-activity']);
+ if (empty($user)) {
+ return;
+ }
+
+ $current_day = DateTimeFormat::utcNow('Y-m-d');
+
+ if ($user['last-activity'] != $current_day) {
+ User::update(['last-activity' => $current_day], $uid);
+ // Set the last actitivy for all identities of the user
+ DBA::update('user', ['last-activity' => $current_day], ['parent-uid' => $uid, 'account_removed' => false]);
+ }
+ }
+
/**
* Generates a human-readable random password
*
}
/**
- * Allowed characters are a-z, A-Z, 0-9 and special characters except white spaces, accentuated letters and colon (:).
+ * Allowed characters are a-z, A-Z, 0-9 and special characters except white spaces and accentuated letters.
*
* Password length is limited to 72 characters if the current default password hashing algorithm is Blowfish.
* From the manual: "Using the PASSWORD_BCRYPT as the algorithm, will result in the password parameter being
*/
public static function getPasswordRegExp(string $delimiter = null): string
{
- $allowed_characters = '!"#$%&\'()*+,-./;<=>?@[\]^_`{|}~';
+ $allowed_characters = ':!"#$%&\'()*+,-./;<=>?@[\]^_`{|}~';
if ($delimiter) {
$allowed_characters = preg_quote($allowed_characters, $delimiter);
}
- return '^[a-zA-Z0-9' . $allowed_characters . ']' . (PASSWORD_DEFAULT !== PASSWORD_BCRYPT ? '{1,72}' : '+') . '$';
+ return '^[a-zA-Z0-9' . $allowed_characters . ']' . (PASSWORD_DEFAULT === PASSWORD_BCRYPT ? '{1,72}' : '+') . '$';
}
/**
}
if (!preg_match('/' . self::getPasswordRegExp('/') . '/', $password)) {
- throw new Exception(DI::l10n()->t('The password can\'t contain accentuated letters, white spaces or colons (:)'));
+ throw new Exception(DI::l10n()->t("The password can't contain white spaces nor accentuated letters"));
}
return self::updatePasswordHashed($uid, self::hashPassword($password));
return DBA::update('user', $fields, ['uid' => $uid]);
}
+ /**
+ * Returns if the given uid is valid and in the admin list
+ *
+ * @param int $uid
+ *
+ * @return bool
+ * @throws Exception
+ */
+ public static function isSiteAdmin(int $uid): bool
+ {
+ return DBA::exists('user', [
+ 'uid' => $uid,
+ 'email' => self::getAdminEmailList()
+ ]);
+ }
+
/**
* Checks if a nickname is in the list of the forbidden nicknames
*
// Disallow somebody creating an account using openid that uses the admin email address,
// since openid bypasses email verification. We'll allow it if there is not yet an admin account.
- if (DI::config()->get('config', 'admin_email') && strlen($openid_url)) {
- $adminlist = explode(',', str_replace(' ', '', strtolower(DI::config()->get('config', 'admin_email'))));
- if (in_array(strtolower($email), $adminlist)) {
- throw new Exception(DI::l10n()->t('Cannot use that email.'));
- }
+ if (strlen($openid_url) && in_array(strtolower($email), self::getAdminEmailList())) {
+ throw new Exception(DI::l10n()->t('Cannot use that email.'));
}
$nickname = $data['nickname'] = strtolower($nickname);
If you are new and do not know anybody here, they may help
you to make some new and interesting friends.
- If you ever want to delete your account, you can do so at %1$s/removeme
+ If you ever want to delete your account, you can do so at %1$s/settings/removeme
Thank you and welcome to %4$s.'));
If you are new and do not know anybody here, they may help
you to make some new and interesting friends.
- If you ever want to delete your account, you can do so at %3$s/removeme
+ If you ever want to delete your account, you can do so at %3$s/settings/removeme
Thank you and welcome to %2$s.',
$user['nickname'],
'active_users_weekly' => 0,
];
- $userStmt = DBA::select('owner-view', ['uid', 'login_date', 'last-item'],
- ["`verified` AND `login_date` > ? AND NOT `blocked`
+ $userStmt = DBA::select('owner-view', ['uid', 'last-activity', 'last-item'],
+ ["`verified` AND `last-activity` > ? AND NOT `blocked`
AND NOT `account_removed` AND NOT `account_expired`",
DBA::NULL_DATETIME]);
if (!DBA::isResult($userStmt)) {
while ($user = DBA::fetch($userStmt)) {
$statistics['total_users']++;
- if ((strtotime($user['login_date']) > $halfyear) || (strtotime($user['last-item']) > $halfyear)
+ if ((strtotime($user['last-activity']) > $halfyear) || (strtotime($user['last-item']) > $halfyear)
) {
$statistics['active_users_halfyear']++;
}
- if ((strtotime($user['login_date']) > $month) || (strtotime($user['last-item']) > $month)
+ if ((strtotime($user['last-activity']) > $month) || (strtotime($user['last-item']) > $month)
) {
$statistics['active_users_monthly']++;
}
- if ((strtotime($user['login_date']) > $week) || (strtotime($user['last-item']) > $week)
+ if ((strtotime($user['last-activity']) > $week) || (strtotime($user['last-item']) > $week)
) {
$statistics['active_users_weekly']++;
}
return DBA::selectToArray('owner-view', [], $condition, $param);
}
+
+ /**
+ * Returns a list of lowercase admin email addresses from the comma-separated list in the config
+ *
+ * @return array
+ */
+ public static function getAdminEmailList(): array
+ {
+ $adminEmails = strtolower(str_replace(' ', '', DI::config()->get('config', 'admin_email')));
+ if (!$adminEmails) {
+ return [];
+ }
+
+ return explode(',', $adminEmails);
+ }
+
+ /**
+ * Returns the complete list of admin user accounts
+ *
+ * @param array $fields
+ * @return array
+ * @throws Exception
+ */
+ public static function getAdminList(array $fields = []): array
+ {
+ $condition = [
+ 'email' => self::getAdminEmailList(),
+ 'parent-uid' => 0,
+ 'blocked' => 0,
+ 'verified' => true,
+ 'account_removed' => false,
+ 'account_expired' => false,
+ ];
+
+ return DBA::selectToArray('user', $fields, $condition, ['order' => ['uid']]);
+ }
+
+ /**
+ * Return a list of admin user accounts where each unique email address appears only once.
+ *
+ * This method is meant for admin notifications that do not need to be sent multiple times to the same email address.
+ *
+ * @param array $fields
+ * @return array
+ * @throws Exception
+ */
+ public static function getAdminListForEmailing(array $fields = []): array
+ {
+ return array_filter(self::getAdminList($fields), function ($user) {
+ static $emails = [];
+
+ if (in_array($user['email'], $emails)) {
+ return false;
+ }
+
+ $emails[] = $user['email'];
+
+ return true;
+ });
+ }
}