diff --git a/src/MisuzuContext.php b/src/MisuzuContext.php index f0e61f7..7c31056 100644 --- a/src/MisuzuContext.php +++ b/src/MisuzuContext.php @@ -263,6 +263,7 @@ class MisuzuContext { $routingCtx->register(new \Misuzu\SharpChat\SharpChatRoutes( $this->config->scopeTo('sockChat'), + $this->config->scopeTo('impersonate'), $this->urls, $this->usersCtx, $this->authCtx, diff --git a/src/SharpChat/SharpChatRoutes.php b/src/SharpChat/SharpChatRoutes.php index 5273814..7b63f50 100644 --- a/src/SharpChat/SharpChatRoutes.php +++ b/src/SharpChat/SharpChatRoutes.php @@ -3,25 +3,21 @@ namespace Misuzu\SharpChat; use RuntimeException; use Index\Colour\Colour; -use Index\Routing\IRouter; -use Index\Routing\IRouteHandler; -use Index\Routing\Route; +use Index\Routing\{IRouter,IRouteHandler,Route}; use Syokuhou\IConfig; use Misuzu\RoutingContext; -use Misuzu\Auth\AuthContext; -use Misuzu\Auth\AuthInfo; -use Misuzu\Auth\Sessions; +use Misuzu\Auth\{AuthContext,AuthInfo,Sessions}; use Misuzu\Emoticons\Emotes; use Misuzu\Perms\Permissions; use Misuzu\URLs\URLRegistry; -use Misuzu\Users\Bans; -use Misuzu\Users\UsersContext; +use Misuzu\Users\{Bans,UsersContext,UserInfo}; final class SharpChatRoutes implements IRouteHandler { private string $hashKey; public function __construct( private IConfig $config, + private IConfig $impersonateConfig, // this sucks lol private URLRegistry $urls, private UsersContext $usersCtx, private AuthContext $authCtx, @@ -79,6 +75,14 @@ final class SharpChatRoutes implements IRouteHandler { )); } + private function canImpersonateUserId(UserInfo $impersonator, string $targetId): bool { + if($impersonator->isSuperUser()) + return true; + + $whitelist = $impersonateConfig->getArray(sprintf('allow.u%s', $impersonator->getId())); + return in_array($targetId, $whitelist, true); + } + #[Route('OPTIONS', '/_sockchat/token')] #[Route('GET', '/_sockchat/token')] public function getToken($response, $request) { @@ -121,7 +125,7 @@ final class SharpChatRoutes implements IRouteHandler { return ['ok' => false, 'err' => 'user']; $userInfo = $this->usersCtx->getUsers()->getUser($sessionInfo->getUserId(), 'id'); - $userId = $tokenInfo->hasImpersonatedUserId() && $userInfo->isSuperUser() + $userId = $tokenInfo->hasImpersonatedUserId() && $this->canImpersonateUserId($userInfo, $tokenInfo->getImpersonatedUserId()) ? $tokenInfo->getImpersonatedUserId() : $userInfo->getId(); @@ -215,7 +219,7 @@ final class SharpChatRoutes implements IRouteHandler { $this->authCtx->getSessions()->recordSessionActivity(sessionInfo: $sessionInfo, remoteAddr: $ipAddress); $userInfo = $this->usersCtx->getUsers()->getUser($sessionInfo->getUserId(), 'id'); - if($tokenInfo->hasImpersonatedUserId() && $userInfo->isSuperUser()) { + if($tokenInfo->hasImpersonatedUserId() && $this->canImpersonateUserId($userInfo, $tokenInfo->getImpersonatedUserId())) { $userInfoReal = $userInfo; try {