Testing redirections with the Symfony HTTP client

Published on 2020-04-15 • Modified on 2020-04-15

In this snippet, we will see how to test redirections with the Symfony Http client. The code we will see is, in fact, a functional test. The trick here is to set the max_redirects parameter to 0. If a redirection is made, then an exception will be raised. Otherwise, the $this->fail() function will be called, and it will flag the test as failed. If the exception is raised as expected, we test the response status code (well we could avoid this because the exception we catch is a RedirectionException). Then we check that the URL is redirected to the expected location. We use a data provider to test several cases. As this test involves external resources (the production server), it is included in a particular "external" test suite.


<?php

declare(strict_types=1);

namespace App\Tests\External;

use App\Tests\WebTestCase;
use Symfony\Component\HttpClient\Exception\RedirectionException;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Contracts\HttpClient\HttpClientInterface;

/**
 * Test the SSL redirections.
 *
 * @see http://www.strangebuzz.com
 */
final class SslTest extends WebTestCase
{
    private const CANONICAL = 'https://www.strangebuzz.com/';

    private HttpClientInterface $httpClient;

    protected function setUp(): void
    {
        $this->httpClient = $this->getHttpClientService();
    }

    /**
     * @return iterable<int, array{0: string, 1: string}>
     */
    public function urlProvider(): iterable
    {
        // http with www
        yield ['http://www.strangebuzz.com', self::CANONICAL];
        yield ['http://www.strangebuzz.com/', self::CANONICAL];
        yield ['http://www.strangebuzz.com/en/snippets/freezing-the-vue-js-version-to-a-minor-version', self::CANONICAL];

        // http with www
        yield ['http://strangebuzz.com', self::CANONICAL];
        yield ['http://strangebuzz.com/', self::CANONICAL];
        yield ['http://strangebuzz.com/en/snippets/freezing-the-vue-js-version-to-a-minor-version', self::CANONICAL];

        // https without www
        yield ['https://strangebuzz.com', self::CANONICAL];
        yield ['https://strangebuzz.com/', self::CANONICAL];
        yield ['https://strangebuzz.com/en/snippets/freezing-the-vue-js-version-to-a-minor-version', self::CANONICAL];
    }

    /**
     * @dataProvider urlProvider
     */
    public function testSsl(string $url, string $location): void
    {
        try {
            $this->httpClient->request('GET', $url, ['max_redirects' => 0])->getContent();
            self::fail(sprintf('URL "%s" non redirigΓ©e.', $url));
        } catch (RedirectionException $e) {
            self::assertSame(Response::HTTP_MOVED_PERMANENTLY, $e->getResponse()->getStatusCode());
            $info = $e->getResponse()->getInfo();
            if (!\is_array($info)) {
                throw new \TypeError('Incorrect type, array expected.');
            }
            self::assertSame($location, $info['redirect_url'] ?? '');
        }
    }
}

 More on Stackoverflow   Read the doc  Random snippet

  Work with me!