Moved forum signatures into dedicated table.

This commit is contained in:
flash 2025-02-08 22:52:36 +00:00
parent d1173c6e0f
commit 8bb2400d3f
11 changed files with 242 additions and 103 deletions

View file

@ -0,0 +1,36 @@
<?php
use Index\Db\DbConnection;
use Index\Db\Migration\DbMigration;
final class MovedForumSignatureToDedicatedTable_20250208_213207 implements DbMigration {
public function migrate(DbConnection $conn): void {
$conn->execute(<<<SQL
CREATE TABLE msz_forum_signatures (
user_id INT UNSIGNED NOT NULL,
signature_body TEXT NOT NULL COLLATE 'utf8mb4_unicode_520_ci',
signature_body_format ENUM('','bb','md') NOT NULL COLLATE 'ascii_general_ci',
signature_created TIMESTAMP NOT NULL DEFAULT NOW(),
PRIMARY KEY (user_id),
CONSTRAINT forum_signatures_users_foreign
FOREIGN KEY (user_id)
REFERENCES msz_users (user_id)
ON UPDATE CASCADE
ON DELETE CASCADE
) COLLATE='utf8mb4_bin';
SQL);
$conn->execute(<<<SQL
INSERT INTO msz_forum_signatures
SELECT user_id, user_signature_content, user_signature_content_format, NOW()
FROM msz_users
WHERE user_signature_content IS NOT NULL
AND TRIM(user_signature_content) <> ''
SQL);
$conn->execute(<<<SQL
ALTER TABLE msz_users
DROP COLUMN user_signature_content,
DROP COLUMN user_signature_content_format;
SQL);
}
}

View file

@ -5,6 +5,7 @@ use stdClass;
use InvalidArgumentException;
use RuntimeException;
use Index\ByteFormat;
use Misuzu\Forum\ForumSignaturesData;
use Misuzu\Parsers\TextFormat;
use Misuzu\Profile\ProfileBackgroundAttach;
use Misuzu\Users\{User,UsersContext};
@ -79,6 +80,8 @@ $avatarAsset = new UserAvatarAsset($userInfo);
$backgroundInfo = $msz->profileCtx->backgrounds->getProfileBackground($userInfo);
$backgroundAsset = new UserBackgroundAsset($userInfo, $backgroundInfo);
$sigInfo = $msz->forumCtx->signatures->getSignature($userInfo);
if($isEditing) {
if(!$canEdit)
Template::throwError(403);
@ -152,18 +155,22 @@ if($isEditing) {
}
}
if(!empty($_POST['signature']) && is_array($_POST['signature'])) {
if(filter_has_var(INPUT_POST, 'sig_body')) {
if(!$perms->edit_signature) {
$notices[] = 'You\'re not allowed to edit your forum signature.';
} else {
$sigText = (string)($_POST['signature']['text'] ?? '');
$sigParse = TextFormat::tryFrom((string)($_POST['signature']['parser'] ?? '')) ?? TextFormat::Plain;
$sigValid = $msz->usersCtx->users->validateForumSignature($sigParse, $sigText);
if($sigValid === '')
$msz->usersCtx->users->updateUser($userInfo, signatureBody: $sigText, signatureBodyFormat: $sigParse);
else
$notices[] = $msz->usersCtx->users->validateForumSignatureText($sigValid);
$sigBody = (string)filter_input(INPUT_POST, 'sig_body');
if(trim($sigBody) === '') {
$msz->forumCtx->signatures->deleteSignature($userInfo);
$sigInfo = null;
} else {
$sigFormat = TextFormat::tryFrom(filter_input(INPUT_POST, 'sig_format'));
$sigValid = ForumSignaturesData::validateSignature($sigFormat, $sigBody);
if($sigValid === '')
$sigInfo = $msz->forumCtx->signatures->updateSignature($userInfo, $sigBody, $sigFormat);
else
$notices[] = ForumSignaturesData::validateSignatureText($sigValid);
}
}
}
@ -395,4 +402,5 @@ Template::render('profile.index', [
'profile_background_asset' => $backgroundAsset,
'profile_can_send_messages' => $viewerPermsGlobal->check(Perm::G_MESSAGES_SEND),
'profile_age' => $msz->usersCtx->birthdates->getUserAge($userInfo),
'profile_forum_signature_info' => $sigInfo,
]);

View file

@ -134,6 +134,7 @@ if(isset($_POST['action']) && is_string($_POST['action'])) {
$tmpFiles[] = db_to_zip($archive, $userInfo, 'comments_posts', ['comment_id:s', 'category_id:s', 'user_id:s:n', 'comment_reply_to:s:n', 'comment_text:s', 'comment_created:t', 'comment_pinned:t:n', 'comment_edited:t:n', 'comment_deleted:t:n']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'comments_votes', ['comment_id:s', 'user_id:s', 'comment_vote:i']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'forum_posts', ['post_id:s', 'topic_id:s', 'forum_id:s', 'user_id:s:n', 'post_remote_addr:a', 'post_text:s', 'post_text_format:s', 'post_display_signature:b', 'post_created:t', 'post_edited:t:n', 'post_deleted:t:n']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'forum_signatures', ['user_id:s', 'signature_body:s', 'signature_body_format:s', 'signature_created:t']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'forum_topics', ['topic_id:s', 'forum_id:s', 'user_id:s:n', 'topic_type:i', 'topic_title:s', 'topic_count_views:i', 'topic_created:t', 'topic_bumped:t', 'topic_deleted:t:n', 'topic_locked:t:n']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'forum_topics_redirects', ['topic_id:s', 'user_id:s:n', 'redir_url:s', 'redir_created:t']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'forum_topics_track', ['user_id:s', 'topic_id:s', 'forum_id:s', 'track_last_read:t']);
@ -149,7 +150,7 @@ if(isset($_POST['action']) && is_string($_POST['action'])) {
$tmpFiles[] = db_to_zip($archive, $userInfo, 'profile_backgrounds', ['user_id:s', 'bg_attach:s', 'bg_blend:i', 'bg_slide:i']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'profile_fields_values', ['field_id:s', 'user_id:s', 'format_id:s', 'field_value:s']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'sessions', ['session_id:s', 'user_id:s', 'session_key:n', 'session_remote_addr_first:a', 'session_remote_addr_last:a:n', 'session_user_agent:s', 'session_country:s', 'session_expires:t', 'session_expires_bump:b', 'session_created:t', 'session_active:t:n']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'users', ['user_id:s', 'user_name:s', 'user_password:n', 'user_email:s', 'user_remote_addr_first:a', 'user_remote_addr_last:a', 'user_super:b', 'user_country:s', 'user_colour:i:n', 'user_created:t', 'user_active:t:n', 'user_deleted:t:n', 'user_display_role_id:s:n', 'user_about_content:s:n', 'user_about_content_format:s', 'user_signature_content:s:n', 'user_signature_content_format:s', 'user_title:s:n']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'users', ['user_id:s', 'user_name:s', 'user_password:n', 'user_email:s', 'user_remote_addr_first:a', 'user_remote_addr_last:a', 'user_super:b', 'user_country:s', 'user_colour:i:n', 'user_created:t', 'user_active:t:n', 'user_deleted:t:n', 'user_display_role_id:s:n', 'user_about_content:s:n', 'user_about_content_format:s', 'user_title:s:n']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'users_bans', ['ban_id:s', 'user_id:s', 'mod_id:n', 'ban_severity:i', 'ban_reason_public:s', 'ban_reason_private:s', 'ban_created:t', 'ban_expires:t:n']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'users_birthdates', ['user_id:s', 'birth_year:i:n', 'birth_month:i', 'birth_day:i']);
$tmpFiles[] = db_to_zip($archive, $userInfo, 'users_password_resets', ['reset_id:s', 'user_id:s', 'reset_remote_addr:a', 'reset_requested:t', 'reset_code:n']);

View file

@ -3,6 +3,7 @@ namespace Misuzu\Forum;
use stdClass;
use Index\Db\DbConnection;
use Misuzu\Parsers\TextFormat;
use Misuzu\Users\UserInfo;
class ForumContext {
@ -10,6 +11,7 @@ class ForumContext {
public private(set) ForumTopicsData $topics;
public private(set) ForumTopicRedirectsData $topicRedirects;
public private(set) ForumPostsData $posts;
public private(set) ForumSignaturesData $signatures;
/** @var array<string, int> */
private array $totalUserTopics = [];
@ -17,11 +19,15 @@ class ForumContext {
/** @var array<string, int> */
private array $totalUserPosts = [];
/** @var array<string, ForumSignatureInfo> */
private array $cachedSignatures = [];
public function __construct(DbConnection $dbConn) {
$this->categories = new ForumCategoriesData($dbConn);
$this->topics = new ForumTopicsData($dbConn);
$this->topicRedirects = new ForumTopicRedirectsData($dbConn);
$this->posts = new ForumPostsData($dbConn);
$this->signatures = new ForumSignaturesData($dbConn);
}
// should be replaced by a static counter
@ -47,4 +53,15 @@ class ForumContext {
return $this->totalUserPosts[$userId] = $this->posts->countPosts(userInfo: $userInfo, deleted: false);
}
public function getCachedSignature(UserInfo|string|null $userInfo): ?ForumSignatureInfo {
if($userInfo === null)
return null;
$userId = $userInfo instanceof UserInfo ? $userInfo->id : $userInfo;
if(array_key_exists($userId, $this->cachedSignatures))
return $this->cachedSignatures[$userId];
return $this->cachedSignatures[$userId] = $this->signatures->getSignature($userInfo);
}
}

View file

@ -0,0 +1,40 @@
<?php
namespace Misuzu\Forum;
use Carbon\CarbonImmutable;
use Index\Db\DbResult;
use Misuzu\Parsers\TextFormat;
class ForumSignatureInfo {
public function __construct(
public private(set) string $userId,
public private(set) string $body,
public private(set) TextFormat $bodyFormat,
public private(set) int $createdTime,
) {}
public static function fromResult(DbResult $result): self {
return new ForumSignatureInfo(
userId: $result->getString(0),
body: $result->getString(1),
bodyFormat: TextFormat::tryFrom($result->getString(2)) ?? TextFormat::Plain,
createdTime: $result->getInteger(3),
);
}
public CarbonImmutable $createdAt {
get => CarbonImmutable::createFromTimestampUTC($this->createdTime);
}
public bool $isBodyPlain {
get => $this->bodyFormat === TextFormat::Plain;
}
public bool $isBodyBBCode {
get => $this->bodyFormat === TextFormat::BBCode;
}
public bool $isBodyMarkdown {
get => $this->bodyFormat === TextFormat::Markdown;
}
}

View file

@ -0,0 +1,84 @@
<?php
namespace Misuzu\Forum;
use RuntimeException;
use Index\Db\{DbConnection,DbStatementCache};
use Misuzu\Parsers\TextFormat;
use Misuzu\Users\UserInfo;
class ForumSignaturesData {
public const int BODY_MAX_LENGTH = 2000;
private DbStatementCache $cache;
public function __construct(DbConnection $dbConn) {
$this->cache = new DbStatementCache($dbConn);
}
public function getSignature(UserInfo|string $userInfo): ?ForumSignatureInfo {
$stmt = $this->cache->get(<<<SQL
SELECT user_id, signature_body, signature_body_format, UNIX_TIMESTAMP(signature_created)
FROM msz_forum_signatures
WHERE user_id = ?
SQL);
$stmt->nextParameter($userInfo instanceof UserInfo ? $userInfo->id : $userInfo);
$stmt->execute();
$result = $stmt->getResult();
return $result->next() ? ForumSignatureInfo::fromResult($result) : null;
}
public function deleteSignature(UserInfo|string $userInfo): void {
$stmt = $this->cache->get(<<<SQL
DELETE FROM msz_forum_signatures
WHERE user_id = ?
SQL);
$stmt->nextParameter($userInfo instanceof UserInfo ? $userInfo->id : $userInfo);
$stmt->execute();
}
public function updateSignature(
UserInfo|string $userInfo,
string $body,
TextFormat|string $format
): ForumSignatureInfo {
if(is_string($format))
$format = TextFormat::from($format);
$stmt = $this->cache->get(<<<SQL
REPLACE INTO msz_forum_signatures (
user_id, signature_body, signature_body_format
) VALUES (?, ?, ?)
SQL);
$stmt->nextParameter($userInfo instanceof UserInfo ? $userInfo->id : $userInfo);
$stmt->nextParameter($body);
$stmt->nextParameter($format->value);
$stmt->execute();
$sigInfo = $this->getSignature($userInfo);
if($sigInfo === null)
throw new RuntimeException('failed to update forum signature');
return $sigInfo;
}
public static function validateSignature(?TextFormat $format, string $text): string {
if($format === null)
return 'parser';
$length = mb_strlen($text);
if($length > self::BODY_MAX_LENGTH)
return 'long';
return '';
}
public static function validateSignatureText(string $error): string {
return match($error) {
'parser' => 'You attempted to select an invalid parser for your forum signature.',
'long' => sprintf('Please keep the length of your forum signature below %d characters.', self::BODY_MAX_LENGTH),
'' => 'Your forum signature is fine, why are you seeing this?',
default => 'Your forum signature is not acceptable.',
};
}
}

View file

@ -15,7 +15,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
use RouteHandlerCommon, UrlSourceCommon;
public function __construct(
private ForumContext $forum,
private ForumContext $forumCtx,
private UsersContext $usersCtx,
private AuditLogData $auditLog,
private AuthInfo $authInfo,
@ -26,7 +26,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
public function getTopic(HttpResponseBuilder $response, HttpRequest $request, string $topicId): mixed {
$isNuked = $deleted = $canDeleteAny = false;
try {
$topic = $this->forum->topics->getTopic(topicId: $topicId);
$topic = $this->forumCtx->topics->getTopic(topicId: $topicId);
$deleted = $topic->deleted;
$perms = $this->authInfo->getPerms('forum', $topic->categoryId);
@ -39,8 +39,8 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
}
if($isNuked || $deleted) {
if($this->forum->topicRedirects->hasTopicRedirect($topicId)) {
$redirect = $this->forum->topicRedirects->getTopicRedirect($topicId);
if($this->forumCtx->topicRedirects->hasTopicRedirect($topicId)) {
$redirect = $this->forumCtx->topicRedirects->getTopicRedirect($topicId);
Template::set('topic_redir_info', $redirect);
if($isNuked || !$canDeleteAny) {
@ -70,7 +70,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
// this should be in the config
$deletePostThreshold = 1;
$categoryInfo = $this->forum->categories->getCategory(topicInfo: $topic);
$categoryInfo = $this->forumCtx->categories->getCategory(topicInfo: $topic);
$isFrozen = $categoryInfo->archived || $deleted;
$canDeleteOwn = !$isFrozen && !$topic->locked && $perms->check(Perm::F_POST_DELETE_OWN);
$canBump = !$isFrozen && $perms->check(Perm::F_TOPIC_BUMP);
@ -86,7 +86,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
)
);
$postInfos = $this->forum->posts->getPosts(
$postInfos = $this->forumCtx->posts->getPosts(
topicInfo: $topic,
deleted: $perms->check(Perm::F_POST_DELETE_ANY) ? null : false,
pagination: $pagination,
@ -95,7 +95,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
return 404;
try {
$originalPostInfo = $this->forum->posts->getPost(topicInfo: $topic);
$originalPostInfo = $this->forumCtx->posts->getPost(topicInfo: $topic);
} catch(RuntimeException $ex) {
return 404;
}
@ -109,7 +109,13 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
if($postInfo->userId !== null) {
$post->user = $this->usersCtx->getUserInfo($postInfo->userId);
$post->colour = $this->usersCtx->getUserColour($post->user);
$post->postsCount = $this->forum->countTotalUserPosts($post->user);
$post->postsCount = $this->forumCtx->countTotalUserPosts($post->user);
if($postInfo->shouldDisplaySignature) {
$sigInfo = $this->forumCtx->getCachedSignature($post->user);
if($sigInfo !== null)
$post->signature = $sigInfo;
}
}
$post->isOriginalPost = $originalPostInfo->id == $postInfo->id;
@ -117,14 +123,14 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
&& $originalPostInfo->userId === $postInfo->userId;
}
if(!$this->forum->topics->checkUserHasReadTopic($this->authInfo->userInfo, $topic))
$this->forum->topics->incrementTopicViews($topic);
if(!$this->forumCtx->topics->checkUserHasReadTopic($this->authInfo->userInfo, $topic))
$this->forumCtx->topics->incrementTopicViews($topic);
$this->forum->topics->updateUserReadTopic($this->authInfo->userInfo, $topic);
$this->forumCtx->topics->updateUserReadTopic($this->authInfo->userInfo, $topic);
return Template::renderRaw('forum.topic', [
'topic_breadcrumbs' => iterator_to_array($this->forum->categories->getCategoryAncestry($topic)),
'global_accent_colour' => $this->forum->categories->getCategoryColour($topic),
'topic_breadcrumbs' => iterator_to_array($this->forumCtx->categories->getCategoryAncestry($topic)),
'global_accent_colour' => $this->forumCtx->categories->getCategoryColour($topic),
'topic_info' => $topic,
'category_info' => $categoryInfo,
'topic_posts' => $posts,
@ -167,7 +173,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
}
try {
$topic = $this->forum->topics->getTopic(
$topic = $this->forumCtx->topics->getTopic(
topicId: $topicId,
deleted: false,
);
@ -231,7 +237,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
$deletePostThreshold = 1;
// deleted posts are intentionally included
$topicPostCount = $this->forum->posts->countPosts(topicInfo: $topic);
$topicPostCount = $this->forumCtx->posts->countPosts(topicInfo: $topic);
if($topicPostCount > $deletePostThreshold) {
$response->statusCode = 403;
return [
@ -243,7 +249,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
}
}
$category = $this->forum->categories->getCategory(topicInfo: $topic);
$category = $this->forumCtx->categories->getCategory(topicInfo: $topic);
if($category->archived) {
$response->statusCode = 400;
return [
@ -254,7 +260,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
];
}
$this->forum->topics->deleteTopic($topic);
$this->forumCtx->topics->deleteTopic($topic);
$this->auditLog->createLog(
$this->authInfo->userInfo,
'FORUM_TOPIC_DELETE',
@ -287,7 +293,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
}
try {
$topic = $this->forum->topics->getTopic(
$topic = $this->forumCtx->topics->getTopic(
topicId: $topicId,
deleted: true,
);
@ -323,7 +329,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
];
}
$category = $this->forum->categories->getCategory(topicInfo: $topic);
$category = $this->forumCtx->categories->getCategory(topicInfo: $topic);
if($category->archived) {
$response->statusCode = 400;
return [
@ -334,7 +340,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
];
}
$this->forum->topics->restoreTopic($topic);
$this->forumCtx->topics->restoreTopic($topic);
$this->auditLog->createLog(
$this->authInfo->userInfo,
'FORUM_TOPIC_RESTORE',
@ -367,7 +373,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
}
try {
$topic = $this->forum->topics->getTopic(
$topic = $this->forumCtx->topics->getTopic(
topicId: $topicId,
deleted: true,
);
@ -403,7 +409,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
];
}
$category = $this->forum->categories->getCategory(topicInfo: $topic);
$category = $this->forumCtx->categories->getCategory(topicInfo: $topic);
if($category->archived) {
$response->statusCode = 400;
return [
@ -414,7 +420,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
];
}
$this->forum->topics->nukeTopic($topic);
$this->forumCtx->topics->nukeTopic($topic);
$this->auditLog->createLog(
$this->authInfo->userInfo,
'FORUM_TOPIC_NUKE',
@ -447,7 +453,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
}
try {
$topic = $this->forum->topics->getTopic(
$topic = $this->forumCtx->topics->getTopic(
topicId: $topicId,
deleted: false,
);
@ -483,7 +489,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
];
}
$category = $this->forum->categories->getCategory(topicInfo: $topic);
$category = $this->forumCtx->categories->getCategory(topicInfo: $topic);
if($category->archived) {
$response->statusCode = 400;
return [
@ -494,7 +500,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
];
}
$this->forum->topics->bumpTopic($topic);
$this->forumCtx->topics->bumpTopic($topic);
$this->auditLog->createLog(
$this->authInfo->userInfo,
'FORUM_TOPIC_BUMP',
@ -527,7 +533,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
}
try {
$topic = $this->forum->topics->getTopic(
$topic = $this->forumCtx->topics->getTopic(
topicId: $topicId,
deleted: false,
);
@ -573,7 +579,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
];
}
$category = $this->forum->categories->getCategory(topicInfo: $topic);
$category = $this->forumCtx->categories->getCategory(topicInfo: $topic);
if($category->archived) {
$response->statusCode = 400;
return [
@ -584,7 +590,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
];
}
$this->forum->topics->lockTopic($topic);
$this->forumCtx->topics->lockTopic($topic);
$this->auditLog->createLog(
$this->authInfo->userInfo,
'FORUM_TOPIC_LOCK',
@ -617,7 +623,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
}
try {
$topic = $this->forum->topics->getTopic(
$topic = $this->forumCtx->topics->getTopic(
topicId: $topicId,
deleted: false,
);
@ -663,7 +669,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
];
}
$category = $this->forum->categories->getCategory(topicInfo: $topic);
$category = $this->forumCtx->categories->getCategory(topicInfo: $topic);
if($category->archived) {
$response->statusCode = 400;
return [
@ -674,7 +680,7 @@ class ForumTopicsRoutes implements RouteHandler, UrlSource {
];
}
$this->forum->topics->unlockTopic($topic);
$this->forumCtx->topics->unlockTopic($topic);
$this->auditLog->createLog(
$this->authInfo->userInfo,
'FORUM_TOPIC_UNLOCK',

View file

@ -23,8 +23,6 @@ class UserInfo {
public private(set) ?string $displayRoleId,
public private(set) ?string $aboutBody,
public private(set) TextFormat $aboutBodyFormat,
public private(set) ?string $signatureBody,
public private(set) TextFormat $signatureBodyFormat,
public private(set) ?string $title,
) {}
@ -45,9 +43,7 @@ class UserInfo {
displayRoleId: $result->getStringOrNull(12),
aboutBody: $result->getStringOrNull(13),
aboutBodyFormat: TextFormat::tryFrom($result->getString(14)) ?? TextFormat::Plain,
signatureBody: $result->getStringOrNull(15),
signatureBodyFormat: TextFormat::tryFrom($result->getString(16)) ?? TextFormat::Plain,
title: $result->getString(17),
title: $result->getString(15),
);
}
@ -98,16 +94,4 @@ class UserInfo {
public bool $isAboutBodyMarkdown {
get => $this->aboutBodyFormat === TextFormat::Markdown;
}
public bool $isSignatureBodyPlain {
get => $this->signatureBodyFormat === TextFormat::Plain;
}
public bool $isSignatureBodyBBCode {
get => $this->signatureBodyFormat === TextFormat::BBCode;
}
public bool $isSignatureBodyMarkdown {
get => $this->signatureBodyFormat === TextFormat::Markdown;
}
}

View file

@ -26,7 +26,6 @@ class UsersData {
public const PASSWORD_UNIQUE = 6;
public const PROFILE_ABOUT_MAX_LENGTH = 50000;
public const FORUM_SIGNATURE_MAX_LENGTH = 2000;
public static function passwordHash(string $password): string {
return password_hash($password, self::PASSWORD_ALGO, self::PASSWORD_OPTS);
@ -178,7 +177,6 @@ class UsersData {
UNIX_TIMESTAMP(u.user_deleted),
u.user_display_role_id,
u.user_about_content, u.user_about_content_format,
u.user_signature_content, u.user_signature_content_format,
u.user_title
FROM msz_users AS u
SQL;
@ -287,7 +285,6 @@ class UsersData {
UNIX_TIMESTAMP(user_deleted),
user_display_role_id,
user_about_content, user_about_content_format,
user_signature_content, user_signature_content_format,
user_title
FROM msz_users
SQL;
@ -359,8 +356,6 @@ class UsersData {
RoleInfo|string|null $displayRoleInfo = null,
?string $aboutBody = null,
TextFormat|string|null $aboutBodyFormat = null,
?string $signatureBody = null,
TextFormat|string|null $signatureBodyFormat = null,
?string $title = null
): void {
if($userInfo instanceof UserInfo)
@ -419,18 +414,6 @@ class UsersData {
$values[] = $aboutBodyFormat->value;
}
if($signatureBody !== null && $signatureBodyFormat !== null) {
if(is_string($signatureBodyFormat))
$signatureBodyFormat = TextFormat::tryFrom($signatureBodyFormat) ?? null;
if(self::validateForumSignature($signatureBodyFormat, $signatureBody) !== '')
throw new InvalidArgumentException('$signatureBody and $signatureBodyFormat contain invalid data!');
$fields[] = 'user_signature_content = ?';
$values[] = $signatureBody;
$fields[] = 'user_signature_content_format = ?';
$values[] = $signatureBodyFormat->value;
}
if($title !== null) {
$fields[] = 'user_title = ?';
$values[] = $title;
@ -726,24 +709,4 @@ class UsersData {
default => 'Your profile about section is not acceptable.',
};
}
public static function validateForumSignature(?TextFormat $format, string $text): string {
if($format === null)
return 'parser';
$length = strlen($text);
if($length > self::FORUM_SIGNATURE_MAX_LENGTH)
return 'long';
return '';
}
public static function validateForumSignatureText(string $error): string {
return match($error) {
'parser' => 'You attempted to select an invalid parser for your forum signature.',
'long' => sprintf('Please keep the length of your forum signature below %d characters.', self::FORUM_SIGNATURE_MAX_LENGTH),
'' => 'Your forum signature is fine, why are you seeing this?',
default => 'Your forum signature is not acceptable.',
};
}
}

View file

@ -482,8 +482,8 @@
{% set author_created = post.user.createdTime %}
{% set author_posts_count = post.postsCount %}
{% set author_is_op = post.isOriginalPoster %}
{% set signature_body = post.user.signatureBody|default('')|escape|parse_text(post.user.signatureBodyFormat) %}
{% set signature_is_markdown = post.user.isSignatureBodyMarkdown %}
{% set signature_body = post.signature.body|default('')|escape|parse_text(post.signature.bodyFormat|default('')) %}
{% set signature_is_markdown = post.signature.isBodyMarkdown|default(false) %}
{% endif %}
{% set viewer_is_author = has_author and user_id == author_id %}

View file

@ -276,18 +276,18 @@
</div>
{% endif %}
{% if (not profile_is_banned or profile_can_edit) and ((profile_is_editing and perms.edit_signature) or profile_user.signatureBody is not empty) %}
{% if (not profile_is_banned or profile_can_edit) and ((profile_is_editing and perms.edit_signature) or profile_forum_signature_info is not null) %}
<div class="container profile__container profile__signature" id="signature">
{{ container_title('Signature') }}
{% if profile_is_editing %}
<div class="profile__signature__editor">
{{ input_select('signature[parser]', parser_options(), profile_user.signatureBodyFormat.value, '', '', false, 'profile__signature__select') }}
<textarea name="signature[text]" class="input__textarea profile__signature__text" id="signature-textarea">{{ profile_user.signatureBody }}</textarea>
{{ input_select('sig_format', parser_options(), profile_forum_signature_info.bodyFormat.value|default('bb'), '', '', false, 'profile__signature__select') }}
<textarea name="sig_body" class="input__textarea profile__signature__text" id="signature-textarea">{{ profile_forum_signature_info.body|default('') }}</textarea>
</div>
{% else %}
<div class="profile__signature__content{% if profile_is_editing %} profile__signature__content--edit{% elseif profile_user.isSignatureBodyMarkdown %} markdown{% endif %}">
{{ profile_user.signatureBody|escape|parse_text(profile_user.signatureBodyFormat)|raw }}
<div class="profile__signature__content{% if profile_is_editing %} profile__signature__content--edit{% elseif profile_forum_signature_info.isBodyMarkdown %} markdown{% endif %}">
{{ profile_forum_signature_info.body|escape|parse_text(profile_forum_signature_info.bodyFormat)|raw }}
</div>
{% endif %}
</div>