mautic / app /middlewares /Tests /HSTSMiddlewareTest.php
chrisbryan17's picture
Upload folder using huggingface_hub
d2897cd verified
<?php
declare(strict_types=1);
namespace Mautic\Middleware\Tests;
use Mautic\CoreBundle\Test\AbstractMauticTestCase;
use Mautic\Middleware\HSTSMiddleware;
use PHPUnit\Framework\Assert;
use PHPUnit\Framework\ExpectationFailedException as PHPUnitException;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
class HSTSMiddlewareTest extends AbstractMauticTestCase
{
public const HSTS_KEY = 'strict-transport-security';
protected \ReflectionProperty $addHSTS;
protected \ReflectionProperty $includeDubDomains;
protected \ReflectionProperty $preload;
protected HSTSMiddleware $middleware;
protected \ReflectionClass $middlewareReflection;
/**
* @throws \ReflectionException
*/
protected function setUp(): void
{
parent::setUp();
$this->middleware = new HSTSMiddleware($this->client->getKernel());
$this->middlewareReflection = new \ReflectionClass($this->middleware);
$this->addHSTS = $this->middlewareReflection->getProperty('enableHSTS');
$this->addHSTS->setAccessible(true);
$this->includeDubDomains = $this->middlewareReflection->getProperty('includeDubDomains');
$this->includeDubDomains->setAccessible(true);
$this->preload = $this->middlewareReflection->getProperty('preload');
$this->preload->setAccessible(true);
}
protected function testResponseHeaders(): void
{
$response = $this->getMiddlewareResponse();
Assert::assertNotEmpty($response->headers);
}
public function testHSTSEnabled(): void
{
$this->setHSTS(true);
$response = $this->getMiddlewareResponse();
Assert::assertTrue(
$response->headers->has(self::HSTS_KEY),
'Strict-Transport-Security is enabled but is missing from the response headers'
);
}
public function testHSTSDisabled(): void
{
$this->setHSTS(false);
$response = $this->getMiddlewareResponse();
Assert::assertFalse(
$response->headers->has(self::HSTS_KEY),
'Strict-Transport-Security is disabled but is present in response headers'
);
}
public function testIncludeSubdomainsEnabled(): void
{
$needle = 'includeSubDomains';
$this->setHSTS(true);
$this->setIncludeDubDomainsValue(true);
$response = $this->getMiddlewareResponse();
Assert::assertStringContainsString(
$needle,
$response->headers->get(self::HSTS_KEY),
'Option include Subdomains is enabled but is missing from the HSTS value'
);
}
public function testIncludeSubdomainsDisabled(): void
{
$needle = 'includeSubDomains';
$this->setHSTS(true);
$this->setIncludeDubDomainsValue(false);
$response = $this->getMiddlewareResponse();
Assert::assertStringNotContainsStringIgnoringCase(
$needle,
$this->getHSTSValue($response),
'Option include Subdomains is disabled but is present in HSTS value'
);
}
public function testPreloadEnabled(): void
{
$needle = 'preload';
$this->setHSTS(true);
$this->setPreloadValue(true);
$response = $this->getMiddlewareResponse();
Assert::assertStringContainsString(
$needle,
$response->headers->get(self::HSTS_KEY),
'Option preload is enabled but is missing from the HSTS value'
);
}
public function testPreloadDisabled(): void
{
$needle = 'preload';
$this->setHSTS(true);
$this->setPreloadValue(false);
$response = $this->getMiddlewareResponse();
Assert::assertStringNotContainsStringIgnoringCase(
$needle,
$this->getHSTSValue($response),
'Option preload is disabled but is present in HSTS value'
);
}
/**
* @throws \ReflectionException
*/
public function testExpireTime(): void
{
$this->setHSTS(true);
$expireTimeValue = 12345;
$expireTime = $this->middlewareReflection->getProperty('expireTime');
$expireTime->setAccessible(true);
$expireTime->setValue($this->middleware, $expireTimeValue);
$response = $this->getMiddlewareResponse();
Assert::assertMatchesRegularExpression(
'/max-age='.$expireTimeValue.'(; includeSubDomains)?/',
$this->getHSTSValue($response),
'Expire time does not match the configuration'
);
}
private function setHSTS(bool $value): void
{
$this->addHSTS->setValue($this->middleware, $value);
}
private function setIncludeDubDomainsValue(bool $value): void
{
$this->includeDubDomains->setValue($this->middleware, $value);
}
private function setPreloadValue(bool $value): void
{
$this->preload->setValue($this->middleware, $value);
}
private function getHSTSValue(Response $response): string
{
return $response->headers->get(self::HSTS_KEY) ?? '';
}
private function getMiddlewareResponse(): Response
{
try {
return $this->middleware->handle(Request::create('s/login', Request::METHOD_GET));
} catch (\Exception $e) {
throw new PHPUnitException($e->getMessage());
}
}
}