mirror of https://github.com/nextcloud/server.git
parent
7215148a24
commit
309354852f
@ -0,0 +1,98 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OC\Core\Controller;
|
||||
|
||||
use OC\Core\Db\ProfileConfigMapper;
|
||||
use OCP\AppFramework\Http\DataResponse;
|
||||
use OCP\AppFramework\OCS\OCSBadRequestException;
|
||||
use OCP\AppFramework\OCS\OCSForbiddenException;
|
||||
use OCP\AppFramework\OCS\OCSNotFoundException;
|
||||
use OCP\AppFramework\OCSController;
|
||||
use OCP\IRequest;
|
||||
use OCP\IUserManager;
|
||||
use OCP\IUserSession;
|
||||
use OC\Profile\ProfileManager;
|
||||
|
||||
class ProfileApiController extends OCSController {
|
||||
|
||||
/** @var ProfileConfigMapper */
|
||||
private $configMapper;
|
||||
|
||||
/** @var ProfileManager */
|
||||
private $profileManager;
|
||||
|
||||
/** @var IUserManager */
|
||||
private $userManager;
|
||||
|
||||
/** @var IUserSession */
|
||||
private $userSession;
|
||||
|
||||
public function __construct(
|
||||
IRequest $request,
|
||||
ProfileConfigMapper $configMapper,
|
||||
ProfileManager $profileManager,
|
||||
IUserManager $userManager,
|
||||
IUserSession $userSession
|
||||
) {
|
||||
parent::__construct('core', $request);
|
||||
$this->configMapper = $configMapper;
|
||||
$this->profileManager = $profileManager;
|
||||
$this->userManager = $userManager;
|
||||
$this->userSession = $userSession;
|
||||
}
|
||||
|
||||
/**
|
||||
* @NoAdminRequired
|
||||
* @NoSubAdminRequired
|
||||
* @PasswordConfirmationRequired
|
||||
*/
|
||||
public function setVisibility(string $targetUserId, string $paramId, string $visibility): DataResponse {
|
||||
$requestingUser = $this->userSession->getUser();
|
||||
$targetUser = $this->userManager->get($targetUserId);
|
||||
|
||||
if (!$this->userManager->userExists($targetUserId)) {
|
||||
throw new OCSNotFoundException('User does not exist');
|
||||
}
|
||||
|
||||
if ($requestingUser !== $targetUser) {
|
||||
throw new OCSForbiddenException('Users can only edit their own visibility settings');
|
||||
}
|
||||
|
||||
// Ensure that a profile config is created in the database
|
||||
$this->profileManager->getProfileConfig($targetUser, $targetUser);
|
||||
$config = $this->configMapper->get($targetUserId);
|
||||
|
||||
if (!in_array($paramId, array_keys($config->getVisibilityMap()), true)) {
|
||||
throw new OCSBadRequestException('User does not have a profile parameter with ID: ' . $paramId);
|
||||
}
|
||||
|
||||
$config->setVisibility($paramId, $visibility);
|
||||
$this->configMapper->update($config);
|
||||
|
||||
return new DataResponse();
|
||||
}
|
||||
}
|
@ -0,0 +1,131 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OC\Core\Controller;
|
||||
|
||||
use OCP\Accounts\IAccountManager;
|
||||
use OCP\AppFramework\Controller;
|
||||
use OCP\AppFramework\Http\TemplateResponse;
|
||||
use OCP\AppFramework\Services\IInitialState;
|
||||
use OCP\IRequest;
|
||||
use OCP\IUserManager;
|
||||
use OCP\IUserSession;
|
||||
use OC\Profile\ProfileManager;
|
||||
use OCP\UserStatus\IManager as IUserStatusManager;
|
||||
|
||||
class ProfilePageController extends Controller {
|
||||
use \OC\Profile\TProfileHelper;
|
||||
|
||||
/** @var IInitialState */
|
||||
private $initialStateService;
|
||||
|
||||
/** @var IAccountManager */
|
||||
private $accountManager;
|
||||
|
||||
/** @var ProfileManager */
|
||||
private $profileManager;
|
||||
|
||||
/** @var IUserManager */
|
||||
private $userManager;
|
||||
|
||||
/** @var IUserSession */
|
||||
private $userSession;
|
||||
|
||||
/** @var IUserStatusManager */
|
||||
private $userStatusManager;
|
||||
|
||||
public function __construct(
|
||||
$appName,
|
||||
IRequest $request,
|
||||
IInitialState $initialStateService,
|
||||
IAccountManager $accountManager,
|
||||
ProfileManager $profileManager,
|
||||
IUserManager $userManager,
|
||||
IUserSession $userSession,
|
||||
IUserStatusManager $userStatusManager
|
||||
) {
|
||||
parent::__construct($appName, $request);
|
||||
$this->initialStateService = $initialStateService;
|
||||
$this->accountManager = $accountManager;
|
||||
$this->profileManager = $profileManager;
|
||||
$this->userManager = $userManager;
|
||||
$this->userSession = $userSession;
|
||||
$this->userStatusManager = $userStatusManager;
|
||||
}
|
||||
|
||||
/**
|
||||
* @PublicPage
|
||||
* @NoCSRFRequired
|
||||
* @NoAdminRequired
|
||||
* @NoSubAdminRequired
|
||||
*/
|
||||
public function index(string $targetUserId): TemplateResponse {
|
||||
if (!$this->userManager->userExists($targetUserId)) {
|
||||
return new TemplateResponse(
|
||||
'core',
|
||||
'404-profile',
|
||||
[],
|
||||
TemplateResponse::RENDER_AS_GUEST,
|
||||
);
|
||||
}
|
||||
|
||||
$visitingUser = $this->userSession->getUser();
|
||||
$targetUser = $this->userManager->get($targetUserId);
|
||||
$targetAccount = $this->accountManager->getAccount($targetUser);
|
||||
|
||||
if (!$this->isProfileEnabled($targetAccount)) {
|
||||
return new TemplateResponse(
|
||||
'core',
|
||||
'404-profile',
|
||||
[],
|
||||
TemplateResponse::RENDER_AS_GUEST,
|
||||
);
|
||||
}
|
||||
|
||||
$userStatuses = $this->userStatusManager->getUserStatuses([$targetUserId]);
|
||||
$status = array_shift($userStatuses);
|
||||
if (!empty($status)) {
|
||||
$this->initialStateService->provideInitialState('status', [
|
||||
'icon' => $status->getIcon(),
|
||||
'message' => $status->getMessage(),
|
||||
]);
|
||||
}
|
||||
|
||||
$this->initialStateService->provideInitialState(
|
||||
'profileParameters',
|
||||
$this->profileManager->getProfileParams($targetUser, $visitingUser),
|
||||
);
|
||||
|
||||
\OCP\Util::addScript('core', 'dist/profile');
|
||||
|
||||
return new TemplateResponse(
|
||||
'core',
|
||||
'profile',
|
||||
[],
|
||||
$this->userSession->isLoggedIn() ? TemplateResponse::RENDER_AS_USER : TemplateResponse::RENDER_AS_PUBLIC,
|
||||
);
|
||||
}
|
||||
}
|
@ -0,0 +1,172 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OC\Core\Db;
|
||||
|
||||
use function Safe\json_decode;
|
||||
use function Safe\json_encode;
|
||||
use \JsonSerializable;
|
||||
use OCP\Accounts\IAccountManager;
|
||||
use OCP\AppFramework\Db\Entity;
|
||||
use OCP\Profile\ParameterDoesNotExistException;
|
||||
|
||||
/**
|
||||
* @method string getUserId()
|
||||
* @method void setUserId(string $userId)
|
||||
* @method string getConfig()
|
||||
* @method void setConfig(string $config)
|
||||
*/
|
||||
class ProfileConfig extends Entity implements JsonSerializable {
|
||||
|
||||
/**
|
||||
* Visible to users, guests, and public access
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public const VISIBILITY_SHOW = 'show';
|
||||
|
||||
/**
|
||||
* Visible to users and guests
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public const VISIBILITY_SHOW_USERS_ONLY = 'show_users_only';
|
||||
|
||||
/**
|
||||
* Visible to nobody
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public const VISIBILITY_HIDE = 'hide';
|
||||
|
||||
/**
|
||||
* Default account property visibility
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public const DEFAULT_PROPERTY_VISIBILITY = [
|
||||
IAccountManager::PROPERTY_ADDRESS => self::VISIBILITY_SHOW_USERS_ONLY,
|
||||
IAccountManager::PROPERTY_AVATAR => self::VISIBILITY_SHOW,
|
||||
IAccountManager::PROPERTY_BIOGRAPHY => self::VISIBILITY_SHOW,
|
||||
IAccountManager::PROPERTY_DISPLAYNAME => self::VISIBILITY_SHOW,
|
||||
IAccountManager::PROPERTY_HEADLINE => self::VISIBILITY_SHOW,
|
||||
IAccountManager::PROPERTY_ORGANISATION => self::VISIBILITY_SHOW,
|
||||
IAccountManager::PROPERTY_ROLE => self::VISIBILITY_SHOW,
|
||||
IAccountManager::PROPERTY_EMAIL => self::VISIBILITY_SHOW_USERS_ONLY,
|
||||
IAccountManager::PROPERTY_PHONE => self::VISIBILITY_SHOW_USERS_ONLY,
|
||||
IAccountManager::PROPERTY_TWITTER => self::VISIBILITY_SHOW,
|
||||
IAccountManager::PROPERTY_WEBSITE => self::VISIBILITY_SHOW,
|
||||
];
|
||||
|
||||
/**
|
||||
* Default visibility
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public const DEFAULT_VISIBILITY = self::VISIBILITY_SHOW_USERS_ONLY;
|
||||
|
||||
/** @var string */
|
||||
protected $userId;
|
||||
|
||||
/** @var string */
|
||||
protected $config;
|
||||
|
||||
public function __construct() {
|
||||
$this->addType('userId', 'string');
|
||||
$this->addType('config', 'string');
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the config in an associative array
|
||||
*/
|
||||
public function getConfigArray(): array {
|
||||
return json_decode($this->config, true);
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the config
|
||||
*/
|
||||
public function setConfigArray(array $config): void {
|
||||
$this->setConfig(json_encode($config));
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the visibility map in an associative array
|
||||
*/
|
||||
public function getVisibilityMap(): array {
|
||||
$config = $this->getConfigArray();
|
||||
$visibilityMap = [];
|
||||
foreach ($config as $paramId => $paramConfig) {
|
||||
$visibilityMap[$paramId] = $paramConfig['visibility'];
|
||||
}
|
||||
|
||||
return $visibilityMap;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the visibility map
|
||||
*/
|
||||
public function setVisibilityMap(array $visibilityMap): void {
|
||||
$config = $this->getConfigArray();
|
||||
foreach ($visibilityMap as $paramId => $visibility) {
|
||||
$config[$paramId] = array_merge(
|
||||
$config[$paramId] ?: [],
|
||||
['visibility' => $visibility],
|
||||
);
|
||||
}
|
||||
|
||||
$this->setConfigArray($config);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the visibility of the parameter
|
||||
*
|
||||
* @throws ParameterDoesNotExistException
|
||||
*/
|
||||
public function getVisibility(string $paramId): string {
|
||||
$visibilityMap = $this->getVisibilityMap();
|
||||
if (isset($visibilityMap[$paramId])) {
|
||||
return $visibilityMap[$paramId];
|
||||
}
|
||||
throw new ParameterDoesNotExistException($paramId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the visibility of the parameter
|
||||
*/
|
||||
public function setVisibility(string $paramId, string $visibility): void {
|
||||
$visibilityMap = $this->getVisibilityMap();
|
||||
$visibilityMap[$paramId] = $visibility;
|
||||
$this->setVisibilityMap($visibilityMap);
|
||||
}
|
||||
|
||||
public function jsonSerialize(): array {
|
||||
return [
|
||||
'userId' => $this->userId,
|
||||
'config' => $this->getConfigArray(),
|
||||
];
|
||||
}
|
||||
}
|
@ -0,0 +1,48 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OC\Core\Db;
|
||||
|
||||
use OCP\AppFramework\Db\QBMapper;
|
||||
use OCP\IDBConnection;
|
||||
|
||||
class ProfileConfigMapper extends QBMapper {
|
||||
public function __construct(IDBConnection $db) {
|
||||
parent::__construct($db, 'profile_config', ProfileConfig::class);
|
||||
}
|
||||
|
||||
public function get(string $userId): ProfileConfig {
|
||||
$qb = $this->db->getQueryBuilder();
|
||||
$qb->select('*')
|
||||
->from($this->getTableName())
|
||||
->where($qb->expr()->eq('user_id', $qb->createNamedParameter($userId)));
|
||||
return $this->findEntity($qb);
|
||||
}
|
||||
|
||||
public function getArray(string $userId): array {
|
||||
return $this->get($userId)->getConfigArray();
|
||||
}
|
||||
}
|
@ -0,0 +1,69 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OC\Core\Migrations;
|
||||
|
||||
use Closure;
|
||||
use OCP\DB\ISchemaWrapper;
|
||||
use OCP\DB\Types;
|
||||
use OCP\Migration\IOutput;
|
||||
use OCP\Migration\SimpleMigrationStep;
|
||||
|
||||
class Version23000Date20210930122352 extends SimpleMigrationStep {
|
||||
private const TABLE_NAME = 'profile_config';
|
||||
|
||||
/**
|
||||
* @param IOutput $output
|
||||
* @param Closure $schemaClosure The `\Closure` returns a `ISchemaWrapper`
|
||||
* @param array $options
|
||||
* @return null|ISchemaWrapper
|
||||
*/
|
||||
public function changeSchema(IOutput $output, Closure $schemaClosure, array $options): ?ISchemaWrapper {
|
||||
/** @var ISchemaWrapper $schema */
|
||||
$schema = $schemaClosure();
|
||||
|
||||
$hasTable = $schema->hasTable(self::TABLE_NAME);
|
||||
if (!$hasTable) {
|
||||
$table = $schema->createTable(self::TABLE_NAME);
|
||||
$table->addColumn('id', Types::INTEGER, [
|
||||
'autoincrement' => true,
|
||||
'notnull' => true,
|
||||
]);
|
||||
$table->addColumn('user_id', Types::STRING, [
|
||||
'notnull' => true,
|
||||
'length' => 64,
|
||||
]);
|
||||
$table->addColumn('config', Types::TEXT, [
|
||||
'notnull' => true,
|
||||
]);
|
||||
$table->setPrimaryKey(['id']);
|
||||
$table->addUniqueIndex(['user_id'], 'user_id');
|
||||
return $schema;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
}
|
@ -0,0 +1 @@
|
||||
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg"><path d="M4.41333 7.19333C5.37333 9.08 6.92 10.62 8.80667 11.5867L10.2733 10.12C10.4533 9.94 10.72 9.88 10.9533 9.96C11.7 10.2067 12.5067 10.34 13.3333 10.34C13.7 10.34 14 10.64 14 11.0067V13.3333C14 13.7 13.7 14 13.3333 14C7.07333 14 2 8.92667 2 2.66667C2 2.3 2.3 2 2.66667 2H5C5.36667 2 5.66667 2.3 5.66667 2.66667C5.66667 3.5 5.8 4.3 6.04667 5.04667C6.12 5.28 6.06667 5.54 5.88 5.72667L4.41333 7.19333Z" fill="black"/></svg>
|
After Width: | Height: | Size: 523 B |
@ -0,0 +1 @@
|
||||
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg"><path d="M8 1C8.92826 1 9.8185 1.36875 10.4749 2.02513C11.1313 2.6815 11.5 3.57174 11.5 4.5C11.5 5.42826 11.1313 6.3185 10.4749 6.97487C9.8185 7.63125 8.92826 8 8 8C7.07174 8 6.1815 7.63125 5.52513 6.97487C4.86875 6.3185 4.5 5.42826 4.5 4.5C4.5 3.57174 4.86875 2.6815 5.52513 2.02513C6.1815 1.36875 7.07174 1 8 1V1ZM8 9.75C11.8675 9.75 15 11.3162 15 13.25V15H1V13.25C1 11.3162 4.1325 9.75 8 9.75Z" fill="black"/></svg>
|
After Width: | Height: | Size: 514 B |
@ -1,3 +1 @@
|
||||
<svg enable-background="new 0 0 15 15" version="1.1" viewBox="0 0 15 15" xml:space="preserve" xmlns="http://www.w3.org/2000/svg" width="16" height="16">
|
||||
<path d="m14.982 7c-0.246-3.744-3.238-6.737-6.982-6.983v-0.017h-1v0.017c-3.744 0.246-6.737 3.239-6.983 6.983h-0.017v1h0.017c0.246 3.744 3.239 6.736 6.983 6.982v0.018h1v-0.018c3.744-0.246 6.736-3.238 6.982-6.982h0.018v-1h-0.018zm-10.287-5.365c-0.483 0.642-0.884 1.447-1.176 2.365h-1.498c0.652-1.017 1.578-1.84 2.674-2.365zm-3.197 3.365h1.758c-0.134 0.632-0.219 1.303-0.246 2h-1.991c0.053-0.704 0.219-1.377 0.479-2zm-0.479 3h1.991c0.027 0.697 0.112 1.368 0.246 2h-1.758c-0.26-0.623-0.426-1.296-0.479-2zm1.002 3h1.497c0.292 0.918 0.693 1.723 1.177 2.365-1.096-0.525-2.022-1.347-2.674-2.365zm4.979 2.936c-1.028-0.275-1.913-1.379-2.45-2.936h2.45v2.936zm0-3.936h-2.731c-0.141-0.623-0.23-1.296-0.259-2h2.99v2zm0-3h-2.99c0.029-0.704 0.118-1.377 0.259-2h2.731v2zm0-3h-2.45c0.537-1.557 1.422-2.661 2.45-2.935v2.935zm5.979 0h-1.496c-0.293-0.918-0.693-1.723-1.178-2.365 1.095 0.525 2.022 1.348 2.674 2.365zm-4.979-2.935c1.027 0.274 1.913 1.378 2.45 2.935h-2.45v-2.935zm0 3.935h2.73c0.142 0.623 0.229 1.296 0.26 2h-2.99v-2zm0 3h2.99c-0.029 0.704-0.118 1.377-0.26 2h-2.73v-2zm0 5.936v-2.936h2.45c-0.537 1.557-1.423 2.661-2.45 2.936zm2.305-0.571c0.483-0.643 0.885-1.447 1.178-2.365h1.496c-0.652 1.018-1.579 1.84-2.674 2.365zm3.197-3.365h-1.758c0.134-0.632 0.219-1.303 0.246-2h1.99c-0.052 0.704-0.218 1.377-0.478 2zm-1.512-3c-0.027-0.697-0.112-1.368-0.246-2h1.758c0.26 0.623 0.426 1.296 0.479 2h-1.991z"/>
|
||||
</svg>
|
||||
<svg enable-background="new 0 0 15 15" version="1.1" viewBox="0 0 15 15" xml:space="preserve" xmlns="http://www.w3.org/2000/svg" width="16" height="16"><path d="m14.982 7c-0.246-3.744-3.238-6.737-6.982-6.983v-0.017h-1v0.017c-3.744 0.246-6.737 3.239-6.983 6.983h-0.017v1h0.017c0.246 3.744 3.239 6.736 6.983 6.982v0.018h1v-0.018c3.744-0.246 6.736-3.238 6.982-6.982h0.018v-1h-0.018zm-10.287-5.365c-0.483 0.642-0.884 1.447-1.176 2.365h-1.498c0.652-1.017 1.578-1.84 2.674-2.365zm-3.197 3.365h1.758c-0.134 0.632-0.219 1.303-0.246 2h-1.991c0.053-0.704 0.219-1.377 0.479-2zm-0.479 3h1.991c0.027 0.697 0.112 1.368 0.246 2h-1.758c-0.26-0.623-0.426-1.296-0.479-2zm1.002 3h1.497c0.292 0.918 0.693 1.723 1.177 2.365-1.096-0.525-2.022-1.347-2.674-2.365zm4.979 2.936c-1.028-0.275-1.913-1.379-2.45-2.936h2.45v2.936zm0-3.936h-2.731c-0.141-0.623-0.23-1.296-0.259-2h2.99v2zm0-3h-2.99c0.029-0.704 0.118-1.377 0.259-2h2.731v2zm0-3h-2.45c0.537-1.557 1.422-2.661 2.45-2.935v2.935zm5.979 0h-1.496c-0.293-0.918-0.693-1.723-1.178-2.365 1.095 0.525 2.022 1.348 2.674 2.365zm-4.979-2.935c1.027 0.274 1.913 1.378 2.45 2.935h-2.45v-2.935zm0 3.935h2.73c0.142 0.623 0.229 1.296 0.26 2h-2.99v-2zm0 3h2.99c-0.029 0.704-0.118 1.377-0.26 2h-2.73v-2zm0 5.936v-2.936h2.45c-0.537 1.557-1.423 2.661-2.45 2.936zm2.305-0.571c0.483-0.643 0.885-1.447 1.178-2.365h1.496c-0.652 1.018-1.579 1.84-2.674 2.365zm3.197-3.365h-1.758c0.134-0.632 0.219-1.303 0.246-2h1.99c-0.052 0.704-0.218 1.377-0.478 2zm-1.512-3c-0.027-0.697-0.112-1.368-0.246-2h1.758c0.26 0.623 0.426 1.296 0.479 2h-1.991z"/></svg>
|
||||
|
Before Width: | Height: | Size: 1.5 KiB After Width: | Height: | Size: 1.5 KiB |
@ -0,0 +1 @@
|
||||
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg"><path d="M14.3194 5.30903C14.329 5.44903 14.329 5.58903 14.329 5.73032C14.329 10.0355 11.0516 15.0006 5.05871 15.0006V14.9981C3.28839 15.0006 1.55484 14.4935 0.0645161 13.5374C0.321935 13.5684 0.580645 13.5839 0.84 13.5845C2.3071 13.5858 3.73226 13.0935 4.88645 12.1871C3.49226 12.1606 2.26968 11.2516 1.84258 9.92452C2.33097 10.0187 2.83419 9.99935 3.31355 9.86839C1.79355 9.56129 0.7 8.22581 0.7 6.67484C0.7 6.66064 0.7 6.6471 0.7 6.63355C1.1529 6.88581 1.66 7.02581 2.17871 7.04129C0.747097 6.08451 0.305806 4.18 1.17032 2.69097C2.82452 4.72645 5.26516 5.96387 7.88516 6.09484C7.62258 4.96322 7.98129 3.77742 8.82774 2.98193C10.14 1.74839 12.2039 1.81161 13.4374 3.12322C14.1671 2.97935 14.8665 2.71161 15.5065 2.33226C15.2632 3.08645 14.7542 3.7271 14.0742 4.13419C14.72 4.05806 15.351 3.88516 15.9452 3.62129C15.5077 4.27677 14.9568 4.84774 14.3194 5.30903Z" fill="black"/></svg>
|
After Width: | Height: | Size: 980 B |
@ -0,0 +1,93 @@
|
||||
<?php
|
||||
|
||||
/**
|
||||
* @copyright 2017 Christoph Wurst <christoph@winzerhof-wurst.at>
|
||||
*
|
||||
* @author Christoph Wurst <christoph@winzerhof-wurst.at>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OC\Contacts\ContactsMenu\Providers;
|
||||
|
||||
use OCP\Accounts\IAccountManager;
|
||||
use OCP\Contacts\ContactsMenu\IActionFactory;
|
||||
use OCP\Contacts\ContactsMenu\IEntry;
|
||||
use OCP\Contacts\ContactsMenu\IProvider;
|
||||
use OCP\IURLGenerator;
|
||||
use OCP\IUserManager;
|
||||
use OCP\L10N\IFactory as IL10NFactory;
|
||||
|
||||
class ProfileProvider implements IProvider {
|
||||
use \OC\Profile\TProfileHelper;
|
||||
|
||||
/** @var IAccountManager */
|
||||
private $accountManager;
|
||||
|
||||
/** @var IActionFactory */
|
||||
private $actionFactory;
|
||||
|
||||
/** @var IL10NFactory */
|
||||
private $l10nFactory;
|
||||
|
||||
/** @var IURLGenerator */
|
||||
private $urlGenerator;
|
||||
|
||||
/** @var IUserManager */
|
||||
private $userManager;
|
||||
|
||||
/**
|
||||
* @param IAccountManager $accountManager
|
||||
* @param IActionFactory $actionFactory
|
||||
* @param IL10NFactory $l10nFactory
|
||||
* @param IURLGenerator $urlGenerator
|
||||
* @param IUserManager $userManager
|
||||
*/
|
||||
public function __construct(
|
||||
IAccountManager $accountManager,
|
||||
IActionFactory $actionFactory,
|
||||
IL10NFactory $l10nFactory,
|
||||
IURLGenerator $urlGenerator,
|
||||
IUserManager $userManager
|
||||
) {
|
||||
$this->accountManager = $accountManager;
|
||||
$this->actionFactory = $actionFactory;
|
||||
$this->l10nFactory = $l10nFactory;
|
||||
$this->urlGenerator = $urlGenerator;
|
||||
$this->userManager = $userManager;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param IEntry $entry
|
||||
*/
|
||||
public function process(IEntry $entry) {
|
||||
$targetUserId = $entry->getProperty('UID');
|
||||
$targetUser = $this->userManager->get($targetUserId);
|
||||
if (!empty($targetUser)) {
|
||||
$account = $this->accountManager->getAccount($targetUser);
|
||||
if ($this->isProfileEnabled($account)) {
|
||||
$iconUrl = $this->urlGenerator->getAbsoluteURL($this->urlGenerator->imagePath('core', 'actions/profile.svg'));
|
||||
$profileActionText = $this->l10nFactory->get('core')->t('View profile');
|
||||
$profileUrl = $this->urlGenerator->linkToRouteAbsolute('core.ProfilePage.index', ['targetUserId' => $targetUserId]);
|
||||
$action = $this->actionFactory->newLinkAction($iconUrl, $profileActionText, $profileUrl);
|
||||
// Set highest priority (by descending order), other actions have the default priority 10 as defined in lib/private/Contacts/ContactsMenu/Actions/LinkAction.php
|
||||
$action->setPriority(20);
|
||||
$entry->addAction($action);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,94 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OC\Profile\Actions;
|
||||
|
||||
use OCP\Accounts\IAccountManager;
|
||||
use OCP\IURLGenerator;
|
||||
use OCP\IUser;
|
||||
use OCP\L10N\IFactory;
|
||||
use OCP\Profile\ILinkAction;
|
||||
|
||||
class EmailAction implements ILinkAction {
|
||||
|
||||
/** @var string */
|
||||
private $value;
|
||||
|
||||
/** @var IAccountManager */
|
||||
private $accountManager;
|
||||
|
||||
/** @var IFactory */
|
||||
private $l10nFactory;
|
||||
|
||||
/** @var IUrlGenerator */
|
||||
private $urlGenerator;
|
||||
|
||||
public function __construct(
|
||||
IAccountManager $accountManager,
|
||||
IFactory $l10nFactory,
|
||||
IURLGenerator $urlGenerator
|
||||
) {
|
||||
$this->accountManager = $accountManager;
|
||||
$this->l10nFactory = $l10nFactory;
|
||||
$this->urlGenerator = $urlGenerator;
|
||||
}
|
||||
|
||||
public function preload(IUser $targetUser): void {
|
||||
$account = $this->accountManager->getAccount($targetUser);
|
||||
$this->value = $account->getProperty(IAccountManager::PROPERTY_EMAIL)->getValue();
|
||||
}
|
||||
|
||||
public function getAppId(): string {
|
||||
return 'core';
|
||||
}
|
||||
|
||||
public function getId(): string {
|
||||
return IAccountManager::PROPERTY_EMAIL;
|
||||
}
|
||||
|
||||
public function getDisplayId(): string {
|
||||
return $this->l10nFactory->get('core')->t('Email');
|
||||
}
|
||||
|
||||
public function getTitle(): string {
|
||||
return $this->l10nFactory->get('core')->t('Mail %s', [$this->value]);
|
||||
}
|
||||
|
||||
public function getPriority(): int {
|
||||
return 20;
|
||||
}
|
||||
|
||||
public function getIcon(): string {
|
||||
return $this->urlGenerator->getAbsoluteURL($this->urlGenerator->imagePath('core', 'actions/mail.svg'));
|
||||
}
|
||||
|
||||
public function getTarget(): ?string {
|
||||
if (empty($this->value)) {
|
||||
return null;
|
||||
}
|
||||
return 'mailto:' . $this->value;
|
||||
}
|
||||
}
|
@ -0,0 +1,94 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OC\Profile\Actions;
|
||||
|
||||
use OCP\Accounts\IAccountManager;
|
||||
use OCP\IURLGenerator;
|
||||
use OCP\IUser;
|
||||
use OCP\L10N\IFactory;
|
||||
use OCP\Profile\ILinkAction;
|
||||
|
||||
class PhoneAction implements ILinkAction {
|
||||
|
||||
/** @var string */
|
||||
private $value;
|
||||
|
||||
/** @var IAccountManager */
|
||||
private $accountManager;
|
||||
|
||||
/** @var IFactory */
|
||||
private $l10nFactory;
|
||||
|
||||
/** @var IUrlGenerator */
|
||||
private $urlGenerator;
|
||||
|
||||
public function __construct(
|
||||
IAccountManager $accountManager,
|
||||
IFactory $l10nFactory,
|
||||
IURLGenerator $urlGenerator
|
||||
) {
|
||||
$this->accountManager = $accountManager;
|
||||
$this->l10nFactory = $l10nFactory;
|
||||
$this->urlGenerator = $urlGenerator;
|
||||
}
|
||||
|
||||
public function preload(IUser $targetUser): void {
|
||||
$account = $this->accountManager->getAccount($targetUser);
|
||||
$this->value = $account->getProperty(IAccountManager::PROPERTY_PHONE)->getValue();
|
||||
}
|
||||
|
||||
public function getAppId(): string {
|
||||
return 'core';
|
||||
}
|
||||
|
||||
public function getId(): string {
|
||||
return IAccountManager::PROPERTY_PHONE;
|
||||
}
|
||||
|
||||
public function getDisplayId(): string {
|
||||
return $this->l10nFactory->get('core')->t('Phone');
|
||||
}
|
||||
|
||||
public function getTitle(): string {
|
||||
return $this->l10nFactory->get('core')->t('Call %s', [$this->value]);
|
||||
}
|
||||
|
||||
public function getPriority(): int {
|
||||
return 30;
|
||||
}
|
||||
|
||||
public function getIcon(): string {
|
||||
return $this->urlGenerator->getAbsoluteURL($this->urlGenerator->imagePath('core', 'actions/phone.svg'));
|
||||
}
|
||||
|
||||
public function getTarget(): ?string {
|
||||
if (empty($this->value)) {
|
||||
return null;
|
||||
}
|
||||
return 'tel:' . $this->value;
|
||||
}
|
||||
}
|
@ -0,0 +1,97 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OC\Profile\Actions;
|
||||
|
||||
use function Safe\substr;
|
||||
use OCP\Accounts\IAccountManager;
|
||||
use OCP\IURLGenerator;
|
||||
use OCP\IUser;
|
||||
use OCP\L10N\IFactory;
|
||||
use OCP\Profile\ILinkAction;
|
||||
|
||||
class TwitterAction implements ILinkAction {
|
||||
|
||||
/** @var string */
|
||||
private $value;
|
||||
|
||||
/** @var IAccountManager */
|
||||
private $accountManager;
|
||||
|
||||
/** @var IFactory */
|
||||
private $l10nFactory;
|
||||
|
||||
/** @var IUrlGenerator */
|
||||
private $urlGenerator;
|
||||
|
||||
public function __construct(
|
||||
IAccountManager $accountManager,
|
||||
IFactory $l10nFactory,
|
||||
IURLGenerator $urlGenerator
|
||||
) {
|
||||
$this->accountManager = $accountManager;
|
||||
$this->l10nFactory = $l10nFactory;
|
||||
$this->urlGenerator = $urlGenerator;
|
||||
}
|
||||
|
||||
public function preload(IUser $targetUser): void {
|
||||
$account = $this->accountManager->getAccount($targetUser);
|
||||
$this->value = $account->getProperty(IAccountManager::PROPERTY_TWITTER)->getValue();
|
||||
}
|
||||
|
||||
public function getAppId(): string {
|
||||
return 'core';
|
||||
}
|
||||
|
||||
public function getId(): string {
|
||||
return IAccountManager::PROPERTY_TWITTER;
|
||||
}
|
||||
|
||||
public function getDisplayId(): string {
|
||||
return $this->l10nFactory->get('core')->t('Twitter');
|
||||
}
|
||||
|
||||
public function getTitle(): string {
|
||||
$displayUsername = $this->value[0] === '@' ? $this->value : '@' . $this->value;
|
||||
return $this->l10nFactory->get('core')->t('View %s on Twitter', [$displayUsername]);
|
||||
}
|
||||
|
||||
public function getPriority(): int {
|
||||
return 50;
|
||||
}
|
||||
|
||||
public function getIcon(): string {
|
||||
return $this->urlGenerator->getAbsoluteURL($this->urlGenerator->imagePath('core', 'actions/twitter.svg'));
|
||||
}
|
||||
|
||||
public function getTarget(): ?string {
|
||||
if (empty($this->value)) {
|
||||
return null;
|
||||
}
|
||||
$username = $this->value[0] === '@' ? substr($this->value, 1) : $this->value;
|
||||
return 'https://twitter.com/' . $username;
|
||||
}
|
||||
}
|
@ -0,0 +1,94 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OC\Profile\Actions;
|
||||
|
||||
use OCP\Accounts\IAccountManager;
|
||||
use OCP\IURLGenerator;
|
||||
use OCP\IUser;
|
||||
use OCP\L10N\IFactory;
|
||||
use OCP\Profile\ILinkAction;
|
||||
|
||||
class WebsiteAction implements ILinkAction {
|
||||
|
||||
/** @var string */
|
||||
private $value;
|
||||
|
||||
/** @var IAccountManager */
|
||||
private $accountManager;
|
||||
|
||||
/** @var IFactory */
|
||||
private $l10nFactory;
|
||||
|
||||
/** @var IUrlGenerator */
|
||||
private $urlGenerator;
|
||||
|
||||
public function __construct(
|
||||
IAccountManager $accountManager,
|
||||
IFactory $l10nFactory,
|
||||
IURLGenerator $urlGenerator
|
||||
) {
|
||||
$this->accountManager = $accountManager;
|
||||
$this->l10nFactory = $l10nFactory;
|
||||
$this->urlGenerator = $urlGenerator;
|
||||
}
|
||||
|
||||
public function preload(IUser $targetUser): void {
|
||||
$account = $this->accountManager->getAccount($targetUser);
|
||||
$this->value = $account->getProperty(IAccountManager::PROPERTY_WEBSITE)->getValue();
|
||||
}
|
||||
|
||||
public function getAppId(): string {
|
||||
return 'core';
|
||||
}
|
||||
|
||||
public function getId(): string {
|
||||
return IAccountManager::PROPERTY_WEBSITE;
|
||||
}
|
||||
|
||||
public function getDisplayId(): string {
|
||||
return $this->l10nFactory->get('core')->t('Website');
|
||||
}
|
||||
|
||||
public function getTitle(): string {
|
||||
return $this->l10nFactory->get('core')->t('Visit %s', [$this->value]);
|
||||
}
|
||||
|
||||
public function getPriority(): int {
|
||||
return 40;
|
||||
}
|
||||
|
||||
public function getIcon(): string {
|
||||
return $this->urlGenerator->getAbsoluteURL($this->urlGenerator->imagePath('core', 'actions/timezone.svg'));
|
||||
}
|
||||
|
||||
public function getTarget(): ?string {
|
||||
if (empty($this->value)) {
|
||||
return null;
|
||||
}
|
||||
return $this->value;
|
||||
}
|
||||
}
|
@ -0,0 +1,333 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OC\Profile;
|
||||
|
||||
use function Safe\usort;
|
||||
|
||||
use OC\AppFramework\Bootstrap\Coordinator;
|
||||
use OC\Core\Db\ProfileConfig;
|
||||
use OC\Core\Db\ProfileConfigMapper;
|
||||
use OC\KnownUser\KnownUserService;
|
||||
use OC\Profile\Actions\EmailAction;
|
||||
use OC\Profile\Actions\PhoneAction;
|
||||
use OC\Profile\Actions\TwitterAction;
|
||||
use OC\Profile\Actions\WebsiteAction;
|
||||
use OCP\Accounts\IAccountManager;
|
||||
use OCP\Accounts\PropertyDoesNotExistException;
|
||||
use OCP\App\IAppManager;
|
||||
use OCP\AppFramework\Db\DoesNotExistException;
|
||||
use OCP\IUser;
|
||||
use OCP\L10N\IFactory;
|
||||
use OCP\Profile\ILinkAction;
|
||||
use Psr\Container\ContainerInterface;
|
||||
use Psr\Log\LoggerInterface;
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
class ProfileManager {
|
||||
|
||||
/** @var IAccountManager */
|
||||
private $accountManager;
|
||||
|
||||
/** @var IAppManager */
|
||||
private $appManager;
|
||||
|
||||
/** @var ProfileConfigMapper */
|
||||
private $configMapper;
|
||||
|
||||
/** @var ContainerInterface */
|
||||
private $container;
|
||||
|
||||
/** @var KnownUserService */
|
||||
private $knownUserService;
|
||||
|
||||
/** @var IFactory */
|
||||
private $l10nFactory;
|
||||
|
||||
/** @var LoggerInterface */
|
||||
private $logger;
|
||||
|
||||
/** @var Coordinator */
|
||||
private $coordinator;
|
||||
|
||||
/** @var ILinkAction[] */
|
||||
private $actions = [];
|
||||
|
||||
private const ACCOUNT_PROPERTY_ACTIONS = [
|
||||
EmailAction::class,
|
||||
PhoneAction::class,
|
||||
WebsiteAction::class,
|
||||
TwitterAction::class,
|
||||
];
|
||||
|
||||
/**
|
||||
* Array of account properties displayed on the profile
|
||||
*/
|
||||
private const PROFILE_PROPERTIES = [
|
||||
IAccountManager::PROPERTY_ADDRESS,
|
||||
IAccountManager::PROPERTY_BIOGRAPHY,
|
||||
IAccountManager::PROPERTY_DISPLAYNAME,
|
||||
IAccountManager::PROPERTY_HEADLINE,
|
||||
IAccountManager::PROPERTY_ORGANISATION,
|
||||
IAccountManager::PROPERTY_ROLE,
|
||||
];
|
||||
|
||||
public function __construct(
|
||||
IAccountManager $accountManager,
|
||||
IAppManager $appManager,
|
||||
ProfileConfigMapper $configMapper,
|
||||
ContainerInterface $container,
|
||||
KnownUserService $knownUserService,
|
||||
IFactory $l10nFactory,
|
||||
LoggerInterface $logger,
|
||||
Coordinator $coordinator
|
||||
) {
|
||||
$this->accountManager = $accountManager;
|
||||
$this->appManager = $appManager;
|
||||
$this->configMapper = $configMapper;
|
||||
$this->container = $container;
|
||||
$this->knownUserService = $knownUserService;
|
||||
$this->l10nFactory = $l10nFactory;
|
||||
$this->logger = $logger;
|
||||
$this->coordinator = $coordinator;
|
||||
}
|
||||
|
||||
/**
|
||||
* Register an action for the user
|
||||
*/
|
||||
private function registerAction(IUser $targetUser, ?IUser $visitingUser, ILinkAction $action): void {
|
||||
$action->preload($targetUser);
|
||||
|
||||
if ($action->getTarget() === null) {
|
||||
// Actions without a target are not registered
|
||||
return;
|
||||
}
|
||||
|
||||
if (isset($this->actions[$action->getId()])) {
|
||||
$this->logger->error('Cannot register duplicate action: ' . $action->getId());
|
||||
return;
|
||||
}
|
||||
|
||||
if ($action->getAppId() !== 'core') {
|
||||
if (!$this->appManager->isEnabledForUser($action->getAppId(), $targetUser)) {
|
||||
$this->logger->notice('App: ' . $action->getAppId() . ' cannot register actions as it is not enabled for the user: ' . $targetUser->getUID());
|
||||
return;
|
||||
}
|
||||
if ($visitingUser === null) {
|
||||
$this->logger->notice('App: ' . $action->getAppId() . ' cannot register actions as it is not available to non logged in users');
|
||||
return;
|
||||
}
|
||||
if (!$this->appManager->isEnabledForUser($action->getAppId(), $visitingUser)) {
|
||||
$this->logger->notice('App: ' . $action->getAppId() . ' cannot register actions as it is not enabled for the visiting user: ' . $visitingUser->getUID());
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// Add action to associative array of actions
|
||||
$this->actions[$action->getId()] = $action;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return an array of registered profile actions for the user
|
||||
*
|
||||
* @return ILinkAction[]
|
||||
*/
|
||||
private function getActions(IUser $targetUser, ?IUser $visitingUser): array {
|
||||
$context = $this->coordinator->getRegistrationContext();
|
||||
if ($context === null) {
|
||||
return [];
|
||||
}
|
||||
|
||||
foreach (self::ACCOUNT_PROPERTY_ACTIONS as $actionClass) {
|
||||
/** @var ILinkAction $provider */
|
||||
$provider = $this->container->get($actionClass);
|
||||
$this->registerAction($targetUser, $visitingUser, $provider);
|
||||
}
|
||||
|
||||
foreach ($context->getProfileActions() as $registration) {
|
||||
/** @var ILinkAction $provider */
|
||||
$provider = $this->container->get($registration->getService());
|
||||
$this->registerAction($targetUser, $visitingUser, $provider);
|
||||
}
|
||||
|
||||
$actionsClone = $this->actions;
|
||||
// Sort associative array into indexed array in ascending order of priority
|
||||
usort($actionsClone, function (ILinkAction $a, ILinkAction $b) {
|
||||
return $a->getPriority() === $b->getPriority() ? 0 : ($a->getPriority() < $b->getPriority() ? -1 : 1);
|
||||
});
|
||||
return $actionsClone;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return whether the profile parameter is visible to the visiting user
|
||||
*/
|
||||
private function isParameterVisible(IUser $targetUser, ?IUser $visitingUser, string $paramId): bool {
|
||||
try {
|
||||
$account = $this->accountManager->getAccount($targetUser);
|
||||
$scope = $account->getProperty($paramId)->getScope();
|
||||
} catch (PropertyDoesNotExistException $e) {
|
||||
// Allow the exception as not all profile parameters are account properties
|
||||
}
|
||||
|
||||
$visibility = $this->getProfileConfig($targetUser, $visitingUser)[$paramId]['visibility'];
|
||||
// Handle profile visibility and account property scope
|
||||
switch ($visibility) {
|
||||
case ProfileConfig::VISIBILITY_HIDE:
|
||||
return false;
|
||||
case ProfileConfig::VISIBILITY_SHOW_USERS_ONLY:
|
||||
if (!empty($scope)) {
|
||||
switch ($scope) {
|
||||
case IAccountManager::SCOPE_PRIVATE:
|
||||
return $visitingUser !== null && $this->knownUserService->isKnownToUser($targetUser->getUID(), $visitingUser->getUID());
|
||||
case IAccountManager::SCOPE_LOCAL:
|
||||
case IAccountManager::SCOPE_FEDERATED:
|
||||
case IAccountManager::SCOPE_PUBLISHED:
|
||||
return $visitingUser !== null;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return $visitingUser !== null;
|
||||
case ProfileConfig::VISIBILITY_SHOW:
|
||||
if (!empty($scope)) {
|
||||
switch ($scope) {
|
||||
case IAccountManager::SCOPE_PRIVATE:
|
||||
return $visitingUser !== null && $this->knownUserService->isKnownToUser($targetUser->getUID(), $visitingUser->getUID());
|
||||
case IAccountManager::SCOPE_LOCAL:
|
||||
case IAccountManager::SCOPE_FEDERATED:
|
||||
case IAccountManager::SCOPE_PUBLISHED:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
public function getProfileParams(IUser $targetUser, ?IUser $visitingUser): array {
|
||||
$account = $this->accountManager->getAccount($targetUser);
|
||||
// Initialize associative array of profile parameters
|
||||
$profileParameters = [
|
||||
'userId' => $account->getUser()->getUID(),
|
||||
];
|
||||
|
||||
// Add account properties
|
||||
foreach (self::PROFILE_PROPERTIES as $property) {
|
||||
$profileParameters[$property] =
|
||||
$this->isParameterVisible($targetUser, $visitingUser, $property)
|
||||
// Explicitly set to null when value is empty string
|
||||
? ($account->getProperty($property)->getValue() ?: null)
|
||||
: null;
|
||||
}
|
||||
|
||||
// Add avatar visibility
|
||||
$profileParameters['isUserAvatarVisible'] = $this->isParameterVisible($targetUser, $visitingUser, IAccountManager::PROPERTY_AVATAR);
|
||||
|
||||
// Add actions
|
||||
$profileParameters['actions'] = array_map(
|
||||
function (ILinkAction $action) {
|
||||
return [
|
||||
'id' => $action->getId(),
|
||||
'icon' => $action->getIcon(),
|
||||
'title' => $action->getTitle(),
|
||||
'target' => $action->getTarget(),
|
||||
];
|
||||
},
|
||||
// This is needed to reindex the array after filtering
|
||||
array_values(
|
||||
array_filter(
|
||||
$this->getActions($targetUser, $visitingUser),
|
||||
function (ILinkAction $action) use ($targetUser, $visitingUser) {
|
||||
return $this->isParameterVisible($targetUser, $visitingUser, $action->getId());
|
||||
}
|
||||
),
|
||||
)
|
||||
);
|
||||
|
||||
return $profileParameters;
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
public function getProfileConfig(IUser $targetUser, ?IUser $visitingUser): array {
|
||||
try {
|
||||
$configArray = $this->configMapper->getArray($targetUser->getUID());
|
||||
} catch (DoesNotExistException $e) {
|
||||
$config = new ProfileConfig();
|
||||
$config->setUserId($targetUser->getUID());
|
||||
|
||||
// Map of account properties to display IDs
|
||||
$propertyDisplayMap = [
|
||||
IAccountManager::PROPERTY_ADDRESS => $this->l10nFactory->get('core')->t('Address'),
|
||||
IAccountManager::PROPERTY_AVATAR => $this->l10nFactory->get('core')->t('Avatar'),
|
||||
IAccountManager::PROPERTY_BIOGRAPHY => $this->l10nFactory->get('core')->t('About'),
|
||||
IAccountManager::PROPERTY_DISPLAYNAME => $this->l10nFactory->get('core')->t('Full name'),
|
||||
IAccountManager::PROPERTY_HEADLINE => $this->l10nFactory->get('core')->t('Headline'),
|
||||
IAccountManager::PROPERTY_ORGANISATION => $this->l10nFactory->get('core')->t('Organisation'),
|
||||
IAccountManager::PROPERTY_ROLE => $this->l10nFactory->get('core')->t('Role'),
|
||||
IAccountManager::PROPERTY_EMAIL => $this->l10nFactory->get('core')->t('Email'),
|
||||
IAccountManager::PROPERTY_PHONE => $this->l10nFactory->get('core')->t('Phone'),
|
||||
IAccountManager::PROPERTY_TWITTER => $this->l10nFactory->get('core')->t('Twitter'),
|
||||
IAccountManager::PROPERTY_WEBSITE => $this->l10nFactory->get('core')->t('Website'),
|
||||
];
|
||||
|
||||
// Contruct the default config for account properties
|
||||
$propertiesConfig = [];
|
||||
foreach ($propertyDisplayMap as $property => $displayId) {
|
||||
$propertiesConfig[$property] = [
|
||||
'displayId' => $displayId,
|
||||
'visibility' => ProfileConfig::DEFAULT_PROPERTY_VISIBILITY[$property] ?: ProfileConfig::DEFAULT_VISIBILITY,
|
||||
];
|
||||
}
|
||||
|
||||
// Contruct the default config for actions
|
||||
$actionsConfig = [];
|
||||
/** @var ILinkAction $action */
|
||||
foreach ($this->getActions($targetUser, $visitingUser) as $action) {
|
||||
$actionsConfig[$action->getId()] = [
|
||||
'displayId' => $action->getDisplayId(),
|
||||
'visibility' => ProfileConfig::DEFAULT_VISIBILITY,
|
||||
];
|
||||
}
|
||||
|
||||
// Set the default config
|
||||
$config->setConfigArray(array_merge($propertiesConfig, $actionsConfig));
|
||||
$this->configMapper->insert($config);
|
||||
$configArray = $config->getConfigArray();
|
||||
}
|
||||
|
||||
return $configArray;
|
||||
}
|
||||
}
|
@ -0,0 +1,46 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OC\Profile;
|
||||
|
||||
use OCP\Accounts\IAccount;
|
||||
use OCP\Accounts\IAccountManager;
|
||||
|
||||
trait TProfileHelper {
|
||||
|
||||
/**
|
||||
* Returns whether the profile is enabled for the account
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
protected function isProfileEnabled(IAccount $account): ?bool {
|
||||
return filter_var(
|
||||
$account->getProperty(IAccountManager::PROPERTY_PROFILE_ENABLED)->getValue(),
|
||||
FILTER_VALIDATE_BOOLEAN,
|
||||
FILTER_NULL_ON_FAILURE,
|
||||
);
|
||||
}
|
||||
}
|
@ -0,0 +1,115 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OCP\Profile;
|
||||
|
||||
use OCP\IUser;
|
||||
|
||||
/**
|
||||
* @since 23.0.0
|
||||
*/
|
||||
interface ILinkAction {
|
||||
|
||||
/**
|
||||
* Preload the user specific value required by the action
|
||||
*
|
||||
* e.g. the email is loaded for the email action and the userId for the Talk action
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public function preload(IUser $targetUser): void;
|
||||
|
||||
/**
|
||||
* Returns the app ID of the action
|
||||
*
|
||||
* e.g. 'spreed'
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public function getAppId(): string;
|
||||
|
||||
/**
|
||||
* Returns the unique ID of the action
|
||||
*
|
||||
* *For account properties this is the constant defined in lib/public/Accounts/IAccountManager.php*
|
||||
*
|
||||
* e.g. 'email'
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public function getId(): string;
|
||||
|
||||
/**
|
||||
* Returns the translated unique display ID of the action
|
||||
*
|
||||
* Should be something short and descriptive of the action
|
||||
* as this is seen by the end-user when configuring actions
|
||||
*
|
||||
* e.g. 'Email'
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public function getDisplayId(): string;
|
||||
|
||||
/**
|
||||
* Returns the translated title
|
||||
*
|
||||
* e.g. 'Mail user@domain.com'
|
||||
*
|
||||
* Use the L10N service to translate it
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public function getTitle(): string;
|
||||
|
||||
/**
|
||||
* Returns the priority
|
||||
*
|
||||
* *Actions are sorted in ascending order*
|
||||
*
|
||||
* e.g. 60
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public function getPriority(): int;
|
||||
|
||||
/**
|
||||
* Returns the URL link to the 16*16 SVG icon
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public function getIcon(): string;
|
||||
|
||||
/**
|
||||
* Returns the target of the action,
|
||||
* if null is returned the action won't be registered
|
||||
*
|
||||
* e.g. 'mailto:user@domain.com'
|
||||
*
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public function getTarget(): ?string;
|
||||
}
|
@ -0,0 +1,40 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
/**
|
||||
* @copyright 2021 Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @author Christopher Ng <chrng8@gmail.com>
|
||||
*
|
||||
* @license GNU AGPL version 3 or any later version
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace OCP\Profile;
|
||||
|
||||
/**
|
||||
* @since 23.0.0
|
||||
*/
|
||||
class ParameterDoesNotExistException extends \Exception {
|
||||
|
||||
/**
|
||||
* @since 23.0.0
|
||||
*/
|
||||
public function __construct($parameter) {
|
||||
parent::__construct("Parameter $parameter does not exist.");
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue