Authn/z rework.

This commit is contained in:
flash 2025-03-31 15:34:20 +00:00
parent 28be4f16c2
commit e4c3e4c052
Signed by: flash
GPG key ID: 2C9C2C574D47FE3E
49 changed files with 833 additions and 664 deletions
public

View file

@ -6,8 +6,8 @@ use Index\MediaType;
use Index\Http\Content\MultipartFormContent;
use Index\Http\Content\Multipart\ValueMultipartFormData;
use Index\Http\Routing\Router;
use Index\Http\Routing\Processors\Before;
use Index\Http\Routing\Routes\RouteInfo;
use Misuzu\Auth\{AuthTokenBuilder,AuthTokenCookie,AuthTokenInfo};
require_once __DIR__ . '/../misuzu.php';
@ -28,90 +28,6 @@ if(is_file($msz->dbCtx->getMigrateLockPath())) {
$request = \Index\Http\HttpRequest::fromRequest();
$tokenPacker = $msz->authCtx->createAuthTokenPacker();
if(!empty($_COOKIE['msz_auth']) && is_string($_COOKIE['msz_auth']))
$tokenInfo = $tokenPacker->unpack($_COOKIE['msz_auth']);
elseif(!empty($_COOKIE['msz_uid']) && !empty($_COOKIE['msz_sid']) && is_string($_COOKIE['msz_uid']) && is_string($_COOKIE['msz_sid'])) {
$tokenBuilder = new AuthTokenBuilder;
$tokenBuilder->setUserId($_COOKIE['msz_uid']);
$tokenBuilder->setSessionToken($_COOKIE['msz_sid']);
$tokenInfo = $tokenBuilder->toInfo();
$tokenBuilder = null;
} else
$tokenInfo = AuthTokenInfo::empty();
$userInfo = null;
$sessionInfo = null;
$userInfoReal = null;
$remoteAddr = $_SERVER['REMOTE_ADDR'];
if($tokenInfo->hasUserId && $tokenInfo->hasSessionToken) {
$tokenBuilder = new AuthTokenBuilder($tokenInfo);
try {
$sessionInfo = $msz->authCtx->sessions->getSession(sessionToken: $tokenInfo->sessionToken);
if($sessionInfo->expired) {
$tokenBuilder->removeUserId();
$tokenBuilder->removeSessionToken();
} elseif($sessionInfo->userId === $tokenInfo->userId) {
$userInfo = $msz->usersCtx->users->getUser($tokenInfo->userId, 'id');
if($userInfo->deleted) {
$tokenBuilder->removeUserId();
$tokenBuilder->removeSessionToken();
} else {
$msz->usersCtx->users->recordUserActivity($userInfo, remoteAddr: $remoteAddr);
$msz->authCtx->sessions->recordSessionActivity(sessionInfo: $sessionInfo, remoteAddr: $remoteAddr);
if($sessionInfo->shouldBumpExpires)
$tokenBuilder->setEdited();
if($tokenInfo->hasImpersonatedUserId) {
$allowToImpersonate = $userInfo->super;
$impersonatedUserId = $tokenInfo->impersonatedUserId;
if(!$allowToImpersonate) {
$allowImpersonateUsers = $msz->config->getArray(sprintf('impersonate.allow.u%s', $userInfo->id));
$allowToImpersonate = in_array((string)$impersonatedUserId, $allowImpersonateUsers, true);
}
if($allowToImpersonate) {
$userInfoReal = $userInfo;
try {
$userInfo = $msz->usersCtx->users->getUser($impersonatedUserId, 'id');
} catch(RuntimeException $ex) {
$userInfo = $userInfoReal;
$userInfoReal = null;
$tokenBuilder->removeImpersonatedUserId();
}
} else $tokenBuilder->removeImpersonatedUserId();
}
}
}
} catch(RuntimeException $ex) {
$tokenBuilder->removeUserId();
$tokenBuilder->removeSessionToken();
$tokenBuilder->removeImpersonatedUserId();
$userInfo = null;
$sessionInfo = null;
$userInfoReal = null;
}
if($tokenBuilder->isEdited()) {
$tokenInfo = $tokenBuilder->toInfo();
AuthTokenCookie::apply($tokenPacker->pack($tokenInfo));
}
}
$msz->authInfo->setInfo($tokenInfo, $userInfo, $sessionInfo, $userInfoReal);
CSRF::init(
$msz->config->getString('csrf.secret', 'soup'),
($msz->authInfo->loggedIn ? $sessionInfo->token : $remoteAddr)
);
// order for these two currently matters i think: it shouldn't.
$router = $msz->createRouting($request);
$msz->startTemplating();
@ -125,16 +41,21 @@ if($msz->domainRoles->hasRole($request->getHeaderLine('Host'), 'main')) {
$mszLegacyPathReal = realpath($mszLegacyPath);
if($mszLegacyPath === $mszLegacyPathReal || $mszLegacyPath === $mszLegacyPathReal . '/') {
// this is here so filters can run...
$router->router->route(RouteInfo::exact($request->method, $request->requestTarget, function() {}));
$router->router->route(RouteInfo::exact(
$request->method,
$request->requestTarget,
#[Before('authz:cookie')]
function() use ($msz, $mszRequestPath) {
if(str_starts_with($mszRequestPath, 'manage') && !$msz->hasManageAccess())
return 403;
},
));
$response = $router->router->handle($request);
if($response->getBody()->getSize() > 0) {
Router::output($response);
exit;
}
if(str_starts_with($mszRequestPath, 'manage') && !$msz->hasManageAccess())
Template::throwError(403);
if(is_dir($mszLegacyPath))
$mszLegacyPath .= '/index.php';