misuzu/src/TemplatingExtension.php

261 lines
9.9 KiB
PHP
Raw Normal View History

2023-08-31 21:33:34 +00:00
<?php
namespace Misuzu;
use DateTimeInterface;
use Carbon\CarbonImmutable;
use Misuzu\Parsers\{Parsers,TextFormat};
use Twig\{TwigFilter,TwigFunction};
2023-08-31 21:33:34 +00:00
use Twig\Extension\AbstractExtension;
2024-10-05 02:40:29 +00:00
final class TemplatingExtension extends AbstractExtension {
public function __construct(
private MisuzuContext $ctx,
private AssetInfo $assetInfo
) {}
2023-08-31 21:33:34 +00:00
public function getFilters() {
return [
new TwigFilter('country_name', Tools::countryName(...)),
new TwigFilter('parse_text', fn(string $text, TextFormat|string $parser): string => Parsers::instance($parser)->parseText($text)),
new TwigFilter('parse_md', fn(string $text): string => Parsers::instance(TextFormat::Markdown)->parseText($text)),
2023-08-31 21:33:34 +00:00
new TwigFilter('time_format', $this->timeFormat(...)),
];
}
public function getFunctions() {
return [
new TwigFunction('asset', $this->assetInfo->getAssetUrl(...)),
new TwigFunction('url', $this->ctx->urls->format(...)),
new TwigFunction('csrf_available', CSRF::available(...)),
2023-08-31 21:33:34 +00:00
new TwigFunction('csrf_token', CSRF::token(...)),
new TwigFunction('git_commit_hash', GitInfo::hash(...)),
new TwigFunction('git_tag', GitInfo::tag(...)),
new TwigFunction('git_branch', GitInfo::branch(...)),
new TwigFunction('startup_time', fn(float $time = MSZ_STARTUP) => microtime(true) - $time),
new TwigFunction('sql_query_count', $this->ctx->dbCtx->getQueryCount(...)),
2023-08-31 21:33:34 +00:00
new TwigFunction('msz_header_menu', $this->getHeaderMenu(...)),
new TwigFunction('msz_user_menu', $this->getUserMenu(...)),
new TwigFunction('msz_manage_menu', $this->getManageMenu(...)),
new TwigFunction('parser_options', function() {
return [
TextFormat::Plain->value => 'Plain text',
TextFormat::BBCode->value => 'BB Code',
TextFormat::Markdown->value => 'Markdown',
];
}),
2023-08-31 21:33:34 +00:00
];
}
public function timeFormat(DateTimeInterface|string|int|null $dateTime): string {
2023-08-31 21:33:34 +00:00
if($dateTime === null)
return 'never';
if(is_string($dateTime))
$dateTime = new CarbonImmutable($dateTime);
2023-08-31 21:33:34 +00:00
elseif(is_int($dateTime))
$dateTime = CarbonImmutable::createFromTimestampUTC($dateTime);
elseif(!($dateTime instanceof CarbonImmutable))
$dateTime = new CarbonImmutable($dateTime);
2023-08-31 21:33:34 +00:00
return $dateTime->diffForHumans();
2023-08-31 21:33:34 +00:00
}
2024-12-02 21:33:15 +00:00
/**
* @return array{
* title: string,
* url: string,
* menu?: array{
* title: string,
* url: string
* }[]
* }[]
*/
2023-08-31 21:33:34 +00:00
public function getHeaderMenu(): array {
$menu = [];
$home = [
'title' => 'Home',
'url' => $this->ctx->urls->format('index'),
2023-08-31 21:33:34 +00:00
'menu' => [],
];
2025-02-02 02:09:56 +00:00
if($this->ctx->authInfo->loggedIn)
2023-08-31 21:33:34 +00:00
$home['menu'][] = [
'title' => 'Members',
'url' => $this->ctx->urls->format('user-list'),
2023-08-31 21:33:34 +00:00
];
$home['menu'][] = [
'title' => 'Changelog',
'url' => $this->ctx->urls->format('changelog-index'),
2023-08-31 21:33:34 +00:00
];
$home['menu'][] = [
'title' => 'Contact',
'url' => $this->ctx->urls->format('info', ['title' => 'contact']),
2023-08-31 21:33:34 +00:00
];
$home['menu'][] = [
'title' => 'Rules',
'url' => $this->ctx->urls->format('info', ['title' => 'rules']),
2023-08-31 21:33:34 +00:00
];
if(!empty($this->ctx->siteInfo->bsky))
$home['menu'][] = [
'title' => 'Bluesky',
'url' => $this->ctx->siteInfo->bsky,
];
2023-08-31 21:33:34 +00:00
$menu[] = $home;
$menu[] = [
'title' => 'News',
'url' => $this->ctx->urls->format('news-index'),
2023-08-31 21:33:34 +00:00
];
$forum = [
'title' => 'Forum',
'url' => $this->ctx->urls->format('forum-index'),
2023-08-31 21:33:34 +00:00
'menu' => [],
];
if($this->ctx->authInfo->getPerms('global')->check(Perm::G_FORUM_LEADERBOARD_VIEW))
2023-08-31 21:33:34 +00:00
$forum['menu'][] = [
'title' => 'Leaderboard',
'url' => $this->ctx->urls->format('forum-leaderboard'),
2023-08-31 21:33:34 +00:00
];
$menu[] = $forum;
$chatPath = $this->ctx->getChatURL();
if(!empty($chatPath))
$menu[] = [
'title' => 'Chat',
'url' => $chatPath,
];
return $menu;
}
2024-12-02 21:33:15 +00:00
/**
* @return array{
* title: string,
* url: string,
* icon: string
* }[]
*/
2023-08-31 21:33:34 +00:00
public function getUserMenu(bool $inBroomCloset, string $manageUrl = ''): array {
$menu = [];
2025-02-02 02:09:56 +00:00
if($this->ctx->authInfo->loggedIn) {
$userInfo = $this->ctx->authInfo->userInfo;
$globalPerms = $this->ctx->authInfo->getPerms('global');
2023-08-31 21:33:34 +00:00
$menu[] = [
'title' => 'Profile',
2024-11-30 04:20:20 +00:00
'url' => $this->ctx->urls->format('user-profile', ['user' => $userInfo->id]),
2023-08-31 21:33:34 +00:00
'icon' => 'fas fa-user fa-fw',
];
2024-01-30 23:47:02 +00:00
if($globalPerms->check(Perm::G_MESSAGES_VIEW))
$menu[] = [
'title' => 'Messages',
'url' => $this->ctx->urls->format('messages-index'),
2024-01-30 23:47:02 +00:00
'icon' => 'fas fa-envelope fa-fw',
'class' => 'js-header-pms-button',
];
2023-08-31 21:33:34 +00:00
$menu[] = [
'title' => 'Settings',
'url' => $this->ctx->urls->format('settings-index'),
2023-08-31 21:33:34 +00:00
'icon' => 'fas fa-cog fa-fw',
];
$menu[] = [
'title' => 'Search',
'url' => $this->ctx->urls->format('search-index'),
2023-08-31 21:33:34 +00:00
'icon' => 'fas fa-search fa-fw',
];
if(!$this->ctx->usersCtx->hasActiveBan($userInfo) && $globalPerms->check(Perm::G_IS_JANITOR)) {
2023-08-31 21:33:34 +00:00
// restore behaviour where clicking this button switches between
// site version and broom version
if($inBroomCloset)
$menu[] = [
'title' => 'Exit Broom Closet',
'url' => $manageUrl === '' ? $this->ctx->urls->format('index') : $manageUrl,
2023-08-31 21:33:34 +00:00
'icon' => 'fas fa-door-open fa-fw',
];
else
$menu[] = [
'title' => 'Enter Broom Closet',
'url' => $manageUrl === '' ? $this->ctx->urls->format('manage-index') : $manageUrl,
2023-08-31 21:33:34 +00:00
'icon' => 'fas fa-door-closed fa-fw',
];
}
$menu[] = [
'title' => 'Log out',
'url' => $this->ctx->urls->format('auth-logout', ['csrf' => CSRF::token()]),
2023-08-31 21:33:34 +00:00
'icon' => 'fas fa-sign-out-alt fa-fw',
];
} else {
$menu[] = [
'title' => 'Register',
'url' => $this->ctx->urls->format('auth-register'),
2023-08-31 21:33:34 +00:00
'icon' => 'fas fa-user-plus fa-fw',
];
$menu[] = [
'title' => 'Log in',
'url' => $this->ctx->urls->format('auth-login'),
2023-08-31 21:33:34 +00:00
'icon' => 'fas fa-sign-in-alt fa-fw',
];
}
return $menu;
}
2024-12-02 21:33:15 +00:00
/** @return array<string, array<string, string>> */
2023-08-31 21:33:34 +00:00
public function getManageMenu(): array {
$globalPerms = $this->ctx->authInfo->getPerms('global');
2025-02-02 02:09:56 +00:00
if(!$this->ctx->authInfo->loggedIn || !$globalPerms->check(Perm::G_IS_JANITOR))
2023-08-31 21:33:34 +00:00
return [];
$menu = [
'General' => [
'Overview' => $this->ctx->urls->format('manage-general-overview'),
2023-08-31 21:33:34 +00:00
],
];
if($globalPerms->check(Perm::G_LOGS_VIEW))
$menu['General']['Logs'] = $this->ctx->urls->format('manage-general-logs');
2023-08-31 21:33:34 +00:00
if($globalPerms->check(Perm::G_EMOTES_MANAGE))
$menu['General']['Emoticons'] = $this->ctx->urls->format('manage-general-emoticons');
2023-08-31 21:33:34 +00:00
if($globalPerms->check(Perm::G_CONFIG_MANAGE))
$menu['General']['Settings'] = $this->ctx->urls->format('manage-general-settings');
2023-08-31 21:33:34 +00:00
$userPerms = $this->ctx->authInfo->getPerms('user');
2023-08-31 21:33:34 +00:00
if($userPerms->check(Perm::U_USERS_MANAGE))
$menu['Users & Roles']['Users'] = $this->ctx->urls->format('manage-users');
2023-08-31 21:33:34 +00:00
if($userPerms->check(Perm::U_ROLES_MANAGE))
$menu['Users & Roles']['Roles'] = $this->ctx->urls->format('manage-roles');
2023-08-31 21:33:34 +00:00
if($userPerms->check(Perm::U_NOTES_MANAGE))
$menu['Users & Roles']['Notes'] = $this->ctx->urls->format('manage-users-notes');
2023-08-31 21:33:34 +00:00
if($userPerms->check(Perm::U_WARNINGS_MANAGE))
$menu['Users & Roles']['Warnings'] = $this->ctx->urls->format('manage-users-warnings');
2023-08-31 21:33:34 +00:00
if($userPerms->check(Perm::U_BANS_MANAGE))
$menu['Users & Roles']['Bans'] = $this->ctx->urls->format('manage-users-bans');
2023-08-31 21:33:34 +00:00
if($globalPerms->check(Perm::G_NEWS_POSTS_MANAGE))
$menu['News']['Posts'] = $this->ctx->urls->format('manage-news-posts');
2023-08-31 21:33:34 +00:00
if($globalPerms->check(Perm::G_NEWS_CATEGORIES_MANAGE))
$menu['News']['Categories'] = $this->ctx->urls->format('manage-news-categories');
2023-08-31 21:33:34 +00:00
if($globalPerms->check(Perm::G_FORUM_CATEGORIES_MANAGE))
$menu['Forum']['Permission Calculator'] = $this->ctx->urls->format('manage-forum-categories');
2023-08-31 21:33:34 +00:00
if($globalPerms->check(Perm::G_FORUM_TOPIC_REDIRS_MANAGE))
$menu['Forum']['Topic Redirects'] = $this->ctx->urls->format('manage-forum-topic-redirs');
2023-08-31 21:33:34 +00:00
if($globalPerms->check(Perm::G_CL_CHANGES_MANAGE))
$menu['Changelog']['Changes'] = $this->ctx->urls->format('manage-changelog-changes');
2023-08-31 21:33:34 +00:00
if($globalPerms->check(Perm::G_CL_TAGS_MANAGE))
$menu['Changelog']['Tags'] = $this->ctx->urls->format('manage-changelog-tags');
2023-08-31 21:33:34 +00:00
return $menu;
}
}