diff --git a/src/Security/Security.php b/src/Security/Security.php index 0b0f5e701..98dedb977 100644 --- a/src/Security/Security.php +++ b/src/Security/Security.php @@ -317,14 +317,23 @@ class Security extends Controller implements TemplateGlobalProvider public static function permissionFailure($controller = null, $messageSet = null) { self::set_ignore_disallowed_actions(true); - $shouldEscapeHtml = function ($message) { + + // Parse raw message / escape type + $parseMessage = function ($message) { if ($message instanceof DBField) { - $escapeHtml = $message->config()->escape_type === 'raw'; - } else { - $escapeHtml = true; + return [ + $message->getValue(), + $message->config()->get('escape_type') === 'raw' + ? ValidationResult::CAST_TEXT + : ValidationResult::CAST_HTML, + ]; } - return $escapeHtml; + // Default to escaped value + return [ + $message, + ValidationResult::CAST_TEXT, + ]; }; if (!$controller && Controller::has_curr()) { @@ -389,7 +398,8 @@ class Security extends Controller implements TemplateGlobalProvider $message = $messageSet['default']; } - static::singleton()->setSessionMessage($message, ValidationResult::TYPE_WARNING, $shouldEscapeHtml($message) ? ValidationResult::CAST_TEXT : ValidationResult::CAST_HTML); + list($messageText, $messageCast) = $parseMessage($message); + static::singleton()->setSessionMessage($messageText, ValidationResult::TYPE_WARNING, $messageCast); $request = new HTTPRequest('GET', '/'); if ($controller) { $request->setSession($controller->getRequest()->getSession()); @@ -408,13 +418,8 @@ class Security extends Controller implements TemplateGlobalProvider $message = $messageSet['default']; } - static::singleton()->setSessionMessage( - $message, - ValidationResult::TYPE_WARNING, - $shouldEscapeHtml($message) ? - ValidationResult::CAST_TEXT : - ValidationResult::CAST_HTML - ); + list($messageText, $messageCast) = $parseMessage($message); + static::singleton()->setSessionMessage($messageText, ValidationResult::TYPE_WARNING, $messageCast); $controller->getRequest()->getSession()->set("BackURL", $_SERVER['REQUEST_URI']); diff --git a/tests/php/Security/SecurityTest.php b/tests/php/Security/SecurityTest.php index 469371ec0..3e7321a78 100644 --- a/tests/php/Security/SecurityTest.php +++ b/tests/php/Security/SecurityTest.php @@ -16,6 +16,7 @@ use SilverStripe\ORM\DataObject; use SilverStripe\ORM\DB; use SilverStripe\ORM\FieldType\DBClassName; use SilverStripe\ORM\FieldType\DBDatetime; +use SilverStripe\ORM\FieldType\DBField; use SilverStripe\ORM\ValidationResult; use SilverStripe\Security\LoginAttempt; use SilverStripe\Security\Member; @@ -129,6 +130,26 @@ class SecurityTest extends FunctionalTest $controller->getResponse()->getBody(), "Message set passed to Security::permissionFailure() didn't override Config values" ); + + // Test DBField cast messages work + Security::permissionFailure( + $controller, + DBField::create_field('HTMLFragment', '

Custom HTML & Message

') + ); + $this->assertContains( + '

Custom HTML & Message

', + $controller->getResponse()->getBody() + ); + + // Plain text DBText + Security::permissionFailure( + $controller, + DBField::create_field('Text', 'Safely escaped & message') + ); + $this->assertContains( + 'Safely escaped & message', + $controller->getResponse()->getBody() + ); } /**