Moved Templating stuff into a class and use Index CSRFP for verification.

This commit is contained in:
flash 2023-08-16 23:17:14 +00:00
parent 0d692454eb
commit 8b47c866ed
4 changed files with 76 additions and 52 deletions

4
composer.lock generated
View file

@ -12,7 +12,7 @@
"source": {
"type": "git",
"url": "https://git.flash.moe/flash/index.git",
"reference": "553b7c4a14aa7f2403c87ce474933986ac17d040"
"reference": "a4c1d5627e590e669998f68cae64691b1ce0e0ac"
},
"require": {
"ext-mbstring": "*",
@ -50,7 +50,7 @@
],
"description": "Composer package for the common library for my projects.",
"homepage": "https://railgun.sh/index",
"time": "2023-08-03T01:29:57+00:00"
"time": "2023-08-16T23:03:01+00:00"
},
{
"name": "symfony/polyfill-ctype",

View file

@ -2,54 +2,36 @@
namespace Mince;
use Index\XString;
use Index\Data\DbType;
use Index\Http\HttpFx;
use Twig\Environment as TwigEnvironment;
use Twig\Loader\FilesystemLoader as TwigLoaderFilesystem;
use Index\Security\CSRFP;
require_once __DIR__ . '/../mince.php';
if(empty($_COOKIE['mc_random'])) {
$sVerification = XString::random(32);
setcookie('mc_random', $sVerification, strtotime('1 day'), '/', $_SERVER['HTTP_HOST']);
} else
$sVerification = (string)filter_input(INPUT_COOKIE, 'mc_random');
$sVerification = hash('sha256', $sVerification);
// replace this with id.flashii.net shit
$userInfo = ChatAuth::attempt($db, $config['chat_endpoint'], $config['chat_secret'], (string)filter_input(INPUT_COOKIE, 'msz_auth'));
$authToken = (string)filter_input(INPUT_COOKIE, 'msz_auth');
$userInfo = ChatAuth::attempt($db, $config['chat_endpoint'], $config['chat_secret'], $authToken);
// need a more permanent solution for this
$twigLoader = new TwigLoaderFilesystem([MCR_DIR_TPL]);
$twigEnv = new TwigEnvironment($twigLoader, [
//'cache' => $cache ?? false,
'debug' => MCR_DEBUG,
'strict_variables' => true,
]);
$twigArgs = [
$csrfp = new CSRFP(
$config['csrf_secret'],
$userInfo->success ? $authToken : $_SERVER['REMOTE_ADDR']
);
$templating = new Templating;
$templating->addPath(MCR_DIR_TPL);
$templating->addVars([
'global' => [
'title' => 'Flashii Minecraft Servers',
'loginUrl' => $config['login_url'],
],
'auth' => $userInfo,
'verification' => $sVerification,
];
function tpl_vars(array $args): void {
global $twigArgs;
$twigArgs = array_merge($twigArgs, $args);
}
function tpl_render(string $name, array $args, string $suffix = '.twig'): string {
global $twigEnv, $twigArgs;
return $twigEnv->render($name . $suffix, array_merge($twigArgs, $args));
}
'csrfp' => $csrfp->createToken(),
]);
$router = new HttpFx;
$router->setDefaultErrorHandler(function($response, $request, $code, $text) use ($userInfo) {
$response->setContent(tpl_render('http-error', [
$router->setDefaultErrorHandler(function($response, $request, $code, $text) use ($userInfo, $templating) {
$response->setContent($templating->render('http-error', [
'error' => [
'code' => sprintf('%03d', $code),
'text' => $text,
@ -57,7 +39,7 @@ $router->setDefaultErrorHandler(function($response, $request, $code, $text) use
]));
});
$router->use('/', function($response) {
$router->use('/', function($response, $request) {
$response->setPoweredBy('Mince');
});
@ -65,7 +47,7 @@ $router->get('/index.php', function($response) {
$response->redirect('/', true);
});
$router->get('/', function($response, $request) use ($userInfo) {
$router->get('/', function($response, $request) use ($userInfo, $templating) {
$name = (string)$request->getParam('name');
$error = (string)$request->getParam('error');
@ -90,7 +72,7 @@ $router->get('/', function($response, $request) use ($userInfo) {
$mErrorComment = $error;
}
tpl_vars([
$templating->addVars([
'error' => [
'title' => $mErrorTitle,
'body' => $mErrorComment,
@ -99,14 +81,14 @@ $router->get('/', function($response, $request) use ($userInfo) {
}
if($userInfo->mc_whitelisted > 0)
tpl_vars(['whitelist_pending' => floor($userInfo->mc_whitelisted / 300) === floor(time() / 300)]);
$templating->setVar('whitelist_pending', floor($userInfo->mc_whitelisted / 300) === floor(time() / 300));
return tpl_render('index', [
return $templating->render('index', [
'wladdform_username' => $name,
]);
});
$router->use('/whitelist', function($response, $request) use ($sVerification) {
$router->use('/whitelist', function($response, $request) use ($csrfp) {
if(!$request->isFormContent()) {
$response->redirect('/?error=request');
return true;
@ -114,7 +96,7 @@ $router->use('/whitelist', function($response, $request) use ($sVerification) {
$body = $request->getContent();
if(!$body->hasParam('boob') || !hash_equals($sVerification, (string)$body->getParam('boob'))) {
if(!$body->hasParam('csrfp') || !$csrfp->verifyToken((string)$body->getParam('csrfp'))) {
$response->redirect('/?error=verify');
return true;
}
@ -148,11 +130,4 @@ $router->post('/whitelist/remove', function($response) use ($db, $userInfo) {
$response->redirect("/?error={$resp}");
});
$router->get('/errors/:code', function($res, $req, $code) {
$code = (int)$code;
if($code < 100 || $code >= 600)
$code = 400;
return $code;
});
$router->dispatch();

49
src/Templating.php Normal file
View file

@ -0,0 +1,49 @@
<?php
namespace Mince;
use Twig\Environment as TwigEnvironment;
use Twig\Loader\FilesystemLoader as TwigLoaderFilesystem;
class Templating {
private const FILE_EXT = '.twig';
private TwigEnvironment $env;
private TwigLoaderFilesystem $loader;
private array $vars = [];
public function __construct() {
$this->loader = new TwigLoaderFilesystem;
$this->env = new TwigEnvironment($this->loader, [
//'cache' => $cache ?? false,
'debug' => MCR_DEBUG,
'strict_variables' => true,
]);
}
public function addPath(string $path): void {
$this->loader->addPath($path);
}
public function setVar(string $path, $value): void {
$path = array_reverse(explode('.', $path));
$target = &$this->vars;
$targetName = array_pop($path);
if(!empty($path))
while(($name = array_pop($path)) !== null) {
if(!array_key_exists($name, $target))
$target[$name] = [];
$target = &$target[$name];
}
$target[$targetName] = $value;
}
public function addVars(array $vars): void {
$this->vars = array_merge($this->vars, $vars);
}
public function render(string $path, array $vars = []): string {
return $this->env->render($path . self::FILE_EXT, array_merge($this->vars, $vars));
}
}

View file

@ -20,7 +20,7 @@
<h2>Add to Whitelist</h2>
<p>This will give you access to the server.</p>
<form method="post" action="/whitelist/add">
<input type="hidden" name="boob" value="{{ verification }}">
<input type="hidden" name="csrfp" value="{{ csrfp }}">
<label>
<div class="label-header">Username</div>
<div class="label-input"><input type="text" name="name" value="{{ wladdform_username }}"></div>
@ -56,7 +56,7 @@
<p>If you're playing a modpack, take that time to start the game up; it'll take a while.</p>
{% endif %}
<form method="post" action="/whitelist/remove">
<input type="hidden" name="boob" value="{{ verification }}">
<input type="hidden" name="csrfp" value="{{ csrfp }}">
<input type="submit" value="Remove me from the whitelist">
</form>
</div>